Bug #75079 [NEW]: self is only resolved once for closure in trait

From: Date: Wed, 16 Aug 2017 18:12:17 +0000
Subject: Bug #75079 [NEW]: self is only resolved once for closure in trait
Groups: php.bugs 
Request: Send a blank email to php-bugs+get-210694@lists.php.net to get a copy of this message
From: aidantwoods at gmail dot com Operating system: OSX; Kali Linux (Debian) PHP version: 7.1.8 Package: Class/Object related Bug Type: Bug Bug description:self is only resolved once for closure in trait Description: ------------ Traits are meant to be syntactic sugar for "copy-pasting" things into classes. As such, when the self keyword is used inside a trait, it does not resolve to the name of the trait, but rather resolves to be the name of the class in which the trait was used in. If the self keyword is used within a type hint in a closure that is used inside a trait, this closure does not appear to be re-resolved per inclusion. For example, from the test script included, it should not be possible for the closure to throw a TypeError in any circumstance (if a type error is to be thrown, it should be thrown by the outer method) public function selfDo(self ...$Selfs) { array_map( function (self $Self) : self { return $Self; }, $Selfs ); } As expected, when calling exclusively the following $Bar->selfDo($Bar, $Bar); No TypeError is thrown. Alternatively, when calling exclusively the following $Baz->selfDo($Baz, $Baz); Also no TypeError is thrown. The problem arises when calling one after the other (does not need to be immediately after). Depending on the order those last two lines of the test script are called in, you will see a different error thrown. In the order given, the following is generated (trimmed for brevity) Fatal error: Uncaught TypeError: Argument 1 passed to Baz::{closure}() must be an instance of Bar, instance of Baz given in[...] It seems that once the method is initially called, the self type hint in the closure in the trait resolves to be the name of the class in which it was used in (no bug here), the bug is that this initial class name is now permanently resolved as its current value in latter calls to the same method (from a different unrelated class). Test script: --------------- <?php trait Foo { public function selfDo(self ...$Selfs) { array_map( function (self $Self) : self { return $Self; }, $Selfs ); } } class Bar { use Foo; } class Baz { use Foo; } $Bar = new Bar; $Baz = new Baz; $Bar->selfDo($Bar, $Bar); $Baz->selfDo($Baz, $Baz); Actual result: -------------- Fatal error: Uncaught TypeError: Argument 1 passed to Baz::{closure}() must be an instance of Bar, instance of Baz given in /Users/Aidan/traits.php:8 Stack trace: #0 [internal function]: Baz->{closure}(Object(Baz)) #1 /Users/Aidan/traits.php(12): array_map(Object(Closure), Array) #2 /Users/Aidan/traits.php(31): Baz->selfDo(Object(Baz), Object(Baz)) #3 {main} thrown in /Users/Aidan/traits.php on line 8 -- Edit bug report at https://bugs.php.net/bug.php?id=75079&edit=1 -- Try a snapshot (PHP 5.4): https://bugs.php.net/fix.php?id=75079&r=trysnapshot54 Try a snapshot (PHP 5.5): https://bugs.php.net/fix.php?id=75079&r=trysnapshot55 Try a snapshot (trunk): https://bugs.php.net/fix.php?id=75079&r=trysnapshottrunk Fixed in SVN: https://bugs.php.net/fix.php?id=75079&r=fixed Fixed in release: https://bugs.php.net/fix.php?id=75079&r=alreadyfixed Need backtrace: https://bugs.php.net/fix.php?id=75079&r=needtrace Need Reproduce Script: https://bugs.php.net/fix.php?id=75079&r=needscript Try newer version: https://bugs.php.net/fix.php?id=75079&r=oldversion Not developer issue: https://bugs.php.net/fix.php?id=75079&r=support Expected behavior: https://bugs.php.net/fix.php?id=75079&r=notwrong Not enough info: https://bugs.php.net/fix.php?id=75079&r=notenoughinfo Submitted twice: https://bugs.php.net/fix.php?id=75079&r=submittedtwice register_globals: https://bugs.php.net/fix.php?id=75079&r=globals PHP 4 support discontinued: https://bugs.php.net/fix.php?id=75079&r=php4 Daylight Savings: https://bugs.php.net/fix.php?id=75079&r=dst IIS Stability: https://bugs.php.net/fix.php?id=75079&r=isapi Install GNU Sed: https://bugs.php.net/fix.php?id=75079&r=gnused Floating point limitations: https://bugs.php.net/fix.php?id=75079&r=float No Zend Extensions: https://bugs.php.net/fix.php?id=75079&r=nozend MySQL Configuration Error: https://bugs.php.net/fix.php?id=75079&r=mysqlcfg

« previous php.bugs (#210694) next »