@arianee/arianee-access-token
Advanced tools
Comparing version 1.42.0 to 1.43.0
{ | ||
"name": "@arianee/arianee-access-token", | ||
"version": "1.42.0", | ||
"version": "1.43.0", | ||
"dependencies": { | ||
@@ -16,6 +16,6 @@ "@arianee/0xcert-cert": "^2.0.2", | ||
"peerDependencies": { | ||
"@arianee/common-types": "1.42.0", | ||
"@arianee/core": "1.42.0", | ||
"@arianee/permit721-sdk": "1.42.0", | ||
"@arianee/utils": "1.42.0", | ||
"@arianee/common-types": "1.43.0", | ||
"@arianee/core": "1.43.0", | ||
"@arianee/permit721-sdk": "1.43.0", | ||
"@arianee/utils": "1.43.0", | ||
"tslib": "2.5.0" | ||
@@ -22,0 +22,0 @@ }, |
export * from './lib/arianee-access-token'; | ||
export * from './lib/types/ArianeeAccessTokenPayload'; | ||
export * from './lib/types/JwtHeaderInterface'; | ||
export * from './lib/types/ArianeeAccessTokenPayload'; | ||
export * from './lib/types/SmartAssetSharingTokenPayload'; |
@@ -5,4 +5,4 @@ "use strict"; | ||
tslib_1.__exportStar(require("./lib/arianee-access-token"), exports); | ||
tslib_1.__exportStar(require("./lib/types/ArianeeAccessTokenPayload"), exports); | ||
tslib_1.__exportStar(require("./lib/types/JwtHeaderInterface"), exports); | ||
tslib_1.__exportStar(require("./lib/types/ArianeeAccessTokenPayload"), exports); | ||
tslib_1.__exportStar(require("./lib/types/SmartAssetSharingTokenPayload"), exports); |
@@ -8,3 +8,2 @@ "use strict"; | ||
const jwtGeneric_1 = require("./helpers/jwtGeneric"); | ||
const timeBeforeExp_1 = require("./helpers/timeBeforeExp"); | ||
class ArianeeAccessToken { | ||
@@ -24,3 +23,7 @@ constructor(core, params) { | ||
let aat = this.storage.getItem(ArianeeAccessToken.LAST_AAT_KEY); | ||
if (!aat || (0, timeBeforeExp_1.isExpInLessThan)(aat, timeBeforeExp)) { | ||
const jwtGenerator = new jwtGeneric_1.JWTGeneric({}); | ||
const shouldRegenerateAAT = aat | ||
? !jwtGenerator.setToken(aat).arePropertiesValid() // if property are all valid, we don't need to regenerate AAT | ||
: true; | ||
if (!aat || shouldRegenerateAAT) { | ||
aat = yield this.createWalletAccessToken(payloadOverride, prefix); | ||
@@ -51,3 +54,4 @@ this.storage.setItem(ArianeeAccessToken.LAST_AAT_KEY, aat); | ||
const iss = jwt.decode().payload.iss; | ||
return jwt.verify(iss, ignoreExpiration); | ||
const expBeforeExpiration = ignoreExpiration ? 0 : -1; | ||
return jwt.verify(iss, expBeforeExpiration); | ||
} | ||
@@ -69,4 +73,7 @@ static decodeJwt(arianeeAccessToken, ignoreExpiration = false) { | ||
const jwtGenerator = new jwtGeneric_1.JWTGeneric({ signer }); | ||
const nowInSeconds = Math.floor(Date.now() / 1000); | ||
const now = Date.now(); | ||
const basicPayload = Object.assign({ iss: this.core.getAddress(), sub: 'wallet', exp: now + 5 * 60 * 1000, iat: now }, payload); | ||
const basicPayload = Object.assign({ iss: this.core.getAddress(), sub: 'wallet', | ||
// TODO: remove the * 1000 when sdk is deployed everywhere | ||
exp: now + 5 * 60 * 1000, iat: nowInSeconds }, payload); | ||
const jwt = yield jwtGenerator.setPayload(basicPayload); | ||
@@ -73,0 +80,0 @@ return jwt.sign(prefix); |
@@ -28,11 +28,3 @@ import { ArianeeAccessTokenPayload } from '../types/ArianeeAccessTokenPayload'; | ||
*/ | ||
setToken(encodedToken: string): { | ||
decode: () => { | ||
prefix: string; | ||
header: JwtHeaderInterface; | ||
payload: ArianeeAccessTokenPayload; | ||
signature: string; | ||
}; | ||
verify: (pubKey: string, ignoreExpiration?: boolean) => boolean; | ||
}; | ||
setToken: (encodedToken: string) => this; | ||
private static base64Stringified; | ||
@@ -45,6 +37,19 @@ private static fromBase64JSONParse; | ||
*/ | ||
private verify; | ||
private arePropertiesValid; | ||
private decode; | ||
verify: (pubKey: string, timeBeforeExp?: number) => boolean; | ||
/** | ||
* Check if expiration is before now + timeBeforeExpInSec. | ||
* If timeBeforeExpInSec === -1 we skip the expiration check | ||
* ex: does my token expires in the next 10 minutes | ||
* @param timeBeforeExpInSec | ||
* @returns | ||
*/ | ||
isExpValid: (timeBeforeExpInSec?: number) => boolean; | ||
arePropertiesValid: (timeBeforeExpInSec?: number) => boolean; | ||
decode: () => { | ||
prefix: string; | ||
header: JwtHeaderInterface; | ||
payload: ArianeeAccessTokenPayload; | ||
signature: string; | ||
}; | ||
private signature; | ||
} |
@@ -25,11 +25,56 @@ "use strict"; | ||
}); | ||
this.arePropertiesValid = (payload, ignoreExpiration = false) => { | ||
if (payload.exp && !ignoreExpiration) { | ||
const isExpired = new Date(payload.exp).getTime() < Date.now(); | ||
if (isExpired) { | ||
return false; | ||
} | ||
/** | ||
* Set token to be verified or decoded | ||
* @param encodedToken | ||
*/ | ||
this.setToken = (encodedToken) => { | ||
this.encodedToken = encodedToken; | ||
return this; | ||
}; | ||
/** | ||
* Verify if signature was signed by pubKey and return true/false | ||
* @param pubKey | ||
*/ | ||
this.verify = (pubKey, timeBeforeExp) => { | ||
if (!this.params.recover) { | ||
throw new Error('You should provide a decoder to verify your token'); | ||
} | ||
const { prefix, header, payload, signature } = this.decode(); | ||
const signedMessage = `${prefix}${JWTGeneric.base64Stringified(header)}.${JWTGeneric.base64Stringified(payload)}`; | ||
const decode = this.params.recover(signedMessage, signature); | ||
const arePropertyValid = this.arePropertiesValid(timeBeforeExp); | ||
if (!arePropertyValid) { | ||
return false; | ||
} | ||
return pubKey.toLowerCase() === decode.toLowerCase(); | ||
}; | ||
/** | ||
* Check if expiration is before now + timeBeforeExpInSec. | ||
* If timeBeforeExpInSec === -1 we skip the expiration check | ||
* ex: does my token expires in the next 10 minutes | ||
* @param timeBeforeExpInSec | ||
* @returns | ||
*/ | ||
this.isExpValid = (timeBeforeExpInSec = 0) => { | ||
if (timeBeforeExpInSec === -1) { | ||
return true; | ||
} | ||
const decoded = this.decode(); | ||
const now = new Date().getTime(); | ||
const isExpInMilliseconds = decoded.payload.exp.toString().length === 13; | ||
const expInMilliseconds = isExpInMilliseconds | ||
? decoded.payload.exp | ||
: decoded.payload.exp * 1000; | ||
return now + timeBeforeExpInSec * 1000 < expInMilliseconds; | ||
}; | ||
this.arePropertiesValid = (timeBeforeExpInSec = 0) => { | ||
const { payload } = this.decode(); | ||
const isExpired = !this.isExpValid(timeBeforeExpInSec); | ||
if (isExpired) { | ||
return false; | ||
} | ||
if (payload.nbf) { | ||
const isBefore = new Date(payload.nbf).getTime() > Date.now(); | ||
const nbfInMS = payload.nbf * 1000; | ||
const isBefore = new Date(nbfInMS).getTime() > Date.now(); | ||
console.log(isBefore); | ||
if (isBefore) { | ||
@@ -41,12 +86,14 @@ return false; | ||
}; | ||
} | ||
/** | ||
* Set token to be verified or decoded | ||
* @param encodedToken | ||
*/ | ||
setToken(encodedToken) { | ||
this.encodedToken = encodedToken; | ||
return { | ||
decode: this.decode.bind(this), | ||
verify: this.verify.bind(this), | ||
this.decode = () => { | ||
const headerType = this.encodedToken.includes(JWTGeneric.JWT_HEADER_ETH) | ||
? JWTGeneric.JWT_HEADER_ETH | ||
: JWTGeneric.JWT_HEADER_secp256k1; | ||
const [prefix, remainder] = this.encodedToken.split(`${headerType}.`); | ||
const [header, payload, signature] = [headerType, ...remainder.split('.')]; | ||
return { | ||
prefix: prefix !== null && prefix !== void 0 ? prefix : '', | ||
header: JWTGeneric.fromBase64JSONParse(header), | ||
payload: JWTGeneric.fromBase64JSONParse(payload), | ||
signature: signature, | ||
}; | ||
}; | ||
@@ -72,32 +119,2 @@ } | ||
} | ||
/** | ||
* Verify if signature was signed by pubKey and return true/false | ||
* @param pubKey | ||
*/ | ||
verify(pubKey, ignoreExpiration = false) { | ||
if (!this.params.recover) { | ||
throw new Error('You should provide a decoder to verify your token'); | ||
} | ||
const { prefix, header, payload, signature } = this.decode(); | ||
const signedMessage = `${prefix}${JWTGeneric.base64Stringified(header)}.${JWTGeneric.base64Stringified(payload)}`; | ||
const decode = this.params.recover(signedMessage, signature); | ||
const arePropertyValid = this.arePropertiesValid(payload, ignoreExpiration); | ||
if (!arePropertyValid) { | ||
return false; | ||
} | ||
return pubKey.toLowerCase() === decode.toLowerCase(); | ||
} | ||
decode() { | ||
const headerType = this.encodedToken.includes(JWTGeneric.JWT_HEADER_ETH) | ||
? JWTGeneric.JWT_HEADER_ETH | ||
: JWTGeneric.JWT_HEADER_secp256k1; | ||
const [prefix, remainder] = this.encodedToken.split(`${headerType}.`); | ||
const [header, payload, signature] = [headerType, ...remainder.split('.')]; | ||
return { | ||
prefix: prefix !== null && prefix !== void 0 ? prefix : '', | ||
header: JWTGeneric.fromBase64JSONParse(header), | ||
payload: JWTGeneric.fromBase64JSONParse(payload), | ||
signature: signature, | ||
}; | ||
} | ||
signature(prefix) { | ||
@@ -104,0 +121,0 @@ if (!this.params.signer) { |
19187
332
14