mirror of
https://github.com/jonasroussel/dart_jsonwebtoken.git
synced 2025-08-01 17:01:33 +08:00
v2.1.0
This commit is contained in:
@ -1,3 +1,8 @@
|
|||||||
|
## 2.1.0
|
||||||
|
|
||||||
|
- When an undefined error occur `JWTUndefinedError` is thrown containing the original error in `error` property (https://github.com/jonasroussel/jsonwebtoken/issues/9)
|
||||||
|
- **BREAKING CHANGE**: `jwt.verify` no longer support `throwUndefinedErrors` parameter
|
||||||
|
|
||||||
## 2.0.1
|
## 2.0.1
|
||||||
|
|
||||||
- Fixing `JWT.sign` to include `iat` & other attributes when payload is an empty Map
|
- Fixing `JWT.sign` to include `iat` & other attributes when payload is an empty Map
|
||||||
|
@ -12,19 +12,41 @@ class JWTError extends Error {
|
|||||||
/// An error thrown when jwt is invalid
|
/// An error thrown when jwt is invalid
|
||||||
class JWTInvalidError extends JWTError {
|
class JWTInvalidError extends JWTError {
|
||||||
JWTInvalidError(String message) : super(message);
|
JWTInvalidError(String message) : super(message);
|
||||||
|
|
||||||
|
@override
|
||||||
|
String toString() => 'JWTInvalidError: $message';
|
||||||
}
|
}
|
||||||
|
|
||||||
/// An error thrown when jwt is expired
|
/// An error thrown when jwt is expired
|
||||||
class JWTExpiredError extends JWTError {
|
class JWTExpiredError extends JWTError {
|
||||||
JWTExpiredError() : super('jwt expired');
|
JWTExpiredError() : super('jwt expired');
|
||||||
|
|
||||||
|
@override
|
||||||
|
String toString() => 'JWTExpiredError: $message';
|
||||||
}
|
}
|
||||||
|
|
||||||
/// An error thrown when jwt is not active
|
/// An error thrown when jwt is not active
|
||||||
class JWTNotActiveError extends JWTError {
|
class JWTNotActiveError extends JWTError {
|
||||||
JWTNotActiveError() : super('jwt not active');
|
JWTNotActiveError() : super('jwt not active');
|
||||||
|
|
||||||
|
@override
|
||||||
|
String toString() => 'JWTNotActiveError: $message';
|
||||||
}
|
}
|
||||||
|
|
||||||
/// An error thrown when parsing failed
|
/// An error thrown when parsing failed
|
||||||
class JWTParseError extends JWTError {
|
class JWTParseError extends JWTError {
|
||||||
JWTParseError(String message) : super(message);
|
JWTParseError(String message) : super(message);
|
||||||
|
|
||||||
|
@override
|
||||||
|
String toString() => 'JWTParseError: $message';
|
||||||
|
}
|
||||||
|
|
||||||
|
/// An error thrown by default
|
||||||
|
class JWTUndefinedError extends JWTError {
|
||||||
|
JWTUndefinedError(this.error) : super(error.toString());
|
||||||
|
|
||||||
|
final Error error;
|
||||||
|
|
||||||
|
@override
|
||||||
|
String toString() => 'JWTUndefinedError: $message';
|
||||||
}
|
}
|
||||||
|
101
lib/src/jwt.dart
101
lib/src/jwt.dart
@ -20,7 +20,6 @@ class JWT {
|
|||||||
bool checkHeaderType = true,
|
bool checkHeaderType = true,
|
||||||
bool checkExpiresIn = true,
|
bool checkExpiresIn = true,
|
||||||
bool checkNotBefore = true,
|
bool checkNotBefore = true,
|
||||||
bool throwUndefinedErrors = false,
|
|
||||||
Duration? issueAt,
|
Duration? issueAt,
|
||||||
String? audience,
|
String? audience,
|
||||||
String? subject,
|
String? subject,
|
||||||
@ -129,10 +128,10 @@ class JWT {
|
|||||||
return JWT(payload);
|
return JWT(payload);
|
||||||
}
|
}
|
||||||
} catch (ex) {
|
} catch (ex) {
|
||||||
if (throwUndefinedErrors) {
|
if (ex is Error) {
|
||||||
rethrow;
|
throw JWTUndefinedError(ex);
|
||||||
} else {
|
} else {
|
||||||
throw JWTInvalidError('invalid token');
|
rethrow;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -175,56 +174,64 @@ class JWT {
|
|||||||
Duration? notBefore,
|
Duration? notBefore,
|
||||||
bool noIssueAt = false,
|
bool noIssueAt = false,
|
||||||
}) {
|
}) {
|
||||||
final header = {'alg': algorithm.name, 'typ': 'JWT'};
|
try {
|
||||||
|
final header = {'alg': algorithm.name, 'typ': 'JWT'};
|
||||||
|
|
||||||
if (payload is Map<String, dynamic> || payload is Map<dynamic, dynamic>) {
|
if (payload is Map<String, dynamic> || payload is Map<dynamic, dynamic>) {
|
||||||
|
try {
|
||||||
|
payload = Map<String, dynamic>.from(payload);
|
||||||
|
|
||||||
|
if (!noIssueAt) payload['iat'] = secondsSinceEpoch(DateTime.now());
|
||||||
|
if (expiresIn != null) {
|
||||||
|
payload['exp'] = secondsSinceEpoch(DateTime.now().add(expiresIn));
|
||||||
|
}
|
||||||
|
if (notBefore != null) {
|
||||||
|
payload['nbf'] = secondsSinceEpoch(DateTime.now().add(notBefore));
|
||||||
|
}
|
||||||
|
if (audience != null) payload['aud'] = audience;
|
||||||
|
if (subject != null) payload['sub'] = subject;
|
||||||
|
if (issuer != null) payload['iss'] = issuer;
|
||||||
|
if (jwtId != null) payload['jti'] = jwtId;
|
||||||
|
} catch (ex) {
|
||||||
|
assert(
|
||||||
|
payload is Map<String, dynamic>,
|
||||||
|
'If payload is a Map its must be a Map<String, dynamic>',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
final b64Header = base64Unpadded(jsonBase64.encode(header));
|
||||||
|
|
||||||
|
String b64Payload;
|
||||||
try {
|
try {
|
||||||
payload = Map<String, dynamic>.from(payload);
|
b64Payload = base64Unpadded(
|
||||||
|
payload is String
|
||||||
if (!noIssueAt) payload['iat'] = secondsSinceEpoch(DateTime.now());
|
? base64.encode(utf8.encode(payload))
|
||||||
if (expiresIn != null) {
|
: jsonBase64.encode(payload),
|
||||||
payload['exp'] = secondsSinceEpoch(DateTime.now().add(expiresIn));
|
);
|
||||||
}
|
|
||||||
if (notBefore != null) {
|
|
||||||
payload['nbf'] = secondsSinceEpoch(DateTime.now().add(notBefore));
|
|
||||||
}
|
|
||||||
if (audience != null) payload['aud'] = audience;
|
|
||||||
if (subject != null) payload['sub'] = subject;
|
|
||||||
if (issuer != null) payload['iss'] = issuer;
|
|
||||||
if (jwtId != null) payload['jti'] = jwtId;
|
|
||||||
} catch (ex) {
|
} catch (ex) {
|
||||||
assert(
|
throw JWTError(
|
||||||
payload is Map<String, dynamic>,
|
'invalid payload json format (Map keys must be String type)',
|
||||||
'If payload is a Map its must be a Map<String, dynamic>',
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
final b64Header = base64Unpadded(jsonBase64.encode(header));
|
final body = '$b64Header.$b64Payload';
|
||||||
|
final signature = base64Unpadded(
|
||||||
String b64Payload;
|
base64Url.encode(
|
||||||
try {
|
algorithm.sign(
|
||||||
b64Payload = base64Unpadded(
|
key,
|
||||||
payload is String
|
Uint8List.fromList(utf8.encode(body)),
|
||||||
? base64.encode(utf8.encode(payload))
|
),
|
||||||
: jsonBase64.encode(payload),
|
|
||||||
);
|
|
||||||
} catch (ex) {
|
|
||||||
throw JWTError(
|
|
||||||
'invalid payload json format (Map keys must be String type)',
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
final body = '$b64Header.$b64Payload';
|
|
||||||
final signature = base64Unpadded(
|
|
||||||
base64Url.encode(
|
|
||||||
algorithm.sign(
|
|
||||||
key,
|
|
||||||
Uint8List.fromList(utf8.encode(body)),
|
|
||||||
),
|
),
|
||||||
),
|
);
|
||||||
);
|
|
||||||
|
|
||||||
return body + '.' + signature;
|
return body + '.' + signature;
|
||||||
|
} catch (ex) {
|
||||||
|
if (ex is Error) {
|
||||||
|
throw JWTUndefinedError(ex);
|
||||||
|
} else {
|
||||||
|
rethrow;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
name: dart_jsonwebtoken
|
name: dart_jsonwebtoken
|
||||||
description: A dart implementation of the famous javascript library 'jsonwebtoken' (JWT).
|
description: A dart implementation of the famous javascript library 'jsonwebtoken' (JWT).
|
||||||
version: 2.0.1
|
version: 2.1.0
|
||||||
repository: https://github.com/jonasroussel/jsonwebtoken
|
repository: https://github.com/jonasroussel/jsonwebtoken
|
||||||
homepage: https://github.com/jonasroussel/jsonwebtoken#readme
|
homepage: https://github.com/jonasroussel/jsonwebtoken#readme
|
||||||
|
|
||||||
@ -8,9 +8,9 @@ environment:
|
|||||||
sdk: '>=2.12.0 <3.0.0'
|
sdk: '>=2.12.0 <3.0.0'
|
||||||
|
|
||||||
dependencies:
|
dependencies:
|
||||||
crypto: ^3.0.0
|
crypto: ^3.0.1
|
||||||
pointycastle: ^3.0.1
|
pointycastle: ^3.0.1
|
||||||
ed25519_edwards: ^0.1.0
|
ed25519_edwards: ^0.1.0
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
pedantic: ^1.9.2
|
pedantic: ^1.11.0
|
||||||
|
Reference in New Issue
Block a user