刚开始使用toms_topic
。我有一个运行在端口8000上的服务器端应用程序,该应用程序通过Laravel Passport对用户进行身份验证,而我的react.js客户端应用程序运行在端口3000上。现在,我正在尝试执行“登录”操作。
当我提供正确的凭据时,会从客户端发送回令牌,并且状态为200。当凭据无效时,将返回401。到目前为止很好。但是,如果我仅以电子邮件形式提供电子邮件,而没有提供密码,则会出现以下与CORS相关的错误:
引发错误时,将发生以下网络调用:
我在客户端的登录名:
barryvdh/laravel-cors
服务器端:
login = (email, password) => {
console.log(email);
fetch("http://localhost:8000/api/auth/login", {
method: 'POST',
body: JSON.stringify({
'email': email,
'password': password
}),
headers: {
'Content-Type': 'application/json'
}
})
.then(res => res.json())
.then(response => {
console.log(response['access_token']); //with correct credentials this is logged out and set in local storage
localStorage.setItem('access_token', response['access_token']);
})
.catch(error => console.error('Error: ', error));
}
public function login(Request $request)
{
$request->validate([
'email' => 'required|string|email',
'password' => 'required|string',
'remember_me' => 'boolean'
]);
$credentials = request(['email', 'password']);
if(!Auth::attempt($credentials)) {
return response()->json([
'message' => 'Unauthorized'
], 401);
}
$user = $request->user();
$tokenResult = $user->createToken('Personal Access Token');
$token = $tokenResult->token;
if ($request->remember_me) {
$token->expires_at = Carbon::now()->addWeeks(1);
}
$token->save();
return response()->json([
'access_token' => $tokenResult->accessToken,
'token_type' => 'Bearer',
'expires_at' => Carbon::parse(
$tokenResult->token->expires_at
)->toDateTimeString()
]);
}
(从barryvdh / laravel-cors软件包中发布):
cors.php
return [
'supportsCredentials' => false,
'allowedOrigins' => ['*'],
'allowedOriginsPatterns' => [],
'allowedHeaders' => ['*'],
'allowedMethods' => ['*'],
'exposedHeaders' => [],
'maxAge' => 0,
];
:
api.php
Route::group(['prefix' => 'auth',], function () {
Route::post('login', 'AuthController@login');
Route::post('register', 'AuthController@register');
Route::get('register/activate/{token}', 'AuthController@registerActivate');
Route::group(['middleware' => 'auth:api'], function() {
Route::get('logout', 'AuthController@logout');
Route::get('user', 'AuthController@user');
});
});
:
Kernel.php
通过邮递员进行相同的POST请求(一个到protected $middlewareGroups = [
'web' => [
\App\Http\Middleware\EncryptCookies::class,
\Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
\Illuminate\Session\Middleware\StartSession::class,
// \Illuminate\Session\Middleware\AuthenticateSession::class,
\Illuminate\View\Middleware\ShareErrorsFromSession::class,
\App\Http\Middleware\VerifyCsrfToken::class,
\Illuminate\Routing\Middleware\SubstituteBindings::class,
],
'api' => [
\Barryvdh\Cors\HandleCors::class,
'throttle:60,1',
'bindings',
],
];
protected $middleware = [
\Barryvdh\Cors\HandleCors::class,
\App\Http\Middleware\CheckForMaintenanceMode::class,
\Illuminate\Foundation\Http\Middleware\ValidatePostSize::class,
\App\Http\Middleware\TrimStrings::class,
\Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull::class,
\App\Http\Middleware\TrustProxies::class
];
,密码除外),我得到了预期的错误消息:
/api/auth/login
但是,通过react client应用程序进行此操作会引发屏幕截图中的错误。我猜想这与浏览器发出的预检HTTP OPTIONS请求有关,这是CORS工作原理的一部分。
我该如何纠正?我希望在密码为空的情况下返回401,以获取状态信息,并让React客户端获得与Postman相同的JSON消息。似乎很奇怪,基于该POST请求的有效负载,会发生CORS相关错误。这是否意味着服务器和/或客户端未正确设置CORS?
答案 0 :(得分:1)
首先是班级成员:
protected $middleware
将为api
和web
都应用中间件
来自 laravel.com/docs/5.8/middleware#registering-middleware
如果希望中间件在对应用程序的每个HTTP请求期间运行,请在app / Http / Kernel.php类的$ middleware属性中列出中间件类。
另请参见: barryvdh/laravel-cors#global-usage
因此,尝试通过删除以下内容来一次注册中间件:
您的\Barryvdh\Cors\HandleCors::class
中间件组中的'api'
。
出于逻辑目的,请使用以下命令重构protected $middleware
:
protected $middleware = [
\App\Http\Middleware\CheckForMaintenanceMode::class,
\Illuminate\Foundation\Http\Middleware\ValidatePostSize::class,
\App\Http\Middleware\TrimStrings::class,
\Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull::class,
\App\Http\Middleware\TrustProxies::class,
\Barryvdh\Cors\HandleCors::class,
];
答案 1 :(得分:1)