Passing the bearer token in yii2 rest returns an error of 401
For those who might face this problem i found out that this was caused by the HttpBearerAuth and when i changed to QueryParamAuth
everything is now working i also made a few other changes as
ON THE CONTROLLER1.Removed the cors filterspublic function behaviors(){ $behaviors = parent::behaviors(); $behaviors['authenticator'] = [ 'class' => CompositeAuth::className(), 'authMethods' => [ HttpBasicAuth::className(), HttpBearerAuth::className(), QueryParamAuth::className(), ], ]; return $behaviors;}
2,In my config main.php
'response' => [ 'format' => yii\web\Response::FORMAT_JSON, 'charset' => 'UTF-8', 'on beforeSend' => function ($event) { header("Access-Control-Allow-Origin: *"); } ], 'urlManager' => [ 'class' => 'yii\web\UrlManager', 'enablePrettyUrl' => true, 'showScriptName' => false, 'rules' => [ ['class' => 'yii\rest\UrlRule', 'controller' => 'auth', 'pluralize'=>false], ...other controlers here ], ],
3.In the .htacess file in the project root i added
Header set Access-Control-Allow-Origin "*" Header set Access-Control-Allow-Headers "Content-Type"
So my angular2 post request looks like
http://127.0.0.1/bcl/api/rest/v1/auth/logout?access-token=your access token
So the access token is always passed as a query parameter
The main reason is because i found out that if the browser sends any header apart from content type an options request is triggered
So now my headers look like
headers.append('Content-Type', 'application/x-www-form-urlencoded'); //i removed the bearer token
I used a different approach:
Added
public function beforeAction($action) { $this->enableCsrfValidation = false; parent::beforeAction($action); if (Yii::$app->getRequest()->getMethod() === 'OPTIONS') { // End it, otherwise a 401 will be shown. Yii::$app->end(); } return true; }
in the controller.
Keep the behaviours function as at your question.
As you mentioned, the issue is that the browser sends a preflighted request.
My assumption is that you are making a cross browser request(localhost:4200), so the browser is making an OPTIONS request first to the server to find out the "Access-Control-Allow" settings, but without an access token in the header. So a 401 is thrown and the CORS process fails.
The difference is that this way, you can have the authorization token in a header.