@inrupt/solid-client-authn-browser 3.0.0 → 3.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +2 -1
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +3 -2
- package/dist/index.mjs.map +1 -1
- package/dist/login/oidc/__mocks__/IOidcOptions.d.ts +1 -1
- package/dist/solid-client-authn.bundle.js +2 -2
- package/dist/solid-client-authn.bundle.js.map +1 -1
- package/package.json +5 -5
- package/src/login/oidc/OidcLoginHandler.spec.ts +75 -0
- package/src/login/oidc/OidcLoginHandler.ts +2 -0
- package/src/login/oidc/__mocks__/IOidcOptions.ts +5 -1
- package/src/login/oidc/oidcHandlers/AuthorizationCodeWithPkceOidcHandler.spec.ts +3 -2
- package/src/login/oidc/oidcHandlers/AuthorizationCodeWithPkceOidcHandler.ts +2 -5
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@inrupt/solid-client-authn-browser",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.1.0",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"types": "dist/index.d.ts",
|
|
6
6
|
"browser": "dist/index.js",
|
|
@@ -26,12 +26,12 @@
|
|
|
26
26
|
"build-docs-preview-site": "npm run build-api-docs; cd docs/api; make html"
|
|
27
27
|
},
|
|
28
28
|
"devDependencies": {
|
|
29
|
-
"@types/node": "^24.0.
|
|
29
|
+
"@types/node": "^24.0.10",
|
|
30
30
|
"@types/uuid": "^10.0.0"
|
|
31
31
|
},
|
|
32
32
|
"dependencies": {
|
|
33
|
-
"@inrupt/oidc-client-ext": "^3.
|
|
34
|
-
"@inrupt/solid-client-authn-core": "^3.
|
|
33
|
+
"@inrupt/oidc-client-ext": "^3.1.0",
|
|
34
|
+
"@inrupt/solid-client-authn-core": "^3.1.0",
|
|
35
35
|
"events": "^3.3.0",
|
|
36
36
|
"jose": "^5.1.3",
|
|
37
37
|
"uuid": "^11.1.0"
|
|
@@ -39,5 +39,5 @@
|
|
|
39
39
|
"publishConfig": {
|
|
40
40
|
"access": "public"
|
|
41
41
|
},
|
|
42
|
-
"gitHead": "
|
|
42
|
+
"gitHead": "c30be8b6ddd243ed45ef93cbb3a27daf4e3faab0"
|
|
43
43
|
}
|
|
@@ -58,6 +58,18 @@ describe("OidcLoginHandler", () => {
|
|
|
58
58
|
);
|
|
59
59
|
}
|
|
60
60
|
|
|
61
|
+
const oidcHandlerWithMocks = () => {
|
|
62
|
+
const actualHandler = defaultMocks.oidcHandler;
|
|
63
|
+
const issuerConfig = IssuerConfigFetcherFetchConfigResponse;
|
|
64
|
+
const handler = getInitialisedHandler({
|
|
65
|
+
issuerConfigFetcher: mockIssuerConfigFetcher(
|
|
66
|
+
issuerConfig,
|
|
67
|
+
) as jest.Mocked<IIssuerConfigFetcher>,
|
|
68
|
+
oidcHandler: actualHandler,
|
|
69
|
+
});
|
|
70
|
+
return { handler, mockOidcHandler: actualHandler };
|
|
71
|
+
};
|
|
72
|
+
|
|
61
73
|
it("should call the actual handler when an Oidc Issuer is provided", async () => {
|
|
62
74
|
const actualHandler = defaultMocks.oidcHandler;
|
|
63
75
|
const handler = getInitialisedHandler({ oidcHandler: actualHandler });
|
|
@@ -322,4 +334,67 @@ describe("OidcLoginHandler", () => {
|
|
|
322
334
|
}),
|
|
323
335
|
);
|
|
324
336
|
});
|
|
337
|
+
|
|
338
|
+
it("ignores malformed scopes", async () => {
|
|
339
|
+
const { handler, mockOidcHandler } = oidcHandlerWithMocks();
|
|
340
|
+
await handler.handle({
|
|
341
|
+
sessionId: "mySession",
|
|
342
|
+
oidcIssuer: "https://arbitrary.url",
|
|
343
|
+
redirectUrl: "https://app.com/redirect",
|
|
344
|
+
tokenType: "DPoP",
|
|
345
|
+
keepAlive: false,
|
|
346
|
+
customScopes: [
|
|
347
|
+
// @ts-expect-error This tests misuse of the API.
|
|
348
|
+
{ not: "a string" },
|
|
349
|
+
"some invalid scope including spaces",
|
|
350
|
+
"valid_scope",
|
|
351
|
+
],
|
|
352
|
+
});
|
|
353
|
+
expect(mockOidcHandler.handle).toHaveBeenCalledWith(
|
|
354
|
+
expect.objectContaining({
|
|
355
|
+
scopes: ["openid", "offline_access", "webid", "valid_scope"],
|
|
356
|
+
}),
|
|
357
|
+
);
|
|
358
|
+
});
|
|
359
|
+
|
|
360
|
+
it("adds provided scopes to default ones", async () => {
|
|
361
|
+
const { handler, mockOidcHandler } = oidcHandlerWithMocks();
|
|
362
|
+
await handler.handle({
|
|
363
|
+
sessionId: "mySession",
|
|
364
|
+
oidcIssuer: "https://arbitrary.url",
|
|
365
|
+
redirectUrl: "https://app.com/redirect",
|
|
366
|
+
tokenType: "DPoP",
|
|
367
|
+
keepAlive: false,
|
|
368
|
+
customScopes: ["scope_1", "scope_2", "scope_3"],
|
|
369
|
+
});
|
|
370
|
+
expect(mockOidcHandler.handle).toHaveBeenCalledWith(
|
|
371
|
+
expect.objectContaining({
|
|
372
|
+
scopes: [
|
|
373
|
+
"openid",
|
|
374
|
+
"offline_access",
|
|
375
|
+
"webid",
|
|
376
|
+
"scope_1",
|
|
377
|
+
"scope_2",
|
|
378
|
+
"scope_3",
|
|
379
|
+
],
|
|
380
|
+
}),
|
|
381
|
+
);
|
|
382
|
+
});
|
|
383
|
+
|
|
384
|
+
it("de-dupes scopes", async () => {
|
|
385
|
+
const { handler, mockOidcHandler } = oidcHandlerWithMocks();
|
|
386
|
+
await handler.handle({
|
|
387
|
+
sessionId: "mySession",
|
|
388
|
+
oidcIssuer: "https://arbitrary.url",
|
|
389
|
+
redirectUrl: "https://app.com/redirect",
|
|
390
|
+
tokenType: "DPoP",
|
|
391
|
+
keepAlive: false,
|
|
392
|
+
customScopes: ["webid", "custom_scope", "custom_scope"],
|
|
393
|
+
});
|
|
394
|
+
expect(mockOidcHandler.handle).toHaveBeenCalledWith(
|
|
395
|
+
expect.objectContaining({
|
|
396
|
+
scopes: ["openid", "offline_access", "webid", "custom_scope"],
|
|
397
|
+
}),
|
|
398
|
+
);
|
|
399
|
+
});
|
|
325
400
|
});
|
|
@@ -42,6 +42,7 @@ import type {
|
|
|
42
42
|
import {
|
|
43
43
|
ConfigurationError,
|
|
44
44
|
handleRegistration,
|
|
45
|
+
normalizeScopes,
|
|
45
46
|
} from "@inrupt/solid-client-authn-core";
|
|
46
47
|
|
|
47
48
|
function hasIssuer(
|
|
@@ -116,6 +117,7 @@ export default class OidcLoginHandler implements ILoginHandler {
|
|
|
116
117
|
...options,
|
|
117
118
|
issuerConfiguration: issuerConfig,
|
|
118
119
|
client: clientRegistration,
|
|
120
|
+
scopes: normalizeScopes(options.customScopes),
|
|
119
121
|
};
|
|
120
122
|
|
|
121
123
|
// Call proper OIDC Handler
|
|
@@ -19,7 +19,10 @@
|
|
|
19
19
|
// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
20
20
|
//
|
|
21
21
|
|
|
22
|
-
import
|
|
22
|
+
import {
|
|
23
|
+
DEFAULT_SCOPES,
|
|
24
|
+
type IOidcOptions,
|
|
25
|
+
} from "@inrupt/solid-client-authn-core";
|
|
23
26
|
import { jest } from "@jest/globals";
|
|
24
27
|
|
|
25
28
|
export const standardOidcOptions: IOidcOptions = {
|
|
@@ -42,4 +45,5 @@ export const standardOidcOptions: IOidcOptions = {
|
|
|
42
45
|
clientId: "coolApp",
|
|
43
46
|
clientType: "dynamic",
|
|
44
47
|
},
|
|
48
|
+
scopes: DEFAULT_SCOPES,
|
|
45
49
|
};
|
|
@@ -235,7 +235,7 @@ describe("AuthorizationCodeWithPkceOidcHandler", () => {
|
|
|
235
235
|
);
|
|
236
236
|
});
|
|
237
237
|
|
|
238
|
-
it("
|
|
238
|
+
it("includes the provided scopes in the authorization request", async () => {
|
|
239
239
|
const oidcModule = mockOidcModule();
|
|
240
240
|
const authorizationCodeWithPkceOidcHandler =
|
|
241
241
|
getAuthorizationCodeWithPkceOidcHandler();
|
|
@@ -245,11 +245,12 @@ describe("AuthorizationCodeWithPkceOidcHandler", () => {
|
|
|
245
245
|
...standardOidcOptions.issuerConfiguration,
|
|
246
246
|
grantTypesSupported: ["authorization_code"],
|
|
247
247
|
},
|
|
248
|
+
scopes: ["openid", "webid", "custom_scope"],
|
|
248
249
|
};
|
|
249
250
|
await authorizationCodeWithPkceOidcHandler.handle(oidcOptions);
|
|
250
251
|
expect(oidcModule.OidcClient).toHaveBeenCalledWith(
|
|
251
252
|
expect.objectContaining({
|
|
252
|
-
scope: "openid
|
|
253
|
+
scope: "openid webid custom_scope",
|
|
253
254
|
}),
|
|
254
255
|
);
|
|
255
256
|
});
|
|
@@ -32,10 +32,7 @@ import type {
|
|
|
32
32
|
IOidcOptions,
|
|
33
33
|
LoginResult,
|
|
34
34
|
} from "@inrupt/solid-client-authn-core";
|
|
35
|
-
import {
|
|
36
|
-
DEFAULT_SCOPES,
|
|
37
|
-
AuthorizationCodeWithPkceOidcHandlerBase,
|
|
38
|
-
} from "@inrupt/solid-client-authn-core";
|
|
35
|
+
import { AuthorizationCodeWithPkceOidcHandlerBase } from "@inrupt/solid-client-authn-core";
|
|
39
36
|
import { OidcClient } from "@inrupt/oidc-client-ext";
|
|
40
37
|
|
|
41
38
|
/**
|
|
@@ -55,7 +52,7 @@ export default class AuthorizationCodeWithPkceOidcHandler
|
|
|
55
52
|
client_secret: oidcLoginOptions.client.clientSecret,
|
|
56
53
|
redirect_uri: oidcLoginOptions.redirectUrl,
|
|
57
54
|
response_type: "code",
|
|
58
|
-
scope:
|
|
55
|
+
scope: oidcLoginOptions.scopes.join(" "),
|
|
59
56
|
filterProtocolClaims: true,
|
|
60
57
|
// The userinfo endpoint on NSS fails, so disable this for now
|
|
61
58
|
// Note that in Solid, information should be retrieved from the
|