@o2js/core 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,10 +1,10 @@
1
1
  # o2js
2
2
 
3
- **A lightweight and provider-agnostic OAuth2 library for Node.js.**
3
+ **A lightweight, provider-agnostic OAuth2 and OpenID Connect library for Node.js.**
4
4
 
5
- o2js provides the core OAuth2 authorization code and refresh token flows.
5
+ o2js provides the core OAuth2 Authorization Code and Refresh Token flows, along with OpenID Connect ID Token validation.
6
6
 
7
- It does not manage users, sessions, token storage, or database operations. It only handles OAuth2 mechanics and leaves the rest to your application.
7
+ It does not manage users, sessions, token storage, or database operations. It handles protocol mechanics and leaves application state and lifecycle management to your application.
8
8
 
9
9
  ## Installation
10
10
 
@@ -19,15 +19,10 @@ First, define a provider:
19
19
  ```typescript
20
20
  import type { Provider } from "@o2js/core";
21
21
 
22
- class MyProvider implements Provider {
23
- authURL(): string {
24
- return "https://example.com/oauth/authorize";
25
- }
26
-
27
- tokenURL(): string {
28
- return "https://example.com/oauth/token";
29
- }
30
- }
22
+ const provider: Provider = {
23
+ authURL: "https://example.com/oauth/authorize",
24
+ tokenURL: "https://example.com/oauth/token",
25
+ };
31
26
  ```
32
27
 
33
28
  Create an OAuth2 client:
@@ -35,14 +30,11 @@ Create an OAuth2 client:
35
30
  ```typescript
36
31
  import { OAuth2 } from "@o2js/core";
37
32
 
38
- const oauth = new OAuth2(
39
- new MyProvider(),
40
- {
41
- clientID: "your-client-id",
42
- clientSecret: "your-client-secret",
43
- redirectURL: "https://yourapp.com/callback",
44
- }
45
- );
33
+ const oauth = new OAuth2(provider, {
34
+ clientID: "your-client-id",
35
+ clientSecret: "your-client-secret",
36
+ redirectURL: "https://yourapp.com/callback",
37
+ });
46
38
  ```
47
39
 
48
40
  Generate an authorization URL:
@@ -104,14 +96,13 @@ const oauth = new OAuth2(provider, {
104
96
 
105
97
  If `clientAuthMethod` is omitted, o2js uses `client_secret_basic`.
106
98
 
107
-
108
99
  ## Custom Parameters
109
100
 
110
101
  OAuth providers may require additional parameters for scopes, PKCE, or other features.
111
102
 
112
- You can pass these parameters directly to the relevant methods.
103
+ You can pass additional parameters directly to the relevant methods.
113
104
 
114
- Additional authorization URL parameters:
105
+ Authorization URL parameters:
115
106
 
116
107
  ```typescript
117
108
  const url = oauth.authCodeURL(state, {
@@ -120,7 +111,7 @@ const url = oauth.authCodeURL(state, {
120
111
  });
121
112
  ```
122
113
 
123
- Additional token request parameters:
114
+ Token request parameters:
124
115
 
125
116
  ```typescript
126
117
  const response = await oauth.exchangeAuthCode(code, {
@@ -138,11 +129,13 @@ const response = await oauth.exchangeRefreshToken(refreshToken, {
138
129
 
139
130
  Check your provider's documentation for supported parameters and their expected values.
140
131
 
141
- ## State and PKCE
132
+ ## State, Nonce and PKCE
142
133
 
143
- o2js provides helpers for generating random state values and PKCE parameters.
134
+ o2js provides helpers for generating cryptographically secure random state, nonce, and PKCE values.
144
135
 
145
- Generate a random state:
136
+ ### State
137
+
138
+ Generate a random state value:
146
139
 
147
140
  ```typescript
148
141
  import { generateRandomState } from "@o2js/core";
@@ -150,6 +143,46 @@ import { generateRandomState } from "@o2js/core";
150
143
  const state = generateRandomState();
151
144
  ```
152
145
 
146
+ Pass it to the authorization URL:
147
+
148
+ ```typescript
149
+ const url = oauth.authCodeURL(state);
150
+ ```
151
+
152
+ Your application is responsible for storing the state and verifying the returned value during the callback.
153
+
154
+ ### Nonce
155
+
156
+ Generate a random nonce:
157
+
158
+ ```typescript
159
+ import { generateRandomNonce } from "@o2js/core";
160
+
161
+ const nonce = generateRandomNonce();
162
+ ```
163
+
164
+ Include it in the authorization request:
165
+
166
+ ```typescript
167
+ const url = oauth.authCodeURL(state, {
168
+ nonce,
169
+ });
170
+ ```
171
+
172
+ After receiving the ID Token, pass the expected nonce to `parseClaims`:
173
+
174
+ ```typescript
175
+ const claims = await oauth.parseClaims(idToken, {
176
+ nonce,
177
+ });
178
+ ```
179
+
180
+ o2js verifies that the nonce in the ID Token matches the expected value.
181
+
182
+ Your application is responsible for storing and managing the nonce throughout the authorization flow.
183
+
184
+ ### PKCE
185
+
153
186
  Generate PKCE parameters:
154
187
 
155
188
  ```typescript
@@ -175,7 +208,147 @@ const response = await oauth.exchangeAuthCode(code, {
175
208
  });
176
209
  ```
177
210
 
178
- State and PKCE values must be stored and managed by your application. o2js does not handle their storage, verification, or lifecycle.
211
+ State, nonce, and PKCE values must be stored and managed by your application. Your application is also responsible for verifying the returned state and managing the lifecycle of these values.
212
+
213
+ o2js does not store or manage these values.
214
+
215
+ ## OpenID Connect
216
+
217
+ o2js supports OpenID Connect ID Token validation through the `parseClaims` method.
218
+
219
+ To enable ID Token validation, provide the issuer and JWKS URLs in your provider configuration:
220
+
221
+ ```typescript
222
+ import type { Provider } from "@o2js/core";
223
+
224
+ const provider: Provider = {
225
+ authURL: "https://example.com/oauth/authorize",
226
+ tokenURL: "https://example.com/oauth/token",
227
+ issuerURL: "https://example.com",
228
+ jwksURL: "https://example.com/.well-known/jwks.json",
229
+ };
230
+ ```
231
+
232
+ The `issuerURL` and `jwksURL` properties are optional for OAuth2-only providers. They are required when using `parseClaims`.
233
+
234
+ ### ID Token Validation
235
+
236
+ After exchanging the authorization code, retrieve the ID Token from the token response and validate it:
237
+
238
+ ```typescript
239
+ const response = await oauth.exchangeAuthCode(code);
240
+
241
+ const idToken = response.data.id_token;
242
+
243
+ if (typeof idToken !== "string") {
244
+ throw new Error("ID Token is missing");
245
+ }
246
+
247
+ const claims = await oauth.parseClaims(idToken);
248
+
249
+ console.log(claims.sub);
250
+ ```
251
+
252
+ `parseClaims` verifies the ID Token signature using the provider's JWKS and validates its issuer, audience, expiration, and required claims.
253
+
254
+ ### Validation Options
255
+
256
+ The `parseClaims` method accepts an optional options object:
257
+
258
+ ```typescript
259
+ type ParseClaimsOptions = {
260
+ nonce?: string;
261
+ maxAge?: number;
262
+ trustedAudiences?: string[];
263
+ algorithms?: (
264
+ | "RS256"
265
+ | "PS256"
266
+ | "ES256"
267
+ | "ES384"
268
+ | "ES512"
269
+ )[];
270
+ };
271
+ ```
272
+
273
+ **Nonce**
274
+
275
+ If a nonce was included in the authorization request, pass the expected value when validating the ID Token:
276
+
277
+ ```typescript
278
+ const claims = await oauth.parseClaims(idToken, {
279
+ nonce: savedNonce,
280
+ });
281
+ ```
282
+
283
+ The nonce must match the value in the ID Token.
284
+
285
+ **Maximum Authentication Age**
286
+
287
+ If you request a maximum authentication age, include `max_age` in the authorization request:
288
+
289
+ ```typescript
290
+ const url = oauth.authCodeURL(state, {
291
+ max_age: "300",
292
+ });
293
+ ```
294
+
295
+ Pass the same value to `parseClaims`:
296
+
297
+ ```typescript
298
+ const claims = await oauth.parseClaims(idToken, {
299
+ maxAge: 300,
300
+ });
301
+ ```
302
+
303
+ When `maxAge` is provided, `auth_time` is required and checked against the requested maximum age.
304
+
305
+ **Trusted Audiences**
306
+
307
+ By default, o2js accepts the configured client ID as a trusted audience.
308
+
309
+ If your application expects additional audiences, specify them explicitly:
310
+
311
+ ```typescript
312
+ const claims = await oauth.parseClaims(idToken, {
313
+ trustedAudiences: [
314
+ "trusted-service",
315
+ ],
316
+ });
317
+ ```
318
+
319
+ Any audience not included in the client ID or the trusted audience list is rejected.
320
+
321
+ **Signing Algorithms**
322
+
323
+ The default signing algorithm is `RS256`.
324
+
325
+ You can specify additional supported algorithms:
326
+
327
+ ```typescript
328
+ const claims = await oauth.parseClaims(idToken, {
329
+ algorithms: ["RS256", "PS256", "ES256"],
330
+ });
331
+ ```
332
+
333
+ Only use algorithms supported and expected by your identity provider.
334
+
335
+ ### ID Token Claims
336
+
337
+ The `parseClaims` method returns an `IDTokenClaims` object:
338
+
339
+ ```typescript
340
+ import type { IDTokenClaims } from "@o2js/core";
341
+ ```
342
+
343
+ The type extends `JWTPayload` and includes the standard claims:
344
+
345
+ - `iss`: Issuer identifier.
346
+ - `sub`: Subject identifier.
347
+ - `aud`: Intended audience.
348
+ - `exp`: Expiration time.
349
+ - `iat`: Issued-at time.
350
+
351
+ Other claims provided by the identity provider are also available through the returned payload.
179
352
 
180
353
  ## Response
181
354
 
@@ -193,7 +366,7 @@ type ExchangeResponse = {
193
366
 
194
367
  ## Error Handling
195
368
 
196
- HTTP and response parsing errors are represented by `HTTPError`.
369
+ HTTP and token response parsing errors are represented by `HTTPError`.
197
370
 
198
371
  ```typescript
199
372
  import { HTTPError } from "@o2js/core";
@@ -211,21 +384,30 @@ try {
211
384
 
212
385
  `body` contains the raw response body when available.
213
386
 
387
+ ID Token validation errors and JWT verification errors are also thrown by `parseClaims`. These may originate from the validation logic or the underlying `jose` library.
388
+
214
389
  ## Providers
215
390
 
216
391
  o2js does not include provider implementations.
217
392
 
218
- You can implement the `Provider` interface yourself or use separate provider packages when available.
219
-
220
- A provider only needs to implement:
393
+ You can define your own provider using the `Provider` interface:
221
394
 
222
395
  ```typescript
223
396
  export interface Provider {
224
- authURL(): string;
225
- tokenURL(): string;
397
+ authURL: string;
398
+ tokenURL: string;
399
+ issuerURL?: string;
400
+ jwksURL?: string;
226
401
  }
227
402
  ```
228
403
 
404
+ - `authURL`: Authorization endpoint URL.
405
+ - `tokenURL`: Token endpoint URL.
406
+ - `issuerURL`: OpenID Connect issuer URL. Required for ID Token validation.
407
+ - `jwksURL`: JSON Web Key Set endpoint URL. Required for ID Token validation.
408
+
409
+ OAuth2-only providers do not need to define `issuerURL` or `jwksURL`.
410
+
229
411
  ## License
230
412
 
231
413
  MIT
package/dist/crypto.d.ts CHANGED
@@ -3,5 +3,6 @@ export type PKCE = {
3
3
  codeChallenge: string;
4
4
  };
5
5
  export declare function generateRandomState(): string;
6
+ export declare function generateRandomNonce(): string;
6
7
  export declare function generateRandomPKCE(): PKCE;
7
8
  //# sourceMappingURL=crypto.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAEA,MAAM,MAAM,IAAI,GAAG;IACf,YAAY,EAAE,MAAM,CAAC;IACrB,aAAa,EAAE,MAAM,CAAC;CACzB,CAAC;AAEF,wBAAgB,mBAAmB,IAAI,MAAM,CAE5C;AAED,wBAAgB,kBAAkB,IAAI,IAAI,CAWzC"}
1
+ {"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAEA,MAAM,MAAM,IAAI,GAAG;IACf,YAAY,EAAE,MAAM,CAAC;IACrB,aAAa,EAAE,MAAM,CAAC;CACzB,CAAC;AAEF,wBAAgB,mBAAmB,IAAI,MAAM,CAE5C;AAED,wBAAgB,mBAAmB,IAAI,MAAM,CAE5C;AAED,wBAAgB,kBAAkB,IAAI,IAAI,CAWzC"}
package/dist/crypto.js CHANGED
@@ -2,6 +2,9 @@ import { randomBytes, createHash } from "node:crypto";
2
2
  export function generateRandomState() {
3
3
  return randomBytes(32).toString("hex");
4
4
  }
5
+ export function generateRandomNonce() {
6
+ return generateRandomState();
7
+ }
5
8
  export function generateRandomPKCE() {
6
9
  const codeVerifier = randomBytes(32).toString("base64url");
7
10
  const codeChallenge = createHash("sha256")
@@ -1 +1 @@
1
- {"version":3,"file":"crypto.js","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAOtD,MAAM,UAAU,mBAAmB;IAC/B,OAAO,WAAW,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;AAC3C,CAAC;AAED,MAAM,UAAU,kBAAkB;IAC9B,MAAM,YAAY,GAAG,WAAW,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,WAAW,CAAC,CAAC;IAE3D,MAAM,aAAa,GAAG,UAAU,CAAC,QAAQ,CAAC;SACrC,MAAM,CAAC,YAAY,CAAC;SACpB,MAAM,CAAC,WAAW,CAAC,CAAC;IAEzB,OAAO;QACH,YAAY;QACZ,aAAa;KAChB,CAAC;AACN,CAAC"}
1
+ {"version":3,"file":"crypto.js","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAOtD,MAAM,UAAU,mBAAmB;IAC/B,OAAO,WAAW,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;AAC3C,CAAC;AAED,MAAM,UAAU,mBAAmB;IAC/B,OAAO,mBAAmB,EAAE,CAAC;AACjC,CAAC;AAED,MAAM,UAAU,kBAAkB;IAC9B,MAAM,YAAY,GAAG,WAAW,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,WAAW,CAAC,CAAC;IAE3D,MAAM,aAAa,GAAG,UAAU,CAAC,QAAQ,CAAC;SACrC,MAAM,CAAC,YAAY,CAAC;SACpB,MAAM,CAAC,WAAW,CAAC,CAAC;IAEzB,OAAO;QACH,YAAY;QACZ,aAAa;KAChB,CAAC;AACN,CAAC"}
package/dist/index.d.ts CHANGED
@@ -1,7 +1,7 @@
1
- export { OAuth2 } from "./oauth2.js";
1
+ export { OAuth2, type IDTokenClaims } from "./oauth2.js";
2
2
  export { HTTPError } from "./errors.js";
3
3
  export type { Provider } from "./provider.js";
4
4
  export type { Config, ClientAuthMethod } from "./config.js";
5
5
  export type { ExchangeResponse } from "./response.js";
6
- export { generateRandomState, generateRandomPKCE, type PKCE } from "./crypto.js";
6
+ export { generateRandomState, generateRandomNonce, generateRandomPKCE, type PKCE } from "./crypto.js";
7
7
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,YAAY,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAC9C,YAAY,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAC5D,YAAY,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AACtD,OAAO,EACH,mBAAmB,EACnB,kBAAkB,EAClB,KAAK,IAAI,EACZ,MAAM,aAAa,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,KAAK,aAAa,EAAE,MAAM,aAAa,CAAC;AACzD,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,YAAY,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAC9C,YAAY,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAC5D,YAAY,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AACtD,OAAO,EACH,mBAAmB,EACnB,mBAAmB,EACnB,kBAAkB,EAClB,KAAK,IAAI,EACZ,MAAM,aAAa,CAAC"}
package/dist/index.js CHANGED
@@ -1,4 +1,4 @@
1
1
  export { OAuth2 } from "./oauth2.js";
2
2
  export { HTTPError } from "./errors.js";
3
- export { generateRandomState, generateRandomPKCE } from "./crypto.js";
3
+ export { generateRandomState, generateRandomNonce, generateRandomPKCE } from "./crypto.js";
4
4
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAIxC,OAAO,EACH,mBAAmB,EACnB,kBAAkB,EAErB,MAAM,aAAa,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAsB,MAAM,aAAa,CAAC;AACzD,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAIxC,OAAO,EACH,mBAAmB,EACnB,mBAAmB,EACnB,kBAAkB,EAErB,MAAM,aAAa,CAAC"}
package/dist/oauth2.d.ts CHANGED
@@ -1,14 +1,29 @@
1
1
  import type { Provider } from "./provider.js";
2
2
  import type { Config } from "./config.js";
3
3
  import type { ExchangeResponse } from "./response.js";
4
+ import { type JWTPayload } from "jose";
5
+ export type IDTokenClaims = JWTPayload & {
6
+ iss: string;
7
+ sub: string;
8
+ aud: string | string[];
9
+ exp: number;
10
+ iat: number;
11
+ };
4
12
  export declare class OAuth2 {
5
13
  private provider;
6
14
  private config;
15
+ private jwks?;
7
16
  constructor(provider: Provider, config: Config);
8
17
  authCodeURL(state: string, urlParams?: Record<string, string>): string;
9
18
  exchangeAuthCode(code: string, tokenParams?: Record<string, string>): Promise<ExchangeResponse>;
10
19
  exchangeRefreshToken(refreshToken: string, tokenParams?: Record<string, string>): Promise<ExchangeResponse>;
11
20
  private exchange;
21
+ parseClaims(idToken: string, options?: {
22
+ nonce?: string;
23
+ maxAge?: number;
24
+ trustedAudiences?: string[];
25
+ algorithms?: ("RS256" | "PS256" | "ES256" | "ES384" | "ES512")[];
26
+ }): Promise<IDTokenClaims>;
12
27
  private validate;
13
28
  }
14
29
  //# sourceMappingURL=oauth2.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"oauth2.d.ts","sourceRoot":"","sources":["../src/oauth2.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAC9C,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AActD,qBAAa,MAAM;IAEX,OAAO,CAAC,QAAQ;IAChB,OAAO,CAAC,MAAM;IAFlB,YACY,QAAQ,EAAE,QAAQ,EAClB,MAAM,EAAE,MAAM,EAGzB;IAED,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CA0BrE;IAEK,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAYpG;IAEK,oBAAoB,CAAC,YAAY,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAgBhH;YAEa,QAAQ;IAqGtB,OAAO,CAAC,QAAQ;CAoCnB"}
1
+ {"version":3,"file":"oauth2.d.ts","sourceRoot":"","sources":["../src/oauth2.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAC9C,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAQtD,OAAO,EAGH,KAAK,UAAU,EAClB,MAAM,MAAM,CAAC;AAEd,MAAM,MAAM,aAAa,GAAG,UAAU,GAAG;IACrC,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IACvB,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;CACf,CAAC;AAQF,qBAAa,MAAM;IAIX,OAAO,CAAC,QAAQ;IAChB,OAAO,CAAC,MAAM;IAJlB,OAAO,CAAC,IAAI,CAAC,CAAwC;IAErD,YACY,QAAQ,EAAE,QAAQ,EAClB,MAAM,EAAE,MAAM,EAGzB;IAED,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CA0BrE;IAEK,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAYpG;IAEK,oBAAoB,CAAC,YAAY,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAehH;YAEa,QAAQ;IAqGhB,WAAW,CACb,OAAO,EAAE,MAAM,EACf,OAAO,CAAC,EAAE;QACN,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,gBAAgB,CAAC,EAAE,MAAM,EAAE,CAAC;QAC5B,UAAU,CAAC,EAAE,CAAC,OAAO,GAAG,OAAO,GAAG,OAAO,GAAG,OAAO,GAAG,OAAO,CAAC,EAAE,CAAC;KACpE,GACF,OAAO,CAAC,aAAa,CAAC,CAmKxB;IAED,OAAO,CAAC,QAAQ;CAoCnB"}
package/dist/oauth2.js CHANGED
@@ -1,5 +1,6 @@
1
1
  import { HTTPError } from "./errors.js";
2
2
  import { parseParams, baseReservedParams, } from "./params.js";
3
+ import { createRemoteJWKSet, jwtVerify, } from "jose";
3
4
  function encodeFormValue(value) {
4
5
  return new URLSearchParams([["value", value]])
5
6
  .toString()
@@ -8,6 +9,7 @@ function encodeFormValue(value) {
8
9
  export class OAuth2 {
9
10
  provider;
10
11
  config;
12
+ jwks;
11
13
  constructor(provider, config) {
12
14
  this.provider = provider;
13
15
  this.config = config;
@@ -24,7 +26,7 @@ export class OAuth2 {
24
26
  if (state !== "") {
25
27
  params.set("state", state);
26
28
  }
27
- const url = new URL(this.provider.authURL());
29
+ const url = new URL(this.provider.authURL);
28
30
  params.forEach((value, key) => {
29
31
  url.searchParams.set(key, value);
30
32
  });
@@ -46,7 +48,6 @@ export class OAuth2 {
46
48
  }
47
49
  const params = new URLSearchParams();
48
50
  params.set("refresh_token", refreshToken);
49
- params.set("redirect_uri", this.config.redirectURL);
50
51
  params.set("grant_type", "refresh_token");
51
52
  return this.exchange(params, baseReservedParams(), tokenParams);
52
53
  }
@@ -68,7 +69,7 @@ export class OAuth2 {
68
69
  }
69
70
  let response;
70
71
  try {
71
- response = await fetch(this.provider.tokenURL(), {
72
+ response = await fetch(this.provider.tokenURL, {
72
73
  method: "POST",
73
74
  headers,
74
75
  body: params.toString(),
@@ -104,6 +105,110 @@ export class OAuth2 {
104
105
  data: parsed,
105
106
  };
106
107
  }
108
+ async parseClaims(idToken, options) {
109
+ if (!idToken.trim()) {
110
+ throw new Error("ID Token cannot be empty");
111
+ }
112
+ const issuer = this.provider.issuerURL;
113
+ const jwksURL = this.provider.jwksURL;
114
+ if (!issuer?.trim()) {
115
+ throw new Error("Provider issuer URL is required");
116
+ }
117
+ if (!jwksURL?.trim()) {
118
+ throw new Error("Provider JWKS URL is required");
119
+ }
120
+ if (options?.nonce !== undefined &&
121
+ !options.nonce.trim()) {
122
+ throw new Error("Nonce cannot be empty");
123
+ }
124
+ if (options?.maxAge !== undefined &&
125
+ (!Number.isFinite(options.maxAge) || options.maxAge < 0)) {
126
+ throw new Error("maxAge must be a non-negative number");
127
+ }
128
+ if (options?.trustedAudiences?.some((audience) => !audience.trim())) {
129
+ throw new Error("Trusted audiences cannot contain empty values");
130
+ }
131
+ const algorithms = options?.algorithms ?? ["RS256"];
132
+ if (algorithms.length === 0) {
133
+ throw new Error("At least one signing algorithm is required");
134
+ }
135
+ if (!this.jwks) {
136
+ this.jwks = createRemoteJWKSet(new URL(jwksURL));
137
+ }
138
+ const { payload } = await jwtVerify(idToken, this.jwks, {
139
+ issuer,
140
+ audience: this.config.clientID,
141
+ algorithms,
142
+ clockTolerance: 5,
143
+ });
144
+ // Subject
145
+ if (typeof payload.sub !== "string" ||
146
+ !payload.sub) {
147
+ throw new Error("Invalid ID Token: missing subject");
148
+ }
149
+ // Audience
150
+ const audiences = typeof payload.aud === "string"
151
+ ? [payload.aud]
152
+ : payload.aud;
153
+ if (!Array.isArray(audiences) ||
154
+ audiences.length === 0 ||
155
+ audiences.some((audience) => typeof audience !== "string" ||
156
+ !audience)) {
157
+ throw new Error("Invalid ID Token: invalid audience");
158
+ }
159
+ const trustedAudiences = new Set([
160
+ this.config.clientID,
161
+ ...(options?.trustedAudiences ?? []),
162
+ ]);
163
+ if (audiences.some((audience) => !trustedAudiences.has(audience))) {
164
+ throw new Error("Invalid ID Token: untrusted audience");
165
+ }
166
+ // Expiration
167
+ if (typeof payload.exp !== "number" ||
168
+ !Number.isFinite(payload.exp)) {
169
+ throw new Error("Invalid ID Token: invalid expiration");
170
+ }
171
+ // Issued at
172
+ if (typeof payload.iat !== "number" ||
173
+ !Number.isFinite(payload.iat) ||
174
+ payload.iat < 0) {
175
+ throw new Error("Invalid ID Token: invalid issued-at claim");
176
+ }
177
+ // Nonce
178
+ if (options?.nonce !== undefined) {
179
+ if (typeof payload.nonce !== "string" ||
180
+ payload.nonce !== options.nonce) {
181
+ throw new Error("Invalid ID Token: nonce mismatch");
182
+ }
183
+ }
184
+ // Authorized party
185
+ if (audiences.length > 1 && typeof payload.azp !== "string") {
186
+ throw new Error("Invalid ID Token: missing authorized party");
187
+ }
188
+ if (payload.azp !== undefined &&
189
+ (typeof payload.azp !== "string" ||
190
+ payload.azp !== this.config.clientID)) {
191
+ throw new Error("Invalid ID Token: authorized party mismatch");
192
+ }
193
+ // Authentication time
194
+ if (options?.maxAge !== undefined) {
195
+ if (typeof payload.auth_time !== "number") {
196
+ throw new Error("Invalid ID Token: missing authentication time");
197
+ }
198
+ const now = Math.floor(Date.now() / 1000);
199
+ const authTime = payload.auth_time;
200
+ if (!Number.isFinite(authTime) || authTime < 0) {
201
+ throw new Error("Invalid ID Token: invalid authentication time");
202
+ }
203
+ if (authTime > now + 5) {
204
+ throw new Error("Invalid ID Token: authentication time is in the future");
205
+ }
206
+ if (now - authTime > options.maxAge + 5) {
207
+ throw new Error("Invalid ID Token: authentication is too old");
208
+ }
209
+ }
210
+ return payload;
211
+ }
107
212
  validate() {
108
213
  if (!this.provider) {
109
214
  throw new Error("Provider cannot be null or undefined");
@@ -111,10 +216,10 @@ export class OAuth2 {
111
216
  if (!this.config) {
112
217
  throw new Error("Config cannot be null or undefined");
113
218
  }
114
- if (!this.provider.authURL().trim()) {
219
+ if (!this.provider.authURL.trim()) {
115
220
  throw new Error("Provider authorization URL cannot be empty");
116
221
  }
117
- if (!this.provider.tokenURL().trim()) {
222
+ if (!this.provider.tokenURL.trim()) {
118
223
  throw new Error("Provider token URL cannot be empty");
119
224
  }
120
225
  if (!this.config.clientID.trim()) {
@@ -1 +1 @@
1
- {"version":3,"file":"oauth2.js","sourceRoot":"","sources":["../src/oauth2.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EACH,WAAW,EACX,kBAAkB,GACrB,MAAM,aAAa,CAAC;AAErB,SAAS,eAAe,CAAC,KAAa;IAClC,OAAO,IAAI,eAAe,CAAC,CAAC,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC,CAAC;SACzC,QAAQ,EAAE;SACV,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC;AAChC,CAAC;AAED,MAAM,OAAO,MAAM;IAEH,QAAQ;IACR,MAAM;IAFlB,YACY,QAAkB,EAClB,MAAc;wBADd,QAAQ;sBACR,MAAM;QAEd,IAAI,CAAC,QAAQ,EAAE,CAAC;IACpB,CAAC;IAED,WAAW,CAAC,KAAa,EAAE,SAAkC;QACzD,MAAM,MAAM,GAAG,IAAI,eAAe,EAAE,CAAC;QAErC,MAAM,CAAC,GAAG,CAAC,WAAW,EAAE,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;QAC9C,MAAM,CAAC,GAAG,CAAC,cAAc,EAAE,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QACpD,MAAM,CAAC,GAAG,CAAC,eAAe,EAAE,MAAM,CAAC,CAAC;QAEpC,WAAW,CACP,kBAAkB,EAAE,EACpB,SAAS,IAAI,EAAE,EACf,CAAC,GAAG,EAAE,KAAK,EAAE,EAAE;YACX,MAAM,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;QAC3B,CAAC,CACJ,CAAC;QAEF,IAAI,KAAK,KAAK,EAAE,EAAE,CAAC;YACf,MAAM,CAAC,GAAG,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;QAC/B,CAAC;QAED,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC,CAAC;QAE7C,MAAM,CAAC,OAAO,CAAC,CAAC,KAAK,EAAE,GAAG,EAAE,EAAE;YAC1B,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;QACrC,CAAC,CAAC,CAAC;QAEH,OAAO,GAAG,CAAC,QAAQ,EAAE,CAAC;IAC1B,CAAC;IAED,KAAK,CAAC,gBAAgB,CAAC,IAAY,EAAE,WAAoC;QACrE,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,EAAE,CAAC;YACf,MAAM,IAAI,KAAK,CAAC,sBAAsB,CAAC,CAAC;QAC5C,CAAC;QAED,MAAM,MAAM,GAAG,IAAI,eAAe,EAAE,CAAC;QAErC,MAAM,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;QACzB,MAAM,CAAC,GAAG,CAAC,cAAc,EAAE,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QACpD,MAAM,CAAC,GAAG,CAAC,YAAY,EAAE,oBAAoB,CAAC,CAAC;QAE/C,OAAO,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,kBAAkB,EAAE,EAAE,WAAW,CAAC,CAAC;IACpE,CAAC;IAED,KAAK,CAAC,oBAAoB,CAAC,YAAoB,EAAE,WAAoC;QACjF,IAAI,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,CAAC;YACvB,MAAM,IAAI,KAAK,CAAC,+BAA+B,CAAC,CAAC;QACrD,CAAC;QAED,MAAM,MAAM,GAAG,IAAI,eAAe,EAAE,CAAC;QAErC,MAAM,CAAC,GAAG,CAAC,eAAe,EAAE,YAAY,CAAC,CAAC;QAC1C,MAAM,CAAC,GAAG,CAAC,cAAc,EAAE,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QACpD,MAAM,CAAC,GAAG,CAAC,YAAY,EAAE,eAAe,CAAC,CAAC;QAE1C,OAAO,IAAI,CAAC,QAAQ,CAChB,MAAM,EACN,kBAAkB,EAAE,EACpB,WAAW,CACd,CAAC;IACN,CAAC;IAEO,KAAK,CAAC,QAAQ,CAClB,MAAuB,EACvB,cAA2B,EAC3B,WAAoC;QAGpC,WAAW,CACP,cAAc,EACd,WAAW,IAAI,EAAE,EACjB,CAAC,GAAG,EAAE,KAAK,EAAE,EAAE;YACX,MAAM,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;QAC3B,CAAC,CACJ,CAAC;QAEF,MAAM,UAAU,GAAG,IAAI,CAAC,MAAM,CAAC,gBAAgB,IAAI,qBAAqB,CAAC;QAEzE,MAAM,OAAO,GAA2B;YACpC,cAAc,EAAE,mCAAmC;SACtD,CAAC;QAEF,IAAI,UAAU,KAAK,qBAAqB,EAAE,CAAC;YACvC,MAAM,WAAW,GAAG,MAAM,CAAC,IAAI,CAC3B,GAAG,eAAe,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,eAAe,CAAC,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,EAAE,EACvF,MAAM,CACT,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;YAErB,OAAO,CAAC,eAAe,CAAC,GAAG,SAAS,WAAW,EAAE,CAAC;QACtD,CAAC;aAAM,CAAC;YACJ,MAAM,CAAC,GAAG,CAAC,WAAW,EAAE,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;YAC9C,MAAM,CAAC,GAAG,CAAC,eAAe,EAAE,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC;QAC1D,CAAC;QAED,IAAI,QAAkB,CAAC;QAEvB,IAAI,CAAC;YACD,QAAQ,GAAG,MAAM,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,EAAE,EAAE;gBAC7C,MAAM,EAAE,MAAM;gBACd,OAAO;gBACP,IAAI,EAAE,MAAM,CAAC,QAAQ,EAAE;aAC1B,CAAC,CAAC;QACP,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,MAAM,IAAI,SAAS,CACf,wCAAwC,EACxC,SAAS,EACT,SAAS,EACT,EAAE,KAAK,EAAE,KAAK,EAAE,CACnB,CAAC;QACN,CAAC;QAED,IAAI,GAAW,CAAC;QAEhB,IAAI,CAAC;YACD,GAAG,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;QAChC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,MAAM,IAAI,SAAS,CACf,yCAAyC,EACzC,QAAQ,CAAC,MAAM,EACf,SAAS,EACT,EAAE,KAAK,EAAE,KAAK,EAAE,CACnB,CAAC;QACN,CAAC;QAED,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;YACf,MAAM,IAAI,SAAS,CACf,8CAA8C,QAAQ,CAAC,MAAM,EAAE,EAC/D,QAAQ,CAAC,MAAM,EACf,GAAG,CACN,CAAC;QACN,CAAC;QAED,IAAI,MAAe,CAAC;QAEpB,IAAI,CAAC;YACD,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QAC7B,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,MAAM,IAAI,SAAS,CACf,0CAA0C,EAC1C,QAAQ,CAAC,MAAM,EACf,GAAG,EACH,EAAE,KAAK,EAAE,KAAK,EAAE,CACnB,CAAC;QACN,CAAC;QAED,IACI,OAAO,MAAM,KAAK,QAAQ;YAC1B,MAAM,KAAK,IAAI;YACf,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,EACvB,CAAC;YACC,MAAM,IAAI,SAAS,CACf,gDAAgD,EAChD,QAAQ,CAAC,MAAM,EACf,GAAG,CACN,CAAC;QACN,CAAC;QAED,OAAO;YACH,GAAG;YACH,IAAI,EAAE,MAAiC;SAC1C,CAAC;IACN,CAAC;IAEO,QAAQ;QACZ,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC;YACjB,MAAM,IAAI,KAAK,CAAC,sCAAsC,CAAC,CAAC;QAC5D,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE,CAAC;YACf,MAAM,IAAI,KAAK,CAAC,oCAAoC,CAAC,CAAC;QAC1D,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC,IAAI,EAAE,EAAE,CAAC;YAClC,MAAM,IAAI,KAAK,CAAC,4CAA4C,CAAC,CAAC;QAClE,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,EAAE,CAAC,IAAI,EAAE,EAAE,CAAC;YACnC,MAAM,IAAI,KAAK,CAAC,oCAAoC,CAAC,CAAC;QAC1D,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,EAAE,EAAE,CAAC;YAC/B,MAAM,IAAI,KAAK,CAAC,2BAA2B,CAAC,CAAC;QACjD,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,CAAC;YACnC,MAAM,IAAI,KAAK,CAAC,+BAA+B,CAAC,CAAC;QACrD,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,IAAI,EAAE,EAAE,CAAC;YAClC,MAAM,IAAI,KAAK,CAAC,8BAA8B,CAAC,CAAC;QACpD,CAAC;QAED,IACI,IAAI,CAAC,MAAM,CAAC,gBAAgB,KAAK,SAAS;YAC1C,CAAC,CAAC,qBAAqB,EAAE,oBAAoB,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,MAAM,CAAC,gBAAgB,CAAC,EACvF,CAAC;YACC,MAAM,IAAI,KAAK,CAAC,0CAA0C,CAAC,CAAC;QAChE,CAAC;IACL,CAAC;CACJ"}
1
+ {"version":3,"file":"oauth2.js","sourceRoot":"","sources":["../src/oauth2.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,7 @@
1
1
  export interface Provider {
2
- authURL(): string;
3
- tokenURL(): string;
2
+ authURL: string;
3
+ tokenURL: string;
4
+ issuerURL?: string;
5
+ jwksURL?: string;
4
6
  }
5
7
  //# sourceMappingURL=provider.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"provider.d.ts","sourceRoot":"","sources":["../src/provider.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,QAAQ;IACrB,OAAO,IAAI,MAAM,CAAC;IAClB,QAAQ,IAAI,MAAM,CAAC;CACtB"}
1
+ {"version":3,"file":"provider.d.ts","sourceRoot":"","sources":["../src/provider.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,QAAQ;IACrB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;CACpB"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@o2js/core",
3
- "version": "0.1.0",
3
+ "version": "0.2.0",
4
4
  "description": "A minimal, provider-agnostic OAuth 2.0 client for Node.js.",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -23,9 +23,16 @@
23
23
  "oauth",
24
24
  "oauth2",
25
25
  "oauth-2.0",
26
+ "openid",
27
+ "openid-connect",
28
+ "oidc",
29
+ "pkce",
30
+ "authorization-code",
31
+ "refresh-token",
26
32
  "authentication",
27
33
  "authorization",
28
34
  "node",
35
+ "nodejs",
29
36
  "typescript"
30
37
  ],
31
38
  "scripts": {
@@ -35,5 +42,8 @@
35
42
  "devDependencies": {
36
43
  "@types/node": "^26.6.6",
37
44
  "typescript": "^7.0.2"
45
+ },
46
+ "dependencies": {
47
+ "jose": "^6.2.15"
38
48
  }
39
- }
49
+ }