@osdk/oauth 1.1.0-beta.2 → 1.1.0-beta.3
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/CHANGELOG.md +8 -0
- package/build/browser/AuthorizationServer.test.d.ts +2 -0
- package/build/browser/AuthorizationServer.test.d.ts.map +1 -0
- package/build/browser/AuthorizationServer.test.js +45 -0
- package/build/browser/AuthorizationServer.test.js.map +1 -0
- package/build/browser/common.d.ts +1 -2
- package/build/browser/common.d.ts.map +1 -1
- package/build/browser/common.js +3 -4
- package/build/browser/common.js.map +1 -1
- package/build/browser/createConfidentialOauthClient.d.ts.map +1 -1
- package/build/browser/createConfidentialOauthClient.js +1 -1
- package/build/browser/createConfidentialOauthClient.js.map +1 -1
- package/build/browser/createPublicOauthClient.d.ts +2 -2
- package/build/browser/publicOauth.test.d.ts +2 -0
- package/build/browser/publicOauth.test.d.ts.map +1 -0
- package/build/browser/publicOauth.test.js +242 -0
- package/build/browser/publicOauth.test.js.map +1 -0
- package/build/browser/utils.js +1 -1
- package/build/browser/utils.js.map +1 -1
- package/build/esm/AuthorizationServer.test.d.ts +2 -0
- package/build/esm/AuthorizationServer.test.d.ts.map +1 -0
- package/build/esm/AuthorizationServer.test.js +45 -0
- package/build/esm/AuthorizationServer.test.js.map +1 -0
- package/build/esm/common.d.ts +1 -2
- package/build/esm/common.d.ts.map +1 -1
- package/build/esm/common.js +3 -4
- package/build/esm/common.js.map +1 -1
- package/build/esm/createConfidentialOauthClient.d.ts.map +1 -1
- package/build/esm/createConfidentialOauthClient.js +1 -1
- package/build/esm/createConfidentialOauthClient.js.map +1 -1
- package/build/esm/createPublicOauthClient.d.ts +2 -2
- package/build/esm/publicOauth.test.d.ts +2 -0
- package/build/esm/publicOauth.test.d.ts.map +1 -0
- package/build/esm/publicOauth.test.js +242 -0
- package/build/esm/publicOauth.test.js.map +1 -0
- package/build/esm/utils.js +1 -1
- package/build/esm/utils.js.map +1 -1
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
# @osdk/oauth
|
|
2
2
|
|
|
3
|
+
## 1.1.0-beta.3
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- 91cfa3a: Fixing url parsing for client.
|
|
8
|
+
- d501104: Adds unit testing of public oauth flow
|
|
9
|
+
- 91cfa3a: Fixing URL parsing for custom entry points.
|
|
10
|
+
|
|
3
11
|
## 1.1.0-beta.2
|
|
4
12
|
|
|
5
13
|
### Minor Changes
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AuthorizationServer.test.d.ts","sourceRoot":"","sources":["../../src/AuthorizationServer.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2024 Palantir Technologies, Inc. All rights reserved.
|
|
3
|
+
*
|
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
+
* you may not use this file except in compliance with the License.
|
|
6
|
+
* You may obtain a copy of the License at
|
|
7
|
+
*
|
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
+
*
|
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
+
* See the License for the specific language governing permissions and
|
|
14
|
+
* limitations under the License.
|
|
15
|
+
*/
|
|
16
|
+
import { describe, expect, it } from "vitest";
|
|
17
|
+
import { createAuthorizationServer } from "./common.js";
|
|
18
|
+
describe("Create authorization server", () => {
|
|
19
|
+
it("works with old multipass ctx path", () => {
|
|
20
|
+
const authServer = createAuthorizationServer("/multipass", "https://stack.palantir.com");
|
|
21
|
+
expect(authServer).toEqual({
|
|
22
|
+
token_endpoint: "https://stack.palantir.com/multipass/api/oauth2/token",
|
|
23
|
+
authorization_endpoint: "https://stack.palantir.com/multipass/api/oauth2/authorize",
|
|
24
|
+
revocation_endpoint: "https://stack.palantir.com/multipass/api/oauth2/revoke_token",
|
|
25
|
+
issuer: "https://stack.palantir.com/multipass"
|
|
26
|
+
});
|
|
27
|
+
});
|
|
28
|
+
it("works with new multipass ctx path", () => {
|
|
29
|
+
const authServer = createAuthorizationServer("multipass", "https://stack.palantir.com");
|
|
30
|
+
expect(authServer).toEqual({
|
|
31
|
+
token_endpoint: "https://stack.palantir.com/multipass/api/oauth2/token",
|
|
32
|
+
authorization_endpoint: "https://stack.palantir.com/multipass/api/oauth2/authorize",
|
|
33
|
+
revocation_endpoint: "https://stack.palantir.com/multipass/api/oauth2/revoke_token",
|
|
34
|
+
issuer: "https://stack.palantir.com/multipass"
|
|
35
|
+
});
|
|
36
|
+
const authServerCustom = createAuthorizationServer("multipass", "https://stack.palantir.com/foo/first/someStuff");
|
|
37
|
+
expect(authServerCustom).toEqual({
|
|
38
|
+
token_endpoint: "https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/token",
|
|
39
|
+
authorization_endpoint: "https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/authorize",
|
|
40
|
+
revocation_endpoint: "https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/revoke_token",
|
|
41
|
+
issuer: "https://stack.palantir.com/foo/first/someStuff/multipass"
|
|
42
|
+
});
|
|
43
|
+
});
|
|
44
|
+
});
|
|
45
|
+
//# sourceMappingURL=AuthorizationServer.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AuthorizationServer.test.js","names":["describe","expect","it","createAuthorizationServer","authServer","toEqual","token_endpoint","authorization_endpoint","revocation_endpoint","issuer","authServerCustom"],"sources":["AuthorizationServer.test.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { describe, expect, it, } from \"vitest\";\nimport { createAuthorizationServer } from \"./common.js\";\ndescribe(\"Create authorization server\", () => {\n it(\"works with old multipass ctx path\", () => {\n const authServer = createAuthorizationServer(\"/multipass\", \"https://stack.palantir.com\");\n expect(authServer).toEqual({\n token_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/token\",\n authorization_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/authorize\",\n revocation_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/revoke_token\",\n issuer: \"https://stack.palantir.com/multipass\",\n });\n });\n it(\"works with new multipass ctx path\", () => {\n const authServer = createAuthorizationServer(\"multipass\", \"https://stack.palantir.com\");\n expect(authServer).toEqual({\n token_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/token\",\n authorization_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/authorize\",\n revocation_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/revoke_token\",\n issuer: \"https://stack.palantir.com/multipass\",\n });\n const authServerCustom = createAuthorizationServer(\"multipass\", \"https://stack.palantir.com/foo/first/someStuff\");\n expect(authServerCustom).toEqual({\n token_endpoint: \"https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/token\",\n authorization_endpoint: \"https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/authorize\",\n revocation_endpoint: \"https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/revoke_token\",\n issuer: \"https://stack.palantir.com/foo/first/someStuff/multipass\",\n });\n });\n});\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAASA,QAAQ,EAAEC,MAAM,EAAEC,EAAE,QAAS,QAAQ;AAC9C,SAASC,yBAAyB,QAAQ,aAAa;AACvDH,QAAQ,CAAC,6BAA6B,EAAE,MAAM;EAC1CE,EAAE,CAAC,mCAAmC,EAAE,MAAM;IAC1C,MAAME,UAAU,GAAGD,yBAAyB,CAAC,YAAY,EAAE,4BAA4B,CAAC;IACxFF,MAAM,CAACG,UAAU,CAAC,CAACC,OAAO,CAAC;MACvBC,cAAc,EAAE,uDAAuD;MACvEC,sBAAsB,EAAE,2DAA2D;MACnFC,mBAAmB,EAAE,8DAA8D;MACnFC,MAAM,EAAE;IACZ,CAAC,CAAC;EACN,CAAC,CAAC;EACFP,EAAE,CAAC,mCAAmC,EAAE,MAAM;IAC1C,MAAME,UAAU,GAAGD,yBAAyB,CAAC,WAAW,EAAE,4BAA4B,CAAC;IACvFF,MAAM,CAACG,UAAU,CAAC,CAACC,OAAO,CAAC;MACvBC,cAAc,EAAE,uDAAuD;MACvEC,sBAAsB,EAAE,2DAA2D;MACnFC,mBAAmB,EAAE,8DAA8D;MACnFC,MAAM,EAAE;IACZ,CAAC,CAAC;IACF,MAAMC,gBAAgB,GAAGP,yBAAyB,CAAC,WAAW,EAAE,gDAAgD,CAAC;IACjHF,MAAM,CAACS,gBAAgB,CAAC,CAACL,OAAO,CAAC;MAC7BC,cAAc,EAAE,2EAA2E;MAC3FC,sBAAsB,EAAE,+EAA+E;MACvGC,mBAAmB,EAAE,kFAAkF;MACvGC,MAAM,EAAE;IACZ,CAAC,CAAC;EACN,CAAC,CAAC;AACN,CAAC,CAAC","ignoreList":[]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { AuthorizationServer, Client, HttpRequestOptions, OAuth2TokenEndpointResponse } from "oauth4webapi";
|
|
2
2
|
import type { BaseOauthClient, Events } from "./BaseOauthClient.js";
|
|
3
3
|
import type { Token } from "./Token.js";
|
|
4
|
-
type LocalStorageState = {
|
|
4
|
+
export type LocalStorageState = {
|
|
5
5
|
refresh_token?: never;
|
|
6
6
|
codeVerifier?: never;
|
|
7
7
|
state?: never;
|
|
@@ -32,5 +32,4 @@ export declare function common<R extends undefined | (() => Promise<Token | unde
|
|
|
32
32
|
makeTokenAndSaveRefresh: (resp: OAuth2TokenEndpointResponse, type: "signIn" | "refresh") => Token;
|
|
33
33
|
};
|
|
34
34
|
export declare function createAuthorizationServer(ctxPath: string, url: string): Required<Pick<AuthorizationServer, "issuer" | "token_endpoint" | "authorization_endpoint" | "revocation_endpoint">>;
|
|
35
|
-
export {};
|
|
36
35
|
//# sourceMappingURL=common.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"common.d.ts","sourceRoot":"","sources":["../../src/common.ts"],"names":[],"mappings":"AAgBA,OAAO,KAAK,EACV,mBAAmB,EACnB,MAAM,EACN,kBAAkB,EAClB,2BAA2B,EAC5B,MAAM,cAAc,CAAC;AAItB,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AAEpE,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"common.d.ts","sourceRoot":"","sources":["../../src/common.ts"],"names":[],"mappings":"AAgBA,OAAO,KAAK,EACV,mBAAmB,EACnB,MAAM,EACN,kBAAkB,EAClB,2BAA2B,EAC5B,MAAM,cAAc,CAAC;AAItB,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AAEpE,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAwBxC,MAAM,MAAM,iBAAiB,GAEzB;IACA,aAAa,CAAC,EAAE,KAAK,CAAC;IACtB,YAAY,CAAC,EAAE,KAAK,CAAC;IACrB,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB,GAEC;IACA,aAAa,CAAC,EAAE,KAAK,CAAC;IACtB,YAAY,EAAE,MAAM,CAAC;IACrB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB,GAEC;IACA,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,YAAY,CAAC,EAAE,KAAK,CAAC;IACrB,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,MAAM,CAAC,EAAE,KAAK,CAAC;CAChB,GACC;IACA,aAAa,CAAC,EAAE,KAAK,CAAC;IACtB,YAAY,CAAC,EAAE,KAAK,CAAC;IACrB,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,MAAM,CAAC,EAAE,KAAK,CAAC;CAChB,CAAC;AAEJ,wBAAgB,SAAS,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,EAAE,iBAAiB,QAM7D;AAED,wBAAgB,WAAW,CAAC,MAAM,EAAE,MAAM,QAKzC;AAED,wBAAgB,SAAS,CAAC,MAAM,EAAE,MAAM,GAAG,iBAAiB,CAQ3D;AAED,wBAAgB,MAAM,CACpB,CAAC,SAAS,SAAS,GAAG,CAAC,MAAM,OAAO,CAAC,KAAK,GAAG,SAAS,CAAC,CAAC,EAExD,MAAM,EAAE,MAAM,EACd,EAAE,EAAE,mBAAmB,EACvB,OAAO,EAAE,MAAM,OAAO,CAAC,KAAK,CAAC,EAC7B,gBAAgB,EAAE,kBAAkB,EACpC,OAAO,EAAE,CAAC,GACT;IACD,QAAQ,EAAE,eAAe,CAAC,MAAM,MAAM,GAAG,MAAM,CAAC,GAAG;QAAE,OAAO,EAAE,CAAC,CAAA;KAAE,CAAC;IAClE,uBAAuB,EAAE,CACvB,IAAI,EAAE,2BAA2B,EACjC,IAAI,EAAE,QAAQ,GAAG,SAAS,KACvB,KAAK,CAAC;CACZ,CA0GA;AAED,wBAAgB,yBAAyB,CACvC,OAAO,EAAE,MAAM,EACf,GAAG,EAAE,MAAM,GACV,QAAQ,CACT,IAAI,CACF,mBAAmB,EACjB,QAAQ,GACR,gBAAgB,GAChB,wBAAwB,GACxB,qBAAqB,CACxB,CACF,CAQA"}
|
package/build/browser/common.js
CHANGED
|
@@ -20,19 +20,18 @@ import { throwIfError } from "./throwIfError.js";
|
|
|
20
20
|
// Node 18 is supposed to have a `CustomEvent` but it is not exposed on `globalThis`
|
|
21
21
|
// which creates a problem for making a single codebase for node and browser. This polyfill works around it
|
|
22
22
|
const CustomEvent = globalThis.CustomEvent;
|
|
23
|
-
const localStorage = globalThis.localStorage;
|
|
24
23
|
export function saveLocal(client, x) {
|
|
25
24
|
// MUST `localStorage?` as nodejs does not have localStorage
|
|
26
|
-
localStorage?.setItem(`@osdk/oauth : refresh : ${client.client_id}`, JSON.stringify(x));
|
|
25
|
+
globalThis.localStorage?.setItem(`@osdk/oauth : refresh : ${client.client_id}`, JSON.stringify(x));
|
|
27
26
|
}
|
|
28
27
|
export function removeLocal(client) {
|
|
29
28
|
// MUST `localStorage?` as nodejs does not have localStorage
|
|
30
|
-
localStorage?.removeItem(`@osdk/oauth : refresh : ${client.client_id}`);
|
|
29
|
+
globalThis.localStorage?.removeItem(`@osdk/oauth : refresh : ${client.client_id}`);
|
|
31
30
|
}
|
|
32
31
|
export function readLocal(client) {
|
|
33
32
|
return JSON.parse(
|
|
34
33
|
// MUST `localStorage?` as nodejs does not have localStorage
|
|
35
|
-
localStorage?.getItem(`@osdk/oauth : refresh : ${client.client_id}`) ?? "{}");
|
|
34
|
+
globalThis.localStorage?.getItem(`@osdk/oauth : refresh : ${client.client_id}`) ?? "{}");
|
|
36
35
|
}
|
|
37
36
|
export function common(client, as, _signIn, oauthHttpOptions, refresh) {
|
|
38
37
|
let token;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"common.js","names":["processRevocationResponse","revocationRequest","invariant","TypedEventTarget","throwIfError","CustomEvent","globalThis","
|
|
1
|
+
{"version":3,"file":"common.js","names":["processRevocationResponse","revocationRequest","invariant","TypedEventTarget","throwIfError","CustomEvent","globalThis","saveLocal","client","x","localStorage","setItem","client_id","JSON","stringify","removeLocal","removeItem","readLocal","parse","getItem","common","as","_signIn","oauthHttpOptions","refresh","token","eventTarget","makeTokenAndSaveRefresh","resp","type","refresh_token","expires_in","access_token","process","env","NODE_ENV","expires_at","Date","now","dispatchTypedEvent","detail","refreshTimeout","rmTimeout","clearTimeout","restartRefreshTimer","evt","setTimeout","pendingSignIn","signIn","undefined","addEventListener","getTokenOrUndefined","getToken","Object","assign","signOut","result","Event","bind","removeEventListener","createAuthorizationServer","ctxPath","url","issuer","URL","token_endpoint","authorization_endpoint","revocation_endpoint"],"sources":["common.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { processRevocationResponse, revocationRequest } from \"oauth4webapi\";\nimport invariant from \"tiny-invariant\";\nimport { TypedEventTarget } from \"typescript-event-target\";\nimport { throwIfError } from \"./throwIfError.js\";\n// Node 18 is supposed to have a `CustomEvent` but it is not exposed on `globalThis`\n// which creates a problem for making a single codebase for node and browser. This polyfill works around it\nconst CustomEvent = process.env.TARGET === \"browser\"\n ? globalThis.CustomEvent\n : globalThis.CustomEvent\n ?? class CustomEvent extends Event {\n #detail;\n constructor(type, options) {\n super(type, options);\n this.#detail = options?.detail ?? null;\n }\n get detail() {\n return this.#detail;\n }\n };\nexport function saveLocal(client, x) {\n // MUST `localStorage?` as nodejs does not have localStorage\n globalThis.localStorage?.setItem(`@osdk/oauth : refresh : ${client.client_id}`, JSON.stringify(x));\n}\nexport function removeLocal(client) {\n // MUST `localStorage?` as nodejs does not have localStorage\n globalThis.localStorage?.removeItem(`@osdk/oauth : refresh : ${client.client_id}`);\n}\nexport function readLocal(client) {\n return JSON.parse(\n // MUST `localStorage?` as nodejs does not have localStorage\n globalThis.localStorage?.getItem(`@osdk/oauth : refresh : ${client.client_id}`)\n ?? \"{}\");\n}\nexport function common(client, as, _signIn, oauthHttpOptions, refresh) {\n let token;\n const eventTarget = new TypedEventTarget();\n function makeTokenAndSaveRefresh(resp, type) {\n const { refresh_token, expires_in, access_token } = resp;\n invariant(expires_in != null);\n saveLocal(client, { refresh_token });\n token = {\n refresh_token,\n expires_in,\n access_token,\n expires_at: Date.now() + expires_in * 1000,\n };\n eventTarget.dispatchTypedEvent(type, new CustomEvent(type, { detail: token }));\n return token;\n }\n let refreshTimeout;\n function rmTimeout() {\n if (refreshTimeout)\n clearTimeout(refreshTimeout);\n }\n function restartRefreshTimer(evt) {\n if (refresh) {\n rmTimeout();\n refreshTimeout = setTimeout(refresh, evt.detail.expires_in * 1000 - 60 * 1000);\n }\n }\n async function signOut() {\n invariant(token, \"not signed in\");\n const result = await processRevocationResponse(await revocationRequest(as, client, token.access_token, oauthHttpOptions));\n rmTimeout();\n // Clean up\n removeLocal(client);\n token = undefined;\n throwIfError(result);\n eventTarget.dispatchTypedEvent(\"signOut\", new Event(\"signOut\"));\n }\n let pendingSignIn;\n async function signIn() {\n if (pendingSignIn) {\n return pendingSignIn;\n }\n try {\n pendingSignIn = _signIn();\n return await pendingSignIn;\n }\n finally {\n pendingSignIn = undefined;\n }\n }\n eventTarget.addEventListener(\"signIn\", restartRefreshTimer);\n eventTarget.addEventListener(\"refresh\", restartRefreshTimer);\n function getTokenOrUndefined() {\n if (!token || Date.now() >= token.expires_at) {\n return undefined;\n }\n return token?.access_token;\n }\n const getToken = Object.assign(async function getToken() {\n if (!token || Date.now() >= token.expires_at) {\n token = await signIn();\n }\n return token?.access_token;\n }, {\n signIn,\n refresh,\n signOut,\n rmTimeout,\n getTokenOrUndefined,\n addEventListener: eventTarget.addEventListener.bind(eventTarget),\n removeEventListener: eventTarget.removeEventListener.bind(eventTarget),\n });\n return { getToken, makeTokenAndSaveRefresh };\n}\nexport function createAuthorizationServer(ctxPath, url) {\n const issuer = `${new URL(ctxPath, url)}`;\n return {\n token_endpoint: `${issuer}/api/oauth2/token`,\n authorization_endpoint: `${issuer}/api/oauth2/authorize`,\n revocation_endpoint: `${issuer}/api/oauth2/revoke_token`,\n issuer,\n };\n}\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createConfidentialOauthClient.d.ts","sourceRoot":"","sources":["../../src/createConfidentialOauthClient.ts"],"names":[],"mappings":"AAuBA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,8BAA8B,CAAC;AAG5E;;;;;;;;GAQG;AACH,wBAAgB,6BAA6B,CAC3C,SAAS,EAAE,MAAM,EACjB,aAAa,EAAE,MAAM,EACrB,GAAG,EAAE,MAAM,EACX,MAAM,GAAE,MAAM,EAAwC,EACtD,OAAO,GAAE,OAAO,UAAU,CAAC,KAAwB,EACnD,OAAO,GAAE,
|
|
1
|
+
{"version":3,"file":"createConfidentialOauthClient.d.ts","sourceRoot":"","sources":["../../src/createConfidentialOauthClient.ts"],"names":[],"mappings":"AAuBA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,8BAA8B,CAAC;AAG5E;;;;;;;;GAQG;AACH,wBAAgB,6BAA6B,CAC3C,SAAS,EAAE,MAAM,EACjB,aAAa,EAAE,MAAM,EACrB,GAAG,EAAE,MAAM,EACX,MAAM,GAAE,MAAM,EAAwC,EACtD,OAAO,GAAE,OAAO,UAAU,CAAC,KAAwB,EACnD,OAAO,GAAE,MAAoB,GAC5B,uBAAuB,CAgCzB"}
|
|
@@ -25,7 +25,7 @@ import { throwIfError } from "./throwIfError.js";
|
|
|
25
25
|
* @param ctxPath
|
|
26
26
|
* @returns which can be used as a token provider
|
|
27
27
|
*/
|
|
28
|
-
export function createConfidentialOauthClient(client_id, client_secret, url, scopes = ["api:read-data", "api:write-data"], fetchFn = globalThis.fetch, ctxPath = "
|
|
28
|
+
export function createConfidentialOauthClient(client_id, client_secret, url, scopes = ["api:read-data", "api:write-data"], fetchFn = globalThis.fetch, ctxPath = "multipass") {
|
|
29
29
|
const client = {
|
|
30
30
|
client_id,
|
|
31
31
|
client_secret
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createConfidentialOauthClient.js","names":["clientCredentialsGrantRequest","customFetch","processClientCredentialsResponse","common","createAuthorizationServer","throwIfError","createConfidentialOauthClient","client_id","client_secret","url","scopes","fetchFn","globalThis","fetch","ctxPath","client","authServer","oauthHttpOptions","getToken","makeTokenAndSaveRefresh","URLSearchParams","scope","join","undefined"],"sources":["createConfidentialOauthClient.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { clientCredentialsGrantRequest, customFetch, processClientCredentialsResponse, } from \"oauth4webapi\";\nimport { common, createAuthorizationServer } from \"./common.js\";\nimport { throwIfError } from \"./throwIfError.js\";\n/**\n * @param client_id\n * @param client_secret\n * @param url the base url of your foundry server\n * @param scopes\n * @param fetchFn\n * @param ctxPath\n * @returns which can be used as a token provider\n */\nexport function createConfidentialOauthClient(client_id, client_secret, url, scopes = [\"api:read-data\", \"api:write-data\"], fetchFn = globalThis.fetch, ctxPath = \"
|
|
1
|
+
{"version":3,"file":"createConfidentialOauthClient.js","names":["clientCredentialsGrantRequest","customFetch","processClientCredentialsResponse","common","createAuthorizationServer","throwIfError","createConfidentialOauthClient","client_id","client_secret","url","scopes","fetchFn","globalThis","fetch","ctxPath","client","authServer","oauthHttpOptions","getToken","makeTokenAndSaveRefresh","URLSearchParams","scope","join","undefined"],"sources":["createConfidentialOauthClient.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { clientCredentialsGrantRequest, customFetch, processClientCredentialsResponse, } from \"oauth4webapi\";\nimport { common, createAuthorizationServer } from \"./common.js\";\nimport { throwIfError } from \"./throwIfError.js\";\n/**\n * @param client_id\n * @param client_secret\n * @param url the base url of your foundry server\n * @param scopes\n * @param fetchFn\n * @param ctxPath\n * @returns which can be used as a token provider\n */\nexport function createConfidentialOauthClient(client_id, client_secret, url, scopes = [\"api:read-data\", \"api:write-data\"], fetchFn = globalThis.fetch, ctxPath = \"multipass\") {\n const client = { client_id, client_secret };\n const authServer = createAuthorizationServer(ctxPath, url);\n const oauthHttpOptions = { [customFetch]: fetchFn };\n const { getToken, makeTokenAndSaveRefresh } = common(client, authServer, _signIn, oauthHttpOptions, undefined);\n async function _signIn() {\n return makeTokenAndSaveRefresh(throwIfError(await processClientCredentialsResponse(authServer, client, await clientCredentialsGrantRequest(authServer, client, new URLSearchParams({ scope: scopes.join(\" \") }), oauthHttpOptions))), \"signIn\");\n }\n return getToken;\n}\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAASA,6BAA6B,EAAEC,WAAW,EAAEC,gCAAgC,QAAS,cAAc;AAC5G,SAASC,MAAM,EAAEC,yBAAyB,QAAQ,aAAa;AAC/D,SAASC,YAAY,QAAQ,mBAAmB;AAChD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO,SAASC,6BAA6BA,CAACC,SAAS,EAAEC,aAAa,EAAEC,GAAG,EAAEC,MAAM,GAAG,CAAC,eAAe,EAAE,gBAAgB,CAAC,EAAEC,OAAO,GAAGC,UAAU,CAACC,KAAK,EAAEC,OAAO,GAAG,WAAW,EAAE;EAC1K,MAAMC,MAAM,GAAG;IAAER,SAAS;IAAEC;EAAc,CAAC;EAC3C,MAAMQ,UAAU,GAAGZ,yBAAyB,CAACU,OAAO,EAAEL,GAAG,CAAC;EAC1D,MAAMQ,gBAAgB,GAAG;IAAE,CAAChB,WAAW,GAAGU;EAAQ,CAAC;EACnD,MAAM;IAAEO,QAAQ;IAAEC;EAAwB,CAAC,GAAGhB,MAAM,CAACY,MAAM,EAAEC,UAAU,EACvE,kBAAyB;IACrB,OAAOG,uBAAuB,CAACd,YAAY,CAAC,MAAMH,gCAAgC,CAACc,UAAU,EAAED,MAAM,EAAE,MAAMf,6BAA6B,CAACgB,UAAU,EAAED,MAAM,EAAE,IAAIK,eAAe,CAAC;MAAEC,KAAK,EAAEX,MAAM,CAACY,IAAI,CAAC,GAAG;IAAE,CAAC,CAAC,EAAEL,gBAAgB,CAAC,CAAC,CAAC,EAAE,QAAQ,CAAC;EACnP,CAAC,EAHiFA,gBAAgB,EAAEM,SAAS,CAAC;EAI9G,OAAOL,QAAQ;AACnB","ignoreList":[]}
|
|
@@ -21,7 +21,7 @@ export interface PublicOauthClientOptions {
|
|
|
21
21
|
*/
|
|
22
22
|
fetchFn?: typeof globalThis.fetch;
|
|
23
23
|
/**
|
|
24
|
-
* Context path for the authorization server (defaults to "
|
|
24
|
+
* Context path for the authorization server (defaults to "multipass")
|
|
25
25
|
*/
|
|
26
26
|
ctxPath?: string;
|
|
27
27
|
}
|
|
@@ -46,7 +46,7 @@ export declare function createPublicOauthClient(clientId: string, url: string, r
|
|
|
46
46
|
* @param {string} postLoginPage - URL to return to after completed authentication cycle (defaults to `window.location.toString()`)
|
|
47
47
|
* @param {string[]} scopes - OAuth scopes to request. If not provided, defaults to `["api:read-data", "api:write-data"]`
|
|
48
48
|
* @param {typeof globalThis.fetch} fetchFn - Custom fetch function to use for requests (defaults to `globalThis.fetch`)
|
|
49
|
-
* @param {string} ctxPath - Context path for the authorization server (defaults to "
|
|
49
|
+
* @param {string} ctxPath - Context path for the authorization server (defaults to "multipass")
|
|
50
50
|
* @returns {PublicOauthClient} A client that can be used as a token provider
|
|
51
51
|
*/
|
|
52
52
|
export declare function createPublicOauthClient(client_id: string, url: string, redirectUrl: string, useHistory?: boolean, loginPage?: string, postLoginPage?: string, scopes?: string[], fetchFn?: typeof globalThis.fetch, ctxPath?: string): PublicOauthClient;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"publicOauth.test.d.ts","sourceRoot":"","sources":["../../src/publicOauth.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,242 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2024 Palantir Technologies, Inc. All rights reserved.
|
|
3
|
+
*
|
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
+
* you may not use this file except in compliance with the License.
|
|
6
|
+
* You may obtain a copy of the License at
|
|
7
|
+
*
|
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
+
*
|
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
+
* See the License for the specific language governing permissions and
|
|
14
|
+
* limitations under the License.
|
|
15
|
+
*/
|
|
16
|
+
/* eslint-disable @typescript-eslint/consistent-type-imports */
|
|
17
|
+
import { afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
|
|
18
|
+
import * as commonJs from "./common.js";
|
|
19
|
+
import { createPublicOauthClient } from "./createPublicOauthClient.js";
|
|
20
|
+
const hoistedMocks = vi.hoisted(() => {
|
|
21
|
+
return {
|
|
22
|
+
makeTokenAndSaveRefresh: vi.fn()
|
|
23
|
+
};
|
|
24
|
+
});
|
|
25
|
+
vi.mock("delay", async importOriginal => {
|
|
26
|
+
const original = await importOriginal();
|
|
27
|
+
return {
|
|
28
|
+
default: vi.fn((ms, opts) => {
|
|
29
|
+
// speed up the tests
|
|
30
|
+
return original.default(ms / 100, opts);
|
|
31
|
+
})
|
|
32
|
+
};
|
|
33
|
+
});
|
|
34
|
+
vi.mock("./common.js", async importOriginal => {
|
|
35
|
+
const original = await importOriginal();
|
|
36
|
+
return {
|
|
37
|
+
...original,
|
|
38
|
+
common: vi.fn((...args) => {
|
|
39
|
+
const result = original.common(...args);
|
|
40
|
+
return {
|
|
41
|
+
...result,
|
|
42
|
+
makeTokenAndSaveRefresh: hoistedMocks.makeTokenAndSaveRefresh
|
|
43
|
+
};
|
|
44
|
+
}),
|
|
45
|
+
readLocal: vi.spyOn(original, "readLocal")
|
|
46
|
+
// vi.fn(original.readLocal),
|
|
47
|
+
};
|
|
48
|
+
});
|
|
49
|
+
vi.mock("oauth4webapi");
|
|
50
|
+
describe(createPublicOauthClient, () => {
|
|
51
|
+
const DEFAULT_CUR_URL = new URL("https://fauxurl");
|
|
52
|
+
const fetchFn = vi.fn();
|
|
53
|
+
const mockWindow = {
|
|
54
|
+
location: {
|
|
55
|
+
toString: vi.fn(() => DEFAULT_CUR_URL),
|
|
56
|
+
assign: vi.fn(),
|
|
57
|
+
href: DEFAULT_CUR_URL.href,
|
|
58
|
+
pathname: DEFAULT_CUR_URL.pathname
|
|
59
|
+
},
|
|
60
|
+
history: {
|
|
61
|
+
replaceState: vi.fn()
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
const mockLocalStorage = {
|
|
65
|
+
setItem: vi.fn(),
|
|
66
|
+
getItem: vi.fn(),
|
|
67
|
+
removeItem: vi.fn()
|
|
68
|
+
};
|
|
69
|
+
beforeEach(() => {
|
|
70
|
+
vi.restoreAllMocks();
|
|
71
|
+
fetchFn.mockRestore();
|
|
72
|
+
});
|
|
73
|
+
afterEach(() => {
|
|
74
|
+
vi.clearAllMocks();
|
|
75
|
+
fetchFn.mockReset();
|
|
76
|
+
});
|
|
77
|
+
beforeAll(() => {
|
|
78
|
+
vi.stubGlobal("window", mockWindow);
|
|
79
|
+
vi.stubGlobal("localStorage", mockLocalStorage);
|
|
80
|
+
});
|
|
81
|
+
afterAll(() => {
|
|
82
|
+
vi.unstubAllGlobals();
|
|
83
|
+
});
|
|
84
|
+
const BASE_CLIENT_ARGS = {
|
|
85
|
+
clientId: "this-would-be-client-id",
|
|
86
|
+
foundryUrl: "https://a.foundry.url.local",
|
|
87
|
+
redirectUrl: "https://my.redirect.url.local",
|
|
88
|
+
fetchFn
|
|
89
|
+
};
|
|
90
|
+
const fullLoginUrl = new URL("/loginPage", DEFAULT_CUR_URL);
|
|
91
|
+
describe.each([{
|
|
92
|
+
name: "Basic Usage",
|
|
93
|
+
currentUrl: DEFAULT_CUR_URL,
|
|
94
|
+
clientArgs: {
|
|
95
|
+
...BASE_CLIENT_ARGS
|
|
96
|
+
},
|
|
97
|
+
should: {
|
|
98
|
+
redirectToLoginPage: false
|
|
99
|
+
}
|
|
100
|
+
}, {
|
|
101
|
+
name: "Base w/ full loginPage and curUrl is root",
|
|
102
|
+
currentUrl: DEFAULT_CUR_URL,
|
|
103
|
+
clientArgs: {
|
|
104
|
+
...BASE_CLIENT_ARGS,
|
|
105
|
+
loginPage: fullLoginUrl.toString()
|
|
106
|
+
},
|
|
107
|
+
should: {
|
|
108
|
+
redirectToLoginPage: true
|
|
109
|
+
}
|
|
110
|
+
}, {
|
|
111
|
+
name: "Base w/ full loginPage and curUrl is login page",
|
|
112
|
+
currentUrl: fullLoginUrl,
|
|
113
|
+
clientArgs: {
|
|
114
|
+
...BASE_CLIENT_ARGS,
|
|
115
|
+
loginPage: fullLoginUrl.toString()
|
|
116
|
+
},
|
|
117
|
+
should: {
|
|
118
|
+
redirectToLoginPage: false
|
|
119
|
+
}
|
|
120
|
+
}, {
|
|
121
|
+
name: "Base w/ short loginPage and curUrl is root",
|
|
122
|
+
currentUrl: DEFAULT_CUR_URL,
|
|
123
|
+
clientArgs: {
|
|
124
|
+
...BASE_CLIENT_ARGS,
|
|
125
|
+
loginPage: "/loginPage"
|
|
126
|
+
},
|
|
127
|
+
should: {
|
|
128
|
+
redirectToLoginPage: true
|
|
129
|
+
}
|
|
130
|
+
}, {
|
|
131
|
+
name: "Base w/ short loginPage and curUrl is loginPage",
|
|
132
|
+
currentUrl: new URL("/loginPage", DEFAULT_CUR_URL),
|
|
133
|
+
clientArgs: {
|
|
134
|
+
...BASE_CLIENT_ARGS,
|
|
135
|
+
loginPage: "/loginPage"
|
|
136
|
+
},
|
|
137
|
+
should: {
|
|
138
|
+
redirectToLoginPage: false
|
|
139
|
+
}
|
|
140
|
+
}])("$name", ({
|
|
141
|
+
clientArgs,
|
|
142
|
+
currentUrl,
|
|
143
|
+
should
|
|
144
|
+
}) => {
|
|
145
|
+
let client;
|
|
146
|
+
beforeEach(() => {
|
|
147
|
+
client = createPublicOauthClient(clientArgs.clientId, clientArgs.foundryUrl, clientArgs.redirectUrl, clientArgs.useHistory, clientArgs.loginPage, clientArgs.postLoginPage, clientArgs.scopes, clientArgs.fetchFn, clientArgs.ctxPath);
|
|
148
|
+
mockWindow.location.href = new URL(currentUrl).href;
|
|
149
|
+
mockWindow.location.pathname = new URL(currentUrl).pathname;
|
|
150
|
+
});
|
|
151
|
+
it("calls common with expected values", () => {
|
|
152
|
+
expect(vi.mocked(commonJs.common)).toHaveBeenCalledWith(expect.objectContaining({
|
|
153
|
+
client_id: clientArgs.clientId,
|
|
154
|
+
token_endpoint_auth_method: "none"
|
|
155
|
+
}), commonJs.createAuthorizationServer(clientArgs.ctxPath ?? "/multipass", clientArgs.foundryUrl), expect.any(Function), expect.anything(), expect.any(Function));
|
|
156
|
+
});
|
|
157
|
+
describe.each([{
|
|
158
|
+
refresh_token: "a-refresh-token"
|
|
159
|
+
}, {
|
|
160
|
+
codeVerifier: "hi",
|
|
161
|
+
state: "mom",
|
|
162
|
+
oldUrl: "https://someoldurl.local"
|
|
163
|
+
}, {}])("Initial Local State: %s", initialLocalState => {
|
|
164
|
+
const ACCESS_TOKEN = (Math.random() + 1).toString(36).substring(7);
|
|
165
|
+
beforeEach(() => {
|
|
166
|
+
vi.mocked(commonJs.readLocal).mockImplementation(() => initialLocalState);
|
|
167
|
+
hoistedMocks.makeTokenAndSaveRefresh.mockImplementation(() => ({
|
|
168
|
+
access_token: ACCESS_TOKEN,
|
|
169
|
+
expires_at: Date.now(),
|
|
170
|
+
expires_in: 10000
|
|
171
|
+
}));
|
|
172
|
+
});
|
|
173
|
+
if (Object.keys(initialLocalState).length === 0) {
|
|
174
|
+
if (should.redirectToLoginPage) {
|
|
175
|
+
it("redirects to login page", async () => {
|
|
176
|
+
const tokenPromise = client();
|
|
177
|
+
expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);
|
|
178
|
+
if (should.redirectToLoginPage) {
|
|
179
|
+
// expect save local
|
|
180
|
+
await expect(tokenPromise).resolves.toBeUndefined();
|
|
181
|
+
expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({
|
|
182
|
+
oldUrl: window.location.toString()
|
|
183
|
+
}));
|
|
184
|
+
expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, "", clientArgs.loginPage);
|
|
185
|
+
}
|
|
186
|
+
});
|
|
187
|
+
} else {
|
|
188
|
+
it("redirects to multipass", async () => {
|
|
189
|
+
const tokenPromise = client();
|
|
190
|
+
expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);
|
|
191
|
+
if (should.redirectToLoginPage) {
|
|
192
|
+
// expect save local
|
|
193
|
+
await expect(tokenPromise).resolves.toBeUndefined();
|
|
194
|
+
expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({
|
|
195
|
+
oldUrl: window.location.toString()
|
|
196
|
+
}));
|
|
197
|
+
expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, "", clientArgs.loginPage);
|
|
198
|
+
return;
|
|
199
|
+
}
|
|
200
|
+
// we assume window.location.assign will take you away therefore we
|
|
201
|
+
// also have to expect in this scenario that the thrown error happens
|
|
202
|
+
await expect(tokenPromise).rejects.toThrowError(new Error("Unable to redirect"));
|
|
203
|
+
expect(mockWindow.location.assign).toHaveBeenCalledOnce();
|
|
204
|
+
const url = new URL(mockWindow.location.assign.mock.calls[0][0]);
|
|
205
|
+
expect(url.origin).toEqual(clientArgs.foundryUrl);
|
|
206
|
+
expect(url.pathname).toEqual("/multipass/api/oauth2/authorize");
|
|
207
|
+
expect(Object.fromEntries(url.searchParams.entries())).toEqual(expect.objectContaining({
|
|
208
|
+
client_id: clientArgs.clientId,
|
|
209
|
+
code_challenge: expect.any(String),
|
|
210
|
+
redirect_uri: clientArgs.redirectUrl,
|
|
211
|
+
response_type: "code",
|
|
212
|
+
code_challenge_method: "S256",
|
|
213
|
+
scope: "offline_access api:read-data api:write-data",
|
|
214
|
+
state: expect.any(String)
|
|
215
|
+
}));
|
|
216
|
+
});
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
if (initialLocalState.codeVerifier) {
|
|
220
|
+
it("tries to auth with return results", async () => {
|
|
221
|
+
await expect(client()).resolves.toEqual(ACCESS_TOKEN);
|
|
222
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);
|
|
223
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined,
|
|
224
|
+
// this is only because we didn't mock out the internals
|
|
225
|
+
"signIn");
|
|
226
|
+
expect(mockWindow.history.replaceState).toHaveBeenCalledTimes(1);
|
|
227
|
+
expect(mockWindow.history.replaceState).toBeCalledWith(expect.anything(), expect.anything(), initialLocalState.oldUrl);
|
|
228
|
+
});
|
|
229
|
+
}
|
|
230
|
+
if (initialLocalState.refresh_token) {
|
|
231
|
+
it("refreshes", async () => {
|
|
232
|
+
await expect(client()).resolves.toEqual(ACCESS_TOKEN);
|
|
233
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);
|
|
234
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined,
|
|
235
|
+
// this is only because we didn't mock out the internals
|
|
236
|
+
"refresh");
|
|
237
|
+
});
|
|
238
|
+
}
|
|
239
|
+
});
|
|
240
|
+
});
|
|
241
|
+
});
|
|
242
|
+
//# sourceMappingURL=publicOauth.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"publicOauth.test.js","names":["afterAll","afterEach","beforeAll","beforeEach","describe","expect","it","vi","commonJs","createPublicOauthClient","hoistedMocks","hoisted","makeTokenAndSaveRefresh","fn","mock","importOriginal","original","default","ms","opts","common","args","result","readLocal","spyOn","DEFAULT_CUR_URL","URL","fetchFn","mockWindow","location","toString","assign","href","pathname","history","replaceState","mockLocalStorage","setItem","getItem","removeItem","restoreAllMocks","mockRestore","clearAllMocks","mockReset","stubGlobal","unstubAllGlobals","BASE_CLIENT_ARGS","clientId","foundryUrl","redirectUrl","fullLoginUrl","each","name","currentUrl","clientArgs","should","redirectToLoginPage","loginPage","client","useHistory","postLoginPage","scopes","ctxPath","mocked","toHaveBeenCalledWith","objectContaining","client_id","token_endpoint_auth_method","createAuthorizationServer","any","Function","anything","refresh_token","codeVerifier","state","oldUrl","initialLocalState","ACCESS_TOKEN","Math","random","substring","mockImplementation","access_token","expires_at","Date","now","expires_in","Object","keys","length","tokenPromise","toBeCalledTimes","resolves","toBeUndefined","toBeCalledWith","JSON","stringify","window","rejects","toThrowError","Error","toHaveBeenCalledOnce","url","calls","origin","toEqual","fromEntries","searchParams","entries","code_challenge","String","redirect_uri","response_type","code_challenge_method","scope","toHaveBeenCalledTimes","undefined"],"sources":["publicOauth.test.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n/* eslint-disable @typescript-eslint/consistent-type-imports */\nimport { afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi, } from \"vitest\";\nimport * as commonJs from \"./common.js\";\nimport { createPublicOauthClient } from \"./createPublicOauthClient.js\";\nconst hoistedMocks = vi.hoisted(() => {\n return {\n makeTokenAndSaveRefresh: vi.fn(),\n };\n});\nvi.mock(\"delay\", async (importOriginal) => {\n const original = await importOriginal();\n return {\n default: vi.fn((ms, opts) => {\n // speed up the tests\n return original.default(ms / 100, opts);\n }),\n };\n});\nvi.mock(\"./common.js\", async (importOriginal) => {\n const original = await importOriginal();\n return {\n ...original,\n common: vi.fn((...args) => {\n const result = original.common(...args);\n return {\n ...result,\n makeTokenAndSaveRefresh: hoistedMocks.makeTokenAndSaveRefresh,\n };\n }),\n readLocal: vi.spyOn(original, \"readLocal\"),\n // vi.fn(original.readLocal),\n };\n});\nvi.mock(\"oauth4webapi\");\ndescribe(createPublicOauthClient, () => {\n const DEFAULT_CUR_URL = new URL(\"https://fauxurl\");\n const fetchFn = vi.fn();\n const mockWindow = {\n location: {\n toString: vi.fn(() => DEFAULT_CUR_URL),\n assign: vi.fn(),\n href: DEFAULT_CUR_URL.href,\n pathname: DEFAULT_CUR_URL.pathname,\n },\n history: {\n replaceState: vi.fn(),\n },\n };\n const mockLocalStorage = {\n setItem: vi.fn(),\n getItem: vi.fn(),\n removeItem: vi.fn(),\n };\n beforeEach((context) => {\n vi.restoreAllMocks();\n fetchFn.mockRestore();\n });\n afterEach((context) => {\n vi.clearAllMocks();\n fetchFn.mockReset();\n });\n beforeAll(() => {\n vi.stubGlobal(\"window\", mockWindow);\n vi.stubGlobal(\"localStorage\", mockLocalStorage);\n });\n afterAll(() => {\n vi.unstubAllGlobals();\n });\n const BASE_CLIENT_ARGS = {\n clientId: \"this-would-be-client-id\",\n foundryUrl: \"https://a.foundry.url.local\",\n redirectUrl: \"https://my.redirect.url.local\",\n fetchFn,\n };\n const fullLoginUrl = new URL(\"/loginPage\", DEFAULT_CUR_URL);\n describe.each([\n {\n name: \"Basic Usage\",\n currentUrl: DEFAULT_CUR_URL,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n },\n should: {\n redirectToLoginPage: false,\n },\n },\n {\n name: \"Base w/ full loginPage and curUrl is root\",\n currentUrl: DEFAULT_CUR_URL,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: fullLoginUrl.toString(),\n },\n should: {\n redirectToLoginPage: true,\n },\n },\n {\n name: \"Base w/ full loginPage and curUrl is login page\",\n currentUrl: fullLoginUrl,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: fullLoginUrl.toString(),\n },\n should: {\n redirectToLoginPage: false,\n },\n },\n {\n name: \"Base w/ short loginPage and curUrl is root\",\n currentUrl: DEFAULT_CUR_URL,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: \"/loginPage\",\n },\n should: {\n redirectToLoginPage: true,\n },\n },\n {\n name: \"Base w/ short loginPage and curUrl is loginPage\",\n currentUrl: new URL(\"/loginPage\", DEFAULT_CUR_URL),\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: \"/loginPage\",\n },\n should: {\n redirectToLoginPage: false,\n },\n },\n ])(\"$name\", ({ clientArgs, currentUrl, should }) => {\n let client;\n beforeEach(() => {\n client = createPublicOauthClient(clientArgs.clientId, clientArgs.foundryUrl, clientArgs.redirectUrl, clientArgs.useHistory, clientArgs.loginPage, clientArgs.postLoginPage, clientArgs.scopes, clientArgs.fetchFn, clientArgs.ctxPath);\n mockWindow.location.href = new URL(currentUrl).href;\n mockWindow.location.pathname = new URL(currentUrl).pathname;\n });\n it(\"calls common with expected values\", () => {\n expect(vi.mocked(commonJs.common)).toHaveBeenCalledWith(expect.objectContaining({\n client_id: clientArgs.clientId,\n token_endpoint_auth_method: \"none\",\n }), commonJs.createAuthorizationServer(clientArgs.ctxPath ?? \"/multipass\", clientArgs.foundryUrl), expect.any(Function), expect.anything(), expect.any(Function));\n });\n describe.each([\n {\n refresh_token: \"a-refresh-token\",\n },\n {\n codeVerifier: \"hi\",\n state: \"mom\",\n oldUrl: \"https://someoldurl.local\",\n },\n {},\n ])(\"Initial Local State: %s\", (initialLocalState) => {\n const ACCESS_TOKEN = (Math.random() + 1).toString(36).substring(7);\n beforeEach(() => {\n vi.mocked(commonJs.readLocal).mockImplementation(() => initialLocalState);\n hoistedMocks.makeTokenAndSaveRefresh.mockImplementation(() => ({\n access_token: ACCESS_TOKEN,\n expires_at: Date.now(),\n expires_in: 10000,\n }));\n });\n if (Object.keys(initialLocalState).length === 0) {\n if (should.redirectToLoginPage) {\n it(\"redirects to login page\", async () => {\n const tokenPromise = client();\n expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);\n if (should.redirectToLoginPage) {\n // expect save local\n await expect(tokenPromise).resolves.toBeUndefined();\n expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({ oldUrl: window.location.toString() }));\n expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, \"\", clientArgs.loginPage);\n return;\n }\n });\n }\n else {\n it(\"redirects to multipass\", async () => {\n const tokenPromise = client();\n expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);\n if (should.redirectToLoginPage) {\n // expect save local\n await expect(tokenPromise).resolves.toBeUndefined();\n expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({ oldUrl: window.location.toString() }));\n expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, \"\", clientArgs.loginPage);\n return;\n }\n // we assume window.location.assign will take you away therefore we\n // also have to expect in this scenario that the thrown error happens\n await expect(tokenPromise)\n .rejects.toThrowError(new Error(\"Unable to redirect\"));\n expect(mockWindow.location.assign).toHaveBeenCalledOnce();\n const url = new URL(mockWindow.location.assign.mock.calls[0][0]);\n expect(url.origin).toEqual(clientArgs.foundryUrl);\n expect(url.pathname).toEqual(\"/multipass/api/oauth2/authorize\");\n expect(Object.fromEntries(url.searchParams.entries())).toEqual(expect.objectContaining({\n client_id: clientArgs.clientId,\n code_challenge: expect.any(String),\n redirect_uri: clientArgs.redirectUrl,\n response_type: \"code\",\n code_challenge_method: \"S256\",\n scope: \"offline_access api:read-data api:write-data\",\n state: expect.any(String),\n }));\n });\n }\n }\n if (initialLocalState.codeVerifier) {\n it(\"tries to auth with return results\", async () => {\n await expect(client()).resolves.toEqual(ACCESS_TOKEN);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined, // this is only because we didn't mock out the internals\n \"signIn\");\n expect(mockWindow.history.replaceState).toHaveBeenCalledTimes(1);\n expect(mockWindow.history.replaceState).toBeCalledWith(expect.anything(), expect.anything(), initialLocalState.oldUrl);\n });\n }\n if (initialLocalState.refresh_token) {\n it(\"refreshes\", async () => {\n await expect(client()).resolves.toEqual(ACCESS_TOKEN);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined, // this is only because we didn't mock out the internals\n \"refresh\");\n });\n }\n });\n });\n});\n"],"mappings":"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","ignoreList":[]}
|
package/build/browser/utils.js
CHANGED
|
@@ -38,7 +38,7 @@ export function processOptionsAndAssignDefaults(url, redirect_uri, useHistory, l
|
|
|
38
38
|
postLoginPage: options.postLoginPage || window.location.toString(),
|
|
39
39
|
scopes: options.scopes ?? ["api:read-data", "api:write-data"],
|
|
40
40
|
fetchFn: options.fetchFn ?? globalThis.fetch,
|
|
41
|
-
ctxPath: options.ctxPath ?? "
|
|
41
|
+
ctxPath: options.ctxPath ?? "multipass"
|
|
42
42
|
};
|
|
43
43
|
}
|
|
44
44
|
//# sourceMappingURL=utils.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.js","names":["invariant","processOptionsAndAssignDefaults","url","redirect_uri","useHistory","loginPage","postLoginPage","scopes","fetchFn","ctxPath","options","process","env","NODE_ENV","window","location","toString","globalThis","fetch"],"sources":["utils.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport invariant from \"tiny-invariant\";\nexport function processOptionsAndAssignDefaults(url, redirect_uri, useHistory, loginPage, postLoginPage, scopes, fetchFn, ctxPath) {\n let options = {};\n if (typeof useHistory === \"object\") {\n invariant(!loginPage && !postLoginPage && !scopes && !fetchFn && !ctxPath, \"If useHistory is an object, other options should not be provided\");\n options = useHistory;\n }\n else {\n options = {\n useHistory,\n loginPage,\n postLoginPage,\n scopes,\n fetchFn,\n ctxPath,\n };\n }\n invariant(url, \"url is required\");\n invariant(redirect_uri, \"redirectUrl is required\");\n // Assign defaults\n return {\n useHistory: options.useHistory ?? true,\n loginPage: options.loginPage,\n postLoginPage: options.postLoginPage || window.location.toString(),\n scopes: options.scopes ?? [\"api:read-data\", \"api:write-data\"],\n fetchFn: options.fetchFn ?? globalThis.fetch,\n ctxPath: options.ctxPath ?? \"
|
|
1
|
+
{"version":3,"file":"utils.js","names":["invariant","processOptionsAndAssignDefaults","url","redirect_uri","useHistory","loginPage","postLoginPage","scopes","fetchFn","ctxPath","options","process","env","NODE_ENV","window","location","toString","globalThis","fetch"],"sources":["utils.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport invariant from \"tiny-invariant\";\nexport function processOptionsAndAssignDefaults(url, redirect_uri, useHistory, loginPage, postLoginPage, scopes, fetchFn, ctxPath) {\n let options = {};\n if (typeof useHistory === \"object\") {\n invariant(!loginPage && !postLoginPage && !scopes && !fetchFn && !ctxPath, \"If useHistory is an object, other options should not be provided\");\n options = useHistory;\n }\n else {\n options = {\n useHistory,\n loginPage,\n postLoginPage,\n scopes,\n fetchFn,\n ctxPath,\n };\n }\n invariant(url, \"url is required\");\n invariant(redirect_uri, \"redirectUrl is required\");\n // Assign defaults\n return {\n useHistory: options.useHistory ?? true,\n loginPage: options.loginPage,\n postLoginPage: options.postLoginPage || window.location.toString(),\n scopes: options.scopes ?? [\"api:read-data\", \"api:write-data\"],\n fetchFn: options.fetchFn ?? globalThis.fetch,\n ctxPath: options.ctxPath ?? \"multipass\",\n };\n}\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAOA,SAAS,MAAM,gBAAgB;AACtC,OAAO,SAASC,+BAA+BA,CAACC,GAAG,EAAEC,YAAY,EAAEC,UAAU,EAAEC,SAAS,EAAEC,aAAa,EAAEC,MAAM,EAAEC,OAAO,EAAEC,OAAO,EAAE;EAC/H,IAAIC,OAAO,GAAG,CAAC,CAAC;EAChB,IAAI,OAAON,UAAU,KAAK,QAAQ,EAAE;IAChC,EAAU,CAACC,SAAS,IAAI,CAACC,aAAa,IAAI,CAACC,MAAM,IAAI,CAACC,OAAO,IAAI,CAACC,OAAO,IAAAE,OAAA,CAAAC,GAAA,CAAAC,QAAA,oBAAzEb,SAAS,QAAkE,kEAAkE,IAA7IA,SAAS;IACTU,OAAO,GAAGN,UAAU;EACxB,CAAC,MACI;IACDM,OAAO,GAAG;MACNN,UAAU;MACVC,SAAS;MACTC,aAAa;MACbC,MAAM;MACNC,OAAO;MACPC;IACJ,CAAC;EACL;EACA,CAAUP,GAAG,GAAAS,OAAA,CAAAC,GAAA,CAAAC,QAAA,oBAAbb,SAAS,QAAM,iBAAiB,IAAhCA,SAAS;EACT,CAAUG,YAAY,GAAAQ,OAAA,CAAAC,GAAA,CAAAC,QAAA,oBAAtBb,SAAS,QAAe,yBAAyB,IAAjDA,SAAS;EACT;EACA,OAAO;IACHI,UAAU,EAAEM,OAAO,CAACN,UAAU,IAAI,IAAI;IACtCC,SAAS,EAAEK,OAAO,CAACL,SAAS;IAC5BC,aAAa,EAAEI,OAAO,CAACJ,aAAa,IAAIQ,MAAM,CAACC,QAAQ,CAACC,QAAQ,CAAC,CAAC;IAClET,MAAM,EAAEG,OAAO,CAACH,MAAM,IAAI,CAAC,eAAe,EAAE,gBAAgB,CAAC;IAC7DC,OAAO,EAAEE,OAAO,CAACF,OAAO,IAAIS,UAAU,CAACC,KAAK;IAC5CT,OAAO,EAAEC,OAAO,CAACD,OAAO,IAAI;EAChC,CAAC;AACL","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AuthorizationServer.test.d.ts","sourceRoot":"","sources":["../../src/AuthorizationServer.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2024 Palantir Technologies, Inc. All rights reserved.
|
|
3
|
+
*
|
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
+
* you may not use this file except in compliance with the License.
|
|
6
|
+
* You may obtain a copy of the License at
|
|
7
|
+
*
|
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
+
*
|
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
+
* See the License for the specific language governing permissions and
|
|
14
|
+
* limitations under the License.
|
|
15
|
+
*/
|
|
16
|
+
import { describe, expect, it } from "vitest";
|
|
17
|
+
import { createAuthorizationServer } from "./common.js";
|
|
18
|
+
describe("Create authorization server", () => {
|
|
19
|
+
it("works with old multipass ctx path", () => {
|
|
20
|
+
const authServer = createAuthorizationServer("/multipass", "https://stack.palantir.com");
|
|
21
|
+
expect(authServer).toEqual({
|
|
22
|
+
token_endpoint: "https://stack.palantir.com/multipass/api/oauth2/token",
|
|
23
|
+
authorization_endpoint: "https://stack.palantir.com/multipass/api/oauth2/authorize",
|
|
24
|
+
revocation_endpoint: "https://stack.palantir.com/multipass/api/oauth2/revoke_token",
|
|
25
|
+
issuer: "https://stack.palantir.com/multipass"
|
|
26
|
+
});
|
|
27
|
+
});
|
|
28
|
+
it("works with new multipass ctx path", () => {
|
|
29
|
+
const authServer = createAuthorizationServer("multipass", "https://stack.palantir.com");
|
|
30
|
+
expect(authServer).toEqual({
|
|
31
|
+
token_endpoint: "https://stack.palantir.com/multipass/api/oauth2/token",
|
|
32
|
+
authorization_endpoint: "https://stack.palantir.com/multipass/api/oauth2/authorize",
|
|
33
|
+
revocation_endpoint: "https://stack.palantir.com/multipass/api/oauth2/revoke_token",
|
|
34
|
+
issuer: "https://stack.palantir.com/multipass"
|
|
35
|
+
});
|
|
36
|
+
const authServerCustom = createAuthorizationServer("multipass", "https://stack.palantir.com/foo/first/someStuff");
|
|
37
|
+
expect(authServerCustom).toEqual({
|
|
38
|
+
token_endpoint: "https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/token",
|
|
39
|
+
authorization_endpoint: "https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/authorize",
|
|
40
|
+
revocation_endpoint: "https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/revoke_token",
|
|
41
|
+
issuer: "https://stack.palantir.com/foo/first/someStuff/multipass"
|
|
42
|
+
});
|
|
43
|
+
});
|
|
44
|
+
});
|
|
45
|
+
//# sourceMappingURL=AuthorizationServer.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AuthorizationServer.test.js","names":["describe","expect","it","createAuthorizationServer","authServer","toEqual","token_endpoint","authorization_endpoint","revocation_endpoint","issuer","authServerCustom"],"sources":["AuthorizationServer.test.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { describe, expect, it, } from \"vitest\";\nimport { createAuthorizationServer } from \"./common.js\";\ndescribe(\"Create authorization server\", () => {\n it(\"works with old multipass ctx path\", () => {\n const authServer = createAuthorizationServer(\"/multipass\", \"https://stack.palantir.com\");\n expect(authServer).toEqual({\n token_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/token\",\n authorization_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/authorize\",\n revocation_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/revoke_token\",\n issuer: \"https://stack.palantir.com/multipass\",\n });\n });\n it(\"works with new multipass ctx path\", () => {\n const authServer = createAuthorizationServer(\"multipass\", \"https://stack.palantir.com\");\n expect(authServer).toEqual({\n token_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/token\",\n authorization_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/authorize\",\n revocation_endpoint: \"https://stack.palantir.com/multipass/api/oauth2/revoke_token\",\n issuer: \"https://stack.palantir.com/multipass\",\n });\n const authServerCustom = createAuthorizationServer(\"multipass\", \"https://stack.palantir.com/foo/first/someStuff\");\n expect(authServerCustom).toEqual({\n token_endpoint: \"https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/token\",\n authorization_endpoint: \"https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/authorize\",\n revocation_endpoint: \"https://stack.palantir.com/foo/first/someStuff/multipass/api/oauth2/revoke_token\",\n issuer: \"https://stack.palantir.com/foo/first/someStuff/multipass\",\n });\n });\n});\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAASA,QAAQ,EAAEC,MAAM,EAAEC,EAAE,QAAS,QAAQ;AAC9C,SAASC,yBAAyB,QAAQ,aAAa;AACvDH,QAAQ,CAAC,6BAA6B,EAAE,MAAM;EAC1CE,EAAE,CAAC,mCAAmC,EAAE,MAAM;IAC1C,MAAME,UAAU,GAAGD,yBAAyB,CAAC,YAAY,EAAE,4BAA4B,CAAC;IACxFF,MAAM,CAACG,UAAU,CAAC,CAACC,OAAO,CAAC;MACvBC,cAAc,EAAE,uDAAuD;MACvEC,sBAAsB,EAAE,2DAA2D;MACnFC,mBAAmB,EAAE,8DAA8D;MACnFC,MAAM,EAAE;IACZ,CAAC,CAAC;EACN,CAAC,CAAC;EACFP,EAAE,CAAC,mCAAmC,EAAE,MAAM;IAC1C,MAAME,UAAU,GAAGD,yBAAyB,CAAC,WAAW,EAAE,4BAA4B,CAAC;IACvFF,MAAM,CAACG,UAAU,CAAC,CAACC,OAAO,CAAC;MACvBC,cAAc,EAAE,uDAAuD;MACvEC,sBAAsB,EAAE,2DAA2D;MACnFC,mBAAmB,EAAE,8DAA8D;MACnFC,MAAM,EAAE;IACZ,CAAC,CAAC;IACF,MAAMC,gBAAgB,GAAGP,yBAAyB,CAAC,WAAW,EAAE,gDAAgD,CAAC;IACjHF,MAAM,CAACS,gBAAgB,CAAC,CAACL,OAAO,CAAC;MAC7BC,cAAc,EAAE,2EAA2E;MAC3FC,sBAAsB,EAAE,+EAA+E;MACvGC,mBAAmB,EAAE,kFAAkF;MACvGC,MAAM,EAAE;IACZ,CAAC,CAAC;EACN,CAAC,CAAC;AACN,CAAC,CAAC","ignoreList":[]}
|
package/build/esm/common.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { AuthorizationServer, Client, HttpRequestOptions, OAuth2TokenEndpointResponse } from "oauth4webapi";
|
|
2
2
|
import type { BaseOauthClient, Events } from "./BaseOauthClient.js";
|
|
3
3
|
import type { Token } from "./Token.js";
|
|
4
|
-
type LocalStorageState = {
|
|
4
|
+
export type LocalStorageState = {
|
|
5
5
|
refresh_token?: never;
|
|
6
6
|
codeVerifier?: never;
|
|
7
7
|
state?: never;
|
|
@@ -32,5 +32,4 @@ export declare function common<R extends undefined | (() => Promise<Token | unde
|
|
|
32
32
|
makeTokenAndSaveRefresh: (resp: OAuth2TokenEndpointResponse, type: "signIn" | "refresh") => Token;
|
|
33
33
|
};
|
|
34
34
|
export declare function createAuthorizationServer(ctxPath: string, url: string): Required<Pick<AuthorizationServer, "issuer" | "token_endpoint" | "authorization_endpoint" | "revocation_endpoint">>;
|
|
35
|
-
export {};
|
|
36
35
|
//# sourceMappingURL=common.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"common.d.ts","sourceRoot":"","sources":["../../src/common.ts"],"names":[],"mappings":"AAgBA,OAAO,KAAK,EACV,mBAAmB,EACnB,MAAM,EACN,kBAAkB,EAClB,2BAA2B,EAC5B,MAAM,cAAc,CAAC;AAItB,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AAEpE,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"common.d.ts","sourceRoot":"","sources":["../../src/common.ts"],"names":[],"mappings":"AAgBA,OAAO,KAAK,EACV,mBAAmB,EACnB,MAAM,EACN,kBAAkB,EAClB,2BAA2B,EAC5B,MAAM,cAAc,CAAC;AAItB,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AAEpE,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAwBxC,MAAM,MAAM,iBAAiB,GAEzB;IACA,aAAa,CAAC,EAAE,KAAK,CAAC;IACtB,YAAY,CAAC,EAAE,KAAK,CAAC;IACrB,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB,GAEC;IACA,aAAa,CAAC,EAAE,KAAK,CAAC;IACtB,YAAY,EAAE,MAAM,CAAC;IACrB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB,GAEC;IACA,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,YAAY,CAAC,EAAE,KAAK,CAAC;IACrB,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,MAAM,CAAC,EAAE,KAAK,CAAC;CAChB,GACC;IACA,aAAa,CAAC,EAAE,KAAK,CAAC;IACtB,YAAY,CAAC,EAAE,KAAK,CAAC;IACrB,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,MAAM,CAAC,EAAE,KAAK,CAAC;CAChB,CAAC;AAEJ,wBAAgB,SAAS,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,EAAE,iBAAiB,QAM7D;AAED,wBAAgB,WAAW,CAAC,MAAM,EAAE,MAAM,QAKzC;AAED,wBAAgB,SAAS,CAAC,MAAM,EAAE,MAAM,GAAG,iBAAiB,CAQ3D;AAED,wBAAgB,MAAM,CACpB,CAAC,SAAS,SAAS,GAAG,CAAC,MAAM,OAAO,CAAC,KAAK,GAAG,SAAS,CAAC,CAAC,EAExD,MAAM,EAAE,MAAM,EACd,EAAE,EAAE,mBAAmB,EACvB,OAAO,EAAE,MAAM,OAAO,CAAC,KAAK,CAAC,EAC7B,gBAAgB,EAAE,kBAAkB,EACpC,OAAO,EAAE,CAAC,GACT;IACD,QAAQ,EAAE,eAAe,CAAC,MAAM,MAAM,GAAG,MAAM,CAAC,GAAG;QAAE,OAAO,EAAE,CAAC,CAAA;KAAE,CAAC;IAClE,uBAAuB,EAAE,CACvB,IAAI,EAAE,2BAA2B,EACjC,IAAI,EAAE,QAAQ,GAAG,SAAS,KACvB,KAAK,CAAC;CACZ,CA0GA;AAED,wBAAgB,yBAAyB,CACvC,OAAO,EAAE,MAAM,EACf,GAAG,EAAE,MAAM,GACV,QAAQ,CACT,IAAI,CACF,mBAAmB,EACjB,QAAQ,GACR,gBAAgB,GAChB,wBAAwB,GACxB,qBAAqB,CACxB,CACF,CAQA"}
|
package/build/esm/common.js
CHANGED
|
@@ -29,19 +29,18 @@ const CustomEvent = globalThis.CustomEvent ?? class extends Event {
|
|
|
29
29
|
return this.#detail;
|
|
30
30
|
}
|
|
31
31
|
};
|
|
32
|
-
const localStorage = globalThis.localStorage;
|
|
33
32
|
export function saveLocal(client, x) {
|
|
34
33
|
// MUST `localStorage?` as nodejs does not have localStorage
|
|
35
|
-
localStorage?.setItem(`@osdk/oauth : refresh : ${client.client_id}`, JSON.stringify(x));
|
|
34
|
+
globalThis.localStorage?.setItem(`@osdk/oauth : refresh : ${client.client_id}`, JSON.stringify(x));
|
|
36
35
|
}
|
|
37
36
|
export function removeLocal(client) {
|
|
38
37
|
// MUST `localStorage?` as nodejs does not have localStorage
|
|
39
|
-
localStorage?.removeItem(`@osdk/oauth : refresh : ${client.client_id}`);
|
|
38
|
+
globalThis.localStorage?.removeItem(`@osdk/oauth : refresh : ${client.client_id}`);
|
|
40
39
|
}
|
|
41
40
|
export function readLocal(client) {
|
|
42
41
|
return JSON.parse(
|
|
43
42
|
// MUST `localStorage?` as nodejs does not have localStorage
|
|
44
|
-
localStorage?.getItem(`@osdk/oauth : refresh : ${client.client_id}`) ?? "{}");
|
|
43
|
+
globalThis.localStorage?.getItem(`@osdk/oauth : refresh : ${client.client_id}`) ?? "{}");
|
|
45
44
|
}
|
|
46
45
|
export function common(client, as, _signIn, oauthHttpOptions, refresh) {
|
|
47
46
|
let token;
|
package/build/esm/common.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"common.js","names":["processRevocationResponse","revocationRequest","invariant","TypedEventTarget","throwIfError","CustomEvent","globalThis","Event","detail","constructor","type","options","
|
|
1
|
+
{"version":3,"file":"common.js","names":["processRevocationResponse","revocationRequest","invariant","TypedEventTarget","throwIfError","CustomEvent","globalThis","Event","detail","constructor","type","options","saveLocal","client","x","localStorage","setItem","client_id","JSON","stringify","removeLocal","removeItem","readLocal","parse","getItem","common","as","_signIn","oauthHttpOptions","refresh","token","eventTarget","makeTokenAndSaveRefresh","resp","refresh_token","expires_in","access_token","process","env","NODE_ENV","expires_at","Date","now","dispatchTypedEvent","refreshTimeout","rmTimeout","clearTimeout","restartRefreshTimer","evt","setTimeout","pendingSignIn","signIn","undefined","addEventListener","getTokenOrUndefined","getToken","Object","assign","signOut","result","bind","removeEventListener","createAuthorizationServer","ctxPath","url","issuer","URL","token_endpoint","authorization_endpoint","revocation_endpoint"],"sources":["common.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { processRevocationResponse, revocationRequest } from \"oauth4webapi\";\nimport invariant from \"tiny-invariant\";\nimport { TypedEventTarget } from \"typescript-event-target\";\nimport { throwIfError } from \"./throwIfError.js\";\n// Node 18 is supposed to have a `CustomEvent` but it is not exposed on `globalThis`\n// which creates a problem for making a single codebase for node and browser. This polyfill works around it\nconst CustomEvent = process.env.TARGET === \"browser\"\n ? globalThis.CustomEvent\n : globalThis.CustomEvent\n ?? class CustomEvent extends Event {\n #detail;\n constructor(type, options) {\n super(type, options);\n this.#detail = options?.detail ?? null;\n }\n get detail() {\n return this.#detail;\n }\n };\nexport function saveLocal(client, x) {\n // MUST `localStorage?` as nodejs does not have localStorage\n globalThis.localStorage?.setItem(`@osdk/oauth : refresh : ${client.client_id}`, JSON.stringify(x));\n}\nexport function removeLocal(client) {\n // MUST `localStorage?` as nodejs does not have localStorage\n globalThis.localStorage?.removeItem(`@osdk/oauth : refresh : ${client.client_id}`);\n}\nexport function readLocal(client) {\n return JSON.parse(\n // MUST `localStorage?` as nodejs does not have localStorage\n globalThis.localStorage?.getItem(`@osdk/oauth : refresh : ${client.client_id}`)\n ?? \"{}\");\n}\nexport function common(client, as, _signIn, oauthHttpOptions, refresh) {\n let token;\n const eventTarget = new TypedEventTarget();\n function makeTokenAndSaveRefresh(resp, type) {\n const { refresh_token, expires_in, access_token } = resp;\n invariant(expires_in != null);\n saveLocal(client, { refresh_token });\n token = {\n refresh_token,\n expires_in,\n access_token,\n expires_at: Date.now() + expires_in * 1000,\n };\n eventTarget.dispatchTypedEvent(type, new CustomEvent(type, { detail: token }));\n return token;\n }\n let refreshTimeout;\n function rmTimeout() {\n if (refreshTimeout)\n clearTimeout(refreshTimeout);\n }\n function restartRefreshTimer(evt) {\n if (refresh) {\n rmTimeout();\n refreshTimeout = setTimeout(refresh, evt.detail.expires_in * 1000 - 60 * 1000);\n }\n }\n async function signOut() {\n invariant(token, \"not signed in\");\n const result = await processRevocationResponse(await revocationRequest(as, client, token.access_token, oauthHttpOptions));\n rmTimeout();\n // Clean up\n removeLocal(client);\n token = undefined;\n throwIfError(result);\n eventTarget.dispatchTypedEvent(\"signOut\", new Event(\"signOut\"));\n }\n let pendingSignIn;\n async function signIn() {\n if (pendingSignIn) {\n return pendingSignIn;\n }\n try {\n pendingSignIn = _signIn();\n return await pendingSignIn;\n }\n finally {\n pendingSignIn = undefined;\n }\n }\n eventTarget.addEventListener(\"signIn\", restartRefreshTimer);\n eventTarget.addEventListener(\"refresh\", restartRefreshTimer);\n function getTokenOrUndefined() {\n if (!token || Date.now() >= token.expires_at) {\n return undefined;\n }\n return token?.access_token;\n }\n const getToken = Object.assign(async function getToken() {\n if (!token || Date.now() >= token.expires_at) {\n token = await signIn();\n }\n return token?.access_token;\n }, {\n signIn,\n refresh,\n signOut,\n rmTimeout,\n getTokenOrUndefined,\n addEventListener: eventTarget.addEventListener.bind(eventTarget),\n removeEventListener: eventTarget.removeEventListener.bind(eventTarget),\n });\n return { getToken, makeTokenAndSaveRefresh };\n}\nexport function createAuthorizationServer(ctxPath, url) {\n const issuer = `${new URL(ctxPath, url)}`;\n return {\n token_endpoint: `${issuer}/api/oauth2/token`,\n authorization_endpoint: `${issuer}/api/oauth2/authorize`,\n revocation_endpoint: `${issuer}/api/oauth2/revoke_token`,\n issuer,\n };\n}\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createConfidentialOauthClient.d.ts","sourceRoot":"","sources":["../../src/createConfidentialOauthClient.ts"],"names":[],"mappings":"AAuBA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,8BAA8B,CAAC;AAG5E;;;;;;;;GAQG;AACH,wBAAgB,6BAA6B,CAC3C,SAAS,EAAE,MAAM,EACjB,aAAa,EAAE,MAAM,EACrB,GAAG,EAAE,MAAM,EACX,MAAM,GAAE,MAAM,EAAwC,EACtD,OAAO,GAAE,OAAO,UAAU,CAAC,KAAwB,EACnD,OAAO,GAAE,
|
|
1
|
+
{"version":3,"file":"createConfidentialOauthClient.d.ts","sourceRoot":"","sources":["../../src/createConfidentialOauthClient.ts"],"names":[],"mappings":"AAuBA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,8BAA8B,CAAC;AAG5E;;;;;;;;GAQG;AACH,wBAAgB,6BAA6B,CAC3C,SAAS,EAAE,MAAM,EACjB,aAAa,EAAE,MAAM,EACrB,GAAG,EAAE,MAAM,EACX,MAAM,GAAE,MAAM,EAAwC,EACtD,OAAO,GAAE,OAAO,UAAU,CAAC,KAAwB,EACnD,OAAO,GAAE,MAAoB,GAC5B,uBAAuB,CAgCzB"}
|
|
@@ -25,7 +25,7 @@ import { throwIfError } from "./throwIfError.js";
|
|
|
25
25
|
* @param ctxPath
|
|
26
26
|
* @returns which can be used as a token provider
|
|
27
27
|
*/
|
|
28
|
-
export function createConfidentialOauthClient(client_id, client_secret, url, scopes = ["api:read-data", "api:write-data"], fetchFn = globalThis.fetch, ctxPath = "
|
|
28
|
+
export function createConfidentialOauthClient(client_id, client_secret, url, scopes = ["api:read-data", "api:write-data"], fetchFn = globalThis.fetch, ctxPath = "multipass") {
|
|
29
29
|
const client = {
|
|
30
30
|
client_id,
|
|
31
31
|
client_secret
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createConfidentialOauthClient.js","names":["clientCredentialsGrantRequest","customFetch","processClientCredentialsResponse","common","createAuthorizationServer","throwIfError","createConfidentialOauthClient","client_id","client_secret","url","scopes","fetchFn","globalThis","fetch","ctxPath","client","authServer","oauthHttpOptions","getToken","makeTokenAndSaveRefresh","URLSearchParams","scope","join","undefined"],"sources":["createConfidentialOauthClient.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { clientCredentialsGrantRequest, customFetch, processClientCredentialsResponse, } from \"oauth4webapi\";\nimport { common, createAuthorizationServer } from \"./common.js\";\nimport { throwIfError } from \"./throwIfError.js\";\n/**\n * @param client_id\n * @param client_secret\n * @param url the base url of your foundry server\n * @param scopes\n * @param fetchFn\n * @param ctxPath\n * @returns which can be used as a token provider\n */\nexport function createConfidentialOauthClient(client_id, client_secret, url, scopes = [\"api:read-data\", \"api:write-data\"], fetchFn = globalThis.fetch, ctxPath = \"
|
|
1
|
+
{"version":3,"file":"createConfidentialOauthClient.js","names":["clientCredentialsGrantRequest","customFetch","processClientCredentialsResponse","common","createAuthorizationServer","throwIfError","createConfidentialOauthClient","client_id","client_secret","url","scopes","fetchFn","globalThis","fetch","ctxPath","client","authServer","oauthHttpOptions","getToken","makeTokenAndSaveRefresh","URLSearchParams","scope","join","undefined"],"sources":["createConfidentialOauthClient.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport { clientCredentialsGrantRequest, customFetch, processClientCredentialsResponse, } from \"oauth4webapi\";\nimport { common, createAuthorizationServer } from \"./common.js\";\nimport { throwIfError } from \"./throwIfError.js\";\n/**\n * @param client_id\n * @param client_secret\n * @param url the base url of your foundry server\n * @param scopes\n * @param fetchFn\n * @param ctxPath\n * @returns which can be used as a token provider\n */\nexport function createConfidentialOauthClient(client_id, client_secret, url, scopes = [\"api:read-data\", \"api:write-data\"], fetchFn = globalThis.fetch, ctxPath = \"multipass\") {\n const client = { client_id, client_secret };\n const authServer = createAuthorizationServer(ctxPath, url);\n const oauthHttpOptions = { [customFetch]: fetchFn };\n const { getToken, makeTokenAndSaveRefresh } = common(client, authServer, _signIn, oauthHttpOptions, undefined);\n async function _signIn() {\n return makeTokenAndSaveRefresh(throwIfError(await processClientCredentialsResponse(authServer, client, await clientCredentialsGrantRequest(authServer, client, new URLSearchParams({ scope: scopes.join(\" \") }), oauthHttpOptions))), \"signIn\");\n }\n return getToken;\n}\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAASA,6BAA6B,EAAEC,WAAW,EAAEC,gCAAgC,QAAS,cAAc;AAC5G,SAASC,MAAM,EAAEC,yBAAyB,QAAQ,aAAa;AAC/D,SAASC,YAAY,QAAQ,mBAAmB;AAChD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO,SAASC,6BAA6BA,CAACC,SAAS,EAAEC,aAAa,EAAEC,GAAG,EAAEC,MAAM,GAAG,CAAC,eAAe,EAAE,gBAAgB,CAAC,EAAEC,OAAO,GAAGC,UAAU,CAACC,KAAK,EAAEC,OAAO,GAAG,WAAW,EAAE;EAC1K,MAAMC,MAAM,GAAG;IAAER,SAAS;IAAEC;EAAc,CAAC;EAC3C,MAAMQ,UAAU,GAAGZ,yBAAyB,CAACU,OAAO,EAAEL,GAAG,CAAC;EAC1D,MAAMQ,gBAAgB,GAAG;IAAE,CAAChB,WAAW,GAAGU;EAAQ,CAAC;EACnD,MAAM;IAAEO,QAAQ;IAAEC;EAAwB,CAAC,GAAGhB,MAAM,CAACY,MAAM,EAAEC,UAAU,EACvE,kBAAyB;IACrB,OAAOG,uBAAuB,CAACd,YAAY,CAAC,MAAMH,gCAAgC,CAACc,UAAU,EAAED,MAAM,EAAE,MAAMf,6BAA6B,CAACgB,UAAU,EAAED,MAAM,EAAE,IAAIK,eAAe,CAAC;MAAEC,KAAK,EAAEX,MAAM,CAACY,IAAI,CAAC,GAAG;IAAE,CAAC,CAAC,EAAEL,gBAAgB,CAAC,CAAC,CAAC,EAAE,QAAQ,CAAC;EACnP,CAAC,EAHiFA,gBAAgB,EAAEM,SAAS,CAAC;EAI9G,OAAOL,QAAQ;AACnB","ignoreList":[]}
|
|
@@ -21,7 +21,7 @@ export interface PublicOauthClientOptions {
|
|
|
21
21
|
*/
|
|
22
22
|
fetchFn?: typeof globalThis.fetch;
|
|
23
23
|
/**
|
|
24
|
-
* Context path for the authorization server (defaults to "
|
|
24
|
+
* Context path for the authorization server (defaults to "multipass")
|
|
25
25
|
*/
|
|
26
26
|
ctxPath?: string;
|
|
27
27
|
}
|
|
@@ -46,7 +46,7 @@ export declare function createPublicOauthClient(clientId: string, url: string, r
|
|
|
46
46
|
* @param {string} postLoginPage - URL to return to after completed authentication cycle (defaults to `window.location.toString()`)
|
|
47
47
|
* @param {string[]} scopes - OAuth scopes to request. If not provided, defaults to `["api:read-data", "api:write-data"]`
|
|
48
48
|
* @param {typeof globalThis.fetch} fetchFn - Custom fetch function to use for requests (defaults to `globalThis.fetch`)
|
|
49
|
-
* @param {string} ctxPath - Context path for the authorization server (defaults to "
|
|
49
|
+
* @param {string} ctxPath - Context path for the authorization server (defaults to "multipass")
|
|
50
50
|
* @returns {PublicOauthClient} A client that can be used as a token provider
|
|
51
51
|
*/
|
|
52
52
|
export declare function createPublicOauthClient(client_id: string, url: string, redirectUrl: string, useHistory?: boolean, loginPage?: string, postLoginPage?: string, scopes?: string[], fetchFn?: typeof globalThis.fetch, ctxPath?: string): PublicOauthClient;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"publicOauth.test.d.ts","sourceRoot":"","sources":["../../src/publicOauth.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,242 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2024 Palantir Technologies, Inc. All rights reserved.
|
|
3
|
+
*
|
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
+
* you may not use this file except in compliance with the License.
|
|
6
|
+
* You may obtain a copy of the License at
|
|
7
|
+
*
|
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
+
*
|
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
+
* See the License for the specific language governing permissions and
|
|
14
|
+
* limitations under the License.
|
|
15
|
+
*/
|
|
16
|
+
/* eslint-disable @typescript-eslint/consistent-type-imports */
|
|
17
|
+
import { afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
|
|
18
|
+
import * as commonJs from "./common.js";
|
|
19
|
+
import { createPublicOauthClient } from "./createPublicOauthClient.js";
|
|
20
|
+
const hoistedMocks = vi.hoisted(() => {
|
|
21
|
+
return {
|
|
22
|
+
makeTokenAndSaveRefresh: vi.fn()
|
|
23
|
+
};
|
|
24
|
+
});
|
|
25
|
+
vi.mock("delay", async importOriginal => {
|
|
26
|
+
const original = await importOriginal();
|
|
27
|
+
return {
|
|
28
|
+
default: vi.fn((ms, opts) => {
|
|
29
|
+
// speed up the tests
|
|
30
|
+
return original.default(ms / 100, opts);
|
|
31
|
+
})
|
|
32
|
+
};
|
|
33
|
+
});
|
|
34
|
+
vi.mock("./common.js", async importOriginal => {
|
|
35
|
+
const original = await importOriginal();
|
|
36
|
+
return {
|
|
37
|
+
...original,
|
|
38
|
+
common: vi.fn((...args) => {
|
|
39
|
+
const result = original.common(...args);
|
|
40
|
+
return {
|
|
41
|
+
...result,
|
|
42
|
+
makeTokenAndSaveRefresh: hoistedMocks.makeTokenAndSaveRefresh
|
|
43
|
+
};
|
|
44
|
+
}),
|
|
45
|
+
readLocal: vi.spyOn(original, "readLocal")
|
|
46
|
+
// vi.fn(original.readLocal),
|
|
47
|
+
};
|
|
48
|
+
});
|
|
49
|
+
vi.mock("oauth4webapi");
|
|
50
|
+
describe(createPublicOauthClient, () => {
|
|
51
|
+
const DEFAULT_CUR_URL = new URL("https://fauxurl");
|
|
52
|
+
const fetchFn = vi.fn();
|
|
53
|
+
const mockWindow = {
|
|
54
|
+
location: {
|
|
55
|
+
toString: vi.fn(() => DEFAULT_CUR_URL),
|
|
56
|
+
assign: vi.fn(),
|
|
57
|
+
href: DEFAULT_CUR_URL.href,
|
|
58
|
+
pathname: DEFAULT_CUR_URL.pathname
|
|
59
|
+
},
|
|
60
|
+
history: {
|
|
61
|
+
replaceState: vi.fn()
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
const mockLocalStorage = {
|
|
65
|
+
setItem: vi.fn(),
|
|
66
|
+
getItem: vi.fn(),
|
|
67
|
+
removeItem: vi.fn()
|
|
68
|
+
};
|
|
69
|
+
beforeEach(() => {
|
|
70
|
+
vi.restoreAllMocks();
|
|
71
|
+
fetchFn.mockRestore();
|
|
72
|
+
});
|
|
73
|
+
afterEach(() => {
|
|
74
|
+
vi.clearAllMocks();
|
|
75
|
+
fetchFn.mockReset();
|
|
76
|
+
});
|
|
77
|
+
beforeAll(() => {
|
|
78
|
+
vi.stubGlobal("window", mockWindow);
|
|
79
|
+
vi.stubGlobal("localStorage", mockLocalStorage);
|
|
80
|
+
});
|
|
81
|
+
afterAll(() => {
|
|
82
|
+
vi.unstubAllGlobals();
|
|
83
|
+
});
|
|
84
|
+
const BASE_CLIENT_ARGS = {
|
|
85
|
+
clientId: "this-would-be-client-id",
|
|
86
|
+
foundryUrl: "https://a.foundry.url.local",
|
|
87
|
+
redirectUrl: "https://my.redirect.url.local",
|
|
88
|
+
fetchFn
|
|
89
|
+
};
|
|
90
|
+
const fullLoginUrl = new URL("/loginPage", DEFAULT_CUR_URL);
|
|
91
|
+
describe.each([{
|
|
92
|
+
name: "Basic Usage",
|
|
93
|
+
currentUrl: DEFAULT_CUR_URL,
|
|
94
|
+
clientArgs: {
|
|
95
|
+
...BASE_CLIENT_ARGS
|
|
96
|
+
},
|
|
97
|
+
should: {
|
|
98
|
+
redirectToLoginPage: false
|
|
99
|
+
}
|
|
100
|
+
}, {
|
|
101
|
+
name: "Base w/ full loginPage and curUrl is root",
|
|
102
|
+
currentUrl: DEFAULT_CUR_URL,
|
|
103
|
+
clientArgs: {
|
|
104
|
+
...BASE_CLIENT_ARGS,
|
|
105
|
+
loginPage: fullLoginUrl.toString()
|
|
106
|
+
},
|
|
107
|
+
should: {
|
|
108
|
+
redirectToLoginPage: true
|
|
109
|
+
}
|
|
110
|
+
}, {
|
|
111
|
+
name: "Base w/ full loginPage and curUrl is login page",
|
|
112
|
+
currentUrl: fullLoginUrl,
|
|
113
|
+
clientArgs: {
|
|
114
|
+
...BASE_CLIENT_ARGS,
|
|
115
|
+
loginPage: fullLoginUrl.toString()
|
|
116
|
+
},
|
|
117
|
+
should: {
|
|
118
|
+
redirectToLoginPage: false
|
|
119
|
+
}
|
|
120
|
+
}, {
|
|
121
|
+
name: "Base w/ short loginPage and curUrl is root",
|
|
122
|
+
currentUrl: DEFAULT_CUR_URL,
|
|
123
|
+
clientArgs: {
|
|
124
|
+
...BASE_CLIENT_ARGS,
|
|
125
|
+
loginPage: "/loginPage"
|
|
126
|
+
},
|
|
127
|
+
should: {
|
|
128
|
+
redirectToLoginPage: true
|
|
129
|
+
}
|
|
130
|
+
}, {
|
|
131
|
+
name: "Base w/ short loginPage and curUrl is loginPage",
|
|
132
|
+
currentUrl: new URL("/loginPage", DEFAULT_CUR_URL),
|
|
133
|
+
clientArgs: {
|
|
134
|
+
...BASE_CLIENT_ARGS,
|
|
135
|
+
loginPage: "/loginPage"
|
|
136
|
+
},
|
|
137
|
+
should: {
|
|
138
|
+
redirectToLoginPage: false
|
|
139
|
+
}
|
|
140
|
+
}])("$name", ({
|
|
141
|
+
clientArgs,
|
|
142
|
+
currentUrl,
|
|
143
|
+
should
|
|
144
|
+
}) => {
|
|
145
|
+
let client;
|
|
146
|
+
beforeEach(() => {
|
|
147
|
+
client = createPublicOauthClient(clientArgs.clientId, clientArgs.foundryUrl, clientArgs.redirectUrl, clientArgs.useHistory, clientArgs.loginPage, clientArgs.postLoginPage, clientArgs.scopes, clientArgs.fetchFn, clientArgs.ctxPath);
|
|
148
|
+
mockWindow.location.href = new URL(currentUrl).href;
|
|
149
|
+
mockWindow.location.pathname = new URL(currentUrl).pathname;
|
|
150
|
+
});
|
|
151
|
+
it("calls common with expected values", () => {
|
|
152
|
+
expect(vi.mocked(commonJs.common)).toHaveBeenCalledWith(expect.objectContaining({
|
|
153
|
+
client_id: clientArgs.clientId,
|
|
154
|
+
token_endpoint_auth_method: "none"
|
|
155
|
+
}), commonJs.createAuthorizationServer(clientArgs.ctxPath ?? "/multipass", clientArgs.foundryUrl), expect.any(Function), expect.anything(), expect.any(Function));
|
|
156
|
+
});
|
|
157
|
+
describe.each([{
|
|
158
|
+
refresh_token: "a-refresh-token"
|
|
159
|
+
}, {
|
|
160
|
+
codeVerifier: "hi",
|
|
161
|
+
state: "mom",
|
|
162
|
+
oldUrl: "https://someoldurl.local"
|
|
163
|
+
}, {}])("Initial Local State: %s", initialLocalState => {
|
|
164
|
+
const ACCESS_TOKEN = (Math.random() + 1).toString(36).substring(7);
|
|
165
|
+
beforeEach(() => {
|
|
166
|
+
vi.mocked(commonJs.readLocal).mockImplementation(() => initialLocalState);
|
|
167
|
+
hoistedMocks.makeTokenAndSaveRefresh.mockImplementation(() => ({
|
|
168
|
+
access_token: ACCESS_TOKEN,
|
|
169
|
+
expires_at: Date.now(),
|
|
170
|
+
expires_in: 10000
|
|
171
|
+
}));
|
|
172
|
+
});
|
|
173
|
+
if (Object.keys(initialLocalState).length === 0) {
|
|
174
|
+
if (should.redirectToLoginPage) {
|
|
175
|
+
it("redirects to login page", async () => {
|
|
176
|
+
const tokenPromise = client();
|
|
177
|
+
expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);
|
|
178
|
+
if (should.redirectToLoginPage) {
|
|
179
|
+
// expect save local
|
|
180
|
+
await expect(tokenPromise).resolves.toBeUndefined();
|
|
181
|
+
expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({
|
|
182
|
+
oldUrl: window.location.toString()
|
|
183
|
+
}));
|
|
184
|
+
expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, "", clientArgs.loginPage);
|
|
185
|
+
}
|
|
186
|
+
});
|
|
187
|
+
} else {
|
|
188
|
+
it("redirects to multipass", async () => {
|
|
189
|
+
const tokenPromise = client();
|
|
190
|
+
expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);
|
|
191
|
+
if (should.redirectToLoginPage) {
|
|
192
|
+
// expect save local
|
|
193
|
+
await expect(tokenPromise).resolves.toBeUndefined();
|
|
194
|
+
expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({
|
|
195
|
+
oldUrl: window.location.toString()
|
|
196
|
+
}));
|
|
197
|
+
expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, "", clientArgs.loginPage);
|
|
198
|
+
return;
|
|
199
|
+
}
|
|
200
|
+
// we assume window.location.assign will take you away therefore we
|
|
201
|
+
// also have to expect in this scenario that the thrown error happens
|
|
202
|
+
await expect(tokenPromise).rejects.toThrowError(new Error("Unable to redirect"));
|
|
203
|
+
expect(mockWindow.location.assign).toHaveBeenCalledOnce();
|
|
204
|
+
const url = new URL(mockWindow.location.assign.mock.calls[0][0]);
|
|
205
|
+
expect(url.origin).toEqual(clientArgs.foundryUrl);
|
|
206
|
+
expect(url.pathname).toEqual("/multipass/api/oauth2/authorize");
|
|
207
|
+
expect(Object.fromEntries(url.searchParams.entries())).toEqual(expect.objectContaining({
|
|
208
|
+
client_id: clientArgs.clientId,
|
|
209
|
+
code_challenge: expect.any(String),
|
|
210
|
+
redirect_uri: clientArgs.redirectUrl,
|
|
211
|
+
response_type: "code",
|
|
212
|
+
code_challenge_method: "S256",
|
|
213
|
+
scope: "offline_access api:read-data api:write-data",
|
|
214
|
+
state: expect.any(String)
|
|
215
|
+
}));
|
|
216
|
+
});
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
if (initialLocalState.codeVerifier) {
|
|
220
|
+
it("tries to auth with return results", async () => {
|
|
221
|
+
await expect(client()).resolves.toEqual(ACCESS_TOKEN);
|
|
222
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);
|
|
223
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined,
|
|
224
|
+
// this is only because we didn't mock out the internals
|
|
225
|
+
"signIn");
|
|
226
|
+
expect(mockWindow.history.replaceState).toHaveBeenCalledTimes(1);
|
|
227
|
+
expect(mockWindow.history.replaceState).toBeCalledWith(expect.anything(), expect.anything(), initialLocalState.oldUrl);
|
|
228
|
+
});
|
|
229
|
+
}
|
|
230
|
+
if (initialLocalState.refresh_token) {
|
|
231
|
+
it("refreshes", async () => {
|
|
232
|
+
await expect(client()).resolves.toEqual(ACCESS_TOKEN);
|
|
233
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);
|
|
234
|
+
expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined,
|
|
235
|
+
// this is only because we didn't mock out the internals
|
|
236
|
+
"refresh");
|
|
237
|
+
});
|
|
238
|
+
}
|
|
239
|
+
});
|
|
240
|
+
});
|
|
241
|
+
});
|
|
242
|
+
//# sourceMappingURL=publicOauth.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"publicOauth.test.js","names":["afterAll","afterEach","beforeAll","beforeEach","describe","expect","it","vi","commonJs","createPublicOauthClient","hoistedMocks","hoisted","makeTokenAndSaveRefresh","fn","mock","importOriginal","original","default","ms","opts","common","args","result","readLocal","spyOn","DEFAULT_CUR_URL","URL","fetchFn","mockWindow","location","toString","assign","href","pathname","history","replaceState","mockLocalStorage","setItem","getItem","removeItem","restoreAllMocks","mockRestore","clearAllMocks","mockReset","stubGlobal","unstubAllGlobals","BASE_CLIENT_ARGS","clientId","foundryUrl","redirectUrl","fullLoginUrl","each","name","currentUrl","clientArgs","should","redirectToLoginPage","loginPage","client","useHistory","postLoginPage","scopes","ctxPath","mocked","toHaveBeenCalledWith","objectContaining","client_id","token_endpoint_auth_method","createAuthorizationServer","any","Function","anything","refresh_token","codeVerifier","state","oldUrl","initialLocalState","ACCESS_TOKEN","Math","random","substring","mockImplementation","access_token","expires_at","Date","now","expires_in","Object","keys","length","tokenPromise","toBeCalledTimes","resolves","toBeUndefined","toBeCalledWith","JSON","stringify","window","rejects","toThrowError","Error","toHaveBeenCalledOnce","url","calls","origin","toEqual","fromEntries","searchParams","entries","code_challenge","String","redirect_uri","response_type","code_challenge_method","scope","toHaveBeenCalledTimes","undefined"],"sources":["publicOauth.test.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n/* eslint-disable @typescript-eslint/consistent-type-imports */\nimport { afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi, } from \"vitest\";\nimport * as commonJs from \"./common.js\";\nimport { createPublicOauthClient } from \"./createPublicOauthClient.js\";\nconst hoistedMocks = vi.hoisted(() => {\n return {\n makeTokenAndSaveRefresh: vi.fn(),\n };\n});\nvi.mock(\"delay\", async (importOriginal) => {\n const original = await importOriginal();\n return {\n default: vi.fn((ms, opts) => {\n // speed up the tests\n return original.default(ms / 100, opts);\n }),\n };\n});\nvi.mock(\"./common.js\", async (importOriginal) => {\n const original = await importOriginal();\n return {\n ...original,\n common: vi.fn((...args) => {\n const result = original.common(...args);\n return {\n ...result,\n makeTokenAndSaveRefresh: hoistedMocks.makeTokenAndSaveRefresh,\n };\n }),\n readLocal: vi.spyOn(original, \"readLocal\"),\n // vi.fn(original.readLocal),\n };\n});\nvi.mock(\"oauth4webapi\");\ndescribe(createPublicOauthClient, () => {\n const DEFAULT_CUR_URL = new URL(\"https://fauxurl\");\n const fetchFn = vi.fn();\n const mockWindow = {\n location: {\n toString: vi.fn(() => DEFAULT_CUR_URL),\n assign: vi.fn(),\n href: DEFAULT_CUR_URL.href,\n pathname: DEFAULT_CUR_URL.pathname,\n },\n history: {\n replaceState: vi.fn(),\n },\n };\n const mockLocalStorage = {\n setItem: vi.fn(),\n getItem: vi.fn(),\n removeItem: vi.fn(),\n };\n beforeEach((context) => {\n vi.restoreAllMocks();\n fetchFn.mockRestore();\n });\n afterEach((context) => {\n vi.clearAllMocks();\n fetchFn.mockReset();\n });\n beforeAll(() => {\n vi.stubGlobal(\"window\", mockWindow);\n vi.stubGlobal(\"localStorage\", mockLocalStorage);\n });\n afterAll(() => {\n vi.unstubAllGlobals();\n });\n const BASE_CLIENT_ARGS = {\n clientId: \"this-would-be-client-id\",\n foundryUrl: \"https://a.foundry.url.local\",\n redirectUrl: \"https://my.redirect.url.local\",\n fetchFn,\n };\n const fullLoginUrl = new URL(\"/loginPage\", DEFAULT_CUR_URL);\n describe.each([\n {\n name: \"Basic Usage\",\n currentUrl: DEFAULT_CUR_URL,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n },\n should: {\n redirectToLoginPage: false,\n },\n },\n {\n name: \"Base w/ full loginPage and curUrl is root\",\n currentUrl: DEFAULT_CUR_URL,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: fullLoginUrl.toString(),\n },\n should: {\n redirectToLoginPage: true,\n },\n },\n {\n name: \"Base w/ full loginPage and curUrl is login page\",\n currentUrl: fullLoginUrl,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: fullLoginUrl.toString(),\n },\n should: {\n redirectToLoginPage: false,\n },\n },\n {\n name: \"Base w/ short loginPage and curUrl is root\",\n currentUrl: DEFAULT_CUR_URL,\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: \"/loginPage\",\n },\n should: {\n redirectToLoginPage: true,\n },\n },\n {\n name: \"Base w/ short loginPage and curUrl is loginPage\",\n currentUrl: new URL(\"/loginPage\", DEFAULT_CUR_URL),\n clientArgs: {\n ...BASE_CLIENT_ARGS,\n loginPage: \"/loginPage\",\n },\n should: {\n redirectToLoginPage: false,\n },\n },\n ])(\"$name\", ({ clientArgs, currentUrl, should }) => {\n let client;\n beforeEach(() => {\n client = createPublicOauthClient(clientArgs.clientId, clientArgs.foundryUrl, clientArgs.redirectUrl, clientArgs.useHistory, clientArgs.loginPage, clientArgs.postLoginPage, clientArgs.scopes, clientArgs.fetchFn, clientArgs.ctxPath);\n mockWindow.location.href = new URL(currentUrl).href;\n mockWindow.location.pathname = new URL(currentUrl).pathname;\n });\n it(\"calls common with expected values\", () => {\n expect(vi.mocked(commonJs.common)).toHaveBeenCalledWith(expect.objectContaining({\n client_id: clientArgs.clientId,\n token_endpoint_auth_method: \"none\",\n }), commonJs.createAuthorizationServer(clientArgs.ctxPath ?? \"/multipass\", clientArgs.foundryUrl), expect.any(Function), expect.anything(), expect.any(Function));\n });\n describe.each([\n {\n refresh_token: \"a-refresh-token\",\n },\n {\n codeVerifier: \"hi\",\n state: \"mom\",\n oldUrl: \"https://someoldurl.local\",\n },\n {},\n ])(\"Initial Local State: %s\", (initialLocalState) => {\n const ACCESS_TOKEN = (Math.random() + 1).toString(36).substring(7);\n beforeEach(() => {\n vi.mocked(commonJs.readLocal).mockImplementation(() => initialLocalState);\n hoistedMocks.makeTokenAndSaveRefresh.mockImplementation(() => ({\n access_token: ACCESS_TOKEN,\n expires_at: Date.now(),\n expires_in: 10000,\n }));\n });\n if (Object.keys(initialLocalState).length === 0) {\n if (should.redirectToLoginPage) {\n it(\"redirects to login page\", async () => {\n const tokenPromise = client();\n expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);\n if (should.redirectToLoginPage) {\n // expect save local\n await expect(tokenPromise).resolves.toBeUndefined();\n expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({ oldUrl: window.location.toString() }));\n expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, \"\", clientArgs.loginPage);\n return;\n }\n });\n }\n else {\n it(\"redirects to multipass\", async () => {\n const tokenPromise = client();\n expect(vi.mocked(commonJs.common)).toBeCalledTimes(1);\n if (should.redirectToLoginPage) {\n // expect save local\n await expect(tokenPromise).resolves.toBeUndefined();\n expect(mockLocalStorage.setItem).toBeCalledWith(`@osdk/oauth : refresh : ${clientArgs.clientId}`, JSON.stringify({ oldUrl: window.location.toString() }));\n expect(mockWindow.history.replaceState).toHaveBeenCalledWith({}, \"\", clientArgs.loginPage);\n return;\n }\n // we assume window.location.assign will take you away therefore we\n // also have to expect in this scenario that the thrown error happens\n await expect(tokenPromise)\n .rejects.toThrowError(new Error(\"Unable to redirect\"));\n expect(mockWindow.location.assign).toHaveBeenCalledOnce();\n const url = new URL(mockWindow.location.assign.mock.calls[0][0]);\n expect(url.origin).toEqual(clientArgs.foundryUrl);\n expect(url.pathname).toEqual(\"/multipass/api/oauth2/authorize\");\n expect(Object.fromEntries(url.searchParams.entries())).toEqual(expect.objectContaining({\n client_id: clientArgs.clientId,\n code_challenge: expect.any(String),\n redirect_uri: clientArgs.redirectUrl,\n response_type: \"code\",\n code_challenge_method: \"S256\",\n scope: \"offline_access api:read-data api:write-data\",\n state: expect.any(String),\n }));\n });\n }\n }\n if (initialLocalState.codeVerifier) {\n it(\"tries to auth with return results\", async () => {\n await expect(client()).resolves.toEqual(ACCESS_TOKEN);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined, // this is only because we didn't mock out the internals\n \"signIn\");\n expect(mockWindow.history.replaceState).toHaveBeenCalledTimes(1);\n expect(mockWindow.history.replaceState).toBeCalledWith(expect.anything(), expect.anything(), initialLocalState.oldUrl);\n });\n }\n if (initialLocalState.refresh_token) {\n it(\"refreshes\", async () => {\n await expect(client()).resolves.toEqual(ACCESS_TOKEN);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledTimes(1);\n expect(hoistedMocks.makeTokenAndSaveRefresh).toHaveBeenCalledWith(undefined, // this is only because we didn't mock out the internals\n \"refresh\");\n });\n }\n });\n });\n});\n"],"mappings":"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","ignoreList":[]}
|
package/build/esm/utils.js
CHANGED
|
@@ -38,7 +38,7 @@ export function processOptionsAndAssignDefaults(url, redirect_uri, useHistory, l
|
|
|
38
38
|
postLoginPage: options.postLoginPage || window.location.toString(),
|
|
39
39
|
scopes: options.scopes ?? ["api:read-data", "api:write-data"],
|
|
40
40
|
fetchFn: options.fetchFn ?? globalThis.fetch,
|
|
41
|
-
ctxPath: options.ctxPath ?? "
|
|
41
|
+
ctxPath: options.ctxPath ?? "multipass"
|
|
42
42
|
};
|
|
43
43
|
}
|
|
44
44
|
//# sourceMappingURL=utils.js.map
|
package/build/esm/utils.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.js","names":["invariant","processOptionsAndAssignDefaults","url","redirect_uri","useHistory","loginPage","postLoginPage","scopes","fetchFn","ctxPath","options","process","env","NODE_ENV","window","location","toString","globalThis","fetch"],"sources":["utils.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport invariant from \"tiny-invariant\";\nexport function processOptionsAndAssignDefaults(url, redirect_uri, useHistory, loginPage, postLoginPage, scopes, fetchFn, ctxPath) {\n let options = {};\n if (typeof useHistory === \"object\") {\n invariant(!loginPage && !postLoginPage && !scopes && !fetchFn && !ctxPath, \"If useHistory is an object, other options should not be provided\");\n options = useHistory;\n }\n else {\n options = {\n useHistory,\n loginPage,\n postLoginPage,\n scopes,\n fetchFn,\n ctxPath,\n };\n }\n invariant(url, \"url is required\");\n invariant(redirect_uri, \"redirectUrl is required\");\n // Assign defaults\n return {\n useHistory: options.useHistory ?? true,\n loginPage: options.loginPage,\n postLoginPage: options.postLoginPage || window.location.toString(),\n scopes: options.scopes ?? [\"api:read-data\", \"api:write-data\"],\n fetchFn: options.fetchFn ?? globalThis.fetch,\n ctxPath: options.ctxPath ?? \"
|
|
1
|
+
{"version":3,"file":"utils.js","names":["invariant","processOptionsAndAssignDefaults","url","redirect_uri","useHistory","loginPage","postLoginPage","scopes","fetchFn","ctxPath","options","process","env","NODE_ENV","window","location","toString","globalThis","fetch"],"sources":["utils.js"],"sourcesContent":["/*\n * Copyright 2024 Palantir Technologies, Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\nimport invariant from \"tiny-invariant\";\nexport function processOptionsAndAssignDefaults(url, redirect_uri, useHistory, loginPage, postLoginPage, scopes, fetchFn, ctxPath) {\n let options = {};\n if (typeof useHistory === \"object\") {\n invariant(!loginPage && !postLoginPage && !scopes && !fetchFn && !ctxPath, \"If useHistory is an object, other options should not be provided\");\n options = useHistory;\n }\n else {\n options = {\n useHistory,\n loginPage,\n postLoginPage,\n scopes,\n fetchFn,\n ctxPath,\n };\n }\n invariant(url, \"url is required\");\n invariant(redirect_uri, \"redirectUrl is required\");\n // Assign defaults\n return {\n useHistory: options.useHistory ?? true,\n loginPage: options.loginPage,\n postLoginPage: options.postLoginPage || window.location.toString(),\n scopes: options.scopes ?? [\"api:read-data\", \"api:write-data\"],\n fetchFn: options.fetchFn ?? globalThis.fetch,\n ctxPath: options.ctxPath ?? \"multipass\",\n };\n}\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAOA,SAAS,MAAM,gBAAgB;AACtC,OAAO,SAASC,+BAA+BA,CAACC,GAAG,EAAEC,YAAY,EAAEC,UAAU,EAAEC,SAAS,EAAEC,aAAa,EAAEC,MAAM,EAAEC,OAAO,EAAEC,OAAO,EAAE;EAC/H,IAAIC,OAAO,GAAG,CAAC,CAAC;EAChB,IAAI,OAAON,UAAU,KAAK,QAAQ,EAAE;IAChC,EAAU,CAACC,SAAS,IAAI,CAACC,aAAa,IAAI,CAACC,MAAM,IAAI,CAACC,OAAO,IAAI,CAACC,OAAO,IAAAE,OAAA,CAAAC,GAAA,CAAAC,QAAA,oBAAzEb,SAAS,QAAkE,kEAAkE,IAA7IA,SAAS;IACTU,OAAO,GAAGN,UAAU;EACxB,CAAC,MACI;IACDM,OAAO,GAAG;MACNN,UAAU;MACVC,SAAS;MACTC,aAAa;MACbC,MAAM;MACNC,OAAO;MACPC;IACJ,CAAC;EACL;EACA,CAAUP,GAAG,GAAAS,OAAA,CAAAC,GAAA,CAAAC,QAAA,oBAAbb,SAAS,QAAM,iBAAiB,IAAhCA,SAAS;EACT,CAAUG,YAAY,GAAAQ,OAAA,CAAAC,GAAA,CAAAC,QAAA,oBAAtBb,SAAS,QAAe,yBAAyB,IAAjDA,SAAS;EACT;EACA,OAAO;IACHI,UAAU,EAAEM,OAAO,CAACN,UAAU,IAAI,IAAI;IACtCC,SAAS,EAAEK,OAAO,CAACL,SAAS;IAC5BC,aAAa,EAAEI,OAAO,CAACJ,aAAa,IAAIQ,MAAM,CAACC,QAAQ,CAACC,QAAQ,CAAC,CAAC;IAClET,MAAM,EAAEG,OAAO,CAACH,MAAM,IAAI,CAAC,eAAe,EAAE,gBAAgB,CAAC;IAC7DC,OAAO,EAAEE,OAAO,CAACF,OAAO,IAAIS,UAAU,CAACC,KAAK;IAC5CT,OAAO,EAAEC,OAAO,CAACD,OAAO,IAAI;EAChC,CAAC;AACL","ignoreList":[]}
|