CSRF 检查失败!在邮递员中尝试 POST 方法时(API with slim 3)
Failed CSRF check! in postman when trying POST method (API with slim 3)
我正在使用 Slim 3 项目并安装了 CSRF package ("slim/csrf": "^0.8.2",)
为了发出 POST 的请求,我使用了邮递员。发送操作时出现以下错误:
Failed CSRF check!
这是我的 API 路线(在本例中,关注 POST 路线):
<?php
/* RESTful endpoints or routes */
use App\Controllers\api\users\UserController;
$app->group('/api',function () use ($app){
$app->group('/users', function () {
$this->get('', UserController::class.':index');
$this->get('/{id}', UserController::class.':show');
$this->post('', UserController::class.':store');
});
});
这是控制器应该从 POST 请求中获取信息的地方,但我收到了错误:
//Save a user via API
public function store($request,$response,$args)
{
//todo: validation!
var_dump($request->getParams());//todo: CSRF check failed!
die();
}
这是我注册 CSRF 组件的地方:
//Register the CSRF Component
$container['csrf'] = function ($container){
return new \Slim\Csrf\Guard();
};
我试过这个解决方案:但是没有用。
是否有任何解决方法可以使其正常工作?如何防止 CSRF 在我的 API 路由上 运行?
* 已解决 *
按照的建议,我决定将 CSRF 应用于网络路由,但 APIs 路由除外。
将我所有的网络路由分组:
$app->group('',function ()use($app,$container){
/* ******* H O M E ********** */
require __DIR__ . '/web/home/home.php';
/* ********** T O P I C s ********** */
require __DIR__ . '/web/topics/topics.php';
/* ********** C O N T A C T *********** */
require __DIR__ . '/web/contact/contact.php';
/* And so on and etcetera ....*/
/* ********************************************************************************* */
})->add($container->get('csrf'));//Adding CSRF protection only for web routes
并且,例如,在 topics.php
路由文件中,我有:
$app->group('/topics',function(){
$this->get('',TopicController::class.':index');
$this->get('/{id}',TopicController::class.':show')->setName('topics.show');
});
至于 API 条路线,它们保持不变。
最后,在我的容器中,我评论了以下内容:
//$app->add($container->get('csrf')); //I've commented this line in order to add CSRF for specific routes (all except APIs ones)
您需要确保将 Slim\Csrf\Guard
中间件添加到路由或应用程序(如果您想为所有路由应用 csrf)。例如
将csrf中间件应用到所有路由
$csrf = $container->csrf;
$app->add($csrf);
或仅申请某些航线
$csrf = $container->csrf;
$app->group('/api',function () use ($app, $csrf){
$app->group('/users', function () {
$this->get('', UserController::class.':index')
->add($csrf);
$this->get('/{id}', UserController::class.':show');
$this->post('', UserController::class.':store')
->add($csrf);
});
});
您还需要确保有随请求传递的 Csrf 令牌 name/value 数据。使用Postman时,需要在执行POST.
之前想办法获取token名key/value对
以下代码摘自Slim Csrf Readme。
// CSRF token name and value
$nameKey = $this->csrf->getTokenNameKey();
$valueKey = $this->csrf->getTokenValueKey();
$name = $request->getAttribute($nameKey);
$value = $request->getAttribute($valueKey);
// Render HTML form which POSTs to /bar with two hidden input fields for the
// name and value:
// <input type="hidden" name="<?= $nameKey ?>" value="<?= $name ?>">
// <input type="hidden" name="<?= $valueKey ?>" value="<?= $value ?>">
阅读 Slim Csrf Readme 了解更多信息。
我正在使用 Slim 3 项目并安装了 CSRF package ("slim/csrf": "^0.8.2",)
为了发出 POST 的请求,我使用了邮递员。发送操作时出现以下错误:
Failed CSRF check!
这是我的 API 路线(在本例中,关注 POST 路线):
<?php
/* RESTful endpoints or routes */
use App\Controllers\api\users\UserController;
$app->group('/api',function () use ($app){
$app->group('/users', function () {
$this->get('', UserController::class.':index');
$this->get('/{id}', UserController::class.':show');
$this->post('', UserController::class.':store');
});
});
这是控制器应该从 POST 请求中获取信息的地方,但我收到了错误:
//Save a user via API
public function store($request,$response,$args)
{
//todo: validation!
var_dump($request->getParams());//todo: CSRF check failed!
die();
}
这是我注册 CSRF 组件的地方:
//Register the CSRF Component
$container['csrf'] = function ($container){
return new \Slim\Csrf\Guard();
};
我试过这个解决方案:但是没有用。
是否有任何解决方法可以使其正常工作?如何防止 CSRF 在我的 API 路由上 运行?
* 已解决 *
按照
将我所有的网络路由分组:
$app->group('',function ()use($app,$container){
/* ******* H O M E ********** */
require __DIR__ . '/web/home/home.php';
/* ********** T O P I C s ********** */
require __DIR__ . '/web/topics/topics.php';
/* ********** C O N T A C T *********** */
require __DIR__ . '/web/contact/contact.php';
/* And so on and etcetera ....*/
/* ********************************************************************************* */
})->add($container->get('csrf'));//Adding CSRF protection only for web routes
并且,例如,在 topics.php
路由文件中,我有:
$app->group('/topics',function(){
$this->get('',TopicController::class.':index');
$this->get('/{id}',TopicController::class.':show')->setName('topics.show');
});
至于 API 条路线,它们保持不变。
最后,在我的容器中,我评论了以下内容:
//$app->add($container->get('csrf')); //I've commented this line in order to add CSRF for specific routes (all except APIs ones)
您需要确保将 Slim\Csrf\Guard
中间件添加到路由或应用程序(如果您想为所有路由应用 csrf)。例如
将csrf中间件应用到所有路由
$csrf = $container->csrf;
$app->add($csrf);
或仅申请某些航线
$csrf = $container->csrf;
$app->group('/api',function () use ($app, $csrf){
$app->group('/users', function () {
$this->get('', UserController::class.':index')
->add($csrf);
$this->get('/{id}', UserController::class.':show');
$this->post('', UserController::class.':store')
->add($csrf);
});
});
您还需要确保有随请求传递的 Csrf 令牌 name/value 数据。使用Postman时,需要在执行POST.
之前想办法获取token名key/value对以下代码摘自Slim Csrf Readme。
// CSRF token name and value
$nameKey = $this->csrf->getTokenNameKey();
$valueKey = $this->csrf->getTokenValueKey();
$name = $request->getAttribute($nameKey);
$value = $request->getAttribute($valueKey);
// Render HTML form which POSTs to /bar with two hidden input fields for the
// name and value:
// <input type="hidden" name="<?= $nameKey ?>" value="<?= $name ?>">
// <input type="hidden" name="<?= $valueKey ?>" value="<?= $value ?>">
阅读 Slim Csrf Readme 了解更多信息。