@azure/msal-common 14.2.0 → 14.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/account/AuthToken.mjs +1 -1
- package/dist/account/CcsCredential.mjs +1 -1
- package/dist/account/ClientInfo.mjs +1 -1
- package/dist/authority/Authority.d.ts.map +1 -1
- package/dist/authority/Authority.mjs +4 -5
- package/dist/authority/Authority.mjs.map +1 -1
- package/dist/authority/AuthorityFactory.mjs +1 -1
- package/dist/authority/AuthorityMetadata.d.ts +29 -172
- package/dist/authority/AuthorityMetadata.d.ts.map +1 -1
- package/dist/authority/AuthorityMetadata.mjs +79 -413
- package/dist/authority/AuthorityMetadata.mjs.map +1 -1
- package/dist/authority/AuthorityOptions.d.ts +2 -2
- package/dist/authority/AuthorityOptions.d.ts.map +1 -1
- package/dist/authority/AuthorityOptions.mjs +1 -1
- package/dist/authority/AuthorityOptions.mjs.map +1 -1
- package/dist/authority/AuthorityType.mjs +1 -1
- package/dist/authority/CloudInstanceDiscoveryErrorResponse.mjs +1 -1
- package/dist/authority/CloudInstanceDiscoveryResponse.mjs +1 -1
- package/dist/authority/OpenIdConfigResponse.mjs +1 -1
- package/dist/authority/ProtocolMode.mjs +1 -1
- package/dist/authority/RegionDiscovery.mjs +1 -1
- package/dist/cache/CacheManager.d.ts +24 -19
- package/dist/cache/CacheManager.d.ts.map +1 -1
- package/dist/cache/CacheManager.mjs +51 -33
- package/dist/cache/CacheManager.mjs.map +1 -1
- package/dist/cache/entities/AccessTokenEntity.d.ts +12 -43
- package/dist/cache/entities/AccessTokenEntity.d.ts.map +1 -1
- package/dist/cache/entities/AccountEntity.mjs +1 -1
- package/dist/cache/entities/AppMetadataEntity.mjs +1 -1
- package/dist/cache/entities/AuthorityMetadataEntity.mjs +1 -1
- package/dist/cache/entities/CacheRecord.mjs +1 -1
- package/dist/cache/entities/CredentialEntity.d.ts +15 -73
- package/dist/cache/entities/CredentialEntity.d.ts.map +1 -1
- package/dist/cache/entities/IdTokenEntity.d.ts +4 -30
- package/dist/cache/entities/IdTokenEntity.d.ts.map +1 -1
- package/dist/cache/entities/RefreshTokenEntity.d.ts +2 -33
- package/dist/cache/entities/RefreshTokenEntity.d.ts.map +1 -1
- package/dist/cache/entities/ServerTelemetryEntity.d.ts +2 -9
- package/dist/cache/entities/ServerTelemetryEntity.d.ts.map +1 -1
- package/dist/cache/entities/ThrottlingEntity.mjs +1 -1
- package/dist/cache/persistence/TokenCacheContext.mjs +1 -1
- package/dist/cache/utils/CacheHelpers.d.ts +65 -0
- package/dist/cache/utils/CacheHelpers.d.ts.map +1 -0
- package/dist/cache/utils/CacheHelpers.mjs +242 -0
- package/dist/cache/utils/CacheHelpers.mjs.map +1 -0
- package/dist/client/AuthorizationCodeClient.d.ts +2 -1
- package/dist/client/AuthorizationCodeClient.d.ts.map +1 -1
- package/dist/client/AuthorizationCodeClient.mjs +4 -10
- package/dist/client/AuthorizationCodeClient.mjs.map +1 -1
- package/dist/client/BaseClient.d.ts +1 -1
- package/dist/client/BaseClient.d.ts.map +1 -1
- package/dist/client/BaseClient.mjs +8 -8
- package/dist/client/BaseClient.mjs.map +1 -1
- package/dist/client/RefreshTokenClient.d.ts.map +1 -1
- package/dist/client/RefreshTokenClient.mjs +2 -2
- package/dist/client/RefreshTokenClient.mjs.map +1 -1
- package/dist/client/SilentFlowClient.d.ts.map +1 -1
- package/dist/client/SilentFlowClient.mjs +5 -3
- package/dist/client/SilentFlowClient.mjs.map +1 -1
- package/dist/config/ClientConfiguration.mjs +1 -1
- package/dist/crypto/ICrypto.d.ts +3 -3
- package/dist/crypto/ICrypto.d.ts.map +1 -1
- package/dist/crypto/ICrypto.mjs +1 -1
- package/dist/crypto/ICrypto.mjs.map +1 -1
- package/dist/crypto/JoseHeader.d.ts +3 -3
- package/dist/crypto/JoseHeader.d.ts.map +1 -1
- package/dist/crypto/JoseHeader.mjs +3 -3
- package/dist/crypto/JoseHeader.mjs.map +1 -1
- package/dist/crypto/PopTokenGenerator.d.ts.map +1 -1
- package/dist/crypto/PopTokenGenerator.mjs +3 -3
- package/dist/crypto/PopTokenGenerator.mjs.map +1 -1
- package/dist/crypto/SignedHttpRequest.d.ts +4 -0
- package/dist/crypto/SignedHttpRequest.d.ts.map +1 -1
- package/dist/error/AuthError.mjs +1 -1
- package/dist/error/AuthErrorCodes.mjs +1 -1
- package/dist/error/ClientAuthError.mjs +1 -1
- package/dist/error/ClientAuthErrorCodes.mjs +1 -1
- package/dist/error/ClientConfigurationError.mjs +1 -1
- package/dist/error/ClientConfigurationErrorCodes.mjs +1 -1
- package/dist/error/InteractionRequiredAuthError.mjs +1 -1
- package/dist/error/InteractionRequiredAuthErrorCodes.mjs +1 -1
- package/dist/error/JoseHeaderError.mjs +1 -1
- package/dist/error/JoseHeaderErrorCodes.mjs +1 -1
- package/dist/error/ServerError.mjs +1 -1
- package/dist/index.cjs +2768 -3303
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +4 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.mjs +6 -7
- package/dist/index.mjs.map +1 -1
- package/dist/logger/Logger.mjs +1 -1
- package/dist/network/INetworkModule.mjs +1 -1
- package/dist/network/NetworkManager.mjs +1 -1
- package/dist/network/RequestThumbprint.d.ts +2 -0
- package/dist/network/RequestThumbprint.d.ts.map +1 -1
- package/dist/network/ThrottlingUtils.mjs +1 -1
- package/dist/packageMetadata.d.ts +1 -1
- package/dist/packageMetadata.mjs +2 -2
- package/dist/request/AuthenticationHeaderParser.mjs +1 -1
- package/dist/request/BaseAuthRequest.d.ts +3 -0
- package/dist/request/BaseAuthRequest.d.ts.map +1 -1
- package/dist/request/RequestParameterBuilder.mjs +1 -1
- package/dist/request/RequestValidator.mjs +1 -1
- package/dist/request/ScopeSet.mjs +1 -1
- package/dist/response/ResponseHandler.d.ts +2 -2
- package/dist/response/ResponseHandler.d.ts.map +1 -1
- package/dist/response/ResponseHandler.mjs +23 -29
- package/dist/response/ResponseHandler.mjs.map +1 -1
- package/dist/telemetry/performance/PerformanceClient.mjs +1 -1
- package/dist/telemetry/performance/PerformanceEvent.d.ts +8 -1
- package/dist/telemetry/performance/PerformanceEvent.d.ts.map +1 -1
- package/dist/telemetry/performance/PerformanceEvent.mjs +6 -2
- package/dist/telemetry/performance/PerformanceEvent.mjs.map +1 -1
- package/dist/telemetry/performance/StubPerformanceClient.mjs +1 -1
- package/dist/telemetry/server/ServerTelemetryManager.d.ts.map +1 -1
- package/dist/telemetry/server/ServerTelemetryManager.mjs +11 -8
- package/dist/telemetry/server/ServerTelemetryManager.mjs.map +1 -1
- package/dist/url/UrlString.d.ts +2 -37
- package/dist/url/UrlString.d.ts.map +1 -1
- package/dist/url/UrlString.mjs +7 -126
- package/dist/url/UrlString.mjs.map +1 -1
- package/dist/utils/Constants.d.ts +2 -3
- package/dist/utils/Constants.d.ts.map +1 -1
- package/dist/utils/Constants.mjs +3 -4
- package/dist/utils/Constants.mjs.map +1 -1
- package/dist/utils/FunctionWrappers.mjs +1 -1
- package/dist/utils/ProtocolUtils.mjs +1 -1
- package/dist/utils/StringUtils.mjs +1 -1
- package/dist/utils/TimeUtils.mjs +1 -1
- package/dist/utils/UrlUtils.d.ts +11 -0
- package/dist/utils/UrlUtils.d.ts.map +1 -0
- package/dist/utils/UrlUtils.mjs +52 -0
- package/dist/utils/UrlUtils.mjs.map +1 -0
- package/package.json +1 -1
- package/src/authority/Authority.ts +5 -8
- package/src/authority/AuthorityMetadata.ts +109 -435
- package/src/authority/AuthorityOptions.ts +2 -2
- package/src/cache/CacheManager.ts +79 -42
- package/src/cache/entities/AccessTokenEntity.ts +13 -149
- package/src/cache/entities/CredentialEntity.ts +16 -200
- package/src/cache/entities/IdTokenEntity.ts +4 -64
- package/src/cache/entities/RefreshTokenEntity.ts +2 -69
- package/src/cache/entities/ServerTelemetryEntity.ts +2 -30
- package/src/cache/utils/CacheHelpers.ts +327 -0
- package/src/client/AuthorizationCodeClient.ts +4 -15
- package/src/client/BaseClient.ts +21 -10
- package/src/client/RefreshTokenClient.ts +7 -1
- package/src/client/SilentFlowClient.ts +8 -4
- package/src/crypto/ICrypto.ts +7 -2
- package/src/crypto/JoseHeader.ts +4 -4
- package/src/crypto/PopTokenGenerator.ts +2 -0
- package/src/crypto/SignedHttpRequest.ts +6 -0
- package/src/index.ts +4 -1
- package/src/network/RequestThumbprint.ts +2 -0
- package/src/packageMetadata.ts +1 -1
- package/src/request/BaseAuthRequest.ts +3 -0
- package/src/response/ResponseHandler.ts +36 -41
- package/src/telemetry/performance/PerformanceEvent.ts +12 -1
- package/src/telemetry/server/ServerTelemetryManager.ts +12 -6
- package/src/url/UrlString.ts +6 -153
- package/src/utils/Constants.ts +3 -3
- package/src/utils/UrlUtils.ts +60 -0
- package/dist/cache/entities/AccessTokenEntity.mjs +0 -121
- package/dist/cache/entities/AccessTokenEntity.mjs.map +0 -1
- package/dist/cache/entities/CredentialEntity.mjs +0 -145
- package/dist/cache/entities/CredentialEntity.mjs.map +0 -1
- package/dist/cache/entities/IdTokenEntity.mjs +0 -64
- package/dist/cache/entities/IdTokenEntity.mjs.map +0 -1
- package/dist/cache/entities/RefreshTokenEntity.mjs +0 -67
- package/dist/cache/entities/RefreshTokenEntity.mjs.map +0 -1
- package/dist/cache/entities/ServerTelemetryEntity.mjs +0 -34
- package/dist/cache/entities/ServerTelemetryEntity.mjs.map +0 -1
|
@@ -21,6 +21,7 @@ import {
|
|
|
21
21
|
Separators,
|
|
22
22
|
} from "../utils/Constants";
|
|
23
23
|
import { CredentialEntity } from "./entities/CredentialEntity";
|
|
24
|
+
import { generateCredentialKey } from "./utils/CacheHelpers";
|
|
24
25
|
import { ScopeSet } from "../request/ScopeSet";
|
|
25
26
|
import { AccountEntity } from "./entities/AccountEntity";
|
|
26
27
|
import { AccessTokenEntity } from "./entities/AccessTokenEntity";
|
|
@@ -42,12 +43,10 @@ import { BaseAuthRequest } from "../request/BaseAuthRequest";
|
|
|
42
43
|
import { Logger } from "../logger/Logger";
|
|
43
44
|
import { name, version } from "../packageMetadata";
|
|
44
45
|
import { StoreInCache } from "../request/StoreInCache";
|
|
45
|
-
import {
|
|
46
|
-
getAliasesFromConfigMetadata,
|
|
47
|
-
getHardcodedAliasesForCanonicalAuthority,
|
|
48
|
-
} from "../authority/AuthorityMetadata";
|
|
46
|
+
import { getAliasesFromStaticSources } from "../authority/AuthorityMetadata";
|
|
49
47
|
import { StaticAuthorityOptions } from "../authority/AuthorityOptions";
|
|
50
48
|
import { TokenClaims } from "../account/TokenClaims";
|
|
49
|
+
import { IPerformanceClient } from "../telemetry/performance/IPerformanceClient";
|
|
51
50
|
|
|
52
51
|
/**
|
|
53
52
|
* Interface class which implement cache storage functions used by MSAL to perform validity checks, and store tokens.
|
|
@@ -259,7 +258,13 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
259
258
|
*/
|
|
260
259
|
getAccountInfoFilteredBy(accountFilter: AccountFilter): AccountInfo | null {
|
|
261
260
|
const allAccounts = this.getAllAccounts(accountFilter);
|
|
262
|
-
if (allAccounts.length >
|
|
261
|
+
if (allAccounts.length > 1) {
|
|
262
|
+
// If one or more accounts are found, further filter to the first account that has an ID token
|
|
263
|
+
return allAccounts.filter((account) => {
|
|
264
|
+
return !!account.idTokenClaims;
|
|
265
|
+
})[0];
|
|
266
|
+
} else if (allAccounts.length === 1) {
|
|
267
|
+
// If only one account is found, return it regardless of whether a matching ID token was found
|
|
263
268
|
return allAccounts[0];
|
|
264
269
|
} else {
|
|
265
270
|
return null;
|
|
@@ -303,7 +308,7 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
303
308
|
return accountInfo;
|
|
304
309
|
}
|
|
305
310
|
}
|
|
306
|
-
return
|
|
311
|
+
return accountInfo;
|
|
307
312
|
}
|
|
308
313
|
|
|
309
314
|
private idTokenClaimsMatchAccountFilter(
|
|
@@ -872,29 +877,40 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
872
877
|
|
|
873
878
|
/**
|
|
874
879
|
* Retrieve the cached credentials into a cacherecord
|
|
875
|
-
* @param account
|
|
876
|
-
* @param
|
|
877
|
-
* @param
|
|
878
|
-
* @param
|
|
879
|
-
* @param
|
|
880
|
+
* @param account {AccountInfo}
|
|
881
|
+
* @param request {BaseAuthRequest}
|
|
882
|
+
* @param environment {string}
|
|
883
|
+
* @param performanceClient {?IPerformanceClient}
|
|
884
|
+
* @param correlationId {?string}
|
|
880
885
|
*/
|
|
881
886
|
readCacheRecord(
|
|
882
887
|
account: AccountInfo,
|
|
883
888
|
request: BaseAuthRequest,
|
|
884
|
-
environment: string
|
|
889
|
+
environment: string,
|
|
890
|
+
performanceClient?: IPerformanceClient,
|
|
891
|
+
correlationId?: string
|
|
885
892
|
): CacheRecord {
|
|
886
893
|
const tokenKeys = this.getTokenKeys();
|
|
887
894
|
const cachedAccount = this.readAccountFromCache(account);
|
|
888
|
-
const cachedIdToken = this.getIdToken(
|
|
895
|
+
const cachedIdToken = this.getIdToken(
|
|
896
|
+
account,
|
|
897
|
+
tokenKeys,
|
|
898
|
+
performanceClient,
|
|
899
|
+
correlationId
|
|
900
|
+
);
|
|
889
901
|
const cachedAccessToken = this.getAccessToken(
|
|
890
902
|
account,
|
|
891
903
|
request,
|
|
892
|
-
tokenKeys
|
|
904
|
+
tokenKeys,
|
|
905
|
+
performanceClient,
|
|
906
|
+
correlationId
|
|
893
907
|
);
|
|
894
908
|
const cachedRefreshToken = this.getRefreshToken(
|
|
895
909
|
account,
|
|
896
910
|
false,
|
|
897
|
-
tokenKeys
|
|
911
|
+
tokenKeys,
|
|
912
|
+
performanceClient,
|
|
913
|
+
correlationId
|
|
898
914
|
);
|
|
899
915
|
const cachedAppMetadata = this.readAppMetadataFromCache(environment);
|
|
900
916
|
|
|
@@ -926,13 +942,16 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
926
942
|
|
|
927
943
|
/**
|
|
928
944
|
* Retrieve IdTokenEntity from cache
|
|
929
|
-
* @param
|
|
930
|
-
* @param
|
|
931
|
-
* @param
|
|
945
|
+
* @param account {AccountInfo}
|
|
946
|
+
* @param tokenKeys {?TokenKeys}
|
|
947
|
+
* @param performanceClient {?IPerformanceClient}
|
|
948
|
+
* @param correlationId {?string}
|
|
932
949
|
*/
|
|
933
950
|
getIdToken(
|
|
934
951
|
account: AccountInfo,
|
|
935
|
-
tokenKeys?: TokenKeys
|
|
952
|
+
tokenKeys?: TokenKeys,
|
|
953
|
+
performanceClient?: IPerformanceClient,
|
|
954
|
+
correlationId?: string
|
|
936
955
|
): IdTokenEntity | null {
|
|
937
956
|
this.commonLogger.trace("CacheManager - getIdToken called");
|
|
938
957
|
const idTokenFilter: CredentialFilter = {
|
|
@@ -957,8 +976,14 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
957
976
|
"CacheManager:getIdToken - Multiple id tokens found, clearing them"
|
|
958
977
|
);
|
|
959
978
|
idTokens.forEach((idToken) => {
|
|
960
|
-
this.removeIdToken(
|
|
979
|
+
this.removeIdToken(generateCredentialKey(idToken));
|
|
961
980
|
});
|
|
981
|
+
if (performanceClient && correlationId) {
|
|
982
|
+
performanceClient.addFields(
|
|
983
|
+
{ multiMatchedID: idTokens.length },
|
|
984
|
+
correlationId
|
|
985
|
+
);
|
|
986
|
+
}
|
|
962
987
|
return null;
|
|
963
988
|
}
|
|
964
989
|
|
|
@@ -1043,15 +1068,18 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
1043
1068
|
|
|
1044
1069
|
/**
|
|
1045
1070
|
* Retrieve AccessTokenEntity from cache
|
|
1046
|
-
* @param
|
|
1047
|
-
* @param
|
|
1048
|
-
* @param
|
|
1049
|
-
* @param
|
|
1071
|
+
* @param account {AccountInfo}
|
|
1072
|
+
* @param request {BaseAuthRequest}
|
|
1073
|
+
* @param tokenKeys {?TokenKeys}
|
|
1074
|
+
* @param performanceClient {?IPerformanceClient}
|
|
1075
|
+
* @param correlationId {?string}
|
|
1050
1076
|
*/
|
|
1051
1077
|
getAccessToken(
|
|
1052
1078
|
account: AccountInfo,
|
|
1053
1079
|
request: BaseAuthRequest,
|
|
1054
|
-
tokenKeys?: TokenKeys
|
|
1080
|
+
tokenKeys?: TokenKeys,
|
|
1081
|
+
performanceClient?: IPerformanceClient,
|
|
1082
|
+
correlationId?: string
|
|
1055
1083
|
): AccessTokenEntity | null {
|
|
1056
1084
|
this.commonLogger.trace("CacheManager - getAccessToken called");
|
|
1057
1085
|
const scopes = ScopeSet.createSearchScopes(request.scopes);
|
|
@@ -1113,10 +1141,14 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
1113
1141
|
"CacheManager:getAccessToken - Multiple access tokens found, clearing them"
|
|
1114
1142
|
);
|
|
1115
1143
|
accessTokens.forEach((accessToken) => {
|
|
1116
|
-
void this.removeAccessToken(
|
|
1117
|
-
accessToken.generateCredentialKey()
|
|
1118
|
-
);
|
|
1144
|
+
void this.removeAccessToken(generateCredentialKey(accessToken));
|
|
1119
1145
|
});
|
|
1146
|
+
if (performanceClient && correlationId) {
|
|
1147
|
+
performanceClient.addFields(
|
|
1148
|
+
{ multiMatchedAT: accessTokens.length },
|
|
1149
|
+
correlationId
|
|
1150
|
+
);
|
|
1151
|
+
}
|
|
1120
1152
|
return null;
|
|
1121
1153
|
}
|
|
1122
1154
|
|
|
@@ -1214,14 +1246,18 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
1214
1246
|
|
|
1215
1247
|
/**
|
|
1216
1248
|
* Helper to retrieve the appropriate refresh token from cache
|
|
1217
|
-
* @param
|
|
1218
|
-
* @param
|
|
1219
|
-
* @param
|
|
1249
|
+
* @param account {AccountInfo}
|
|
1250
|
+
* @param familyRT {boolean}
|
|
1251
|
+
* @param tokenKeys {?TokenKeys}
|
|
1252
|
+
* @param performanceClient {?IPerformanceClient}
|
|
1253
|
+
* @param correlationId {?string}
|
|
1220
1254
|
*/
|
|
1221
1255
|
getRefreshToken(
|
|
1222
1256
|
account: AccountInfo,
|
|
1223
1257
|
familyRT: boolean,
|
|
1224
|
-
tokenKeys?: TokenKeys
|
|
1258
|
+
tokenKeys?: TokenKeys,
|
|
1259
|
+
performanceClient?: IPerformanceClient,
|
|
1260
|
+
correlationId?: string
|
|
1225
1261
|
): RefreshTokenEntity | null {
|
|
1226
1262
|
this.commonLogger.trace("CacheManager - getRefreshToken called");
|
|
1227
1263
|
const id = familyRT ? THE_FAMILY_ID : undefined;
|
|
@@ -1264,6 +1300,13 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
1264
1300
|
}
|
|
1265
1301
|
// address the else case after remove functions address environment aliases
|
|
1266
1302
|
|
|
1303
|
+
if (numRefreshTokens > 1 && performanceClient && correlationId) {
|
|
1304
|
+
performanceClient.addFields(
|
|
1305
|
+
{ multiMatchedRT: numRefreshTokens },
|
|
1306
|
+
correlationId
|
|
1307
|
+
);
|
|
1308
|
+
}
|
|
1309
|
+
|
|
1267
1310
|
this.commonLogger.info(
|
|
1268
1311
|
"CacheManager:getRefreshToken - returning refresh token"
|
|
1269
1312
|
);
|
|
@@ -1423,17 +1466,11 @@ export abstract class CacheManager implements ICacheManager {
|
|
|
1423
1466
|
): boolean {
|
|
1424
1467
|
// Check static authority options first for cases where authority metadata has not been resolved and cached yet
|
|
1425
1468
|
if (this.staticAuthorityOptions) {
|
|
1426
|
-
const staticAliases =
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
) ||
|
|
1431
|
-
getHardcodedAliasesForCanonicalAuthority(
|
|
1432
|
-
this.staticAuthorityOptions.canonicalAuthority
|
|
1433
|
-
) ||
|
|
1434
|
-
this.staticAuthorityOptions.knownAuthorities;
|
|
1469
|
+
const staticAliases = getAliasesFromStaticSources(
|
|
1470
|
+
this.staticAuthorityOptions,
|
|
1471
|
+
this.commonLogger
|
|
1472
|
+
);
|
|
1435
1473
|
if (
|
|
1436
|
-
staticAliases &&
|
|
1437
1474
|
staticAliases.includes(environment) &&
|
|
1438
1475
|
staticAliases.includes(entity.environment)
|
|
1439
1476
|
) {
|
|
@@ -4,164 +4,28 @@
|
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
6
|
import { CredentialEntity } from "./CredentialEntity";
|
|
7
|
-
import {
|
|
8
|
-
import { TimeUtils } from "../../utils/TimeUtils";
|
|
9
|
-
import { ICrypto } from "../../crypto/ICrypto";
|
|
10
|
-
import { TokenClaims } from "../../account/TokenClaims";
|
|
11
|
-
import {
|
|
12
|
-
createClientAuthError,
|
|
13
|
-
ClientAuthErrorCodes,
|
|
14
|
-
} from "../../error/ClientAuthError";
|
|
15
|
-
import { extractTokenClaims } from "../../account/AuthToken";
|
|
7
|
+
import { AuthenticationScheme } from "../../utils/Constants";
|
|
16
8
|
|
|
17
9
|
/**
|
|
18
|
-
*
|
|
19
|
-
*
|
|
20
|
-
* Key:Value Schema:
|
|
21
|
-
*
|
|
22
|
-
* Key Example: uid.utid-login.microsoftonline.com-accesstoken-clientId-contoso.com-user.read
|
|
23
|
-
*
|
|
24
|
-
* Value Schema:
|
|
25
|
-
* {
|
|
26
|
-
* homeAccountId: home account identifier for the auth scheme,
|
|
27
|
-
* environment: entity that issued the token, represented as a full host
|
|
28
|
-
* credentialType: Type of credential as a string, can be one of the following: RefreshToken, AccessToken, IdToken, Password, Cookie, Certificate, Other
|
|
29
|
-
* clientId: client ID of the application
|
|
30
|
-
* secret: Actual credential as a string
|
|
31
|
-
* familyId: Family ID identifier, usually only used for refresh tokens
|
|
32
|
-
* realm: Full tenant or organizational identifier that the account belongs to
|
|
33
|
-
* target: Permissions that are included in the token, or for refresh tokens, the resource identifier.
|
|
34
|
-
* cachedAt: Absolute device time when entry was created in the cache.
|
|
35
|
-
* expiresOn: Token expiry time, calculated based on current UTC time in seconds. Represented as a string.
|
|
36
|
-
* extendedExpiresOn: Additional extended expiry time until when token is valid in case of server-side outage. Represented as string in UTC seconds.
|
|
37
|
-
* keyId: used for POP and SSH tokenTypes
|
|
38
|
-
* tokenType: Type of the token issued. Usually "Bearer"
|
|
39
|
-
* }
|
|
10
|
+
* Access token cache type
|
|
40
11
|
*/
|
|
41
|
-
export
|
|
12
|
+
export type AccessTokenEntity = CredentialEntity & {
|
|
13
|
+
/** Full tenant or organizational identifier that the account belongs to */
|
|
42
14
|
realm: string;
|
|
15
|
+
/** Permissions that are included in the token, or for refresh tokens, the resource identifier. */
|
|
43
16
|
target: string;
|
|
17
|
+
/** Absolute device time when entry was created in the cache. */
|
|
44
18
|
cachedAt: string;
|
|
19
|
+
/** Token expiry time, calculated based on current UTC time in seconds. Represented as a string. */
|
|
45
20
|
expiresOn: string;
|
|
21
|
+
/** Additional extended expiry time until when token is valid in case of server-side outage. Represented as string in UTC seconds. */
|
|
46
22
|
extendedExpiresOn?: string;
|
|
23
|
+
/** Used for proactive refresh */
|
|
47
24
|
refreshOn?: string;
|
|
48
|
-
|
|
25
|
+
/** Matches the authentication scheme for which the token was issued (i.e. Bearer or pop) */
|
|
49
26
|
tokenType?: AuthenticationScheme;
|
|
27
|
+
/** Stringified claims object */
|
|
50
28
|
requestedClaims?: string;
|
|
29
|
+
/** Matches the SHA 256 hash of the claims object included in the token request */
|
|
51
30
|
requestedClaimsHash?: string;
|
|
52
|
-
|
|
53
|
-
/**
|
|
54
|
-
* Create AccessTokenEntity
|
|
55
|
-
* @param homeAccountId
|
|
56
|
-
* @param environment
|
|
57
|
-
* @param accessToken
|
|
58
|
-
* @param clientId
|
|
59
|
-
* @param tenantId
|
|
60
|
-
* @param scopes
|
|
61
|
-
* @param expiresOn
|
|
62
|
-
* @param extExpiresOn
|
|
63
|
-
*/
|
|
64
|
-
static createAccessTokenEntity(
|
|
65
|
-
homeAccountId: string,
|
|
66
|
-
environment: string,
|
|
67
|
-
accessToken: string,
|
|
68
|
-
clientId: string,
|
|
69
|
-
tenantId: string,
|
|
70
|
-
scopes: string,
|
|
71
|
-
expiresOn: number,
|
|
72
|
-
extExpiresOn: number,
|
|
73
|
-
cryptoUtils: ICrypto,
|
|
74
|
-
refreshOn?: number,
|
|
75
|
-
tokenType?: AuthenticationScheme,
|
|
76
|
-
userAssertionHash?: string,
|
|
77
|
-
keyId?: string,
|
|
78
|
-
requestedClaims?: string,
|
|
79
|
-
requestedClaimsHash?: string
|
|
80
|
-
): AccessTokenEntity {
|
|
81
|
-
const atEntity: AccessTokenEntity = new AccessTokenEntity();
|
|
82
|
-
|
|
83
|
-
atEntity.homeAccountId = homeAccountId;
|
|
84
|
-
atEntity.credentialType = CredentialType.ACCESS_TOKEN;
|
|
85
|
-
atEntity.secret = accessToken;
|
|
86
|
-
|
|
87
|
-
const currentTime = TimeUtils.nowSeconds();
|
|
88
|
-
atEntity.cachedAt = currentTime.toString();
|
|
89
|
-
|
|
90
|
-
/*
|
|
91
|
-
* Token expiry time.
|
|
92
|
-
* This value should be calculated based on the current UTC time measured locally and the value expires_in Represented as a string in JSON.
|
|
93
|
-
*/
|
|
94
|
-
atEntity.expiresOn = expiresOn.toString();
|
|
95
|
-
atEntity.extendedExpiresOn = extExpiresOn.toString();
|
|
96
|
-
if (refreshOn) {
|
|
97
|
-
atEntity.refreshOn = refreshOn.toString();
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
atEntity.environment = environment;
|
|
101
|
-
atEntity.clientId = clientId;
|
|
102
|
-
atEntity.realm = tenantId;
|
|
103
|
-
atEntity.target = scopes;
|
|
104
|
-
atEntity.userAssertionHash = userAssertionHash;
|
|
105
|
-
|
|
106
|
-
atEntity.tokenType = tokenType || AuthenticationScheme.BEARER;
|
|
107
|
-
|
|
108
|
-
if (requestedClaims) {
|
|
109
|
-
atEntity.requestedClaims = requestedClaims;
|
|
110
|
-
atEntity.requestedClaimsHash = requestedClaimsHash;
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
/*
|
|
114
|
-
* Create Access Token With Auth Scheme instead of regular access token
|
|
115
|
-
* Cast to lower to handle "bearer" from ADFS
|
|
116
|
-
*/
|
|
117
|
-
if (
|
|
118
|
-
atEntity.tokenType?.toLowerCase() !==
|
|
119
|
-
AuthenticationScheme.BEARER.toLowerCase()
|
|
120
|
-
) {
|
|
121
|
-
atEntity.credentialType =
|
|
122
|
-
CredentialType.ACCESS_TOKEN_WITH_AUTH_SCHEME;
|
|
123
|
-
switch (atEntity.tokenType) {
|
|
124
|
-
case AuthenticationScheme.POP:
|
|
125
|
-
// Make sure keyId is present and add it to credential
|
|
126
|
-
const tokenClaims: TokenClaims | null = extractTokenClaims(
|
|
127
|
-
accessToken,
|
|
128
|
-
cryptoUtils.base64Decode
|
|
129
|
-
);
|
|
130
|
-
if (!tokenClaims?.cnf?.kid) {
|
|
131
|
-
throw createClientAuthError(
|
|
132
|
-
ClientAuthErrorCodes.tokenClaimsCnfRequiredForSignedJwt
|
|
133
|
-
);
|
|
134
|
-
}
|
|
135
|
-
atEntity.keyId = tokenClaims.cnf.kid;
|
|
136
|
-
break;
|
|
137
|
-
case AuthenticationScheme.SSH:
|
|
138
|
-
atEntity.keyId = keyId;
|
|
139
|
-
}
|
|
140
|
-
}
|
|
141
|
-
|
|
142
|
-
return atEntity;
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
/**
|
|
146
|
-
* Validates an entity: checks for all expected params
|
|
147
|
-
* @param entity
|
|
148
|
-
*/
|
|
149
|
-
static isAccessTokenEntity(entity: object): boolean {
|
|
150
|
-
if (!entity) {
|
|
151
|
-
return false;
|
|
152
|
-
}
|
|
153
|
-
|
|
154
|
-
return (
|
|
155
|
-
entity.hasOwnProperty("homeAccountId") &&
|
|
156
|
-
entity.hasOwnProperty("environment") &&
|
|
157
|
-
entity.hasOwnProperty("credentialType") &&
|
|
158
|
-
entity.hasOwnProperty("realm") &&
|
|
159
|
-
entity.hasOwnProperty("clientId") &&
|
|
160
|
-
entity.hasOwnProperty("secret") &&
|
|
161
|
-
entity.hasOwnProperty("target") &&
|
|
162
|
-
(entity["credentialType"] === CredentialType.ACCESS_TOKEN ||
|
|
163
|
-
entity["credentialType"] ===
|
|
164
|
-
CredentialType.ACCESS_TOKEN_WITH_AUTH_SCHEME)
|
|
165
|
-
);
|
|
166
|
-
}
|
|
167
|
-
}
|
|
31
|
+
};
|
|
@@ -3,218 +3,34 @@
|
|
|
3
3
|
* Licensed under the MIT License.
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import {
|
|
7
|
-
Separators,
|
|
8
|
-
CredentialType,
|
|
9
|
-
CacheType,
|
|
10
|
-
Constants,
|
|
11
|
-
AuthenticationScheme,
|
|
12
|
-
} from "../../utils/Constants";
|
|
13
|
-
import {
|
|
14
|
-
ClientAuthErrorCodes,
|
|
15
|
-
createClientAuthError,
|
|
16
|
-
} from "../../error/ClientAuthError";
|
|
6
|
+
import { CredentialType, AuthenticationScheme } from "../../utils/Constants";
|
|
17
7
|
|
|
18
8
|
/**
|
|
19
|
-
*
|
|
20
|
-
*
|
|
21
|
-
* Key:Value Schema:
|
|
22
|
-
*
|
|
23
|
-
* Key: <home_account_id*>-<environment>-<credential_type>-<client_id>-<realm*>-<target*>-<requestedClaims*>-<scheme*>
|
|
24
|
-
*
|
|
25
|
-
* Value Schema:
|
|
26
|
-
* {
|
|
27
|
-
* homeAccountId: home account identifier for the auth scheme,
|
|
28
|
-
* environment: entity that issued the token, represented as a full host
|
|
29
|
-
* credentialType: Type of credential as a string, can be one of the following: RefreshToken, AccessToken, IdToken, Password, Cookie, Certificate, Other
|
|
30
|
-
* clientId: client ID of the application
|
|
31
|
-
* secret: Actual credential as a string
|
|
32
|
-
* familyId: Family ID identifier, usually only used for refresh tokens
|
|
33
|
-
* realm: Full tenant or organizational identifier that the account belongs to
|
|
34
|
-
* target: Permissions that are included in the token, or for refresh tokens, the resource identifier.
|
|
35
|
-
* tokenType: Matches the authentication scheme for which the token was issued (i.e. Bearer or pop)
|
|
36
|
-
* requestedClaimsHash: Matches the SHA 256 hash of the claims object included in the token request
|
|
37
|
-
* userAssertionHash: Matches the SHA 256 hash of the obo_assertion for the OBO flow
|
|
38
|
-
* }
|
|
9
|
+
* Credential Cache Type
|
|
39
10
|
*/
|
|
40
|
-
export
|
|
11
|
+
export type CredentialEntity = {
|
|
12
|
+
/** Identifier for the user in their home tenant*/
|
|
41
13
|
homeAccountId: string;
|
|
14
|
+
/** Entity that issued the token, represented as a full host */
|
|
42
15
|
environment: string;
|
|
16
|
+
/** Type of credential */
|
|
43
17
|
credentialType: CredentialType;
|
|
18
|
+
/** Client ID of the application */
|
|
44
19
|
clientId: string;
|
|
20
|
+
/** Actual credential as a string */
|
|
45
21
|
secret: string;
|
|
22
|
+
/** Family ID identifier, usually only used for refresh tokens */
|
|
46
23
|
familyId?: string;
|
|
24
|
+
/** Full tenant or organizational identifier that the account belongs to */
|
|
47
25
|
realm?: string;
|
|
26
|
+
/** Permissions that are included in the token, or for refresh tokens, the resource identifier. */
|
|
48
27
|
target?: string;
|
|
28
|
+
/** Matches the SHA 256 hash of the obo_assertion for the OBO flow */
|
|
49
29
|
userAssertionHash?: string;
|
|
30
|
+
/** Matches the authentication scheme for which the token was issued (i.e. Bearer or pop) */
|
|
50
31
|
tokenType?: AuthenticationScheme;
|
|
32
|
+
/** KeyId for PoP and SSH tokens stored in the kid claim */
|
|
51
33
|
keyId?: string;
|
|
34
|
+
/** Matches the SHA 256 hash of the claims object included in the token request */
|
|
52
35
|
requestedClaimsHash?: string;
|
|
53
|
-
|
|
54
|
-
/**
|
|
55
|
-
* Generate Account Id key component as per the schema: <home_account_id>-<environment>
|
|
56
|
-
*/
|
|
57
|
-
generateAccountId(): string {
|
|
58
|
-
return CredentialEntity.generateAccountIdForCacheKey(
|
|
59
|
-
this.homeAccountId,
|
|
60
|
-
this.environment
|
|
61
|
-
);
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
/**
|
|
65
|
-
* Generate Credential Id key component as per the schema: <credential_type>-<client_id>-<realm>
|
|
66
|
-
*/
|
|
67
|
-
generateCredentialId(): string {
|
|
68
|
-
return CredentialEntity.generateCredentialIdForCacheKey(
|
|
69
|
-
this.credentialType,
|
|
70
|
-
this.clientId,
|
|
71
|
-
this.realm,
|
|
72
|
-
this.familyId
|
|
73
|
-
);
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
/**
|
|
77
|
-
* Generate target key component as per schema: <target>
|
|
78
|
-
*/
|
|
79
|
-
generateTarget(): string {
|
|
80
|
-
return CredentialEntity.generateTargetForCacheKey(this.target);
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
/**
|
|
84
|
-
* generates credential key
|
|
85
|
-
*/
|
|
86
|
-
generateCredentialKey(): string {
|
|
87
|
-
return CredentialEntity.generateCredentialCacheKey(
|
|
88
|
-
this.homeAccountId,
|
|
89
|
-
this.environment,
|
|
90
|
-
this.credentialType,
|
|
91
|
-
this.clientId,
|
|
92
|
-
this.realm,
|
|
93
|
-
this.target,
|
|
94
|
-
this.familyId,
|
|
95
|
-
this.tokenType,
|
|
96
|
-
this.requestedClaimsHash
|
|
97
|
-
);
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
/**
|
|
101
|
-
* returns the type of the cache (in this case credential)
|
|
102
|
-
*/
|
|
103
|
-
generateType(): number {
|
|
104
|
-
switch (this.credentialType) {
|
|
105
|
-
case CredentialType.ID_TOKEN:
|
|
106
|
-
return CacheType.ID_TOKEN;
|
|
107
|
-
case CredentialType.ACCESS_TOKEN:
|
|
108
|
-
case CredentialType.ACCESS_TOKEN_WITH_AUTH_SCHEME:
|
|
109
|
-
return CacheType.ACCESS_TOKEN;
|
|
110
|
-
case CredentialType.REFRESH_TOKEN:
|
|
111
|
-
return CacheType.REFRESH_TOKEN;
|
|
112
|
-
default: {
|
|
113
|
-
throw createClientAuthError(
|
|
114
|
-
ClientAuthErrorCodes.unexpectedCredentialType
|
|
115
|
-
);
|
|
116
|
-
}
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
/**
|
|
121
|
-
* generates credential key
|
|
122
|
-
* <home_account_id*>-\<environment>-<credential_type>-<client_id>-<realm\*>-<target\*>-<scheme\*>
|
|
123
|
-
*/
|
|
124
|
-
static generateCredentialCacheKey(
|
|
125
|
-
homeAccountId: string,
|
|
126
|
-
environment: string,
|
|
127
|
-
credentialType: CredentialType,
|
|
128
|
-
clientId: string,
|
|
129
|
-
realm?: string,
|
|
130
|
-
target?: string,
|
|
131
|
-
familyId?: string,
|
|
132
|
-
tokenType?: AuthenticationScheme,
|
|
133
|
-
requestedClaimsHash?: string
|
|
134
|
-
): string {
|
|
135
|
-
const credentialKey = [
|
|
136
|
-
this.generateAccountIdForCacheKey(homeAccountId, environment),
|
|
137
|
-
this.generateCredentialIdForCacheKey(
|
|
138
|
-
credentialType,
|
|
139
|
-
clientId,
|
|
140
|
-
realm,
|
|
141
|
-
familyId
|
|
142
|
-
),
|
|
143
|
-
this.generateTargetForCacheKey(target),
|
|
144
|
-
this.generateClaimsHashForCacheKey(requestedClaimsHash),
|
|
145
|
-
this.generateSchemeForCacheKey(tokenType),
|
|
146
|
-
];
|
|
147
|
-
|
|
148
|
-
return credentialKey.join(Separators.CACHE_KEY_SEPARATOR).toLowerCase();
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
/**
|
|
152
|
-
* generates Account Id for keys
|
|
153
|
-
* @param homeAccountId
|
|
154
|
-
* @param environment
|
|
155
|
-
*/
|
|
156
|
-
private static generateAccountIdForCacheKey(
|
|
157
|
-
homeAccountId: string,
|
|
158
|
-
environment: string
|
|
159
|
-
): string {
|
|
160
|
-
const accountId: Array<string> = [homeAccountId, environment];
|
|
161
|
-
return accountId.join(Separators.CACHE_KEY_SEPARATOR).toLowerCase();
|
|
162
|
-
}
|
|
163
|
-
|
|
164
|
-
/**
|
|
165
|
-
* Generates Credential Id for keys
|
|
166
|
-
* @param credentialType
|
|
167
|
-
* @param realm
|
|
168
|
-
* @param clientId
|
|
169
|
-
* @param familyId
|
|
170
|
-
*/
|
|
171
|
-
private static generateCredentialIdForCacheKey(
|
|
172
|
-
credentialType: CredentialType,
|
|
173
|
-
clientId: string,
|
|
174
|
-
realm?: string,
|
|
175
|
-
familyId?: string
|
|
176
|
-
): string {
|
|
177
|
-
const clientOrFamilyId =
|
|
178
|
-
credentialType === CredentialType.REFRESH_TOKEN
|
|
179
|
-
? familyId || clientId
|
|
180
|
-
: clientId;
|
|
181
|
-
const credentialId: Array<string> = [
|
|
182
|
-
credentialType,
|
|
183
|
-
clientOrFamilyId,
|
|
184
|
-
realm || Constants.EMPTY_STRING,
|
|
185
|
-
];
|
|
186
|
-
|
|
187
|
-
return credentialId.join(Separators.CACHE_KEY_SEPARATOR).toLowerCase();
|
|
188
|
-
}
|
|
189
|
-
|
|
190
|
-
/**
|
|
191
|
-
* Generate target key component as per schema: <target>
|
|
192
|
-
*/
|
|
193
|
-
private static generateTargetForCacheKey(scopes?: string): string {
|
|
194
|
-
return (scopes || Constants.EMPTY_STRING).toLowerCase();
|
|
195
|
-
}
|
|
196
|
-
|
|
197
|
-
/**
|
|
198
|
-
* Generate requested claims key component as per schema: <requestedClaims>
|
|
199
|
-
*/
|
|
200
|
-
private static generateClaimsHashForCacheKey(
|
|
201
|
-
requestedClaimsHash?: string
|
|
202
|
-
): string {
|
|
203
|
-
return (requestedClaimsHash || Constants.EMPTY_STRING).toLowerCase();
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
/**
|
|
207
|
-
* Generate scheme key componenet as per schema: <scheme>
|
|
208
|
-
*/
|
|
209
|
-
private static generateSchemeForCacheKey(tokenType?: string): string {
|
|
210
|
-
/*
|
|
211
|
-
* PoP Tokens and SSH certs include scheme in cache key
|
|
212
|
-
* Cast to lowercase to handle "bearer" from ADFS
|
|
213
|
-
*/
|
|
214
|
-
return tokenType &&
|
|
215
|
-
tokenType.toLowerCase() !==
|
|
216
|
-
AuthenticationScheme.BEARER.toLowerCase()
|
|
217
|
-
? tokenType.toLowerCase()
|
|
218
|
-
: Constants.EMPTY_STRING;
|
|
219
|
-
}
|
|
220
|
-
}
|
|
36
|
+
};
|