On Tue, Apr 29, 2025 at 9:09 AM Hammed Ajao <hamieg...@gmail.com> wrote:
> On Mon, Apr 28, 2025, 1:22 p.m. Larry Garfield <la...@garfieldtech.com> > wrote: > >> On Mon, Apr 28, 2025, at 11:28 AM, Edmond Dantes wrote: >> >> I have already demonstrated how it can be solved without generics. >> Multiple response channels from a function already exist: Normal returns >> and exceptions. Exceptions as currently designed are just very poorly >> suited to the problem space I am describing. >> > >> > If another error channel is introduced, PHP would end up with *two >> > error channels*. >> > This is harder to understand than the Normal returns + Exception >> > channels + Something new. >> > >> > It seems to me that this creates a bigger problem than the one it is >> > trying to solve. >> > >> > Is it possible to avoid creating two error channels and instead design >> > an alternative handling method that would eliminate the drawbacks of >> > the first approach? >> > >> > If the performance issue is solved, are the other two problems really >> > worth such changes? >> > >> > For example, if we follow the philosophy of `RESULT<X>`, we can say >> > that there are two types of exception handling cases: >> > 1. Suppressing an exception immediately at the first level of function >> > call. >> >> Suppressing? You mean fataling. Suppressing implies ignore, which is >> the exact opposite of what I am proposing. >> >> > 2. Stack unwinding. >> >> Given the choice between: >> >> success return + error-return + the-world-is-broken >> >> vs >> >> success return + the-world-is-broken + >> the-world-is-broken-but-not-really-so-you-have-to-handle-it >> >> The first seems substantially better, frankly. >> >> Exceptions that are sometimes checked and sometimes not is Java, which is >> exactly why everyone hates Java's exception system. >> >> > ```php >> > >> > function someFunction(): string raises SomeException { >> > >> > throw SomeException() >> > } >> > >> > // The backtrace is not generated: >> > >> > $res = try someFunction() catch (SomeException) null; >> > >> > // The backtrace is generated when throw $err executed. >> > >> > $res = try someFunction() catch ($err) {throw $err}; >> > >> > // The backtrace is generated >> > >> > $res = someFunction(); >> > >> > ``` >> > >> > This kind of behavior doesn’t break BC, right? At the same time, it >> > allows improving PHP performance and adding contracts. >> >> The particulars there in that syntax imply the only catch handling would >> be defining a different value, which may not be the desired handling. >> >> Also, that again runs into "throw may be checked or not, you don't always >> know." >> >> It also means the exception is carrying around the extra design baggage >> of exceptions. Even if the trace is elided, it's still carrying useless >> metadata that would lead people astray. It also means dealing with the >> constructor of Exceptions, which is notoriously annoying for extending. >> >> "Make exceptions nicer" is fundamentally not what I am proposing, nor >> will I propose as a solution for this space. It is the wrong approach. >> (Making exceptions nicer is well and good in its own right, and I won't >> block that, but it does not address this problem space.) >> >> It's clear you do not support what I am proposing. Good to know, >> thanks. I still haven't gotten any feedback from major voters, though, so >> leaving this thread open. >> >> --Larry Garfield >> > > > I fail to see the value in this, seems to be solving a problem I've never > encountered. Who cares what baggage exceptions carry? They are meant for > exceptional situations, seems like you're trying to transform exceptions > into something entirely different under the guise of improving them. > > Two rules I try to consider when it comes to exceptions: * Exceptions are expensive computationally, because they trigger a backtrace on instantiation. * Exceptions should not be used for normal application logic flow. If the "error" is recoverable and/or expected, use a different mechanism so you can use standard conditional branching. As such, there are a lot of situations where I may not want to use exceptions. Two common ones: * Input validation. In most cases, _invalid input is expected_, and a condition you will handle in your code. Exceptions are a really poor mechanism for this. * "Not found" conditions, such as not finding a matching row in a database or a cache. Again, this is expected, and something you should handle via conditionals. Currently, there's no _generic_ way to handle these sorts of error conditions from functions. You can create "result" types specific to each operation, but this is a lot of boilerplate. You can resort to exceptions, but these are a poor fit due to performance and logic flow. I'm currently not yet convinced on the proposal Larry is making, but I definitely understand what's driving it, and would love a language-level solution. -- Matthew Weier O'Phinney mweierophin...@gmail.com https://mwop.net/ he/him