bobthecow / psysh

A REPL for PHP
https://psysh.org
MIT License
9.72k stars 309 forks source link

Parse errors when using namespaced classes/functions #652

Closed willemo closed 2 years ago

willemo commented 4 years ago

I'm getting this really weird bug, since I've upgraded my Laravel version to 7.x (Laravel Tinker v2.4.2). The shell doesn't accept me using FQCNs anymore. See the output below:

Psy Shell v0.10.4 (PHP 7.3.20-1+ubuntu18.04.1+deb.sury.org+1 — cli) by Justin Hileman
>>> User::class
=> "User"
>>> \App\User::class
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> namespace App;
>>> User::class
=> "App\User"
>>> App\User::class
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> \App\User::class
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> wtf -a
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
--
 0:  () at vendor/psy/psysh/src/Exception/ParseErrorException.php:40
 1:  Psy\Exception\ParseErrorException::fromParseError() at vendor/psy/psysh/src/CodeCleaner.php:294
 2:  Psy\CodeCleaner->parse() at vendor/psy/psysh/src/CodeCleaner.php:221
 3:  Psy\CodeCleaner->clean() at vendor/psy/psysh/src/Shell.php:829
 4:  Psy\Shell->addCode() at vendor/psy/psysh/src/Shell.php:521
 5:  Psy\Shell->getInput() at vendor/psy/psysh/src/ExecutionLoopClosure.php:40
 6:  Psy\{closure}() at vendor/psy/psysh/src/ExecutionClosure.php:96
 7:  Psy\ExecutionClosure->execute() at vendor/psy/psysh/src/Shell.php:370
 8:  Psy\Shell->doInteractiveRun() at vendor/psy/psysh/src/Shell.php:341
 9:  Psy\Shell->doRun() at vendor/symfony/console/Application.php:140
10:  Symfony\Component\Console\Application->run() at vendor/psy/psysh/src/Shell.php:316
11:  Psy\Shell->run() at vendor/laravel/tinker/src/Console/TinkerCommand.php:81
12:  Laravel\Tinker\Console\TinkerCommand->handle() at n/a:n/a
13:  call_user_func_array() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:37
14:  Illuminate\Container\BoundMethod::Illuminate\Container\{closure}() at vendor/laravel/framework/src/Illuminate/Container/Util.php:37
15:  Illuminate\Container\Util::unwrapIfClosure() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:95
16:  Illuminate\Container\BoundMethod::callBoundMethod() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:39
17:  Illuminate\Container\BoundMethod::call() at vendor/laravel/framework/src/Illuminate/Container/Container.php:596
18:  Illuminate\Container\Container->call() at vendor/laravel/framework/src/Illuminate/Console/Command.php:134
19:  Illuminate\Console\Command->execute() at vendor/symfony/console/Command/Command.php:258
20:  Symfony\Component\Console\Command\Command->run() at vendor/laravel/framework/src/Illuminate/Console/Command.php:121
21:  Illuminate\Console\Command->run() at vendor/symfony/console/Application.php:916
22:  Symfony\Component\Console\Application->doRunCommand() at vendor/symfony/console/Application.php:264
23:  Symfony\Component\Console\Application->doRun() at vendor/symfony/console/Application.php:140
24:  Symfony\Component\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Console/Application.php:93
25:  Illuminate\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Foundation/Console/Kernel.php:129
26:  Illuminate\Foundation\Console\Kernel->handle() at artisan:38

Even running psy\info() doesn't work:

>>> psy\info()
PHP Parse error: Syntax error, unexpected ')' on line 1

I get the same error locally, in a docker container and on our server. I have no config files for psysh, but maybe Laravel adds some configuration through Tinker out of the box.

Do you have any idea how I can fix this?

bobthecow commented 4 years ago

That's quite strange. I'm unable to reproduce it using the same tinker version. The output of psy\info() would be super helpful. Can you get to it via …

namespace Psy
info()
willemo commented 4 years ago

Ah yes, that worked:

[
     "PsySH version" => "v0.10.4",
     "PHP version" => "7.3.20-1+ubuntu18.04.1+deb.sury.org+1",
     "OS" => "Linux",
     "default includes" => [],
     "require semicolons" => false,
     "error logging level" => 32767,
     "config file" => [
       "default config file" => null,
       "local config file" => null,
       "PSYSH_CONFIG env" => false,
     ],
     "loop listeners" => [
       "Psy\ExecutionLoop\ProcessForker",
     ],
     "commands" => [
       "help" => "Psy\Command\HelpCommand",
       "?" => "Psy\Command\HelpCommand",
       "ls" => "Psy\Command\ListCommand",
       "dir" => "Psy\Command\ListCommand",
       "dump" => "Psy\Command\DumpCommand",
       "doc" => "Psy\Command\DocCommand",
       "rtfm" => "Psy\Command\DocCommand",
       "man" => "Psy\Command\DocCommand",
       "show" => "Psy\Command\ShowCommand",
       "wtf" => "Psy\Command\WtfCommand",
       "last-exception" => "Psy\Command\WtfCommand",
       "wtf?" => "Psy\Command\WtfCommand",
       "whereami" => "Psy\Command\WhereamiCommand",
       "throw-up" => "Psy\Command\ThrowUpCommand",
       "timeit" => "Psy\Command\TimeitCommand",
       "trace" => "Psy\Command\TraceCommand",
       "buffer" => "Psy\Command\BufferCommand",
       "buf" => "Psy\Command\BufferCommand",
       "clear" => "Psy\Command\ClearCommand",
       "edit" => "Psy\Command\EditCommand",
       "sudo" => "Psy\Command\SudoCommand",
       "history" => "Psy\Command\HistoryCommand",
       "hist" => "Psy\Command\HistoryCommand",
       "exit" => "Psy\Command\ExitCommand",
       "quit" => "Psy\Command\ExitCommand",
       "q" => "Psy\Command\ExitCommand",
       "clear-compiled" => "Illuminate\Foundation\Console\ClearCompiledCommand",
       "down" => "Illuminate\Foundation\Console\DownCommand",
       "env" => "Illuminate\Foundation\Console\EnvironmentCommand",
       "optimize" => "Illuminate\Foundation\Console\OptimizeCommand",
       "up" => "Illuminate\Foundation\Console\UpCommand",
       "migrate" => "Illuminate\Database\Console\Migrations\MigrateCommand",
       "inspire" => "Illuminate\Foundation\Console\ClosureCommand",
     ],
     "updates" => [
       "update available" => false,
       "latest release version" => "v0.10.4",
       "update check interval" => "never",
       "update cache file" => "~/.config/psysh/update_check.json",
     ],
     "pcntl" => [
       "pcntl available" => true,
       "posix available" => true,
       "use pcntl" => true,
     ],
     "input" => [
       "interactive mode" => "auto",
       "input interactive" => true,
     ],
     "readline" => [
       "readline available" => true,
       "readline enabled" => true,
       "readline service" => "Psy\Readline\Libedit",
       "readline library" => "EditLine wrapper",
       "readline name" => "psysh",
     ],
     "output" => [
       "color mode" => "auto",
       "output decorated" => null,
       "output verbosity" => "normal",
     ],
     "history" => [
       "history file" => "~/.config/psysh/psysh_history",
       "history size" => null,
       "erase duplicates" => null,
     ],
     "docs" => [
       "manual db file" => null,
       "sqlite available" => true,
     ],
     "autocomplete" => [
       "tab completion enabled" => true,
       "bracketed paste" => false,
       "custom matchers" => [],
     ],
   ]
ikari7789 commented 4 years ago

I think it may be due to a recent update to nikic/php-parser (https://github.com/nikic/PHP-Parser/releases/tag/v4.10.0). I was able to eliminate the issue by downgrading from v4.10.0 to v4.9.1 just now @willemo.

I'm getting a similar, but different error, but what's causing the exception to be thrown is the same patch of code?

$ php artisan tinker
Psy Shell v0.9.12 (PHP 7.2.33 — cli) by Justin Hileman
>>> use Our\Internal\Class;
PHP Parse error: Syntax error, unexpected T_NAME_RELATIVE on line 1
>>> wtf -a
PHP Parse error: Syntax error, unexpected T_NAME_RELATIVE on line 1
--
 0:  () at vendor/psy/psysh/src/Exception/ParseErrorException.php:40
 1:  Psy\Exception\ParseErrorException::fromParseError() at vendor/psy/psysh/src/CodeCleaner.php:290
 2:  Psy\CodeCleaner->parse() at vendor/psy/psysh/src/CodeCleaner.php:217
 3:  Psy\CodeCleaner->clean() at vendor/psy/psysh/src/Shell.php:717
 4:  Psy\Shell->addCode() at vendor/psy/psysh/src/Shell.php:409
 5:  Psy\Shell->getInput() at vendor/psy/psysh/src/ExecutionLoopClosure.php:40
 6:  Psy\{closure}() at vendor/psy/psysh/src/ExecutionClosure.php:101
 7:  Psy\ExecutionClosure->execute() at vendor/psy/psysh/src/ExecutionLoop.php:33
 8:  Psy\ExecutionLoop->run() at vendor/psy/psysh/src/Shell.php:350
 9:  Psy\Shell->doRun() at vendor/symfony/console/Application.php:147
10:  Symfony\Component\Console\Application->run() at vendor/psy/psysh/src/Shell.php:315
11:  Psy\Shell->run() at vendor/laravel/tinker/src/Console/TinkerCommand.php:68
12:  Laravel\Tinker\Console\TinkerCommand->handle() at n/a:n/a
13:  call_user_func_array() at vendor/illuminate/container/BoundMethod.php:29
14:  Illuminate\Container\BoundMethod::Illuminate\Container\{closure}() at vendor/illuminate/container/BoundMethod.php:87
15:  Illuminate\Container\BoundMethod::callBoundMethod() at vendor/illuminate/container/BoundMethod.php:31
16:  Illuminate\Container\BoundMethod::call() at vendor/illuminate/container/Container.php:564
17:  Illuminate\Container\Container->call() at vendor/illuminate/console/Command.php:179
18:  Illuminate\Console\Command->execute() at vendor/symfony/console/Command/Command.php:255
19:  Symfony\Component\Console\Command\Command->run() at vendor/illuminate/console/Command.php:166
20:  Illuminate\Console\Command->run() at vendor/symfony/console/Application.php:1005
21:  Symfony\Component\Console\Application->doRunCommand() at vendor/symfony/console/Application.php:271
22:  Symfony\Component\Console\Application->doRun() at vendor/symfony/console/Application.php:147
23:  Symfony\Component\Console\Application->run() at vendor/illuminate/console/Application.php:89
24:  Illuminate\Console\Application->run() at vendor/laravel/lumen-framework/src/Console/Kernel.php:114
25:  Laravel\Lumen\Console\Kernel->handle() at artisan:35

>>> namespace Psy
>>> info()
=> [
     "PsySH version" => "v0.9.12",
     "PHP version" => "7.2.33",
     "OS" => "Linux",
     "default includes" => [],
     "require semicolons" => false,
     "error logging level" => 32767,
     "config file" => [
       "default config file" => null,
       "local config file" => null,
       "PSYSH_CONFIG env" => false,
     ],
     "loop listeners" => [
       "Psy\ExecutionLoop\ProcessForker",
     ],
     "commands" => [
       "help" => "Psy\Command\HelpCommand",
       "?" => "Psy\Command\HelpCommand",
       "ls" => "Psy\Command\ListCommand",
       "list" => "Psy\Command\ListCommand",
       "dir" => "Psy\Command\ListCommand",
       "dump" => "Psy\Command\DumpCommand",
       "doc" => "Psy\Command\DocCommand",
       "rtfm" => "Psy\Command\DocCommand",
       "man" => "Psy\Command\DocCommand",
       "show" => "Psy\Command\ShowCommand",
       "wtf" => "Psy\Command\WtfCommand",
       "last-exception" => "Psy\Command\WtfCommand",
       "wtf?" => "Psy\Command\WtfCommand",
       "whereami" => "Psy\Command\WhereamiCommand",
       "throw-up" => "Psy\Command\ThrowUpCommand",
       "timeit" => "Psy\Command\TimeitCommand",
       "trace" => "Psy\Command\TraceCommand",
       "buffer" => "Psy\Command\BufferCommand",
       "buf" => "Psy\Command\BufferCommand",
       "clear" => "Psy\Command\ClearCommand",
       "edit" => "Psy\Command\EditCommand",
       "sudo" => "Psy\Command\SudoCommand",
       "history" => "Psy\Command\HistoryCommand",
       "hist" => "Psy\Command\HistoryCommand",
       "exit" => "Psy\Command\ExitCommand",
       "quit" => "Psy\Command\ExitCommand",
       "q" => "Psy\Command\ExitCommand",
       "migrate" => "Illuminate\Database\Console\Migrations\MigrateCommand",
     ],
     "updates" => [
       "update available" => true,
       "latest release version" => "v0.10.4",
       "update check interval" => "never",
       "update cache file" => "~/.config/psysh/update_check.json",
     ],
     "pcntl" => [
       "pcntl available" => true,
       "posix available" => true,
     ],
     "readline" => [
       "readline available" => true,
       "readline enabled" => true,
       "readline service" => "Psy\Readline\Libedit",
       "readline library" => "EditLine wrapper",
     ],
     "history" => [
       "history file" => "~/.config/psysh/psysh_history",
       "history size" => null,
       "erase duplicates" => null,
     ],
     "docs" => [
       "manual db file" => null,
       "sqlite available" => true,
     ],
     "autocomplete" => [
       "tab completion enabled" => true,
       "custom matchers" => [],
       "bracketed paste" => false,
     ],
   ]
>>>
willemo commented 4 years ago

Thanks for checking @ikari7789! I was already on v4.9.1 of nikic/php-parser, but I did try to downgrade to v3.1.5 and that solved the issue. Apparently there's a bug in v4.* somewhere.

Thanks again for your help @ikari7789 and @bobthecow!

ikari7789 commented 4 years ago

Are we sure it’s just due to a bug in v4.* somewhere and not due to something needing to be tweaked in psysh to work properly with v4?

willemo commented 4 years ago

I'm not sure, but I did find some issues for nikic/php-parser concerning treating the parsed code as PHP 8 and causing issues when the actual version is 7.*.

bobthecow commented 4 years ago

I'm unable to reproduce it with php parser v4.9.1, v4.10.0, or v4.10.1. There's gotta be something more to this.

Do you mind dumping what's actually being executed when it breaks? In your vendor directory, find PsySH's Shell.php, and add dump calls in onInput and onExecute just before return.

willemo commented 4 years ago

Here's the output:

Psy Shell v0.10.4 (PHP 7.3.20-1+ubuntu18.04.1+deb.sury.org+1 — cli) by Justin Hileman
>>> User::class
^ "User::class"
^ "return User::class;"
=> "User"
>>> \App\User::class
^ "\App\User::class"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> namespace App;
^ "namespace App;"
^ """
namespace App;\n
\n
return new \Psy\CodeCleaner\NoReturnValue();
"""
>>> User::class
^ "User::class"
^ """
namespace App;\n
\n
return User::class;
"""
=> "App\User"
>>> App\User::class
^ "App\User::class"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> psy/info()
^ "psy/info()"
^ """
namespace App;\n
\n
return psy / info();
"""
PHP Warning:  Use of undefined constant psy - assumed 'psy' (this will throw an Error in a future version of PHP) in /path/to/current/foldereval()'d code on line 1
TypeError: Too few arguments to function info(), 0 passed in /path/to/current/foldereval()'d code on line 1 and at least 1 expected

I changed the paths, but the missing space before the eval()'d part was there already.

It looks like it's never reaching the dump in onExecute when the error is occurring.

Edit: I'm running the above code on the server with the v4.* version of php-parser.

bobthecow commented 4 years ago

Just after you get the PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1 can you run wtf -a and paste the result?

willemo commented 4 years ago

Here it is:

>>> \App\User::class
^ "\App\User::class"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> wtf -a
^ "wtf -a"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
--
 0:  () at vendor/psy/psysh/src/Exception/ParseErrorException.php:40
 1:  Psy\Exception\ParseErrorException::fromParseError() at vendor/psy/psysh/src/CodeCleaner.php:294
 2:  Psy\CodeCleaner->parse() at vendor/psy/psysh/src/CodeCleaner.php:221
 3:  Psy\CodeCleaner->clean() at vendor/psy/psysh/src/Shell.php:833
 4:  Psy\Shell->addCode() at vendor/psy/psysh/src/Shell.php:521
 5:  Psy\Shell->getInput() at vendor/psy/psysh/src/ExecutionLoopClosure.php:40
 6:  Psy\{closure}() at vendor/psy/psysh/src/ExecutionClosure.php:96
 7:  Psy\ExecutionClosure->execute() at vendor/psy/psysh/src/Shell.php:370
 8:  Psy\Shell->doInteractiveRun() at vendor/psy/psysh/src/Shell.php:341
 9:  Psy\Shell->doRun() at vendor/symfony/console/Application.php:140
10:  Symfony\Component\Console\Application->run() at vendor/psy/psysh/src/Shell.php:316
11:  Psy\Shell->run() at vendor/laravel/tinker/src/Console/TinkerCommand.php:81
12:  Laravel\Tinker\Console\TinkerCommand->handle() at n/a:n/a
13:  call_user_func_array() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:37
14:  Illuminate\Container\BoundMethod::Illuminate\Container\{closure}() at vendor/laravel/framework/src/Illuminate/Container/Util.php:37
15:  Illuminate\Container\Util::unwrapIfClosure() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:95
16:  Illuminate\Container\BoundMethod::callBoundMethod() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:39
17:  Illuminate\Container\BoundMethod::call() at vendor/laravel/framework/src/Illuminate/Container/Container.php:596
18:  Illuminate\Container\Container->call() at vendor/laravel/framework/src/Illuminate/Console/Command.php:134
19:  Illuminate\Console\Command->execute() at vendor/symfony/console/Command/Command.php:258
20:  Symfony\Component\Console\Command\Command->run() at vendor/laravel/framework/src/Illuminate/Console/Command.php:121
21:  Illuminate\Console\Command->run() at vendor/symfony/console/Application.php:916
22:  Symfony\Component\Console\Application->doRunCommand() at vendor/symfony/console/Application.php:264
23:  Symfony\Component\Console\Application->doRun() at vendor/symfony/console/Application.php:140
24:  Symfony\Component\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Console/Application.php:93
25:  Illuminate\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Foundation/Console/Kernel.php:129
26:  Illuminate\Foundation\Console\Kernel->handle() at artisan:38
bobthecow commented 4 years ago

Yeah, I've got nothing. Add a dump call on vendor/psy/psysh/src/CodeCleaner.php:221 to see what we're passing to CodeCleaner::parse?

willemo commented 4 years ago

This looks like it's all correct:

>>> \App\User::class
^ "\App\User::class"
^ "<?php \App\User::class\n"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
bobthecow commented 4 years ago

Try including the semicolon and see if that makes it through.

We try to detect a bunch of cases where if we just let you hit enter and continue onto the next line, you'll eventually input valid PHP. It could be failing at that, because something about PHP Parser's output changed.

But I'm trying it on PHP 7.3.22, with PsySH v0.10.4 and PHP Parser v4.9.1, and I can't make it break.

willemo commented 4 years ago

It couldn't be the PHP version right? That would be extremely weird.

Sadly, the same issue still occurs:

>>> \App\User::class;
^ "\App\User::class;"
^ "<?php \App\User::class;\n"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> wtf -a
^ "wtf -a"
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
--
 0:  () at vendor/psy/psysh/src/Exception/ParseErrorException.php:40
 1:  Psy\Exception\ParseErrorException::fromParseError() at vendor/psy/psysh/src/CodeCleaner.php:295
 2:  Psy\CodeCleaner->parse() at vendor/psy/psysh/src/CodeCleaner.php:222
 3:  Psy\CodeCleaner->clean() at vendor/psy/psysh/src/Shell.php:833
 4:  Psy\Shell->addCode() at vendor/psy/psysh/src/Shell.php:521
 5:  Psy\Shell->getInput() at vendor/psy/psysh/src/ExecutionLoopClosure.php:40
 6:  Psy\{closure}() at vendor/psy/psysh/src/ExecutionClosure.php:96
 7:  Psy\ExecutionClosure->execute() at vendor/psy/psysh/src/Shell.php:370
 8:  Psy\Shell->doInteractiveRun() at vendor/psy/psysh/src/Shell.php:341
 9:  Psy\Shell->doRun() at vendor/symfony/console/Application.php:140
10:  Symfony\Component\Console\Application->run() at vendor/psy/psysh/src/Shell.php:316
11:  Psy\Shell->run() at vendor/laravel/tinker/src/Console/TinkerCommand.php:81
12:  Laravel\Tinker\Console\TinkerCommand->handle() at n/a:n/a
13:  call_user_func_array() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:37
14:  Illuminate\Container\BoundMethod::Illuminate\Container\{closure}() at vendor/laravel/framework/src/Illuminate/Container/Util.php:37
15:  Illuminate\Container\Util::unwrapIfClosure() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:95
16:  Illuminate\Container\BoundMethod::callBoundMethod() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:39
17:  Illuminate\Container\BoundMethod::call() at vendor/laravel/framework/src/Illuminate/Container/Container.php:596
18:  Illuminate\Container\Container->call() at vendor/laravel/framework/src/Illuminate/Console/Command.php:134
19:  Illuminate\Console\Command->execute() at vendor/symfony/console/Command/Command.php:258
20:  Symfony\Component\Console\Command\Command->run() at vendor/laravel/framework/src/Illuminate/Console/Command.php:121
21:  Illuminate\Console\Command->run() at vendor/symfony/console/Application.php:916
22:  Symfony\Component\Console\Application->doRunCommand() at vendor/symfony/console/Application.php:264
23:  Symfony\Component\Console\Application->doRun() at vendor/symfony/console/Application.php:140
24:  Symfony\Component\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Console/Application.php:93
25:  Illuminate\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Foundation/Console/Kernel.php:129
26:  Illuminate\Foundation\Console\Kernel->handle() at artisan:38

Is it me, or does it look like it's never reaching php-parser?

Anything else I can dump or try?

bobthecow commented 4 years ago

It's definitely hitting it. CodeCleaner is re-throwing a parse error that it got from PHP Parser:

https://github.com/bobthecow/psysh/blob/v0.10.4/src/CodeCleaner.php#L294

The only thing I can come up with is maybe there's some bug with exactly your PHP version and PHP Parser v4.x. Maybe there was a bug in that point release and tokenizing broke, or something. Any chance you can bump to the most recent PHP 7.3.x?

willemo commented 4 years ago

Well, that solved it:

Psy Shell v0.10.4 (PHP 7.3.22-1+ubuntu18.04.1+deb.sury.org+1 — cli) by Justin Hileman
>>> \App\User::class
=> "App\User"

I think it's exactly what you expected. Very strange!

I stupidly did a deploy of my new version (with php-parser on v3.*) while testing, so this is possibly not the solution.

willemo commented 4 years ago

Sadly, the update didn't work:

Psy Shell v0.10.4 (PHP 7.3.22-1+ubuntu18.04.1+deb.sury.org+1 — cli) by Justin Hileman
>>> \App\User::class
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
>>> wtf -a
PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1
--
 0:  () at vendor/psy/psysh/src/Exception/ParseErrorException.php:40
 1:  Psy\Exception\ParseErrorException::fromParseError() at vendor/psy/psysh/src/CodeCleaner.php:294
 2:  Psy\CodeCleaner->parse() at vendor/psy/psysh/src/CodeCleaner.php:221
 3:  Psy\CodeCleaner->clean() at vendor/psy/psysh/src/Shell.php:829
 4:  Psy\Shell->addCode() at vendor/psy/psysh/src/Shell.php:521
 5:  Psy\Shell->getInput() at vendor/psy/psysh/src/ExecutionLoopClosure.php:40
 6:  Psy\{closure}() at vendor/psy/psysh/src/ExecutionClosure.php:96
 7:  Psy\ExecutionClosure->execute() at vendor/psy/psysh/src/Shell.php:370
 8:  Psy\Shell->doInteractiveRun() at vendor/psy/psysh/src/Shell.php:341
 9:  Psy\Shell->doRun() at vendor/symfony/console/Application.php:140
10:  Symfony\Component\Console\Application->run() at vendor/psy/psysh/src/Shell.php:316
11:  Psy\Shell->run() at vendor/laravel/tinker/src/Console/TinkerCommand.php:81
12:  Laravel\Tinker\Console\TinkerCommand->handle() at n/a:n/a
13:  call_user_func_array() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:37
14:  Illuminate\Container\BoundMethod::Illuminate\Container\{closure}() at vendor/laravel/framework/src/Illuminate/Container/Util.php:37
15:  Illuminate\Container\Util::unwrapIfClosure() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:95
16:  Illuminate\Container\BoundMethod::callBoundMethod() at vendor/laravel/framework/src/Illuminate/Container/BoundMethod.php:39
17:  Illuminate\Container\BoundMethod::call() at vendor/laravel/framework/src/Illuminate/Container/Container.php:596
18:  Illuminate\Container\Container->call() at vendor/laravel/framework/src/Illuminate/Console/Command.php:134
19:  Illuminate\Console\Command->execute() at vendor/symfony/console/Command/Command.php:258
20:  Symfony\Component\Console\Command\Command->run() at vendor/laravel/framework/src/Illuminate/Console/Command.php:121
21:  Illuminate\Console\Command->run() at vendor/symfony/console/Application.php:916
22:  Symfony\Component\Console\Application->doRunCommand() at vendor/symfony/console/Application.php:264
23:  Symfony\Component\Console\Application->doRun() at vendor/symfony/console/Application.php:140
24:  Symfony\Component\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Console/Application.php:93
25:  Illuminate\Console\Application->run() at vendor/laravel/framework/src/Illuminate/Foundation/Console/Kernel.php:129
26:  Illuminate\Foundation\Console\Kernel->handle() at artisan:38
composer show nikic/php-parser
name     : nikic/php-parser
descrip. : A PHP parser written in PHP
keywords : parser, php
versions : * v4.10.1
type     : library
license  : BSD 3-Clause "New" or "Revised" License (BSD-3-Clause) (OSI approved) https://spdx.org/licenses/BSD-3-Clause.html#licenseText
homepage : 
source   : [git] https://github.com/nikic/PHP-Parser.git 1b479e7592812411c20c34d9ed33db3957bde66e
dist     : [zip] https://api.github.com/repos/nikic/PHP-Parser/zipball/1b479e7592812411c20c34d9ed33db3957bde66e 1b479e7592812411c20c34d9ed33db3957bde66e
path     : /home/forge/api.staging.house-presentation.com/releases/20200925084949/vendor/nikic/php-parser
names    : nikic/php-parser

autoload
psr-4
PhpParser\ => lib/PhpParser

requires
ext-tokenizer *
php >=7.0

requires (dev)
ircmaxell/php-yacc ^0.0.7
phpunit/phpunit ^6.5 || ^7.0 || ^8.0 || ^9.0
bobthecow commented 4 years ago

Oh boo.

So there's a (default disabled) command that ships with PsySH called parse. Can you add a config file to ~/.config/psysh/config.php (if you don't have one) and enable the command?

<?php

return [
  'commands' => [new \Psy\Command\ParseCommand()],
];

… then run parse \App\User::class and paste the result?

willemo commented 4 years ago

Done:

Psy Shell v0.10.4 (PHP 7.3.22-1+ubuntu18.04.1+deb.sury.org+1 — cli) by Justin Hileman
>>> parse \App\User::class
PhpParser/Error with message 'Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1'
bobthecow commented 4 years ago

Right. Of course it does.

bobthecow commented 3 years ago

I'm sorry, I have no idea what's going on here :(

I've got the same PHP version, the same PsySH version, the same Laravel version, the same Tinker version, the same PHP Parser version. I can't reproduce your issue.

It seems to only happen with slashes. Maybe it's a shell or terminal app encoding thing?

You can try bypassing interactive input entirely by using the edit command. You can also try running php artisan tinker --execute="App\User::class".

willemo commented 3 years ago

Sadly, the same result:

php artisan tinker --execute="App\User::class"

   Psy\Exception\ParseErrorException 

  PHP Parse error: Syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM on line 1

  at vendor/psy/psysh/src/Exception/ParseErrorException.php:40
    36|      * @return ParseErrorException
    37|      */
    38|     public static function fromParseError(\PhpParser\Error $e)
    39|     {
  > 40|         return new self($e->getRawMessage(), $e->getStartLine());
    41|     }
    42| }
    43| 

      +20 vendor frames 
  21  artisan:38
      Illuminate\Foundation\Console\Kernel::handle(Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))

It's really weird you can't reproduce the issue. Of course we have a ton of code and external dependencies, so those could also influence the code. For now I have a solution: use v3.* of php-parser. Thanks a lot for your time and help!

bobthecow commented 3 years ago

Wait I have one more idea. Maybe it's something with the auto-aliasing thing that tinker does?

Try commenting out the ClassAliasAutoloader registration in TinkerCommand.

bobthecow commented 2 years ago

Closing due to inactivity and my inability to repro. Feel free to reopen :)