@Nikita Popov <nikita....@gmail.com>

>  It's not possible to use (ClassName) as a cast syntax, because it is
ambiguous.

Aw. I did not think about a possible conflict here, thanks for bringing
this up!

@Stephen Reay <php-li...@koalephant.com>

> My objection to `as` is that it specifically prevents (or makes very
confusing) the `foreach` use I mentioned. There’s no variables involved in
imports/traits, and neither of those relates to foreach.

I'm sorry, I still don't understand what the issue with foreach is? As I
said before, the proposed syntax does not aim to be used inside the foreach
() parentheses, but rather as an explicit declaration inside the foreach {}
block.

> As for the `string $foo = $bar->getFoo();` ‘looking strongly typed’ and
wondering if it will allow re-declaration - do you think the same when you
see `function (string $foo) { $foo = explode(‘ ‘, $foo); }` ? Functions
have allowed type hints since 5.0 - nearly 15 years ago, and nobody seems
to be confused if those variables can be redeclared. Whether you *should*
redeclare them to a different value is something you need to decide for
yourself.

You have a point. I can't say why, but outside of the function declaration,
it looks more like a static typing to me (and someone else had the same gut
reaction earlier in this thread). I may just be plain wrong.

> As for limiting this to class/interface names - why would you do that? It
took YEARS to get scalar type hints for function parameters, why would you
not include them from the start on anything new that pertains to
essentially the same functionality?

I'm definitely not against supporting other types, it's just that the
original syntax I had in mind was using () casting, which was already
covered for other types.
Now if people like Hack's `as` syntax, it would probably make sense to
generalize it indeed.

@Dan Ackroyd <dan...@basereality.com>

> Similar to the nullable casting idea, you're taking a problem caused
> by your own code/framework, and then thinking it should be solved in
> core, when a simple solution is available in user-land.
> ...
> btw I'm sure you're already aware of it, but this is using a
> 'dependency injector' as a service locator. If your current DI library
> isn't powerful enough for you, rather than abusing it like this,

I think that the sudden focus on the specific case of DI container /
service locator reveals a misunderstanding here. The example I chose is
obviously responsible for that and this choice was perhaps infortunate: it
didn't help convey the true meaning of the proposal.

As I said earlier, I'm a heavy user of Dependency Injection AND Inversion
of Control; my framework does not suffer from any such limitation: my
controllers' and services' dependencies are explicitly declared and
injected automatically, and no such code relies on fetching dependencies
from the container directly. These classes are not even aware of the
existence of the container, and not tied to the DI framework in any way.
Also, my repositories are full blown, and encapsulate the ORM to return
specific entities.

YET, I also do some quick prototypes or CLI scripts that would not benefit
from too much boilerplate, and may use the DI container or the ORM's entity
manager directly. I also get objects from various losely typed data sources
(functions returning mixed types, arrays, iterators of all sorts, etc.)
that I expect to be of a given type, and that would benefit from the
added *readability,
type checking and static analysis capabilities* the current proposal offers.

@Andrey Hristov <p...@hristov.com>

> this is easily solvable with the following (considering strict_types is
enabled)
> function tostr(string $in) : string { return $in; }

This solves it for a single type, but you have to write a function for
every class you want to enforce:

function toEmailService(EmailService $service) : EmailService { return
$service; }
function toUser(User $user) : User { return $user; }

As you can see, this gets ugly real quick. Your IDE and/or static analysis
tool will also probably warn about "Expecting Foo, got mixed", whereas with
an explicit cast/enforced-type-hint, the tooling would know that you're
explicitly stating that this unknown typed value is an instance of Foo.

- Ben



On Tue, 23 Apr 2019 at 12:52, Andrey Hristov <p...@hristov.com> wrote:

>   Hi,
> On 23.04.19 г. 13:44 ч., azjezz wrote:
> > Hello Dan,
> >
> > I don' think this a problem relating to just one use case, some PHP
> builtin functions have weird union return types, where static analysis
> tools would warn you about the return type being `string|bool`, when you
> are expecting `string`.
> >
> > using type constrain :
> > ```
> > $foo = substr($foo, 1, 3) as string;
> > // there's no need to check if `$foo` is false here.
> > ```
>
> this is easily solvable with the following (considering strict_types is
> enabled)
>
> function tostr(string $in) : string { return $in; }
>
> $foo = tostr($foo);
>
> Put it in a convenience namespace and that's it.
>
> Cheers,
> Andrey
>
> >
> >
> > Cheers,
> >
> > - Saif
> >
> >
> > Sent with ProtonMail Secure Email.
> >
> > ‐‐‐‐‐‐‐ Original Message ‐‐‐‐‐‐‐
> > On Tuesday, April 23, 2019 11:33 AM, Dan Ackroyd <dan...@basereality.com>
> wrote:
> >
> >> HI Benjamin,
> >>
> >> Similar to the nullable casting idea, you're taking a problem caused
> >> by your own code/framework, and then thinking it should be solved in
> >> core, when a simple solution is available in user-land.
> >>
> >> If you changed what you currently have:
> >>
> >> $service = $diContainer->get('email.service');
> >>
> >> to also take the expected class:
> >>
> >> $service = $diContainer->get('email.service', EmailService::class);
> >>
> >> And then check inside your 'DI container' whether the expected type is
> >> returned, this solves the problem without needing new syntax.
> >>
> >> btw I'm sure you're already aware of it, but this is using a
> >> 'dependency injector' as a service locator. If your current DI library
> >> isn't powerful enough for you, rather than abusing it like this, I'd
> >> recommend looking at a different one, like
> >> https://github.com/rdlowrey/Auryn
> >>
> >> Also, similar:
> >>
> >>> By the way, this RFC is a special case of something that could be far
> >>> more generic. If it was possible to register callbacks to be used when
> >>> casting, ...
> >>
> >> Apparently this might not be possible as it's ambiguous....which is a
> shame.
> >>
> >> cheers
> >> Dan
> >> Ack
> >>
> >> On Mon, 22 Apr 2019 at 22:47, Benjamin Morel benjamin.mo...@gmail.com
> wrote:
> >>
> >>> Hi internals,
> >>> I'd like to revive an old discussion
> https://externals.io/message/67131 about
> >>> object type casting.
> >>> The idea would be to allow (ClassName) casting:
> >>>
> >>>      $service = (EmailService) $diContainer->get('email.service');
> >>>
> >>>
> >>> The above code would throw a TypeError if the value is not an instance
> of
> >>> the given class. I see the following advantages:
> >>>
> >>> -   Type safety: we can be sure that the value is of the correct type
> or that
> >>>      we'll get an Error. This syntax allows to fail early if the
> variable
> >>>      happens to not be of the expected type, and avoids much more
> verbose checks;
> >>>
> >>> -   Static analysis: IDEs and static code analysis tools can now
> understand
> >>>      the type of the variable, without having to resort to `@var`
> annotations.
> >>>
> >>>
> >>> These combine into a third advantage: readability. Today's equivalent
> of
> >>> the above one-liner could be:
> >>>
> >>>      /** @var EmailService $service */
> >>>      $service = $diContainer->get('email.service');
> >>>      if (! $service instanceof EmailService) {
> >>>          throw new TypeError('Expected instance of EmailService, ...');
> >>>      }
> >>>
> >>>
> >>> Which is a lot of boilerplate code that could be easily avoided by
> >>> introducing this new syntax.
> >>> Before moving forward and working on a formal RFC, I'd like to hear
> your
> >>> thoughts: what's your early feeling about this? Did I miss other
> >>> discussions around this subject? Are there any technical issues that
> come
> >>> to mind? Could this feature help the upcoming JIT compiler produce more
> >>> efficient machine code by knowing the type of the variable at compile
> time?
> >>> etc.
> >>> Note: "casting" might not be the perfect name here as what we're really
> >>> doing is a type check, but this reuses the type casting syntax and
> >>> resembles Java's object casting.
> >>> Thank you,
> >>> Ben
> >>
> >> --
> >>
> >> PHP Internals - PHP Runtime Development Mailing List
> >> To unsubscribe, visit: http://www.php.net/unsub.php
> >
> >
> >
>
>
> --
> PHP Internals - PHP Runtime Development Mailing List
> To unsubscribe, visit: http://www.php.net/unsub.php
>
>

Reply via email to