@plitzi/sdk-auth 0.32.25 → 0.33.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -1,5 +1,8 @@
1
- import { AuthManager as e } from "./AuthManager.mjs";
2
- import t from "./hooks/useAuth/index.mjs";
3
- import { AuthContext as n } from "./AuthContext.mjs";
4
- import r from "./AuthContextProvider.mjs";
5
- export { n as AuthContext, r as AuthContextProvider, e as AuthManager, t as useAuth };
1
+ import { readSessionHint as e } from "./helpers/sessionHint.mjs";
2
+ import { nowInSeconds as t, tokenExpiresAt as n } from "./helpers/tokenClaims.mjs";
3
+ import r from "./AuthProvider.mjs";
4
+ import { AuthManager as i, getAuthProviderNames as a, registerAuthProvider as o } from "./AuthManager.mjs";
5
+ import s from "./hooks/useAuth/index.mjs";
6
+ import { AuthContext as c } from "./AuthContext.mjs";
7
+ import l from "./AuthContextProvider.mjs";
8
+ export { c as AuthContext, l as AuthContextProvider, i as AuthManager, r as AuthProvider, a as getAuthProviderNames, t as nowInSeconds, e as readSessionHint, o as registerAuthProvider, n as tokenExpiresAt, s as useAuth };
@@ -1,39 +1,52 @@
1
1
  import { default as AuthProvider, AuthProviderProps } from '../AuthProvider';
2
- import { Schema, TokenResult } from '@plitzi/sdk-shared';
2
+ import { AuthResult, Schema } from '@plitzi/sdk-shared';
3
3
  export type BasicAuthProviderProps = AuthProviderProps & {
4
- tokenStorage?: Schema['settings']['tokenStorage'];
5
4
  loginUrl?: string;
6
5
  userUrl?: string;
7
6
  refreshUrl?: string;
8
7
  logoutUrl?: string;
9
- detailsPath?: string;
10
- tokenPath?: string;
11
- refreshTokenPath?: string;
12
- expirationTimePath?: string;
13
- isSSR?: boolean;
8
+ sessionExchangeUrl?: Schema['settings']['sessionExchangeUrl'];
9
+ detailsPath?: Schema['settings']['detailsPath'];
10
+ tokenPath?: Schema['settings']['tokenPath'];
11
+ refreshTokenPath?: Schema['settings']['refreshTokenPath'];
12
+ expirationTimePath?: Schema['settings']['expirationTimePath'];
13
+ refreshExpirationTimePath?: Schema['settings']['refreshExpirationTimePath'];
14
14
  };
15
- declare class BasicAuthProvider<T = Record<string, unknown>> extends AuthProvider<T> {
15
+ declare class BasicAuthProvider<U = Record<string, unknown>> extends AuthProvider<U> {
16
16
  readonly name = "basic";
17
- protected baseUrl?: string;
18
- protected options: {
19
- tokenStorage: Exclude<Schema['settings']['tokenStorage'], undefined>;
20
- loginUrl: string;
21
- userUrl: string;
22
- refreshUrl: string;
23
- logoutUrl: string;
24
- detailsPath: string;
25
- tokenPath: string;
26
- refreshTokenPath: string;
27
- expirationTimePath: string;
28
- isSSR: boolean;
17
+ private readonly options;
18
+ constructor({ loginUrl, userUrl, refreshUrl, logoutUrl, sessionExchangeUrl, detailsPath, tokenPath, refreshTokenPath, expirationTimePath, refreshExpirationTimePath, ...providerProps }?: BasicAuthProviderProps);
19
+ protected get capabilities(): {
20
+ renew: boolean;
21
+ identity: boolean;
29
22
  };
30
- constructor({ tokenStorage, enableRefresh, loginUrl, userUrl, refreshUrl, logoutUrl, detailsPath, tokenPath, refreshTokenPath, expirationTimePath, isSSR }?: BasicAuthProviderProps);
31
- init(user?: T, skipAuth?: boolean): Promise<void>;
32
- login(authParams: Record<string, string>): Promise<TokenResult | undefined>;
33
- getUser(): Promise<T | undefined>;
34
- refresh(): Promise<TokenResult | undefined>;
35
- can(permission: string): boolean;
36
- logout(): Promise<void>;
37
- private getTokenFromResponse;
23
+ protected get endpoints(): string[];
24
+ /**
25
+ * Two ways in, because a page may already hold a credential.
26
+ *
27
+ * `mode: 'token'` adopts one the page obtained some other way — handed over by a host application, carried in a
28
+ * link, minted by a CLI — and confirms it against the identity endpoint rather than posting anything. Nothing is
29
+ * taken on trust: an unusable token is refused here rather than becoming a session that fails on its first real
30
+ * request. `mode: 'normal'` (the default) posts the credentials.
31
+ */
32
+ protected requestLogin(params: Record<string, unknown>): Promise<AuthResult<U>>;
33
+ /** Confirms a token by asking who it belongs to, and only then reports it as a session. */
34
+ private adoptToken;
35
+ /**
36
+ * The refresh token travels in the body under the name the backend reads it by, and by cookie when the backend
37
+ * keeps it in one — a browser session normally does, which is why this works with nothing in storage at all.
38
+ */
39
+ protected requestRenewal(refreshToken?: string): Promise<AuthResult<U>>;
40
+ /**
41
+ * Only happens when the space declares `sessionExchangeUrl`, which is how it says its credentials are obtained in
42
+ * the browser rather than issued by the server that renders it. The server is handed the credential and the name
43
+ * of the provider that issued it — it has to know who to verify it with, and it must refuse anything else.
44
+ */
45
+ protected requestExchange(): Promise<AuthResult<U> | undefined>;
46
+ protected requestIdentity(): Promise<AuthResult<U>>;
47
+ protected requestLogout(): Promise<void>;
48
+ private request;
49
+ private toResult;
50
+ private tokenFrom;
38
51
  }
39
52
  export default BasicAuthProvider;
@@ -1,94 +1,174 @@
1
1
  import e from "../AuthProvider.mjs";
2
2
  import { get as t } from "@plitzi/plitzi-ui/helpers";
3
+ import { authFailureFromResponse as n } from "@plitzi/sdk-shared/auth";
3
4
  //#region src/providers/BasicAuthProvider.ts
4
- var n = class extends e {
5
+ var r = (e, n) => t(e, n, void 0), i = (e, t) => {
6
+ let n = r(e, t);
7
+ return typeof n == "string" && n !== "" ? n : null;
8
+ }, a = (e, t) => {
9
+ let n = r(e, t), i = typeof n == "string" ? Number(n) : n;
10
+ return typeof i == "number" && Number.isFinite(i) ? i : null;
11
+ }, o = (e) => typeof e == "string" ? e : typeof e == "number" && Number.isFinite(e) ? String(e) : "", s = class extends e {
5
12
  name = "basic";
6
- baseUrl;
7
13
  options;
8
- constructor({ tokenStorage: e = "localStorage", enableRefresh: t = !0, loginUrl: n = "", userUrl: r = "", refreshUrl: i = "", logoutUrl: a = "", detailsPath: o = "", tokenPath: s = "", refreshTokenPath: c = "", expirationTimePath: l = "", isSSR: u = !1 } = {}) {
9
- super({
10
- enableRefresh: t,
11
- tokenStorage: e
12
- }), this.options = {
13
- tokenStorage: e,
14
- loginUrl: n,
15
- userUrl: r,
16
- refreshUrl: i,
17
- logoutUrl: a,
18
- detailsPath: o,
19
- tokenPath: s,
20
- refreshTokenPath: c,
21
- expirationTimePath: l,
22
- isSSR: u
14
+ constructor({ loginUrl: e = "", userUrl: t = "", refreshUrl: n = "", logoutUrl: r = "", sessionExchangeUrl: i = "", detailsPath: a = "details", tokenPath: o = "access_token", refreshTokenPath: s = "refresh_token", expirationTimePath: c = "expire_at", refreshExpirationTimePath: l = "refresh_expire_at", ...u } = {}) {
15
+ super(u), this.options = {
16
+ loginUrl: e,
17
+ userUrl: t,
18
+ refreshUrl: n,
19
+ logoutUrl: r,
20
+ sessionExchangeUrl: i,
21
+ detailsPath: a,
22
+ tokenPath: o,
23
+ refreshTokenPath: s,
24
+ expirationTimePath: c,
25
+ refreshExpirationTimePath: l
23
26
  };
24
27
  }
25
- async init(e, t) {
26
- if (t) {
27
- this.setState("guest");
28
- return;
29
- }
30
- if (this.setState("initLoading"), !this.options.isSSR) {
31
- await this.getUser();
32
- return;
33
- }
34
- e ? super.internalGetUser(e) : this.setState("guest");
28
+ get capabilities() {
29
+ return {
30
+ renew: !!this.options.refreshUrl,
31
+ identity: !!this.options.userUrl
32
+ };
35
33
  }
36
- async login(e) {
37
- let { username: n = "", password: r = "" } = e;
38
- super.setState("authenticating");
39
- let i = await this.request(this.options.loginUrl, {
40
- credentials: "include",
34
+ get endpoints() {
35
+ let { loginUrl: e, userUrl: t, refreshUrl: n, logoutUrl: r } = this.options;
36
+ return [
37
+ e,
38
+ t,
39
+ n,
40
+ r
41
+ ];
42
+ }
43
+ async requestLogin(e) {
44
+ let t = o(e.token).trim();
45
+ if (e.mode === "token") return t ? this.adoptToken(t) : {
46
+ ok: !1,
47
+ reason: "missing"
48
+ };
49
+ if (!this.options.loginUrl) return {
50
+ ok: !1,
51
+ reason: "missing"
52
+ };
53
+ let n = await this.request(this.options.loginUrl, {
41
54
  method: "POST",
42
- headers: { "Content-Type": "application/json" },
43
55
  body: JSON.stringify({
44
- username: n,
45
- password: r
56
+ username: o(e.username),
57
+ password: o(e.password)
46
58
  })
47
- }), a = this.getTokenFromResponse(i);
48
- return super.internalLogin(t(i.data, this.options.detailsPath), a), a;
59
+ });
60
+ return this.toResult(n);
49
61
  }
50
- async getUser() {
51
- if (this.cache?.user && this.state !== "init") return this.cache.user;
52
- if (!this.options.userUrl) {
53
- super.internalGetUser(void 0);
54
- return;
55
- }
56
- let e = await this.request(this.options.userUrl, {
62
+ async adoptToken(e) {
63
+ if (!this.options.userUrl) return {
64
+ ok: !1,
65
+ reason: "missing"
66
+ };
67
+ let t = await this.request(this.options.userUrl, {
57
68
  method: "GET",
58
- credentials: "include",
59
- headers: { "Content-Type": "application/json" }
69
+ headers: {
70
+ "Content-Type": "application/json",
71
+ Authorization: `Bearer ${e}`
72
+ }
73
+ }), n = this.toResult(t);
74
+ return n.ok ? {
75
+ ok: !0,
76
+ user: n.user,
77
+ token: {
78
+ accessToken: e,
79
+ expiresAt: null,
80
+ refreshToken: null
81
+ }
82
+ } : n;
83
+ }
84
+ async requestRenewal(e) {
85
+ if (!this.options.refreshUrl) return {
86
+ ok: !1,
87
+ reason: "missing"
88
+ };
89
+ let t = await this.request(this.options.refreshUrl, {
90
+ method: "POST",
91
+ body: JSON.stringify(e ? { [this.options.refreshTokenPath]: e } : {})
60
92
  });
61
- return super.internalGetUser(t(e.data, this.options.detailsPath)), e.data;
93
+ return this.toResult(t);
62
94
  }
63
- async refresh() {
64
- let e = await this.request(this.options.refreshUrl, {
95
+ async requestExchange() {
96
+ let e = this.token?.accessToken;
97
+ if (!this.options.sessionExchangeUrl || !e) return;
98
+ let t = await this.request(this.options.sessionExchangeUrl, {
65
99
  method: "POST",
66
- credentials: "include",
67
- headers: { "Content-Type": "application/json" },
68
- body: JSON.stringify({ refreshToken: this.cache?.token?.refreshToken ?? "" })
69
- }), t = this.getTokenFromResponse(e);
70
- return super.internalRefresh(t), t;
100
+ headers: {
101
+ "Content-Type": "application/json",
102
+ ...this.spaceKey ? { "x-access-token": this.spaceKey } : {}
103
+ },
104
+ body: JSON.stringify({
105
+ provider: this.name,
106
+ token: e
107
+ })
108
+ });
109
+ return this.toResult(t);
71
110
  }
72
- can(e) {
73
- return this.cache?.user ? t(this.cache.user, "permissions", []).includes(e) : !1;
111
+ async requestIdentity() {
112
+ if (!this.options.userUrl) return {
113
+ ok: !1,
114
+ reason: "missing"
115
+ };
116
+ let e = await this.request(this.options.userUrl, { method: "GET" });
117
+ return this.toResult(e);
74
118
  }
75
- async logout() {
76
- await this.request(this.options.logoutUrl, {
77
- method: "POST",
78
- credentials: "include",
79
- headers: { "Content-Type": "application/json" }
80
- }), super.internalLogout();
119
+ async requestLogout() {
120
+ this.options.logoutUrl && await this.request(this.options.logoutUrl, { method: "POST" });
121
+ }
122
+ async request(e, t) {
123
+ let r;
124
+ try {
125
+ r = await fetch(e, {
126
+ credentials: "include",
127
+ headers: { "Content-Type": "application/json" },
128
+ ...t
129
+ });
130
+ } catch {
131
+ return {
132
+ status: 0,
133
+ reason: "network"
134
+ };
135
+ }
136
+ let i;
137
+ try {
138
+ i = await r.json();
139
+ } catch {
140
+ i = void 0;
141
+ }
142
+ return {
143
+ data: i,
144
+ status: r.status,
145
+ reason: r.ok ? void 0 : n(r.status, i) ?? "network"
146
+ };
147
+ }
148
+ toResult(e) {
149
+ if (e.reason) return {
150
+ ok: !1,
151
+ reason: e.reason
152
+ };
153
+ let t = r(e.data, this.options.detailsPath);
154
+ return {
155
+ ok: !0,
156
+ user: typeof t == "object" && t ? t : void 0,
157
+ token: this.tokenFrom(e.data)
158
+ };
81
159
  }
82
- getTokenFromResponse(e) {
83
- if (e.status >= 400) return;
84
- let n = {
85
- errors: t(e.data, "errors", {}),
86
- accessToken: t(e.data, this.options.tokenPath, ""),
87
- refreshToken: t(e.data, this.options.refreshTokenPath, ""),
88
- expiresAt: t(e.data, this.options.expirationTimePath, 0)
160
+ tokenFrom(e) {
161
+ let t = i(e, this.options.tokenPath);
162
+ if (!t) return;
163
+ let n = r(e, "errors");
164
+ return {
165
+ ...typeof n == "object" && n ? { errors: n } : {},
166
+ accessToken: t,
167
+ expiresAt: a(e, this.options.expirationTimePath),
168
+ refreshToken: i(e, this.options.refreshTokenPath),
169
+ refreshExpiresAt: a(e, this.options.refreshExpirationTimePath)
89
170
  };
90
- return e.data && !("errors" in e.data) && delete n.errors, n;
91
171
  }
92
172
  };
93
173
  //#endregion
94
- export { n as default };
174
+ export { s as default };
@@ -0,0 +1,6 @@
1
+ import { Schema } from '@plitzi/sdk-shared';
2
+ /**
3
+ * Everything a space declares about its auth backend, handed to whichever provider it selected. Derived from the
4
+ * schema rather than restated, so a setting added there reaches providers without a second definition to keep in step.
5
+ */
6
+ export type AuthProviderSettings = Pick<Schema['settings'], 'tokenStorage' | 'loginUrl' | 'userUrl' | 'refreshUrl' | 'logoutUrl' | 'detailsPath' | 'tokenPath' | 'refreshTokenPath' | 'expirationTimePath' | 'refreshExpirationTimePath' | 'sessionHintCookie' | 'sessionExchangeUrl' | 'sessionGate' | 'sessionRevalidateSeconds'>;
package/dist/types.mjs ADDED
File without changes
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@plitzi/sdk-auth",
3
- "version": "0.32.25",
3
+ "version": "0.33.1",
4
4
  "license": "AGPL-3.0",
5
5
  "files": [
6
6
  "dist"
@@ -19,12 +19,25 @@
19
19
  "import": "./dist/AuthContextProvider.mjs"
20
20
  },
21
21
  "./AuthManager": {
22
+ "types": "./dist/AuthManager.d.ts",
22
23
  "import": "./dist/AuthManager.mjs"
23
24
  },
24
25
  "./AuthProvider": {
25
26
  "types": "./dist/AuthProvider.d.ts",
26
27
  "import": "./dist/AuthProvider.mjs"
27
28
  },
29
+ "./helpers/SessionStore": {
30
+ "types": "./dist/helpers/SessionStore.d.ts",
31
+ "import": "./dist/helpers/SessionStore.mjs"
32
+ },
33
+ "./helpers/sessionHint": {
34
+ "types": "./dist/helpers/sessionHint.d.ts",
35
+ "import": "./dist/helpers/sessionHint.mjs"
36
+ },
37
+ "./helpers/tokenClaims": {
38
+ "types": "./dist/helpers/tokenClaims.d.ts",
39
+ "import": "./dist/helpers/tokenClaims.mjs"
40
+ },
28
41
  "./hooks/useAuth": {
29
42
  "types": "./dist/hooks/useAuth/index.d.ts",
30
43
  "import": "./dist/hooks/useAuth/index.mjs"
@@ -41,13 +54,12 @@
41
54
  "types": "./dist/index.d.ts",
42
55
  "import": "./dist/index.mjs"
43
56
  },
44
- "./providers/Auth0Provider": {
45
- "types": "./dist/providers/Auth0Provider.d.ts",
46
- "import": "./dist/providers/Auth0Provider.mjs"
47
- },
48
57
  "./providers/BasicAuthProvider": {
49
58
  "types": "./dist/providers/BasicAuthProvider.d.ts",
50
59
  "import": "./dist/providers/BasicAuthProvider.mjs"
60
+ },
61
+ "./types": {
62
+ "types": "./dist/types.d.ts"
51
63
  }
52
64
  },
53
65
  "type": "module",
@@ -63,15 +75,15 @@
63
75
  "build:prod": "vite build && node ../sdk-shared/scripts/generate-exports.mjs"
64
76
  },
65
77
  "dependencies": {
66
- "@plitzi/plitzi-ui": "^1.6.18",
67
- "@plitzi/sdk-navigation": "0.32.25",
68
- "@plitzi/sdk-schema": "0.32.25",
69
- "@plitzi/sdk-shared": "0.32.25"
78
+ "@plitzi/plitzi-ui": "^1.6.19",
79
+ "@plitzi/sdk-navigation": "0.33.1",
80
+ "@plitzi/sdk-schema": "0.33.1",
81
+ "@plitzi/sdk-shared": "0.33.1"
70
82
  },
71
83
  "devDependencies": {
72
84
  "eslint": "^9.39.5",
73
85
  "typescript": "^6.0.3",
74
- "vite": "^8.2.0",
86
+ "vite": "^8.2.1",
75
87
  "vitest": "^4.1.10"
76
88
  }
77
89
  }
@@ -1,22 +0,0 @@
1
- import { default as AuthProvider, AuthProviderProps } from '../AuthProvider';
2
- import { Schema, TokenResult } from '@plitzi/sdk-shared';
3
- export type Auth0ProviderProps = AuthProviderProps & {
4
- tokenStorage?: Schema['settings']['tokenStorage'];
5
- loginUrl?: string;
6
- userUrl?: string;
7
- refreshUrl?: string;
8
- logoutUrl?: string;
9
- detailsPath?: string;
10
- tokenPath?: string;
11
- expirationTimePath?: string;
12
- };
13
- declare class Auth0Provider<T = Record<string, unknown>> extends AuthProvider<T> {
14
- readonly name = "auth0";
15
- init(): Promise<void>;
16
- login(...args: unknown[]): Promise<TokenResult | undefined>;
17
- getUser(): Promise<T | undefined>;
18
- refresh(): Promise<TokenResult | undefined>;
19
- can(permission: string): boolean;
20
- logout(): Promise<void>;
21
- }
22
- export default Auth0Provider;
@@ -1,25 +0,0 @@
1
- import e from "../AuthProvider.mjs";
2
- //#region src/providers/Auth0Provider.ts
3
- var t = class extends e {
4
- name = "auth0";
5
- init() {
6
- throw Error("Method not implemented.");
7
- }
8
- login(...e) {
9
- throw console.log(e), Error("Method not implemented.");
10
- }
11
- getUser() {
12
- throw Error("Method not implemented.");
13
- }
14
- refresh() {
15
- throw Error("Method not implemented.");
16
- }
17
- can(e) {
18
- throw console.log(e), Error("Method not implemented.");
19
- }
20
- logout() {
21
- throw Error("Method not implemented.");
22
- }
23
- };
24
- //#endregion
25
- export { t as default };