sizeg / yii2-jwt Goto Github PK
View Code? Open in Web Editor NEWA simple Yii2 component to work with JSON Web Token and JSON Web Signature
Home Page: https://jwt.io/
A simple Yii2 component to work with JSON Web Token and JSON Web Signature
Home Page: https://jwt.io/
$token->getClaims()
and other functions are returning value but $token
is empty
when token expired and don't want to relogin
want a function like 'refreshToken' to refresh a token by an old one ;)
How to make sure if token has expired on validation?
I need to do something only when token is already expired
when i use this
public static function findIdentityByAccessToken($token, $type = null)
{
$data = Yii::$app->jwt->decode($token);
if (!empty($data['id'])) {
return static::findOne(['access_token' => $data['id']]);
}
return null;
}
i got "Calling unknown method: sizeg\jwt\Jwt::decode()",
Hi,
I started using this extension, and being new to yii2 it took me some time to figure things out.
After login I generate Hmac signed token like in examples here, and then I send it to the client.
I then on each request send that token as a Authentication - Bearer header, and i see that yii2 calls the validateToken funciton with all the data from the token. However, it always return false for authorization (401: Your request was made with invalid credentials).
Do I need to manually verify token on each request, or will Yii2 do that automatically?
Do I need to set up these manually again $data->setIssuer('http://mydomain.com'); $data->setAudience('http://mydomain.com'); $data->setId('4f1g23a12aa'); ?
If so, do you have any suggestions how/where do I add the code?
Thanks
I've tried to set JWT token that never expired.
$token = Yii::$app->jwt->getBuilder()->setIssuer(Yii::$app->params['issuer'])// Configures the issuer (iss claim)
->setId(Yii::$app->params['token_id'], true)// Configures the id (jti claim), replicating as a header item
->setIssuedAt(time())// Configures the time that the token was issue (iat claim)
->setExpiration(0)// Configures the expiration time of the token (exp claim) NEVER EXPIRED
->set('username', $params['username'])
->set('password', $params['password'])// Configures a new claim, called "uid"
->sign($signer,Yii::$app->params['secret_key'])
->getToken(); // Retrieves the generated token
Although expression setExpiration() is taken 0 or omitted, $token still expired. Could anyone find anyways to solve this problem. Thanks.
Doesn't component must handle exceptions of JWT Parser? I got this error while parsing invalid JWT:
exception 'InvalidArgumentException' with message 'The JWT string must have two dots' in /var/www/project/vendor/lcobucci/jwt/src/Parser.php:95
Stack trace:
#0 /var/www/project/vendor/lcobucci/jwt/src/Parser.php(59): Lcobucci\JWT\Parser->splitJwt('05cdea76-7107-4...')
#1 /var/www/project/vendor/sizeg/yii2-jwt/Jwt.php(77): Lcobucci\JWT\Parser->parse('05cdea76-7107-4...')
This produces 500
error in my rest interface
Unable to get authorization value
Initially, I have set 15 minutes for the expiration. Even though if a user stays active, after 15 minutes it returning 401 invalid token error. Is there any way to increase the expiry time at each request, so that it won't throw the error if the user stays active.
I'm trying to authenticate in my API with the generated token (my first time with JWT), but i'm receiving an Unauthorized error:
{
"name": "Unauthorized",
"message": "Your request was made with invalid credentials.",
"code": 0,
"status": 401,
"type": "yii\\web\\UnauthorizedHttpException"
}
I did as follows:
LoginController
class LoginController extends ActiveController
{
public $modelClass = 'app\models\User';
public function actionAuth()
{
Yii::$app->response->format = \yii\web\Response::FORMAT_JSON;
$username = Yii::$app->request->post('username');
$pass = Yii::$app->request->post('password');
$modelUser = User::findByUsername($username);
if ($modelUser && $modelUser->validatePassword($pass)) {
$token = (string) User::generateToken();
return [
'status' => true,
'message' => 'Success',
'token' => $token,
];
}
return [
'status' => false,
'message' => 'Wrong username or password'
];
}
}
User (model)
public static function generateToken()
{
$signer = new Sha256();
$token = \Yii::$app->jwt->getBuilder()->setIssuer('http://myurl') // Configures the issuer (iss claim)
->setAudience('http://myurl') // Configures the audience (aud claim)
->setId('myid', true) // Configures the id (jti claim), replicating as a header item
->setIssuedAt(time()) // Configures the time that the token was issue (iat claim)
->setNotBefore(time() + 60) // Configures the time before which the token cannot be accepted (nbf claim)
->setExpiration(time() + 3600) // Configures the expiration time of the token (exp claim)
->set('uid', 1) // Configures a new claim, called "uid"
->sign($signer, 'testing') // creates a signature using "testing" as key
->getToken(); // Retrieves the generated token
return $token;
}
Rest Controller
public function behaviors()
{
$behaviors = parent::behaviors();
$behaviors['authenticator'] = [
'class' => JwtHttpBearerAuth::className(),
];
return $behaviors;
}
Am I forgetting something to work properly?
Thank you!
Hi.
In composer.json
I see that dependency is set to "lcobucci/jwt": "~3.2.0",
. But now that package is already has 3.3.x version.
Are you going to update version constraint? JWT is kind of feature that is better to keep up to date.
Hi, we are thinking about to implement this library as an option for auth mechanism by default for LUYA => https://github.com/luyadev/luya
In order to have a more readability i would suggest to have a changelog file and also write down on what type of versioning you plan to release the library (for example semver i assume). This would be good for us to have more transparency.
Thanks for making such a good library, if we have inputs you can be sure to get some PRs :-)
i'm bit confusing about puting this extension to behavior 'cause in the readme it should place using
'authenticator' but in the comment of file 'JwtHttpBearerAuth.php' it should place using bearerAuth.
so what is correct one? authenticator or bearerAuth?
Hi
I am trying to use the jwt in yii with vue as a front-end framework but the browser before executing the post excecute an options request and gives me unauthorized action. looking for a solution i found one but it doesn't work as expected.
the solution that i found
class CustomCors extends Cors
{
public function beforeAction($action)
{
parent::beforeAction($action);
if (Yii::$app->getRequest()->getMethod() === 'OPTIONS') {
Yii::$app->getResponse()->getHeaders()->set('Allow', 'POST GET PUT');
Yii::$app->end();
}
return true;
}
}
public function behaviors()
{
$behaviors = parent::behaviors();
$behaviors['contentNegotiator'] = [
'class' => ContentNegotiator::className(),
'formats' => [
'application/json' => Response::FORMAT_JSON,
],
];
// add CORS filter for browers with Option on query distants domains
$behaviors['corsFilter'] = [
'class' => CustomCors::className(),
];
$behaviors['authenticator'] = [
'class' => JwtHttpBearerAuth::class,
'except' => [
'authenticate',
'options',
],
];
return $behaviors;
}
'urlManager' => [
'enablePrettyUrl' => true,
'enableStrictParsing' => false,
'showScriptName' => false,
'rules' => [
[
'class' => 'yii\rest\UrlRule',
'pluralize' => false,
'controller' => [
'user'
],
'tokens' => [
'{action}' => '<action:[a-zA-Z0-9\\-]+>',
],
'extraPatterns' => [
'OPTIONS {action}' => 'options',
'POST authenticate' => 'authenticate',
'POST signup' => 'signup',
],
]
],
],
the token its ok because in the postman app works ok, but in the mozilla firefox no matter wath I still receive unauthorized access
I would appreciate any help
Thanks in advance...
When i use Manually ->withClaim('uid', 100)
it's working fine.
if i change uid to 120 or others number ->withClaim('uid', 120)
it's show me "message": "Your request was made with invalid credentials.". But if add others Claim like ->withClaim('name', "Any name")
. it's also work. Why it's problem with changing uid.
Note: My code is exactly README.md Yii2 basic template example.
Hi, sizeg,
I am confused by the verify
function.
var_dump($token->verify($signer, $keychain->getPublicKey('file://{path to your public key}'))); // true when the public key was generated by the private one =)
So, the verify
function belongs to the $token
variable, which is an object
, not a string
.
How do I verify a token string
if a client app ( such as a web app built with React or Vuejs ) sends a token string back in the http header ?
I hope this is not a stupid question. Thanks.
dxd,麻烦升级下依赖,支持php8的,多谢
This project does not have license information
https://packagist.org/packages/sizeg/yii2-jwt
Hi,
$token = Yii::$app->jwt->getBuilder()
->setIssuer('http://example.com')
->setAudience('http://example.org')
->setId('4f1g23a12aa', true) // <-- what is this for?
...
I see this is used pretty much on every example. It's a bit confusing and I would like to know whether it is something I should considered as well.
Hi,
Tried installing yii2-jwt via composer and hit this
- lcobucci/jwt[3.3.0, ..., 3.3.3] require php ^5.6 || ^7.0 -> your php version (8.1.10) does not satisfy that requirement.
Is it possible to update to 4.x which supports php 7.4/8?
Regards
Mark
Version 4.0-beta returns error code 500 instead of 401 when token is expired:
The token violates some mandatory constraints, details:
Regards,
'optional' parameter for login action is not working,
the request "GET /login" returns this:
{
"name": "Unauthorized",
"message": "Your request was made with invalid credentials.",
"code": 0,
"status": 401,
"type": "yii\\web\\UnauthorizedHttpException"
}
I have tried with except like this:
$behaviors = parent::behaviors();
$behaviors['authenticator'] = [
'class' => JwtHttpBearerAuth::class,
'except' => ['login'],
'optional' => [
'login',
]
];
but it doesn't work either.
Also, what is self::$users in User model (and the strange foreach loop :) )? My IDE reports it as undefined...
Compatiblity with PHP 8.1
During inheritance of JsonSerializable: Uncaught yii\\base\\ErrorException: Return type of Lcobucci\\JWT\\Claim\\Basic::jsonSerialize() should either be compatible with JsonSerializable::jsonSerialize(): mixed, or the #[\\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /var/www/html/vendor/lcobucci/jwt/src/Claim/Basic.php:59
Использую вашу библиотеку в одном из проектов. Единственное у меня проблемы с меж сайтовыми запросами при обновление access-token для разработки вышел из положения изменив в JwtHttpBearerAuth.php challenge
public function challenge($response)
{
$response->getHeaders()->set(
'WWW-Authenticate',
"{$this->schema} realm=\"{$this->realm}\", error=\"invalid_token\", error_description=\"The access token invalid or expired\""
);
$response->getHeaders()->set(
'Access-Control-Allow-Origin',
'http://localhost:3000'
);
$response->getHeaders()->set(
'Access-Control-Allow-Credentials',
'true'
);
}
Но как то так себе решение... Вероятно оно продиктованно мои незнанием самого Yii2 если подскажете как правильно выйти из положения для междоменных запросов буду благодарен.
И ещё если я удаляю refresh-token из базы и пытаюсь обновить acces-token то получается неудобная картина, ответ приходит со статусом 200 а в теле ответа приходит сообщение statusCode : 401 неудобство в том что статус 200 обрабатывается как запрос без ошибок на стороне фронта и это ломает логику которая отлавливает проблемные запросы на рефреш чтобы отправить пользователя на страницу логина
пока не смог разобраться как такое получается, если можете подсказать что я делаю не так буду благодарен и за это :)
собирал все в кучу по тутореалу https://www.yiiframework.com/wiki/2568/jwt-authentication-tutorial
i just moved to sizeg/yii2-jwt: ^4.0-beta. i'ts showing error Setting unknown property: sizeg\jwt\Jwt::key
{
"name": "Unknown Property",
"message": "Setting unknown property: sizeg\jwt\Jwt::key",
"code": 0,
"type": "yii\base\UnknownPropertyException",
"file": "/var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/Component.php",
"line": 209,
"stack-trace": [
"#0 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/BaseYii.php(558): yii\base\Component->__set()",
"#1 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/BaseObject.php(107): yii\BaseYii::configure()",
"#2 [internal function]: yii\base\BaseObject->__construct()",
"#3 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/di/Container.php(419): ReflectionClass->newInstanceArgs()",
"#4 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/di/Container.php(170): yii\di\Container->build()",
"#5 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/BaseYii.php(365): yii\di\Container->get()",
"#6 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/di/ServiceLocator.php(137): yii\BaseYii::createObject()",
"#7 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/Module.php(766): yii\di\ServiceLocator->get()",
"#8 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/di/ServiceLocator.php(74): yii\base\Module->get()",
"#9 /var/www/html/ng-crm/yiiapp/backend/controllers/UsersController.php(1065): yii\di\ServiceLocator->__get()",
"#10 /var/www/html/ng-crm/yiiapp/backend/controllers/UsersController.php(1096): backend\controllers\UsersController->generateJwt()",
"#11 [internal function]: backend\controllers\UsersController->actionLogin()",
"#12 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/InlineAction.php(57): call_user_func_array()",
"#13 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/Controller.php(178): yii\base\InlineAction->runWithParams()",
"#14 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/Module.php(552): yii\base\Controller->runAction()",
"#15 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/web/Application.php(103): yii\base\Module->runAction()",
"#16 /var/www/html/ng-crm/yiiapp/vendor/yiisoft/yii2/base/Application.php(384): yii\web\Application->handleRequest()",
"#17 /var/www/html/ng-crm/yiiapp/backend/web/index.php(25): yii\base\Application->run()",
"#18 {main}"
]
}
Hi,
I followed the steps in the readme section, and it works. My only issue is that when the token is expired I get this error
{ "name": "Unauthorized", "message": "Your request was made with invalid credentials.", "code": 0, "status": 401, "type": "yii\\web\\UnauthorizedHttpException" }
I want to customize it to "token expired message" so in the frontend I can handle it and send a request to refresh the token.
do you any idea on how to achieve this?
At the moment, the JwtHttpBearerAuth only checks for expiration. Best practice is to check both on the recieving end:
The consumer of a JWT should always check that the "iss" claim matches the expected issuer (e.g., sso.example.com).
The consumer of a JWT should always verify that the audience matches its own identifier. The value of this claim is again a string value, at the discretion of the issuer. In OAuth 2.0 and OpenID Connect scenarios, this value typically contains the client identifier (e.g., api.example.com).
At the moment, the only way to validate those parameters, is to check the token claims when locating the user in the database. This is ok, but I think most people will forget to check this because it's not in the examples. Maybe you should include an option in the JwtHttpBearerAuth
to add additional claim validation (I noticed a TODO there). Or extend the examples with aud/iss checks in the findIdentityByAccessToken
method?
Is it still active and can we use that library in our next project?
Hi!
Sorry, I'm new to PHP. I think this issue might be because of autoloading?
Error:
"name": "Unknown Property",
"message": "Setting unknown property: sizeg\\jwt\\Jwt::jwtValidationData",
"code": 0,
"type": "yii\\base\\UnknownPropertyException",
"file": "[/vendor/yiisoft/yii2/base/Component.php](http://localhost:8080/Users/<censored>/venueview-api/vendor/yiisoft/yii2/base/Component.php)",
I have this in my web.php under components:
'jwt' => [
'class' => \sizeg\jwt\Jwt::class,
'key' => '!zf$5obLKs6HeACySCkGafA&*j4jhGt65F@',
'jwtValidationData' => \app\components\JwtValidationData::class,
],
I created a new folder called 'components' with this only file within:
<?php
namespace app\components;
use Yii;
class JwtValidationData extends \sizeg\jwt\JwtValidationData
{
public function init() {
$jwtParams = Yii::$app->params['jwt'];
$this->validationData->setIssuer($jwtParams['issuer']);
$this->validationData->setAudience($jwtParams['audience']);
$this->validationData->setId($jwtParams['id']);
parent::init();
}
}
When I try to access login or data methods, a 404 error is displayed. To fix, use this setting on config file:
[ 'class' => 'yii\rest\UrlRule', 'controller' => 'rest', 'extraPatterns' => [ 'GET login' => 'login', 'GET data' => 'data', ], ],
Hello, i've 2 tables for representated users in my App,
1st "Users" table and 2nd one "Members", i've created Members model implement IdentityInterface,
i want every hit API, authenticator check user in "Members" not in "Users", how to do this?
Hi,
I am try to remove the token or force to expire when the users logout, but I cant archive this.
I try to setup time expiration time but not work.
$time = time();
Yii::$app->jwt->getParser()->parse((string) $token)->expiresAt($time+1);
Yii::$app->jwt->loadToken(Yii::$app->jwt->getParser()->parse((string) $token))->expiresAt($time+1);
Other use case is when I want to grow up the expiration time, because the user manting the app open.
I thing that is a bug or issue.
Some libs require new version of lcobucci/jwt, for example kreait/firebase-php. Is it possible to add support for new version?
Hi, I have problem
I know It's not the issue of this package but I'm confusing about this cors errors
I have CustomController extend from yii\rest\controller
`
public function behaviors()
{
$behaviors = parent::behaviors();
$auth = $behaviors['authenticator'];
unset($behaviors['authenticator']);
$behaviors['corsFilter'] = [
'class' => Cors::className(),
'cors' => [
'Origin' => ['*'],
'Access-Control-Request-Method' => ['POST', 'GET', 'OPTIONS'],
'Access-Control-Allow-Headers' => ['*'],
'Access-Control-Expose-Headers' => ['*']
],
];
$behaviors['authenticator'] = $auth;
$behaviors['authenticator']['except'] = ['options'];
return $behaviors;
}`
when I want to use authentication in special controller
and when use
`
public function behaviors()
{
$behaviors = parent::behaviors();
$behaviors['authenticator'] = [
'class' => JwtHttpBearerAuth::class,
'optional' => [
'login',
],
];
return $behaviors;
}
`
I get this error:
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://localhost/shop/api/v1/checkout/addresses. (Reason: CORS header ‘Access-Control-Allow-Origin’ missing).
when I check the header, the header of origin are remove from request
I don't have problem in another controller
we are getting below error,
lcobucci/jwt[3.3.0, ..., 3.3.x-dev] require php ^5.6 || ^7.0 -> your php version (8.1.7) does not satisfy that requirement.
- sizeg/yii2-jwt[v2.0.0, ..., v2.0.2] require lcobucci/jwt ~3.3.0 -> satisfiable by lcobucci/jwt[3.3.0, ..., 3.3.x-dev].
- Root composer.json requires sizeg/yii2-jwt ^2.0 -> satisfiable by sizeg/yii2-jwt[v2.0.0, v2.0.1, v2.0.1.1, v2.0.2].
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.