@auth0/ai 3.4.1 → 3.5.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/cjs/authorizers/federated-connections/FederatedConnectionAuthorizerBase.js +56 -9
- package/dist/cjs/authorizers/federated-connections/FederatedConnectionAuthorizerBase.js.map +1 -1
- package/dist/cjs/authorizers/federated-connections/FederatedConnectionAuthorizerParams.js +16 -0
- package/dist/cjs/authorizers/federated-connections/FederatedConnectionAuthorizerParams.js.map +1 -1
- package/dist/cjs/authorizers/federated-connections/index.js +3 -1
- package/dist/cjs/authorizers/federated-connections/index.js.map +1 -1
- package/dist/cjs/index.js +3 -0
- package/dist/cjs/index.js.map +1 -1
- package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerBase.d.ts +1 -0
- package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerBase.js +56 -9
- package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerBase.js.map +1 -1
- package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerParams.d.ts +24 -1
- package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerParams.js +15 -1
- package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerParams.js.map +1 -1
- package/dist/esm/authorizers/federated-connections/index.d.ts +1 -0
- package/dist/esm/authorizers/federated-connections/index.js +1 -0
- package/dist/esm/authorizers/federated-connections/index.js.map +1 -1
- package/dist/esm/index.d.ts +1 -0
- package/dist/esm/index.js +1 -0
- package/dist/esm/index.js.map +1 -1
- package/package.json +1 -1
|
@@ -14,6 +14,7 @@ const util_1 = require("../../util");
|
|
|
14
14
|
const context_1 = require("../context");
|
|
15
15
|
const types_1 = require("../types");
|
|
16
16
|
const asyncLocalStorage_1 = require("./asyncLocalStorage");
|
|
17
|
+
const FederatedConnectionAuthorizerParams_1 = require("./FederatedConnectionAuthorizerParams");
|
|
17
18
|
/**
|
|
18
19
|
* Requests authorization to a third party service via Federated Connection.
|
|
19
20
|
*/
|
|
@@ -29,19 +30,34 @@ class FederatedConnectionAuthorizerBase {
|
|
|
29
30
|
baseNamespace: [instanceID, "Credentials"],
|
|
30
31
|
getTTL: (credentials) => credentials.expiresIn ? credentials.expiresIn * 1000 : undefined,
|
|
31
32
|
});
|
|
32
|
-
|
|
33
|
-
|
|
33
|
+
// Validate that exactly one token source is provided
|
|
34
|
+
const hasRefreshToken = typeof params.refreshToken !== "undefined";
|
|
35
|
+
const hasAccessToken = typeof params.accessToken !== "undefined";
|
|
36
|
+
const hasSubjectTokenType = typeof params.subjectTokenType !== "undefined";
|
|
37
|
+
if (!hasRefreshToken && !hasAccessToken) {
|
|
34
38
|
throw new Error("Either refreshToken or accessToken must be provided to initialize the Authorizer.");
|
|
35
39
|
}
|
|
36
|
-
if (
|
|
37
|
-
typeof params.refreshToken !== "undefined") {
|
|
40
|
+
if (hasRefreshToken && hasAccessToken) {
|
|
38
41
|
throw new Error("Only one of refreshToken or accessToken can be provided to initialize the Authorizer.");
|
|
39
42
|
}
|
|
43
|
+
// Validate resource server client credentials when using access tokens for token exchange w/ Token Vault
|
|
44
|
+
if (hasAccessToken &&
|
|
45
|
+
hasSubjectTokenType &&
|
|
46
|
+
params.subjectTokenType === FederatedConnectionAuthorizerParams_1.SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN) {
|
|
47
|
+
if (!this.auth0.clientId || !this.auth0.clientSecret) {
|
|
48
|
+
throw new Error("clientId and clientSecret must currently be provided when using accessToken for token exchange with Token Vault.");
|
|
49
|
+
}
|
|
50
|
+
}
|
|
40
51
|
}
|
|
41
52
|
getInstanceID() {
|
|
42
53
|
const props = {
|
|
43
54
|
auth0: this.auth0,
|
|
44
|
-
params: (0, util_1.omit)(this.params, [
|
|
55
|
+
params: (0, util_1.omit)(this.params, [
|
|
56
|
+
"store",
|
|
57
|
+
"refreshToken",
|
|
58
|
+
"accessToken",
|
|
59
|
+
"loginHint",
|
|
60
|
+
]),
|
|
45
61
|
};
|
|
46
62
|
const sh = (0, stable_hash_1.default)(props);
|
|
47
63
|
return crypto_1.default.createHash("MD5").update(sh).digest("hex");
|
|
@@ -74,16 +90,39 @@ class FederatedConnectionAuthorizerBase {
|
|
|
74
90
|
throw new Error("The tool must be wrapped with the FederationConnectionAuthorizer.");
|
|
75
91
|
}
|
|
76
92
|
const { connection } = store;
|
|
77
|
-
|
|
93
|
+
// Determine which token type to use and get the appropriate subject token
|
|
94
|
+
let subjectToken;
|
|
95
|
+
let subjectTokenType;
|
|
96
|
+
if (typeof this.params.refreshToken === "function") {
|
|
97
|
+
subjectToken = await this.getRefreshToken(...toolContext);
|
|
98
|
+
subjectTokenType = "urn:ietf:params:oauth:token-type:refresh_token";
|
|
99
|
+
}
|
|
100
|
+
else if (typeof this.params.accessToken === "function") {
|
|
101
|
+
subjectToken = (await this.getAccessTokenWithToolContext(...toolContext));
|
|
102
|
+
subjectTokenType = "urn:ietf:params:oauth:token-type:access_token";
|
|
103
|
+
}
|
|
104
|
+
else if (typeof this.params.accessToken === "string") {
|
|
105
|
+
subjectToken = this.params.accessToken;
|
|
106
|
+
subjectTokenType = "urn:ietf:params:oauth:token-type:access_token";
|
|
107
|
+
}
|
|
108
|
+
else {
|
|
109
|
+
// This should never happen due to constructor validation, but TypeScript needs this
|
|
110
|
+
throw new Error("Either refreshToken or accessToken must be configured");
|
|
111
|
+
}
|
|
78
112
|
if (!subjectToken) {
|
|
79
113
|
return;
|
|
80
114
|
}
|
|
115
|
+
// Get optional login hint if provided
|
|
116
|
+
const loginHint = typeof this.params.loginHint === "function"
|
|
117
|
+
? await (0, parameters_1.resolveParameter)(this.params.loginHint, toolContext)
|
|
118
|
+
: undefined;
|
|
81
119
|
const exchangeParams = {
|
|
82
120
|
grant_type: "urn:auth0:params:oauth:grant-type:token-exchange:federated-connection-access-token",
|
|
83
121
|
client_id: this.auth0.clientId,
|
|
84
122
|
client_secret: this.auth0.clientSecret,
|
|
85
|
-
subject_token_type:
|
|
123
|
+
subject_token_type: subjectTokenType,
|
|
86
124
|
subject_token: subjectToken,
|
|
125
|
+
login_hint: loginHint,
|
|
87
126
|
connection: connection,
|
|
88
127
|
requested_token_type: "http://auth0.com/oauth/token-type/federated-connection-access-token",
|
|
89
128
|
};
|
|
@@ -101,11 +140,16 @@ class FederatedConnectionAuthorizerBase {
|
|
|
101
140
|
}
|
|
102
141
|
async getAccessToken(...toolContext) {
|
|
103
142
|
let tokenResponse;
|
|
104
|
-
|
|
143
|
+
// Use token exchange for both refresh tokens and access tokens when subjectTokenType is provided
|
|
144
|
+
if (typeof this.params.refreshToken === "function" ||
|
|
145
|
+
(typeof this.params.accessToken !== "undefined" &&
|
|
146
|
+
this.params.subjectTokenType ===
|
|
147
|
+
FederatedConnectionAuthorizerParams_1.SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN)) {
|
|
105
148
|
tokenResponse = await this.getAccessTokenImpl(...toolContext);
|
|
106
149
|
}
|
|
107
150
|
else {
|
|
108
|
-
|
|
151
|
+
// fallback to existing behavior, where third party accessToken can be provided directly
|
|
152
|
+
tokenResponse = (await (0, parameters_1.resolveParameter)(this.params.accessToken, toolContext));
|
|
109
153
|
}
|
|
110
154
|
this.validateToken(tokenResponse);
|
|
111
155
|
return (0, credentials_1.tokenSetFromTokenResponse)(tokenResponse);
|
|
@@ -113,6 +157,9 @@ class FederatedConnectionAuthorizerBase {
|
|
|
113
157
|
async getRefreshToken(...toolContext) {
|
|
114
158
|
return await (0, parameters_1.resolveParameter)(this.params.refreshToken, toolContext);
|
|
115
159
|
}
|
|
160
|
+
async getAccessTokenWithToolContext(...toolContext) {
|
|
161
|
+
return await (0, parameters_1.resolveParameter)(this.params.accessToken, toolContext);
|
|
162
|
+
}
|
|
116
163
|
/**
|
|
117
164
|
*
|
|
118
165
|
* Wraps the execute method of an AI tool to handle Federated Connections authorization.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FederatedConnectionAuthorizerBase.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerBase.ts"],"names":[],"mappings":"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","sourcesContent":["import crypto from \"crypto\";\nimport stableHash from \"stable-hash\";\n\nimport {\n TokenResponse,\n TokenSet,\n tokenSetFromTokenResponse,\n} from \"../../credentials\";\nimport {\n Auth0Interrupt,\n FederatedConnectionError,\n FederatedConnectionInterrupt,\n} from \"../../interrupts\";\nimport { resolveParameter } from \"../../parameters\";\nimport { SubStore } from \"../../stores\";\nimport { omit, RequireFields } from \"../../util\";\nimport { ContextGetter, nsFromContext } from \"../context\";\nimport { Auth0ClientParams, Auth0ClientSchema } from \"../types\";\nimport { asyncLocalStorage, AsyncStorageValue } from \"./asyncLocalStorage\";\nimport { FederatedConnectionAuthorizerParams } from \"./FederatedConnectionAuthorizerParams\";\n\n/**\n * Requests authorization to a third party service via Federated Connection.\n */\n\nexport class FederatedConnectionAuthorizerBase<ToolExecuteArgs extends any[]> {\n private readonly auth0: Auth0ClientParams;\n private readonly params: RequireFields<\n FederatedConnectionAuthorizerParams<ToolExecuteArgs>,\n \"credentialsContext\"\n >;\n private readonly credentialsStore: SubStore<TokenSet>;\n\n constructor(\n auth0: Partial<Auth0ClientParams>,\n params: FederatedConnectionAuthorizerParams<ToolExecuteArgs>\n ) {\n this.auth0 = Auth0ClientSchema.parse(auth0);\n this.params = {\n credentialsContext: \"thread\",\n ...params,\n };\n\n const instanceID = this.getInstanceID();\n\n this.credentialsStore = new SubStore<TokenSet>(params.store, {\n baseNamespace: [instanceID, \"Credentials\"],\n getTTL: (credentials) =>\n credentials.expiresIn ? credentials.expiresIn * 1000 : undefined,\n });\n\n if (\n typeof params.refreshToken === \"undefined\" &&\n typeof params.accessToken === \"undefined\"\n ) {\n throw new Error(\n \"Either refreshToken or accessToken must be provided to initialize the Authorizer.\"\n );\n }\n\n if (\n typeof params.accessToken !== \"undefined\" &&\n typeof params.refreshToken !== \"undefined\"\n ) {\n throw new Error(\n \"Only one of refreshToken or accessToken can be provided to initialize the Authorizer.\"\n );\n }\n }\n\n private getInstanceID(): string {\n const props = {\n auth0: this.auth0,\n params: omit(this.params, [\"store\", \"refreshToken\", \"accessToken\"]),\n };\n const sh = stableHash(props);\n return crypto.createHash(\"MD5\").update(sh).digest(\"hex\");\n }\n\n protected handleAuthorizationInterrupts(err: Auth0Interrupt) {\n throw err;\n }\n\n protected validateToken(tokenResponse?: TokenResponse) {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { scopes, connection } = store;\n\n if (!tokenResponse) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}`,\n connection,\n scopes,\n scopes\n );\n }\n\n const currentScopes = (tokenResponse.scope ?? \"\")\n .replace(/,/g, \" \")\n .split(\" \");\n const missingScopes = scopes.filter((s) => !currentScopes.includes(s));\n store.currentScopes = currentScopes;\n\n if (missingScopes.length > 0) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}. Missing scopes: ${missingScopes.join(\", \")}`,\n connection,\n scopes,\n [...currentScopes, ...scopes]\n );\n }\n }\n\n private async getAccessTokenImpl(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenResponse | undefined> {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { connection } = store;\n\n const subjectToken = await this.getRefreshToken(...toolContext);\n\n if (!subjectToken) {\n return;\n }\n\n const exchangeParams = {\n grant_type:\n \"urn:auth0:params:oauth:grant-type:token-exchange:federated-connection-access-token\",\n client_id: this.auth0.clientId,\n client_secret: this.auth0.clientSecret,\n subject_token_type: \"urn:ietf:params:oauth:token-type:refresh_token\",\n subject_token: subjectToken,\n connection: connection,\n requested_token_type:\n \"http://auth0.com/oauth/token-type/federated-connection-access-token\",\n };\n\n const res = await fetch(`https://${this.auth0.domain}/oauth/token`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify(exchangeParams),\n });\n\n if (!res.ok) {\n //TODO: handle all type of response errors.\n return;\n }\n\n const tokenResponse: TokenResponse = await res.json();\n return tokenResponse;\n }\n\n protected async getAccessToken(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenSet> {\n let tokenResponse: TokenResponse | undefined;\n if (typeof this.params.refreshToken === \"function\") {\n tokenResponse = await this.getAccessTokenImpl(...toolContext);\n } else {\n tokenResponse = await resolveParameter(\n this.params.accessToken!,\n toolContext\n );\n }\n this.validateToken(tokenResponse);\n return tokenSetFromTokenResponse(tokenResponse!);\n }\n\n protected async getRefreshToken(...toolContext: ToolExecuteArgs) {\n return await resolveParameter(this.params.refreshToken, toolContext);\n }\n\n /**\n *\n * Wraps the execute method of an AI tool to handle Federated Connections authorization.\n *\n * @param getContext - A function that returns the context of the tool execution.\n * @param execute - The tool execute method.\n * @returns The wrapped execute method.\n */\n protect(\n getContext: ContextGetter<ToolExecuteArgs>,\n execute: (...args: ToolExecuteArgs) => any\n ): (...args: ToolExecuteArgs) => any {\n return async (...args: ToolExecuteArgs) => {\n const context = getContext(...args);\n const asyncStore: AsyncStorageValue = {\n context: context,\n scopes: this.params.scopes,\n connection: this.params.connection,\n };\n\n if (asyncLocalStorage.getStore()) {\n throw new Error(\n \"Cannot nest tool calls that require federated connection authorization.\"\n );\n }\n\n return asyncLocalStorage.run(asyncStore, async () => {\n const credentialsNS = nsFromContext(\n this.params.credentialsContext,\n context\n );\n try {\n let credentials: TokenSet = await this.credentialsStore.get(\n credentialsNS,\n \"credential\"\n );\n if (!credentials) {\n credentials = await this.getAccessToken(...args);\n await this.credentialsStore.put(\n credentialsNS,\n \"credential\",\n credentials\n );\n }\n asyncStore.credentials = credentials;\n return await execute(...args);\n } catch (err) {\n if (err instanceof FederatedConnectionError) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n const interrupt = new FederatedConnectionInterrupt(\n err.message,\n asyncStore.connection,\n asyncStore.scopes,\n asyncStore.scopes\n );\n return this.handleAuthorizationInterrupts(interrupt);\n }\n if (err instanceof Auth0Interrupt) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n return this.handleAuthorizationInterrupts(err);\n }\n throw err;\n }\n });\n };\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"FederatedConnectionAuthorizerBase.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerBase.ts"],"names":[],"mappings":"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","sourcesContent":["import crypto from \"crypto\";\nimport stableHash from \"stable-hash\";\n\nimport {\n TokenResponse,\n TokenSet,\n tokenSetFromTokenResponse,\n} from \"../../credentials\";\nimport {\n Auth0Interrupt,\n FederatedConnectionError,\n FederatedConnectionInterrupt,\n} from \"../../interrupts\";\nimport { resolveParameter } from \"../../parameters\";\nimport { SubStore } from \"../../stores\";\nimport { omit, RequireFields } from \"../../util\";\nimport { ContextGetter, nsFromContext } from \"../context\";\nimport { Auth0ClientParams, Auth0ClientSchema } from \"../types\";\nimport { asyncLocalStorage, AsyncStorageValue } from \"./asyncLocalStorage\";\nimport {\n FederatedConnectionAuthorizerParams,\n SUBJECT_TOKEN_TYPES,\n} from \"./FederatedConnectionAuthorizerParams\";\n\n/**\n * Requests authorization to a third party service via Federated Connection.\n */\n\nexport class FederatedConnectionAuthorizerBase<ToolExecuteArgs extends any[]> {\n private readonly auth0: Auth0ClientParams;\n private readonly params: RequireFields<\n FederatedConnectionAuthorizerParams<ToolExecuteArgs>,\n \"credentialsContext\"\n >;\n private readonly credentialsStore: SubStore<TokenSet>;\n\n constructor(\n auth0: Partial<Auth0ClientParams>,\n params: FederatedConnectionAuthorizerParams<ToolExecuteArgs>\n ) {\n this.auth0 = Auth0ClientSchema.parse(auth0);\n this.params = {\n credentialsContext: \"thread\",\n ...params,\n };\n\n const instanceID = this.getInstanceID();\n\n this.credentialsStore = new SubStore<TokenSet>(params.store, {\n baseNamespace: [instanceID, \"Credentials\"],\n getTTL: (credentials) =>\n credentials.expiresIn ? credentials.expiresIn * 1000 : undefined,\n });\n\n // Validate that exactly one token source is provided\n const hasRefreshToken = typeof params.refreshToken !== \"undefined\";\n const hasAccessToken = typeof params.accessToken !== \"undefined\";\n const hasSubjectTokenType = typeof params.subjectTokenType !== \"undefined\";\n\n if (!hasRefreshToken && !hasAccessToken) {\n throw new Error(\n \"Either refreshToken or accessToken must be provided to initialize the Authorizer.\"\n );\n }\n\n if (hasRefreshToken && hasAccessToken) {\n throw new Error(\n \"Only one of refreshToken or accessToken can be provided to initialize the Authorizer.\"\n );\n }\n\n // Validate resource server client credentials when using access tokens for token exchange w/ Token Vault\n if (\n hasAccessToken &&\n hasSubjectTokenType &&\n params.subjectTokenType === SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN\n ) {\n if (!this.auth0.clientId || !this.auth0.clientSecret) {\n throw new Error(\n \"clientId and clientSecret must currently be provided when using accessToken for token exchange with Token Vault.\"\n );\n }\n }\n }\n\n private getInstanceID(): string {\n const props = {\n auth0: this.auth0,\n params: omit(this.params, [\n \"store\",\n \"refreshToken\",\n \"accessToken\",\n \"loginHint\",\n ]),\n };\n const sh = stableHash(props);\n return crypto.createHash(\"MD5\").update(sh).digest(\"hex\");\n }\n\n protected handleAuthorizationInterrupts(err: Auth0Interrupt) {\n throw err;\n }\n\n protected validateToken(tokenResponse?: TokenResponse) {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { scopes, connection } = store;\n\n if (!tokenResponse) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}`,\n connection,\n scopes,\n scopes\n );\n }\n\n const currentScopes = (tokenResponse.scope ?? \"\")\n .replace(/,/g, \" \")\n .split(\" \");\n const missingScopes = scopes.filter((s) => !currentScopes.includes(s));\n store.currentScopes = currentScopes;\n\n if (missingScopes.length > 0) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}. Missing scopes: ${missingScopes.join(\", \")}`,\n connection,\n scopes,\n [...currentScopes, ...scopes]\n );\n }\n }\n\n private async getAccessTokenImpl(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenResponse | undefined> {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { connection } = store;\n\n // Determine which token type to use and get the appropriate subject token\n let subjectToken: string | undefined;\n let subjectTokenType: string;\n\n if (typeof this.params.refreshToken === \"function\") {\n subjectToken = await this.getRefreshToken(...toolContext);\n subjectTokenType = \"urn:ietf:params:oauth:token-type:refresh_token\";\n } else if (typeof this.params.accessToken === \"function\") {\n subjectToken = (await this.getAccessTokenWithToolContext(\n ...toolContext\n )) as string;\n subjectTokenType = \"urn:ietf:params:oauth:token-type:access_token\";\n } else if (typeof this.params.accessToken === \"string\") {\n subjectToken = this.params.accessToken;\n subjectTokenType = \"urn:ietf:params:oauth:token-type:access_token\";\n } else {\n // This should never happen due to constructor validation, but TypeScript needs this\n throw new Error(\"Either refreshToken or accessToken must be configured\");\n }\n\n if (!subjectToken) {\n return;\n }\n\n // Get optional login hint if provided\n const loginHint =\n typeof this.params.loginHint === \"function\"\n ? await resolveParameter(this.params.loginHint, toolContext)\n : undefined;\n\n const exchangeParams = {\n grant_type:\n \"urn:auth0:params:oauth:grant-type:token-exchange:federated-connection-access-token\",\n client_id: this.auth0.clientId,\n client_secret: this.auth0.clientSecret,\n subject_token_type: subjectTokenType,\n subject_token: subjectToken,\n login_hint: loginHint,\n connection: connection,\n requested_token_type:\n \"http://auth0.com/oauth/token-type/federated-connection-access-token\",\n };\n\n const res = await fetch(`https://${this.auth0.domain}/oauth/token`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify(exchangeParams),\n });\n\n if (!res.ok) {\n //TODO: handle all type of response errors.\n return;\n }\n\n const tokenResponse: TokenResponse = await res.json();\n return tokenResponse;\n }\n\n protected async getAccessToken(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenSet> {\n let tokenResponse: TokenResponse | undefined;\n // Use token exchange for both refresh tokens and access tokens when subjectTokenType is provided\n if (\n typeof this.params.refreshToken === \"function\" ||\n (typeof this.params.accessToken !== \"undefined\" &&\n this.params.subjectTokenType ===\n SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN)\n ) {\n tokenResponse = await this.getAccessTokenImpl(...toolContext);\n } else {\n // fallback to existing behavior, where third party accessToken can be provided directly\n tokenResponse = (await resolveParameter(\n this.params.accessToken!,\n toolContext\n )) as TokenResponse;\n }\n this.validateToken(tokenResponse);\n return tokenSetFromTokenResponse(tokenResponse!);\n }\n\n protected async getRefreshToken(...toolContext: ToolExecuteArgs) {\n return await resolveParameter(this.params.refreshToken, toolContext);\n }\n\n protected async getAccessTokenWithToolContext(\n ...toolContext: ToolExecuteArgs\n ) {\n return await resolveParameter(this.params.accessToken, toolContext);\n }\n\n /**\n *\n * Wraps the execute method of an AI tool to handle Federated Connections authorization.\n *\n * @param getContext - A function that returns the context of the tool execution.\n * @param execute - The tool execute method.\n * @returns The wrapped execute method.\n */\n protect(\n getContext: ContextGetter<ToolExecuteArgs>,\n execute: (...args: ToolExecuteArgs) => any\n ): (...args: ToolExecuteArgs) => any {\n return async (...args: ToolExecuteArgs) => {\n const context = getContext(...args);\n const asyncStore: AsyncStorageValue = {\n context: context,\n scopes: this.params.scopes,\n connection: this.params.connection,\n };\n\n if (asyncLocalStorage.getStore()) {\n throw new Error(\n \"Cannot nest tool calls that require federated connection authorization.\"\n );\n }\n\n return asyncLocalStorage.run(asyncStore, async () => {\n const credentialsNS = nsFromContext(\n this.params.credentialsContext,\n context\n );\n try {\n let credentials: TokenSet = await this.credentialsStore.get(\n credentialsNS,\n \"credential\"\n );\n if (!credentials) {\n credentials = await this.getAccessToken(...args);\n await this.credentialsStore.put(\n credentialsNS,\n \"credential\",\n credentials\n );\n }\n asyncStore.credentials = credentials;\n return await execute(...args);\n } catch (err) {\n if (err instanceof FederatedConnectionError) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n const interrupt = new FederatedConnectionInterrupt(\n err.message,\n asyncStore.connection,\n asyncStore.scopes,\n asyncStore.scopes\n );\n return this.handleAuthorizationInterrupts(interrupt);\n }\n if (err instanceof Auth0Interrupt) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n return this.handleAuthorizationInterrupts(err);\n }\n throw err;\n }\n });\n };\n }\n}\n"]}
|
|
@@ -1,3 +1,19 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.SUBJECT_TOKEN_TYPES = void 0;
|
|
4
|
+
var SUBJECT_TOKEN_TYPES;
|
|
5
|
+
(function (SUBJECT_TOKEN_TYPES) {
|
|
6
|
+
/**
|
|
7
|
+
* Indicates that the token is an OAuth 2.0 refresh token issued by the given authorization server.
|
|
8
|
+
*
|
|
9
|
+
* @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.4 RFC 8693 Section 3-3.4}
|
|
10
|
+
*/
|
|
11
|
+
SUBJECT_TOKEN_TYPES["SUBJECT_TYPE_REFRESH_TOKEN"] = "urn:ietf:params:oauth:token-type:refresh_token";
|
|
12
|
+
/**
|
|
13
|
+
* Indicates that the token is an OAuth 2.0 access token issued by the given authorization server.
|
|
14
|
+
*
|
|
15
|
+
* @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.2 RFC 8693 Section 3-3.2}
|
|
16
|
+
*/
|
|
17
|
+
SUBJECT_TOKEN_TYPES["SUBJECT_TYPE_ACCESS_TOKEN"] = "urn:ietf:params:oauth:token-type:access_token";
|
|
18
|
+
})(SUBJECT_TOKEN_TYPES || (exports.SUBJECT_TOKEN_TYPES = SUBJECT_TOKEN_TYPES = {}));
|
|
3
19
|
//# sourceMappingURL=FederatedConnectionAuthorizerParams.js.map
|
package/dist/cjs/authorizers/federated-connections/FederatedConnectionAuthorizerParams.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FederatedConnectionAuthorizerParams.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerParams.ts"],"names":[],"mappings":"","sourcesContent":["import { TokenResponse } from \"../../credentials\";\nimport { AuthorizerToolParameter } from \"../../parameters\";\nimport { Store } from \"../../stores\";\nimport { AuthContext } from \"../context\";\n\nexport type FederatedConnectionAuthorizerParams<ToolExecuteArgs extends any[]> =\n {\n /**\n * The Auth0 refresh token to exchange for an Federated Connection access token.\n */\n refreshToken?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;\n\n /**\n * The Federated connection access token if available in the tool context.\n */\n accessToken
|
|
1
|
+
{"version":3,"file":"FederatedConnectionAuthorizerParams.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerParams.ts"],"names":[],"mappings":";;;AAKA,IAAY,mBAcX;AAdD,WAAY,mBAAmB;IAC7B;;;;OAIG;IACH,oGAA6E,CAAA;IAE7E;;;;OAIG;IACH,kGAA2E,CAAA;AAC7E,CAAC,EAdW,mBAAmB,mCAAnB,mBAAmB,QAc9B","sourcesContent":["import { TokenResponse } from \"../../credentials\";\nimport { AuthorizerToolParameter } from \"../../parameters\";\nimport { Store } from \"../../stores\";\nimport { AuthContext } from \"../context\";\n\nexport enum SUBJECT_TOKEN_TYPES {\n /**\n * Indicates that the token is an OAuth 2.0 refresh token issued by the given authorization server.\n *\n * @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.4 RFC 8693 Section 3-3.4}\n */\n SUBJECT_TYPE_REFRESH_TOKEN = \"urn:ietf:params:oauth:token-type:refresh_token\",\n\n /**\n * Indicates that the token is an OAuth 2.0 access token issued by the given authorization server.\n *\n * @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.2 RFC 8693 Section 3-3.2}\n */\n SUBJECT_TYPE_ACCESS_TOKEN = \"urn:ietf:params:oauth:token-type:access_token\",\n}\n\nexport type FederatedConnectionAuthorizerParams<ToolExecuteArgs extends any[]> =\n {\n /**\n * The Auth0 refresh token to exchange for an Federated Connection access token.\n */\n refreshToken?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;\n\n /**\n * The Federated connection access token if available in the tool context.\n * This can also be provided as a string exchange when exchanging an access token for a Federated Connection access token.\n */\n accessToken?:\n | AuthorizerToolParameter<\n ToolExecuteArgs,\n TokenResponse | string | undefined\n >\n | string\n | undefined;\n\n /**\n * This is used to specify the type of token being requested from Auth0 during the OAuth 2.0 token exchange request.\n */\n subjectTokenType?: SUBJECT_TOKEN_TYPES | undefined;\n\n /**\n * Optional login hint to provide when exchanging an access or refresh token for a Federated Connection access token.\n */\n loginHint?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;\n\n /**\n * The scopes required in the access token of the federated connection provider.\n */\n scopes: string[];\n\n /**\n * The connection name of the federated connection provider.\n */\n connection: string;\n\n /**\n * AuthContext defines the scope of credential sharing:\n * - \"tool-call\": Credentials are valid only for a single invocation of the tool.\n * - \"tool\": Credentials are shared across multiple calls to the same tool within the same thread.\n * - \"thread\": Credentials are shared across all tools using the same authorizer within the current thread.\n * - \"agent\": Credentials are shared globally across all threads and tools in the agent.\n *\n * @default \"thread\"\n */\n credentialsContext?: AuthContext;\n\n /**\n * An store used to store the authorization credentials according\n * to the `credentialsContext` scope.\n */\n store: Store;\n };\n"]}
|
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.FederatedConnectionAuthorizerBase = exports.getAccessTokenForConnection = exports.getCredentialsForConnection = exports.asyncLocalStorage = void 0;
|
|
3
|
+
exports.SUBJECT_TOKEN_TYPES = exports.FederatedConnectionAuthorizerBase = exports.getAccessTokenForConnection = exports.getCredentialsForConnection = exports.asyncLocalStorage = void 0;
|
|
4
4
|
var asyncLocalStorage_1 = require("./asyncLocalStorage");
|
|
5
5
|
Object.defineProperty(exports, "asyncLocalStorage", { enumerable: true, get: function () { return asyncLocalStorage_1.asyncLocalStorage; } });
|
|
6
6
|
Object.defineProperty(exports, "getCredentialsForConnection", { enumerable: true, get: function () { return asyncLocalStorage_1.getCredentialsForConnection; } });
|
|
7
7
|
Object.defineProperty(exports, "getAccessTokenForConnection", { enumerable: true, get: function () { return asyncLocalStorage_1.getAccessTokenForConnection; } });
|
|
8
8
|
var FederatedConnectionAuthorizerBase_1 = require("./FederatedConnectionAuthorizerBase");
|
|
9
9
|
Object.defineProperty(exports, "FederatedConnectionAuthorizerBase", { enumerable: true, get: function () { return FederatedConnectionAuthorizerBase_1.FederatedConnectionAuthorizerBase; } });
|
|
10
|
+
var FederatedConnectionAuthorizerParams_1 = require("./FederatedConnectionAuthorizerParams");
|
|
11
|
+
Object.defineProperty(exports, "SUBJECT_TOKEN_TYPES", { enumerable: true, get: function () { return FederatedConnectionAuthorizerParams_1.SUBJECT_TOKEN_TYPES; } });
|
|
10
12
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/index.ts"],"names":[],"mappings":";;;AAEA,yDAI6B;AAH3B,sHAAA,iBAAiB,OAAA;AACjB,gIAAA,2BAA2B,OAAA;AAC3B,gIAAA,2BAA2B,OAAA;AAG7B,yFAAwF;AAA/E,sJAAA,iCAAiC,OAAA","sourcesContent":["export type { AsyncStorageValue } from \"./asyncLocalStorage\";\n\nexport {\n asyncLocalStorage,\n getCredentialsForConnection,\n getAccessTokenForConnection,\n} from \"./asyncLocalStorage\";\n\nexport { FederatedConnectionAuthorizerBase } from \"./FederatedConnectionAuthorizerBase\";\n\nexport type { FederatedConnectionAuthorizerParams } from \"./FederatedConnectionAuthorizerParams\";\n"]}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/index.ts"],"names":[],"mappings":";;;AAEA,yDAI6B;AAH3B,sHAAA,iBAAiB,OAAA;AACjB,gIAAA,2BAA2B,OAAA;AAC3B,gIAAA,2BAA2B,OAAA;AAG7B,yFAAwF;AAA/E,sJAAA,iCAAiC,OAAA;AAI1C,6FAA4E;AAAnE,0IAAA,mBAAmB,OAAA","sourcesContent":["export type { AsyncStorageValue } from \"./asyncLocalStorage\";\n\nexport {\n asyncLocalStorage,\n getCredentialsForConnection,\n getAccessTokenForConnection,\n} from \"./asyncLocalStorage\";\n\nexport { FederatedConnectionAuthorizerBase } from \"./FederatedConnectionAuthorizerBase\";\n\nexport type { FederatedConnectionAuthorizerParams } from \"./FederatedConnectionAuthorizerParams\";\n\nexport { SUBJECT_TOKEN_TYPES } from \"./FederatedConnectionAuthorizerParams\";\n"]}
|
package/dist/cjs/index.js
CHANGED
|
@@ -14,7 +14,10 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
14
14
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
15
|
};
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
exports.SUBJECT_TOKEN_TYPES = void 0;
|
|
17
18
|
__exportStar(require("./errors"), exports);
|
|
19
|
+
var federated_connections_1 = require("./authorizers/federated-connections");
|
|
20
|
+
Object.defineProperty(exports, "SUBJECT_TOKEN_TYPES", { enumerable: true, get: function () { return federated_connections_1.SUBJECT_TOKEN_TYPES; } });
|
|
18
21
|
__exportStar(require("./authorizers/fga/fga-filter"), exports);
|
|
19
22
|
__exportStar(require("./authorizers/fga/fga-client"), exports);
|
|
20
23
|
__exportStar(require("./parameters"), exports);
|
package/dist/cjs/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAEA,2CAAyB;AACzB,6EAA0E;AAAjE,4HAAA,mBAAmB,OAAA;AAC5B,+DAA6C;AAC7C,+DAA6C;AAC7C,+CAA6B","sourcesContent":["export type { AuthParams, Auth0ClientParams } from \"./authorizers/types\";\nexport type * from \"./credentials\";\nexport * from \"./errors\";\nexport { SUBJECT_TOKEN_TYPES } from \"./authorizers/federated-connections\";\nexport * from \"./authorizers/fga/fga-filter\";\nexport * from \"./authorizers/fga/fga-client\";\nexport * from \"./parameters\";\n"]}
|
|
@@ -17,6 +17,7 @@ export declare class FederatedConnectionAuthorizerBase<ToolExecuteArgs extends a
|
|
|
17
17
|
private getAccessTokenImpl;
|
|
18
18
|
protected getAccessToken(...toolContext: ToolExecuteArgs): Promise<TokenSet>;
|
|
19
19
|
protected getRefreshToken(...toolContext: ToolExecuteArgs): Promise<string | undefined>;
|
|
20
|
+
protected getAccessTokenWithToolContext(...toolContext: ToolExecuteArgs): Promise<string | TokenResponse | undefined>;
|
|
20
21
|
/**
|
|
21
22
|
*
|
|
22
23
|
* Wraps the execute method of an AI tool to handle Federated Connections authorization.
|
|
@@ -8,6 +8,7 @@ import { omit } from "../../util";
|
|
|
8
8
|
import { nsFromContext } from "../context";
|
|
9
9
|
import { Auth0ClientSchema } from "../types";
|
|
10
10
|
import { asyncLocalStorage } from "./asyncLocalStorage";
|
|
11
|
+
import { SUBJECT_TOKEN_TYPES, } from "./FederatedConnectionAuthorizerParams";
|
|
11
12
|
/**
|
|
12
13
|
* Requests authorization to a third party service via Federated Connection.
|
|
13
14
|
*/
|
|
@@ -23,19 +24,34 @@ export class FederatedConnectionAuthorizerBase {
|
|
|
23
24
|
baseNamespace: [instanceID, "Credentials"],
|
|
24
25
|
getTTL: (credentials) => credentials.expiresIn ? credentials.expiresIn * 1000 : undefined,
|
|
25
26
|
});
|
|
26
|
-
|
|
27
|
-
|
|
27
|
+
// Validate that exactly one token source is provided
|
|
28
|
+
const hasRefreshToken = typeof params.refreshToken !== "undefined";
|
|
29
|
+
const hasAccessToken = typeof params.accessToken !== "undefined";
|
|
30
|
+
const hasSubjectTokenType = typeof params.subjectTokenType !== "undefined";
|
|
31
|
+
if (!hasRefreshToken && !hasAccessToken) {
|
|
28
32
|
throw new Error("Either refreshToken or accessToken must be provided to initialize the Authorizer.");
|
|
29
33
|
}
|
|
30
|
-
if (
|
|
31
|
-
typeof params.refreshToken !== "undefined") {
|
|
34
|
+
if (hasRefreshToken && hasAccessToken) {
|
|
32
35
|
throw new Error("Only one of refreshToken or accessToken can be provided to initialize the Authorizer.");
|
|
33
36
|
}
|
|
37
|
+
// Validate resource server client credentials when using access tokens for token exchange w/ Token Vault
|
|
38
|
+
if (hasAccessToken &&
|
|
39
|
+
hasSubjectTokenType &&
|
|
40
|
+
params.subjectTokenType === SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN) {
|
|
41
|
+
if (!this.auth0.clientId || !this.auth0.clientSecret) {
|
|
42
|
+
throw new Error("clientId and clientSecret must currently be provided when using accessToken for token exchange with Token Vault.");
|
|
43
|
+
}
|
|
44
|
+
}
|
|
34
45
|
}
|
|
35
46
|
getInstanceID() {
|
|
36
47
|
const props = {
|
|
37
48
|
auth0: this.auth0,
|
|
38
|
-
params: omit(this.params, [
|
|
49
|
+
params: omit(this.params, [
|
|
50
|
+
"store",
|
|
51
|
+
"refreshToken",
|
|
52
|
+
"accessToken",
|
|
53
|
+
"loginHint",
|
|
54
|
+
]),
|
|
39
55
|
};
|
|
40
56
|
const sh = stableHash(props);
|
|
41
57
|
return crypto.createHash("MD5").update(sh).digest("hex");
|
|
@@ -68,16 +84,39 @@ export class FederatedConnectionAuthorizerBase {
|
|
|
68
84
|
throw new Error("The tool must be wrapped with the FederationConnectionAuthorizer.");
|
|
69
85
|
}
|
|
70
86
|
const { connection } = store;
|
|
71
|
-
|
|
87
|
+
// Determine which token type to use and get the appropriate subject token
|
|
88
|
+
let subjectToken;
|
|
89
|
+
let subjectTokenType;
|
|
90
|
+
if (typeof this.params.refreshToken === "function") {
|
|
91
|
+
subjectToken = await this.getRefreshToken(...toolContext);
|
|
92
|
+
subjectTokenType = "urn:ietf:params:oauth:token-type:refresh_token";
|
|
93
|
+
}
|
|
94
|
+
else if (typeof this.params.accessToken === "function") {
|
|
95
|
+
subjectToken = (await this.getAccessTokenWithToolContext(...toolContext));
|
|
96
|
+
subjectTokenType = "urn:ietf:params:oauth:token-type:access_token";
|
|
97
|
+
}
|
|
98
|
+
else if (typeof this.params.accessToken === "string") {
|
|
99
|
+
subjectToken = this.params.accessToken;
|
|
100
|
+
subjectTokenType = "urn:ietf:params:oauth:token-type:access_token";
|
|
101
|
+
}
|
|
102
|
+
else {
|
|
103
|
+
// This should never happen due to constructor validation, but TypeScript needs this
|
|
104
|
+
throw new Error("Either refreshToken or accessToken must be configured");
|
|
105
|
+
}
|
|
72
106
|
if (!subjectToken) {
|
|
73
107
|
return;
|
|
74
108
|
}
|
|
109
|
+
// Get optional login hint if provided
|
|
110
|
+
const loginHint = typeof this.params.loginHint === "function"
|
|
111
|
+
? await resolveParameter(this.params.loginHint, toolContext)
|
|
112
|
+
: undefined;
|
|
75
113
|
const exchangeParams = {
|
|
76
114
|
grant_type: "urn:auth0:params:oauth:grant-type:token-exchange:federated-connection-access-token",
|
|
77
115
|
client_id: this.auth0.clientId,
|
|
78
116
|
client_secret: this.auth0.clientSecret,
|
|
79
|
-
subject_token_type:
|
|
117
|
+
subject_token_type: subjectTokenType,
|
|
80
118
|
subject_token: subjectToken,
|
|
119
|
+
login_hint: loginHint,
|
|
81
120
|
connection: connection,
|
|
82
121
|
requested_token_type: "http://auth0.com/oauth/token-type/federated-connection-access-token",
|
|
83
122
|
};
|
|
@@ -95,11 +134,16 @@ export class FederatedConnectionAuthorizerBase {
|
|
|
95
134
|
}
|
|
96
135
|
async getAccessToken(...toolContext) {
|
|
97
136
|
let tokenResponse;
|
|
98
|
-
|
|
137
|
+
// Use token exchange for both refresh tokens and access tokens when subjectTokenType is provided
|
|
138
|
+
if (typeof this.params.refreshToken === "function" ||
|
|
139
|
+
(typeof this.params.accessToken !== "undefined" &&
|
|
140
|
+
this.params.subjectTokenType ===
|
|
141
|
+
SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN)) {
|
|
99
142
|
tokenResponse = await this.getAccessTokenImpl(...toolContext);
|
|
100
143
|
}
|
|
101
144
|
else {
|
|
102
|
-
|
|
145
|
+
// fallback to existing behavior, where third party accessToken can be provided directly
|
|
146
|
+
tokenResponse = (await resolveParameter(this.params.accessToken, toolContext));
|
|
103
147
|
}
|
|
104
148
|
this.validateToken(tokenResponse);
|
|
105
149
|
return tokenSetFromTokenResponse(tokenResponse);
|
|
@@ -107,6 +151,9 @@ export class FederatedConnectionAuthorizerBase {
|
|
|
107
151
|
async getRefreshToken(...toolContext) {
|
|
108
152
|
return await resolveParameter(this.params.refreshToken, toolContext);
|
|
109
153
|
}
|
|
154
|
+
async getAccessTokenWithToolContext(...toolContext) {
|
|
155
|
+
return await resolveParameter(this.params.accessToken, toolContext);
|
|
156
|
+
}
|
|
110
157
|
/**
|
|
111
158
|
*
|
|
112
159
|
* Wraps the execute method of an AI tool to handle Federated Connections authorization.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FederatedConnectionAuthorizerBase.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerBase.ts"],"names":[],"mappings":"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","sourcesContent":["import crypto from \"crypto\";\nimport stableHash from \"stable-hash\";\n\nimport {\n TokenResponse,\n TokenSet,\n tokenSetFromTokenResponse,\n} from \"../../credentials\";\nimport {\n Auth0Interrupt,\n FederatedConnectionError,\n FederatedConnectionInterrupt,\n} from \"../../interrupts\";\nimport { resolveParameter } from \"../../parameters\";\nimport { SubStore } from \"../../stores\";\nimport { omit, RequireFields } from \"../../util\";\nimport { ContextGetter, nsFromContext } from \"../context\";\nimport { Auth0ClientParams, Auth0ClientSchema } from \"../types\";\nimport { asyncLocalStorage, AsyncStorageValue } from \"./asyncLocalStorage\";\nimport { FederatedConnectionAuthorizerParams } from \"./FederatedConnectionAuthorizerParams\";\n\n/**\n * Requests authorization to a third party service via Federated Connection.\n */\n\nexport class FederatedConnectionAuthorizerBase<ToolExecuteArgs extends any[]> {\n private readonly auth0: Auth0ClientParams;\n private readonly params: RequireFields<\n FederatedConnectionAuthorizerParams<ToolExecuteArgs>,\n \"credentialsContext\"\n >;\n private readonly credentialsStore: SubStore<TokenSet>;\n\n constructor(\n auth0: Partial<Auth0ClientParams>,\n params: FederatedConnectionAuthorizerParams<ToolExecuteArgs>\n ) {\n this.auth0 = Auth0ClientSchema.parse(auth0);\n this.params = {\n credentialsContext: \"thread\",\n ...params,\n };\n\n const instanceID = this.getInstanceID();\n\n this.credentialsStore = new SubStore<TokenSet>(params.store, {\n baseNamespace: [instanceID, \"Credentials\"],\n getTTL: (credentials) =>\n credentials.expiresIn ? credentials.expiresIn * 1000 : undefined,\n });\n\n if (\n typeof params.refreshToken === \"undefined\" &&\n typeof params.accessToken === \"undefined\"\n ) {\n throw new Error(\n \"Either refreshToken or accessToken must be provided to initialize the Authorizer.\"\n );\n }\n\n if (\n typeof params.accessToken !== \"undefined\" &&\n typeof params.refreshToken !== \"undefined\"\n ) {\n throw new Error(\n \"Only one of refreshToken or accessToken can be provided to initialize the Authorizer.\"\n );\n }\n }\n\n private getInstanceID(): string {\n const props = {\n auth0: this.auth0,\n params: omit(this.params, [\"store\", \"refreshToken\", \"accessToken\"]),\n };\n const sh = stableHash(props);\n return crypto.createHash(\"MD5\").update(sh).digest(\"hex\");\n }\n\n protected handleAuthorizationInterrupts(err: Auth0Interrupt) {\n throw err;\n }\n\n protected validateToken(tokenResponse?: TokenResponse) {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { scopes, connection } = store;\n\n if (!tokenResponse) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}`,\n connection,\n scopes,\n scopes\n );\n }\n\n const currentScopes = (tokenResponse.scope ?? \"\")\n .replace(/,/g, \" \")\n .split(\" \");\n const missingScopes = scopes.filter((s) => !currentScopes.includes(s));\n store.currentScopes = currentScopes;\n\n if (missingScopes.length > 0) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}. Missing scopes: ${missingScopes.join(\", \")}`,\n connection,\n scopes,\n [...currentScopes, ...scopes]\n );\n }\n }\n\n private async getAccessTokenImpl(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenResponse | undefined> {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { connection } = store;\n\n const subjectToken = await this.getRefreshToken(...toolContext);\n\n if (!subjectToken) {\n return;\n }\n\n const exchangeParams = {\n grant_type:\n \"urn:auth0:params:oauth:grant-type:token-exchange:federated-connection-access-token\",\n client_id: this.auth0.clientId,\n client_secret: this.auth0.clientSecret,\n subject_token_type: \"urn:ietf:params:oauth:token-type:refresh_token\",\n subject_token: subjectToken,\n connection: connection,\n requested_token_type:\n \"http://auth0.com/oauth/token-type/federated-connection-access-token\",\n };\n\n const res = await fetch(`https://${this.auth0.domain}/oauth/token`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify(exchangeParams),\n });\n\n if (!res.ok) {\n //TODO: handle all type of response errors.\n return;\n }\n\n const tokenResponse: TokenResponse = await res.json();\n return tokenResponse;\n }\n\n protected async getAccessToken(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenSet> {\n let tokenResponse: TokenResponse | undefined;\n if (typeof this.params.refreshToken === \"function\") {\n tokenResponse = await this.getAccessTokenImpl(...toolContext);\n } else {\n tokenResponse = await resolveParameter(\n this.params.accessToken!,\n toolContext\n );\n }\n this.validateToken(tokenResponse);\n return tokenSetFromTokenResponse(tokenResponse!);\n }\n\n protected async getRefreshToken(...toolContext: ToolExecuteArgs) {\n return await resolveParameter(this.params.refreshToken, toolContext);\n }\n\n /**\n *\n * Wraps the execute method of an AI tool to handle Federated Connections authorization.\n *\n * @param getContext - A function that returns the context of the tool execution.\n * @param execute - The tool execute method.\n * @returns The wrapped execute method.\n */\n protect(\n getContext: ContextGetter<ToolExecuteArgs>,\n execute: (...args: ToolExecuteArgs) => any\n ): (...args: ToolExecuteArgs) => any {\n return async (...args: ToolExecuteArgs) => {\n const context = getContext(...args);\n const asyncStore: AsyncStorageValue = {\n context: context,\n scopes: this.params.scopes,\n connection: this.params.connection,\n };\n\n if (asyncLocalStorage.getStore()) {\n throw new Error(\n \"Cannot nest tool calls that require federated connection authorization.\"\n );\n }\n\n return asyncLocalStorage.run(asyncStore, async () => {\n const credentialsNS = nsFromContext(\n this.params.credentialsContext,\n context\n );\n try {\n let credentials: TokenSet = await this.credentialsStore.get(\n credentialsNS,\n \"credential\"\n );\n if (!credentials) {\n credentials = await this.getAccessToken(...args);\n await this.credentialsStore.put(\n credentialsNS,\n \"credential\",\n credentials\n );\n }\n asyncStore.credentials = credentials;\n return await execute(...args);\n } catch (err) {\n if (err instanceof FederatedConnectionError) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n const interrupt = new FederatedConnectionInterrupt(\n err.message,\n asyncStore.connection,\n asyncStore.scopes,\n asyncStore.scopes\n );\n return this.handleAuthorizationInterrupts(interrupt);\n }\n if (err instanceof Auth0Interrupt) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n return this.handleAuthorizationInterrupts(err);\n }\n throw err;\n }\n });\n };\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"FederatedConnectionAuthorizerBase.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerBase.ts"],"names":[],"mappings":"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","sourcesContent":["import crypto from \"crypto\";\nimport stableHash from \"stable-hash\";\n\nimport {\n TokenResponse,\n TokenSet,\n tokenSetFromTokenResponse,\n} from \"../../credentials\";\nimport {\n Auth0Interrupt,\n FederatedConnectionError,\n FederatedConnectionInterrupt,\n} from \"../../interrupts\";\nimport { resolveParameter } from \"../../parameters\";\nimport { SubStore } from \"../../stores\";\nimport { omit, RequireFields } from \"../../util\";\nimport { ContextGetter, nsFromContext } from \"../context\";\nimport { Auth0ClientParams, Auth0ClientSchema } from \"../types\";\nimport { asyncLocalStorage, AsyncStorageValue } from \"./asyncLocalStorage\";\nimport {\n FederatedConnectionAuthorizerParams,\n SUBJECT_TOKEN_TYPES,\n} from \"./FederatedConnectionAuthorizerParams\";\n\n/**\n * Requests authorization to a third party service via Federated Connection.\n */\n\nexport class FederatedConnectionAuthorizerBase<ToolExecuteArgs extends any[]> {\n private readonly auth0: Auth0ClientParams;\n private readonly params: RequireFields<\n FederatedConnectionAuthorizerParams<ToolExecuteArgs>,\n \"credentialsContext\"\n >;\n private readonly credentialsStore: SubStore<TokenSet>;\n\n constructor(\n auth0: Partial<Auth0ClientParams>,\n params: FederatedConnectionAuthorizerParams<ToolExecuteArgs>\n ) {\n this.auth0 = Auth0ClientSchema.parse(auth0);\n this.params = {\n credentialsContext: \"thread\",\n ...params,\n };\n\n const instanceID = this.getInstanceID();\n\n this.credentialsStore = new SubStore<TokenSet>(params.store, {\n baseNamespace: [instanceID, \"Credentials\"],\n getTTL: (credentials) =>\n credentials.expiresIn ? credentials.expiresIn * 1000 : undefined,\n });\n\n // Validate that exactly one token source is provided\n const hasRefreshToken = typeof params.refreshToken !== \"undefined\";\n const hasAccessToken = typeof params.accessToken !== \"undefined\";\n const hasSubjectTokenType = typeof params.subjectTokenType !== \"undefined\";\n\n if (!hasRefreshToken && !hasAccessToken) {\n throw new Error(\n \"Either refreshToken or accessToken must be provided to initialize the Authorizer.\"\n );\n }\n\n if (hasRefreshToken && hasAccessToken) {\n throw new Error(\n \"Only one of refreshToken or accessToken can be provided to initialize the Authorizer.\"\n );\n }\n\n // Validate resource server client credentials when using access tokens for token exchange w/ Token Vault\n if (\n hasAccessToken &&\n hasSubjectTokenType &&\n params.subjectTokenType === SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN\n ) {\n if (!this.auth0.clientId || !this.auth0.clientSecret) {\n throw new Error(\n \"clientId and clientSecret must currently be provided when using accessToken for token exchange with Token Vault.\"\n );\n }\n }\n }\n\n private getInstanceID(): string {\n const props = {\n auth0: this.auth0,\n params: omit(this.params, [\n \"store\",\n \"refreshToken\",\n \"accessToken\",\n \"loginHint\",\n ]),\n };\n const sh = stableHash(props);\n return crypto.createHash(\"MD5\").update(sh).digest(\"hex\");\n }\n\n protected handleAuthorizationInterrupts(err: Auth0Interrupt) {\n throw err;\n }\n\n protected validateToken(tokenResponse?: TokenResponse) {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { scopes, connection } = store;\n\n if (!tokenResponse) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}`,\n connection,\n scopes,\n scopes\n );\n }\n\n const currentScopes = (tokenResponse.scope ?? \"\")\n .replace(/,/g, \" \")\n .split(\" \");\n const missingScopes = scopes.filter((s) => !currentScopes.includes(s));\n store.currentScopes = currentScopes;\n\n if (missingScopes.length > 0) {\n throw new FederatedConnectionInterrupt(\n `Authorization required to access the Federated Connection: ${this.params.connection}. Missing scopes: ${missingScopes.join(\", \")}`,\n connection,\n scopes,\n [...currentScopes, ...scopes]\n );\n }\n }\n\n private async getAccessTokenImpl(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenResponse | undefined> {\n const store = asyncLocalStorage.getStore();\n if (!store) {\n throw new Error(\n \"The tool must be wrapped with the FederationConnectionAuthorizer.\"\n );\n }\n\n const { connection } = store;\n\n // Determine which token type to use and get the appropriate subject token\n let subjectToken: string | undefined;\n let subjectTokenType: string;\n\n if (typeof this.params.refreshToken === \"function\") {\n subjectToken = await this.getRefreshToken(...toolContext);\n subjectTokenType = \"urn:ietf:params:oauth:token-type:refresh_token\";\n } else if (typeof this.params.accessToken === \"function\") {\n subjectToken = (await this.getAccessTokenWithToolContext(\n ...toolContext\n )) as string;\n subjectTokenType = \"urn:ietf:params:oauth:token-type:access_token\";\n } else if (typeof this.params.accessToken === \"string\") {\n subjectToken = this.params.accessToken;\n subjectTokenType = \"urn:ietf:params:oauth:token-type:access_token\";\n } else {\n // This should never happen due to constructor validation, but TypeScript needs this\n throw new Error(\"Either refreshToken or accessToken must be configured\");\n }\n\n if (!subjectToken) {\n return;\n }\n\n // Get optional login hint if provided\n const loginHint =\n typeof this.params.loginHint === \"function\"\n ? await resolveParameter(this.params.loginHint, toolContext)\n : undefined;\n\n const exchangeParams = {\n grant_type:\n \"urn:auth0:params:oauth:grant-type:token-exchange:federated-connection-access-token\",\n client_id: this.auth0.clientId,\n client_secret: this.auth0.clientSecret,\n subject_token_type: subjectTokenType,\n subject_token: subjectToken,\n login_hint: loginHint,\n connection: connection,\n requested_token_type:\n \"http://auth0.com/oauth/token-type/federated-connection-access-token\",\n };\n\n const res = await fetch(`https://${this.auth0.domain}/oauth/token`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify(exchangeParams),\n });\n\n if (!res.ok) {\n //TODO: handle all type of response errors.\n return;\n }\n\n const tokenResponse: TokenResponse = await res.json();\n return tokenResponse;\n }\n\n protected async getAccessToken(\n ...toolContext: ToolExecuteArgs\n ): Promise<TokenSet> {\n let tokenResponse: TokenResponse | undefined;\n // Use token exchange for both refresh tokens and access tokens when subjectTokenType is provided\n if (\n typeof this.params.refreshToken === \"function\" ||\n (typeof this.params.accessToken !== \"undefined\" &&\n this.params.subjectTokenType ===\n SUBJECT_TOKEN_TYPES.SUBJECT_TYPE_ACCESS_TOKEN)\n ) {\n tokenResponse = await this.getAccessTokenImpl(...toolContext);\n } else {\n // fallback to existing behavior, where third party accessToken can be provided directly\n tokenResponse = (await resolveParameter(\n this.params.accessToken!,\n toolContext\n )) as TokenResponse;\n }\n this.validateToken(tokenResponse);\n return tokenSetFromTokenResponse(tokenResponse!);\n }\n\n protected async getRefreshToken(...toolContext: ToolExecuteArgs) {\n return await resolveParameter(this.params.refreshToken, toolContext);\n }\n\n protected async getAccessTokenWithToolContext(\n ...toolContext: ToolExecuteArgs\n ) {\n return await resolveParameter(this.params.accessToken, toolContext);\n }\n\n /**\n *\n * Wraps the execute method of an AI tool to handle Federated Connections authorization.\n *\n * @param getContext - A function that returns the context of the tool execution.\n * @param execute - The tool execute method.\n * @returns The wrapped execute method.\n */\n protect(\n getContext: ContextGetter<ToolExecuteArgs>,\n execute: (...args: ToolExecuteArgs) => any\n ): (...args: ToolExecuteArgs) => any {\n return async (...args: ToolExecuteArgs) => {\n const context = getContext(...args);\n const asyncStore: AsyncStorageValue = {\n context: context,\n scopes: this.params.scopes,\n connection: this.params.connection,\n };\n\n if (asyncLocalStorage.getStore()) {\n throw new Error(\n \"Cannot nest tool calls that require federated connection authorization.\"\n );\n }\n\n return asyncLocalStorage.run(asyncStore, async () => {\n const credentialsNS = nsFromContext(\n this.params.credentialsContext,\n context\n );\n try {\n let credentials: TokenSet = await this.credentialsStore.get(\n credentialsNS,\n \"credential\"\n );\n if (!credentials) {\n credentials = await this.getAccessToken(...args);\n await this.credentialsStore.put(\n credentialsNS,\n \"credential\",\n credentials\n );\n }\n asyncStore.credentials = credentials;\n return await execute(...args);\n } catch (err) {\n if (err instanceof FederatedConnectionError) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n const interrupt = new FederatedConnectionInterrupt(\n err.message,\n asyncStore.connection,\n asyncStore.scopes,\n asyncStore.scopes\n );\n return this.handleAuthorizationInterrupts(interrupt);\n }\n if (err instanceof Auth0Interrupt) {\n this.credentialsStore.delete(credentialsNS, \"credential\");\n return this.handleAuthorizationInterrupts(err);\n }\n throw err;\n }\n });\n };\n }\n}\n"]}
|
|
@@ -2,6 +2,20 @@ import { TokenResponse } from "../../credentials";
|
|
|
2
2
|
import { AuthorizerToolParameter } from "../../parameters";
|
|
3
3
|
import { Store } from "../../stores";
|
|
4
4
|
import { AuthContext } from "../context";
|
|
5
|
+
export declare enum SUBJECT_TOKEN_TYPES {
|
|
6
|
+
/**
|
|
7
|
+
* Indicates that the token is an OAuth 2.0 refresh token issued by the given authorization server.
|
|
8
|
+
*
|
|
9
|
+
* @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.4 RFC 8693 Section 3-3.4}
|
|
10
|
+
*/
|
|
11
|
+
SUBJECT_TYPE_REFRESH_TOKEN = "urn:ietf:params:oauth:token-type:refresh_token",
|
|
12
|
+
/**
|
|
13
|
+
* Indicates that the token is an OAuth 2.0 access token issued by the given authorization server.
|
|
14
|
+
*
|
|
15
|
+
* @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.2 RFC 8693 Section 3-3.2}
|
|
16
|
+
*/
|
|
17
|
+
SUBJECT_TYPE_ACCESS_TOKEN = "urn:ietf:params:oauth:token-type:access_token"
|
|
18
|
+
}
|
|
5
19
|
export type FederatedConnectionAuthorizerParams<ToolExecuteArgs extends any[]> = {
|
|
6
20
|
/**
|
|
7
21
|
* The Auth0 refresh token to exchange for an Federated Connection access token.
|
|
@@ -9,8 +23,17 @@ export type FederatedConnectionAuthorizerParams<ToolExecuteArgs extends any[]> =
|
|
|
9
23
|
refreshToken?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;
|
|
10
24
|
/**
|
|
11
25
|
* The Federated connection access token if available in the tool context.
|
|
26
|
+
* This can also be provided as a string exchange when exchanging an access token for a Federated Connection access token.
|
|
27
|
+
*/
|
|
28
|
+
accessToken?: AuthorizerToolParameter<ToolExecuteArgs, TokenResponse | string | undefined> | string | undefined;
|
|
29
|
+
/**
|
|
30
|
+
* This is used to specify the type of token being requested from Auth0 during the OAuth 2.0 token exchange request.
|
|
31
|
+
*/
|
|
32
|
+
subjectTokenType?: SUBJECT_TOKEN_TYPES | undefined;
|
|
33
|
+
/**
|
|
34
|
+
* Optional login hint to provide when exchanging an access or refresh token for a Federated Connection access token.
|
|
12
35
|
*/
|
|
13
|
-
|
|
36
|
+
loginHint?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;
|
|
14
37
|
/**
|
|
15
38
|
* The scopes required in the access token of the federated connection provider.
|
|
16
39
|
*/
|
|
@@ -1,2 +1,16 @@
|
|
|
1
|
-
export
|
|
1
|
+
export var SUBJECT_TOKEN_TYPES;
|
|
2
|
+
(function (SUBJECT_TOKEN_TYPES) {
|
|
3
|
+
/**
|
|
4
|
+
* Indicates that the token is an OAuth 2.0 refresh token issued by the given authorization server.
|
|
5
|
+
*
|
|
6
|
+
* @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.4 RFC 8693 Section 3-3.4}
|
|
7
|
+
*/
|
|
8
|
+
SUBJECT_TOKEN_TYPES["SUBJECT_TYPE_REFRESH_TOKEN"] = "urn:ietf:params:oauth:token-type:refresh_token";
|
|
9
|
+
/**
|
|
10
|
+
* Indicates that the token is an OAuth 2.0 access token issued by the given authorization server.
|
|
11
|
+
*
|
|
12
|
+
* @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.2 RFC 8693 Section 3-3.2}
|
|
13
|
+
*/
|
|
14
|
+
SUBJECT_TOKEN_TYPES["SUBJECT_TYPE_ACCESS_TOKEN"] = "urn:ietf:params:oauth:token-type:access_token";
|
|
15
|
+
})(SUBJECT_TOKEN_TYPES || (SUBJECT_TOKEN_TYPES = {}));
|
|
2
16
|
//# sourceMappingURL=FederatedConnectionAuthorizerParams.js.map
|
package/dist/esm/authorizers/federated-connections/FederatedConnectionAuthorizerParams.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FederatedConnectionAuthorizerParams.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerParams.ts"],"names":[],"mappings":"","sourcesContent":["import { TokenResponse } from \"../../credentials\";\nimport { AuthorizerToolParameter } from \"../../parameters\";\nimport { Store } from \"../../stores\";\nimport { AuthContext } from \"../context\";\n\nexport type FederatedConnectionAuthorizerParams<ToolExecuteArgs extends any[]> =\n {\n /**\n * The Auth0 refresh token to exchange for an Federated Connection access token.\n */\n refreshToken?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;\n\n /**\n * The Federated connection access token if available in the tool context.\n */\n accessToken
|
|
1
|
+
{"version":3,"file":"FederatedConnectionAuthorizerParams.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/FederatedConnectionAuthorizerParams.ts"],"names":[],"mappings":"AAKA,MAAM,CAAN,IAAY,mBAcX;AAdD,WAAY,mBAAmB;IAC7B;;;;OAIG;IACH,oGAA6E,CAAA;IAE7E;;;;OAIG;IACH,kGAA2E,CAAA;AAC7E,CAAC,EAdW,mBAAmB,KAAnB,mBAAmB,QAc9B","sourcesContent":["import { TokenResponse } from \"../../credentials\";\nimport { AuthorizerToolParameter } from \"../../parameters\";\nimport { Store } from \"../../stores\";\nimport { AuthContext } from \"../context\";\n\nexport enum SUBJECT_TOKEN_TYPES {\n /**\n * Indicates that the token is an OAuth 2.0 refresh token issued by the given authorization server.\n *\n * @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.4 RFC 8693 Section 3-3.4}\n */\n SUBJECT_TYPE_REFRESH_TOKEN = \"urn:ietf:params:oauth:token-type:refresh_token\",\n\n /**\n * Indicates that the token is an OAuth 2.0 access token issued by the given authorization server.\n *\n * @see {@link https://datatracker.ietf.org/doc/html/rfc8693#section-3-3.2 RFC 8693 Section 3-3.2}\n */\n SUBJECT_TYPE_ACCESS_TOKEN = \"urn:ietf:params:oauth:token-type:access_token\",\n}\n\nexport type FederatedConnectionAuthorizerParams<ToolExecuteArgs extends any[]> =\n {\n /**\n * The Auth0 refresh token to exchange for an Federated Connection access token.\n */\n refreshToken?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;\n\n /**\n * The Federated connection access token if available in the tool context.\n * This can also be provided as a string exchange when exchanging an access token for a Federated Connection access token.\n */\n accessToken?:\n | AuthorizerToolParameter<\n ToolExecuteArgs,\n TokenResponse | string | undefined\n >\n | string\n | undefined;\n\n /**\n * This is used to specify the type of token being requested from Auth0 during the OAuth 2.0 token exchange request.\n */\n subjectTokenType?: SUBJECT_TOKEN_TYPES | undefined;\n\n /**\n * Optional login hint to provide when exchanging an access or refresh token for a Federated Connection access token.\n */\n loginHint?: AuthorizerToolParameter<ToolExecuteArgs, string | undefined>;\n\n /**\n * The scopes required in the access token of the federated connection provider.\n */\n scopes: string[];\n\n /**\n * The connection name of the federated connection provider.\n */\n connection: string;\n\n /**\n * AuthContext defines the scope of credential sharing:\n * - \"tool-call\": Credentials are valid only for a single invocation of the tool.\n * - \"tool\": Credentials are shared across multiple calls to the same tool within the same thread.\n * - \"thread\": Credentials are shared across all tools using the same authorizer within the current thread.\n * - \"agent\": Credentials are shared globally across all threads and tools in the agent.\n *\n * @default \"thread\"\n */\n credentialsContext?: AuthContext;\n\n /**\n * An store used to store the authorization credentials according\n * to the `credentialsContext` scope.\n */\n store: Store;\n };\n"]}
|
|
@@ -2,4 +2,5 @@ export type { AsyncStorageValue } from "./asyncLocalStorage";
|
|
|
2
2
|
export { asyncLocalStorage, getCredentialsForConnection, getAccessTokenForConnection, } from "./asyncLocalStorage";
|
|
3
3
|
export { FederatedConnectionAuthorizerBase } from "./FederatedConnectionAuthorizerBase";
|
|
4
4
|
export type { FederatedConnectionAuthorizerParams } from "./FederatedConnectionAuthorizerParams";
|
|
5
|
+
export { SUBJECT_TOKEN_TYPES } from "./FederatedConnectionAuthorizerParams";
|
|
5
6
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1,3 +1,4 @@
|
|
|
1
1
|
export { asyncLocalStorage, getCredentialsForConnection, getAccessTokenForConnection, } from "./asyncLocalStorage";
|
|
2
2
|
export { FederatedConnectionAuthorizerBase } from "./FederatedConnectionAuthorizerBase";
|
|
3
|
+
export { SUBJECT_TOKEN_TYPES } from "./FederatedConnectionAuthorizerParams";
|
|
3
4
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/index.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,iBAAiB,EACjB,2BAA2B,EAC3B,2BAA2B,GAC5B,MAAM,qBAAqB,CAAC;AAE7B,OAAO,EAAE,iCAAiC,EAAE,MAAM,qCAAqC,CAAC","sourcesContent":["export type { AsyncStorageValue } from \"./asyncLocalStorage\";\n\nexport {\n asyncLocalStorage,\n getCredentialsForConnection,\n getAccessTokenForConnection,\n} from \"./asyncLocalStorage\";\n\nexport { FederatedConnectionAuthorizerBase } from \"./FederatedConnectionAuthorizerBase\";\n\nexport type { FederatedConnectionAuthorizerParams } from \"./FederatedConnectionAuthorizerParams\";\n"]}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/authorizers/federated-connections/index.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,iBAAiB,EACjB,2BAA2B,EAC3B,2BAA2B,GAC5B,MAAM,qBAAqB,CAAC;AAE7B,OAAO,EAAE,iCAAiC,EAAE,MAAM,qCAAqC,CAAC;AAIxF,OAAO,EAAE,mBAAmB,EAAE,MAAM,uCAAuC,CAAC","sourcesContent":["export type { AsyncStorageValue } from \"./asyncLocalStorage\";\n\nexport {\n asyncLocalStorage,\n getCredentialsForConnection,\n getAccessTokenForConnection,\n} from \"./asyncLocalStorage\";\n\nexport { FederatedConnectionAuthorizerBase } from \"./FederatedConnectionAuthorizerBase\";\n\nexport type { FederatedConnectionAuthorizerParams } from \"./FederatedConnectionAuthorizerParams\";\n\nexport { SUBJECT_TOKEN_TYPES } from \"./FederatedConnectionAuthorizerParams\";\n"]}
|
package/dist/esm/index.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
export type { AuthParams, Auth0ClientParams } from "./authorizers/types";
|
|
2
2
|
export type * from "./credentials";
|
|
3
3
|
export * from "./errors";
|
|
4
|
+
export { SUBJECT_TOKEN_TYPES } from "./authorizers/federated-connections";
|
|
4
5
|
export * from "./authorizers/fga/fga-filter";
|
|
5
6
|
export * from "./authorizers/fga/fga-client";
|
|
6
7
|
export * from "./parameters";
|
package/dist/esm/index.js
CHANGED
package/dist/esm/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAEA,cAAc,UAAU,CAAC;AACzB,cAAc,8BAA8B,CAAC;AAC7C,cAAc,8BAA8B,CAAC;AAC7C,cAAc,cAAc,CAAC","sourcesContent":["export type { AuthParams, Auth0ClientParams } from \"./authorizers/types\";\nexport type * from \"./credentials\";\nexport * from \"./errors\";\nexport * from \"./authorizers/fga/fga-filter\";\nexport * from \"./authorizers/fga/fga-client\";\nexport * from \"./parameters\";\n"]}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAEA,cAAc,UAAU,CAAC;AACzB,OAAO,EAAE,mBAAmB,EAAE,MAAM,qCAAqC,CAAC;AAC1E,cAAc,8BAA8B,CAAC;AAC7C,cAAc,8BAA8B,CAAC;AAC7C,cAAc,cAAc,CAAC","sourcesContent":["export type { AuthParams, Auth0ClientParams } from \"./authorizers/types\";\nexport type * from \"./credentials\";\nexport * from \"./errors\";\nexport { SUBJECT_TOKEN_TYPES } from \"./authorizers/federated-connections\";\nexport * from \"./authorizers/fga/fga-filter\";\nexport * from \"./authorizers/fga/fga-client\";\nexport * from \"./parameters\";\n"]}
|