Laravel 11中PHPUnit测试时Passport:install执行失败的修复方案
解决Laravel 11测试中
passport:install执行失败的问题 方案1:使用无交互模式执行命令
stream_isatty()错误源于Passport的install命令在非交互式测试环境中尝试终端交互,添加--force参数跳过确认,并通过NullOutput避免流冲突:
public function manageDatabase(): void { Artisan::call('config:clear'); Artisan::call('migrate:fresh --seed'); // 跳过交互并屏蔽输出流 Artisan::call('passport:install --force', [], new \Symfony\Component\Console\Output\NullOutput()); Artisan::call('config:clear'); }
--force会自动生成加密密钥和默认客户端,NullOutput解决流转换时的缓冲数据丢失问题。
方案2:手动创建Passport客户端与密钥
若命令行方式仍有问题,可直接通过代码完成passport:install的核心操作:
public function manageDatabase(): void { Artisan::call('config:clear'); Artisan::call('migrate:fresh --seed'); // 生成Passport加密密钥 Artisan::call('passport:keys --force'); // 创建个人访问客户端 $personalClient = \Laravel\Passport\Client::create([ 'name' => 'Personal Access Client', 'secret' => \Illuminate\Support\Str::random(40), 'redirect' => 'http://localhost', 'personal_access_client' => true, 'password_client' => false, 'revoked' => false, ]); // 创建密码授权客户端 $passwordClient = \Laravel\Passport\Client::create([ 'name' => 'Password Grant Client', 'secret' => \Illuminate\Support\Str::random(40), 'redirect' => 'http://localhost', 'personal_access_client' => false, 'password_client' => true, 'revoked' => false, ]); // 同步客户端信息到配置 config(['passport.personal_access_client.id' => $personalClient->id]); config(['passport.personal_access_client.secret' => $personalClient->secret]); Artisan::call('config:clear'); }
该方式绕开命令行交互,直接操作数据库确保oauth_clients表生成数据。
方案3:调整PHPUnit环境配置
在phpunit.xml中添加环境变量,模拟终端环境:
<php> <!-- 原有配置 --> <env name="TERM" value="xterm"/> <env name="STDIN" value="php://stdin"/> </php>
设置TERM让命令识别为终端环境,避免流检测错误。
内容的提问来源于stack exchange,提问作者Hilal Najem
相关产品推荐
相关产品推荐

