编辑:我应该在一开始就这么说,我在前端使用 AngularJS,并且我通过 XHR 发出所有请求。 我正在针对每个用户请求使用
CSRF Token
开发一个应用程序。
我应该在每次请求后重新生成
Token
吗?
类似
Session::forget("_token") and Session::put("_token", RANDOM_SOMETHING)
或者每个用户使用同一个就足够了吗
Session
?
有什么好处吗?
Laravel 5 使用 Blades 模板,这非常简单。
如果您只想要csrf token的值,可以通过以下方式生成:
{{ csrf_token() }}
生成如下所示的代币值:
7YC0Sxth7AYe4RFSjzaPf2ygLCecJhPbyXhz6vvF
如果您使用表单,您可以在表单中添加以下代码行:
{{ csrf_field() }}
它将生成这样的html:
<input type="hidden" name="_token" value="7YC0Sxth7AYe4RFSjzaPf2ygLCecJhblahblah">
Laravel 应该为你做这件事,你不需要管理
_token
的创建/删除
<input type="hidden" name="_token" value="<?php echo csrf_token(); ?>">
请参阅此处文档中的“CSRF 保护”部分:https://laravel.com/docs/10.x/csrf#
如果您使用 Laravel 5.6,请在表单顶部执行以下操作,为 CSRF 令牌创建隐藏输入字段
@csrf
视情况而定。如果攻击者不是 MITM,从某种意义上说,他们无法窃听您的 Web 应用程序和 API 服务器之间的流量,则整个会话的单个 CSRF 令牌就足够了。
假设您也保护服务器端的敏感操作(即仅允许资源所有者访问资源,例如“删除我的帐户”等),令牌将确保发出请求的浏览器是合法的,经过身份验证的用户浏览器。我想这就是你应该担心的。
另一方面,如果攻击者能够查看 Web 应用程序和 API 之间的非安全流量,他们可能会获取 CSRF 令牌和您的 session_id 并透明地做坏事。在这种情况下,为每个请求(POST,或任何执行敏感操作的类型)授予、使用并随后丢弃令牌只会使他们的工作变得更加困难,但你仍然注定失败。
我的2美分...
CSRF 令牌通过将 cookie 令牌与 服务器令牌。
您可以通过
csrf_token()
辅助函数在 Laravel 中生成 csrf 令牌。如果你想要完整的csrf字段,那么你可以使用csrf_field()
函数,csrf内部逻辑是
function csrf_field()
{
return new HtmlString('<input type="hidden" name="_token" value="'.csrf_token().'">');
}
当新请求生成时,laravel 每次都会创建随机令牌,并在存储后存储在浏览器 cookie 和会话中,它们之间的比较如下
cookie == session token
Laravel 内部逻辑如下,你可以在
VerifyCsrfToken
中间件中找到它。
/**
* Determine if the session and input CSRF tokens match.
*
* @param \Illuminate\Http\Request $request
* @return bool
*/
protected function tokensMatch($request)
{
$token = $this->getTokenFromRequest($request);
return is_string($request->session()->token()) &&
is_string($token) &&
hash_equals($request->session()->token(), $token);
}
/**
* Get the CSRF token from the request.
*
* @param \Illuminate\Http\Request $request
* @return string
*/
protected function getTokenFromRequest($request)
{
$token = $request->input('_token') ?: $request->header('X-CSRF-TOKEN');
if (! $token && $header = $request->header('X-XSRF-TOKEN')) {
$token = $this->encrypter->decrypt($header);
}
return $token;
}
/**
* Add the CSRF token to the response cookies.
*
* @param \Illuminate\Http\Request $request
* @param \Symfony\Component\HttpFoundation\Response $response
* @return \Symfony\Component\HttpFoundation\Response
*/
protected function addCookieToResponse($request, $response)
{
$config = config('session');
$response->headers->setCookie(
new Cookie(
'XSRF-TOKEN', $request->session()->token(), $this->availableAt(60 * $config['lifetime']),
$config['path'], $config['domain'], $config['secure'], false, false, $config['same_site'] ?? null
)
);
return $response;
}
如果你想在控制器中获取 CSRF 令牌,那么你可以像这样使用它并重定向 post Route
$CSRFToken = csrf_token();
简单的豌豆 希望对你有帮助