Laravel PHPUnit始终通过CSRF

Hed*_*dam 0 php phpunit laravel

我目前正在编写测试,以确保我们的CSRF保护功能可在Laravel中使用。测试看起来像这样。

public function testSecurityIncorrectCSRF()
{
    $this->visit('/login')
     ->type('REDACTED', 'email')
     ->type('123123', 'password');

     session()->regenerateToken();

     $this->press('login')
     ->seePageIs('/login');
}
Run Code Online (Sandbox Code Playgroud)

无论我做什么,即使我传递了错误的_token,登录请求也将始终成功。我已经在PHPUnit测试之外尝试过,并且CSRF保护有效。我所有的中间件都已启用,因此应该启用CSRF保护。

谁能解释为什么会这样?

小智 5

看一下Illuminate\Foundation\Http\Middleware\VerifyCsrfToken类,尤其是handle方法。

public function handle($request, Closure $next)
{
    if (
        $this->isReading($request) ||
        $this->runningUnitTests() ||
        $this->shouldPassThrough($request) ||
        $this->tokensMatch($request)
    ) {
        return $this->addCookieToResponse($request, $next($request));
    }

    throw new TokenMismatchException;
}
Run Code Online (Sandbox Code Playgroud)

如果它检测到请求来自单元测试,它将始终通过csrf令牌检查: $this->runningUnitTests()

一种解决方案是将以下代码放在测试功能的开头:

public function handle($request, Closure $next)
{
    if (
        $this->isReading($request) ||
        $this->runningUnitTests() ||
        $this->shouldPassThrough($request) ||
        $this->tokensMatch($request)
    ) {
        return $this->addCookieToResponse($request, $next($request));
    }

    throw new TokenMismatchException;
}
Run Code Online (Sandbox Code Playgroud)

这会将环境更改为生产环境,从而启用csrf令牌检查。