@atproto/oauth-provider 0.5.2 → 0.6.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/CHANGELOG.md +37 -0
- package/dist/account/account-manager.d.ts +7 -5
- package/dist/account/account-manager.d.ts.map +1 -1
- package/dist/account/account-manager.js +34 -25
- package/dist/account/account-manager.js.map +1 -1
- package/dist/account/account-store.d.ts +7 -0
- package/dist/account/account-store.d.ts.map +1 -1
- package/dist/account/account-store.js.map +1 -1
- package/dist/account/account.d.ts +1 -11
- package/dist/account/account.d.ts.map +1 -1
- package/dist/account/{sign-up-data.d.ts → sign-up-input.d.ts} +3 -3
- package/dist/account/sign-up-input.d.ts.map +1 -0
- package/dist/account/{sign-up-data.js → sign-up-input.js} +3 -3
- package/dist/account/sign-up-input.js.map +1 -0
- package/dist/assets/assets-middleware.d.ts +2 -0
- package/dist/assets/assets-middleware.d.ts.map +1 -1
- package/dist/assets/assets-middleware.js +12 -14
- package/dist/assets/assets-middleware.js.map +1 -1
- package/dist/lib/csp/index.d.ts +5 -6
- package/dist/lib/csp/index.d.ts.map +1 -1
- package/dist/lib/csp/index.js +14 -11
- package/dist/lib/csp/index.js.map +1 -1
- package/dist/lib/hcaptcha.d.ts +15 -12
- package/dist/lib/hcaptcha.d.ts.map +1 -1
- package/dist/lib/hcaptcha.js +11 -7
- package/dist/lib/hcaptcha.js.map +1 -1
- package/dist/lib/html/build-document.d.ts +2 -2
- package/dist/lib/html/build-document.d.ts.map +1 -1
- package/dist/lib/html/build-document.js +11 -7
- package/dist/lib/html/build-document.js.map +1 -1
- package/dist/lib/html/html.d.ts.map +1 -1
- package/dist/lib/html/html.js +10 -13
- package/dist/lib/html/html.js.map +1 -1
- package/dist/lib/html/util.d.ts +0 -1
- package/dist/lib/html/util.d.ts.map +1 -1
- package/dist/lib/html/util.js +0 -4
- package/dist/lib/html/util.js.map +1 -1
- package/dist/lib/http/response.d.ts +3 -1
- package/dist/lib/http/response.d.ts.map +1 -1
- package/dist/lib/http/response.js +3 -0
- package/dist/lib/http/response.js.map +1 -1
- package/dist/lib/http/security-headers.d.ts +48 -0
- package/dist/lib/http/security-headers.d.ts.map +1 -0
- package/dist/lib/http/security-headers.js +62 -0
- package/dist/lib/http/security-headers.js.map +1 -0
- package/dist/lib/util/type.d.ts +8 -0
- package/dist/lib/util/type.d.ts.map +1 -1
- package/dist/lib/util/type.js.map +1 -1
- package/dist/oauth-hooks.d.ts +4 -25
- package/dist/oauth-hooks.d.ts.map +1 -1
- package/dist/oauth-provider.js +2 -2
- package/dist/oauth-provider.js.map +1 -1
- package/dist/output/backend-data.d.ts +4 -0
- package/dist/output/backend-data.d.ts.map +1 -0
- package/dist/output/backend-data.js +19 -0
- package/dist/output/backend-data.js.map +1 -0
- package/dist/output/build-authorize-data.d.ts +3 -19
- package/dist/output/build-authorize-data.d.ts.map +1 -1
- package/dist/output/build-authorize-data.js.map +1 -1
- package/dist/output/build-customization-data.d.ts +11 -18
- package/dist/output/build-customization-data.d.ts.map +1 -1
- package/dist/output/build-customization-data.js +1 -1
- package/dist/output/build-customization-data.js.map +1 -1
- package/dist/output/build-error-data.d.ts +3 -0
- package/dist/output/build-error-data.d.ts.map +1 -0
- package/dist/output/build-error-data.js +10 -0
- package/dist/output/build-error-data.js.map +1 -0
- package/dist/output/build-error-payload.d.ts +2 -1
- package/dist/output/build-error-payload.d.ts.map +1 -1
- package/dist/output/build-error-payload.js.map +1 -1
- package/dist/output/output-manager.d.ts +10 -4
- package/dist/output/output-manager.d.ts.map +1 -1
- package/dist/output/output-manager.js +68 -39
- package/dist/output/output-manager.js.map +1 -1
- package/dist/output/send-web-page.d.ts +6 -10
- package/dist/output/send-web-page.d.ts.map +1 -1
- package/dist/output/send-web-page.js +27 -47
- package/dist/output/send-web-page.js.map +1 -1
- package/dist/signer/signed-token-payload.d.ts +3 -3
- package/dist/signer/signer.d.ts +2 -2
- package/package.json +8 -41
- package/src/account/account-manager.ts +55 -34
- package/src/account/account-store.ts +8 -0
- package/src/account/account.ts +1 -14
- package/src/account/{sign-up-data.ts → sign-up-input.ts} +2 -2
- package/src/assets/assets-middleware.ts +11 -17
- package/src/lib/csp/index.ts +16 -13
- package/src/lib/hcaptcha.ts +14 -10
- package/src/lib/html/build-document.ts +15 -8
- package/src/lib/html/html.ts +11 -18
- package/src/lib/html/util.ts +0 -4
- package/src/lib/http/response.ts +9 -1
- package/src/lib/http/security-headers.ts +91 -0
- package/src/lib/util/type.ts +18 -0
- package/src/oauth-hooks.ts +4 -25
- package/src/oauth-provider.ts +2 -2
- package/src/output/backend-data.ts +18 -0
- package/src/output/build-authorize-data.ts +3 -26
- package/src/output/build-customization-data.ts +2 -13
- package/src/output/build-error-data.ts +8 -0
- package/src/output/build-error-payload.ts +4 -2
- package/src/output/output-manager.ts +86 -47
- package/src/output/send-web-page.ts +29 -58
- package/tsconfig.backend.json +1 -2
- package/tsconfig.backend.tsbuildinfo +1 -1
- package/tsconfig.json +1 -5
- package/.linguirc +0 -57
- package/dist/account/sign-up-data.d.ts.map +0 -1
- package/dist/account/sign-up-data.js.map +0 -1
- package/dist/assets/app/bundle-manifest.json +0 -614
- package/dist/assets/app/index-DZHZ9kCP.js +0 -36
- package/dist/assets/app/index-DZHZ9kCP.js.map +0 -1
- package/dist/assets/app/main-B_dNxQo_.js +0 -4
- package/dist/assets/app/main-B_dNxQo_.js.map +0 -1
- package/dist/assets/app/main-Dr6y26KY.css +0 -3
- package/dist/assets/app/main-Dr6y26KY.js +0 -306
- package/dist/assets/app/main-Dr6y26KY.js.map +0 -1
- package/dist/assets/app/messages-6_mYuGzB.js +0 -4
- package/dist/assets/app/messages-6_mYuGzB.js.map +0 -1
- package/dist/assets/app/messages-7wdeBTpD.js +0 -4
- package/dist/assets/app/messages-7wdeBTpD.js.map +0 -1
- package/dist/assets/app/messages-B-YFoWKc.js +0 -4
- package/dist/assets/app/messages-B-YFoWKc.js.map +0 -1
- package/dist/assets/app/messages-B10DUOE-.js +0 -4
- package/dist/assets/app/messages-B10DUOE-.js.map +0 -1
- package/dist/assets/app/messages-B4AwFEeZ.js +0 -4
- package/dist/assets/app/messages-B4AwFEeZ.js.map +0 -1
- package/dist/assets/app/messages-BDP8MyEC.js +0 -4
- package/dist/assets/app/messages-BDP8MyEC.js.map +0 -1
- package/dist/assets/app/messages-BIS87lxQ.js +0 -4
- package/dist/assets/app/messages-BIS87lxQ.js.map +0 -1
- package/dist/assets/app/messages-BI_Wbjdt.js +0 -4
- package/dist/assets/app/messages-BI_Wbjdt.js.map +0 -1
- package/dist/assets/app/messages-BMAouhRx.js +0 -4
- package/dist/assets/app/messages-BMAouhRx.js.map +0 -1
- package/dist/assets/app/messages-BdckMnJj.js +0 -4
- package/dist/assets/app/messages-BdckMnJj.js.map +0 -1
- package/dist/assets/app/messages-BgBLzc46.js +0 -4
- package/dist/assets/app/messages-BgBLzc46.js.map +0 -1
- package/dist/assets/app/messages-BobD78yK.js +0 -4
- package/dist/assets/app/messages-BobD78yK.js.map +0 -1
- package/dist/assets/app/messages-BtThT9UZ.js +0 -4
- package/dist/assets/app/messages-BtThT9UZ.js.map +0 -1
- package/dist/assets/app/messages-BwKHkbeh.js +0 -4
- package/dist/assets/app/messages-BwKHkbeh.js.map +0 -1
- package/dist/assets/app/messages-C417YUvA.js +0 -4
- package/dist/assets/app/messages-C417YUvA.js.map +0 -1
- package/dist/assets/app/messages-C4CxO4bO.js +0 -4
- package/dist/assets/app/messages-C4CxO4bO.js.map +0 -1
- package/dist/assets/app/messages-C5vd04e6.js +0 -4
- package/dist/assets/app/messages-C5vd04e6.js.map +0 -1
- package/dist/assets/app/messages-CAri2Wnz.js +0 -4
- package/dist/assets/app/messages-CAri2Wnz.js.map +0 -1
- package/dist/assets/app/messages-CPtWTZeG.js +0 -4
- package/dist/assets/app/messages-CPtWTZeG.js.map +0 -1
- package/dist/assets/app/messages-CiaM5zm8.js +0 -4
- package/dist/assets/app/messages-CiaM5zm8.js.map +0 -1
- package/dist/assets/app/messages-CkL-L2R6.js +0 -4
- package/dist/assets/app/messages-CkL-L2R6.js.map +0 -1
- package/dist/assets/app/messages-Cy_4XLNe.js +0 -4
- package/dist/assets/app/messages-Cy_4XLNe.js.map +0 -1
- package/dist/assets/app/messages-D5_ad-Eo.js +0 -4
- package/dist/assets/app/messages-D5_ad-Eo.js.map +0 -1
- package/dist/assets/app/messages-DChMl9mT.js +0 -4
- package/dist/assets/app/messages-DChMl9mT.js.map +0 -1
- package/dist/assets/app/messages-DWX-DIfv.js +0 -4
- package/dist/assets/app/messages-DWX-DIfv.js.map +0 -1
- package/dist/assets/app/messages-DgfsOphe.js +0 -4
- package/dist/assets/app/messages-DgfsOphe.js.map +0 -1
- package/dist/assets/app/messages-Dj5B_DR6.js +0 -4
- package/dist/assets/app/messages-Dj5B_DR6.js.map +0 -1
- package/dist/assets/app/messages-Dwzqo4eA.js +0 -4
- package/dist/assets/app/messages-Dwzqo4eA.js.map +0 -1
- package/dist/assets/app/messages-ESCIXJR7.js +0 -4
- package/dist/assets/app/messages-ESCIXJR7.js.map +0 -1
- package/dist/assets/app/messages-dglB2edb.js +0 -4
- package/dist/assets/app/messages-dglB2edb.js.map +0 -1
- package/dist/assets/app/messages-e_ClRrWc.js +0 -4
- package/dist/assets/app/messages-e_ClRrWc.js.map +0 -1
- package/dist/assets/app/messages-evvDxmrP.js +0 -4
- package/dist/assets/app/messages-evvDxmrP.js.map +0 -1
- package/dist/assets/app/messages-pPbdLb5B.js +0 -4
- package/dist/assets/app/messages-pPbdLb5B.js.map +0 -1
- package/dist/assets/app/messages-tJv8gHL2.js +0 -4
- package/dist/assets/app/messages-tJv8gHL2.js.map +0 -1
- package/dist/assets/app/messages-vLRVEw96.js +0 -4
- package/dist/assets/app/messages-vLRVEw96.js.map +0 -1
- package/dist/assets/asset.d.ts +0 -9
- package/dist/assets/asset.d.ts.map +0 -1
- package/dist/assets/asset.js +0 -3
- package/dist/assets/asset.js.map +0 -1
- package/dist/assets/index.d.ts +0 -5
- package/dist/assets/index.d.ts.map +0 -1
- package/dist/assets/index.js +0 -78
- package/dist/assets/index.js.map +0 -1
- package/rollup.config.js +0 -98
- package/src/assets/app/app.tsx +0 -43
- package/src/assets/app/backend-data.ts +0 -27
- package/src/assets/app/backend-types.ts +0 -66
- package/src/assets/app/components/forms/button-toggle-visibility.tsx +0 -43
- package/src/assets/app/components/forms/button.tsx +0 -60
- package/src/assets/app/components/forms/fieldset.tsx +0 -55
- package/src/assets/app/components/forms/form-card-async.tsx +0 -103
- package/src/assets/app/components/forms/form-card.tsx +0 -49
- package/src/assets/app/components/forms/input-checkbox.tsx +0 -78
- package/src/assets/app/components/forms/input-container.tsx +0 -107
- package/src/assets/app/components/forms/input-email-address.tsx +0 -65
- package/src/assets/app/components/forms/input-new-password.tsx +0 -62
- package/src/assets/app/components/forms/input-password.tsx +0 -87
- package/src/assets/app/components/forms/input-text.tsx +0 -82
- package/src/assets/app/components/forms/input-token.tsx +0 -94
- package/src/assets/app/components/forms/wizard-card.tsx +0 -116
- package/src/assets/app/components/layouts/layout-title-page.tsx +0 -77
- package/src/assets/app/components/layouts/layout-welcome.tsx +0 -73
- package/src/assets/app/components/utils/account-identifier.tsx +0 -23
- package/src/assets/app/components/utils/account-image.tsx +0 -33
- package/src/assets/app/components/utils/admonition.tsx +0 -52
- package/src/assets/app/components/utils/client-name.tsx +0 -45
- package/src/assets/app/components/utils/error-card.tsx +0 -93
- package/src/assets/app/components/utils/error-message.tsx +0 -88
- package/src/assets/app/components/utils/help-card.tsx +0 -46
- package/src/assets/app/components/utils/icons.tsx +0 -88
- package/src/assets/app/components/utils/link-anchor.tsx +0 -28
- package/src/assets/app/components/utils/link-title.tsx +0 -26
- package/src/assets/app/components/utils/multi-lang-string.tsx +0 -56
- package/src/assets/app/components/utils/password-strength-label.tsx +0 -37
- package/src/assets/app/components/utils/password-strength-meter.tsx +0 -58
- package/src/assets/app/components/utils/url-viewer.tsx +0 -73
- package/src/assets/app/cookies.ts +0 -11
- package/src/assets/app/hooks/use-api.ts +0 -178
- package/src/assets/app/hooks/use-async-action.ts +0 -120
- package/src/assets/app/hooks/use-bound-dispatch.ts +0 -5
- package/src/assets/app/hooks/use-browser-color-scheme.ts +0 -31
- package/src/assets/app/hooks/use-csrf-token.ts +0 -5
- package/src/assets/app/hooks/use-random-string.ts +0 -37
- package/src/assets/app/hooks/use-stepper.ts +0 -87
- package/src/assets/app/index.html +0 -182
- package/src/assets/app/lib/api.ts +0 -289
- package/src/assets/app/lib/clsx.ts +0 -6
- package/src/assets/app/lib/json-client.ts +0 -94
- package/src/assets/app/lib/password.ts +0 -98
- package/src/assets/app/lib/ref.ts +0 -17
- package/src/assets/app/lib/util.ts +0 -13
- package/src/assets/app/locales/an/messages.po +0 -490
- package/src/assets/app/locales/ast/messages.po +0 -490
- package/src/assets/app/locales/ca/messages.po +0 -490
- package/src/assets/app/locales/da/messages.po +0 -490
- package/src/assets/app/locales/de/messages.po +0 -490
- package/src/assets/app/locales/el/messages.po +0 -490
- package/src/assets/app/locales/en/messages.po +0 -490
- package/src/assets/app/locales/en-GB/messages.po +0 -490
- package/src/assets/app/locales/es/messages.po +0 -490
- package/src/assets/app/locales/eu/messages.po +0 -490
- package/src/assets/app/locales/fi/messages.po +0 -490
- package/src/assets/app/locales/fr/messages.po +0 -490
- package/src/assets/app/locales/ga/messages.po +0 -490
- package/src/assets/app/locales/gl/messages.po +0 -490
- package/src/assets/app/locales/hi/messages.po +0 -490
- package/src/assets/app/locales/hu/messages.po +0 -490
- package/src/assets/app/locales/ia/messages.po +0 -490
- package/src/assets/app/locales/id/messages.po +0 -490
- package/src/assets/app/locales/it/messages.po +0 -490
- package/src/assets/app/locales/ja/messages.po +0 -490
- package/src/assets/app/locales/km/messages.po +0 -490
- package/src/assets/app/locales/ko/messages.po +0 -490
- package/src/assets/app/locales/load.ts +0 -8
- package/src/assets/app/locales/locale-context.ts +0 -19
- package/src/assets/app/locales/locale-provider.tsx +0 -112
- package/src/assets/app/locales/locale-selector.tsx +0 -58
- package/src/assets/app/locales/locales.ts +0 -168
- package/src/assets/app/locales/ne/messages.po +0 -490
- package/src/assets/app/locales/nl/messages.po +0 -490
- package/src/assets/app/locales/pl/messages.po +0 -490
- package/src/assets/app/locales/pt-BR/messages.po +0 -490
- package/src/assets/app/locales/ro/messages.po +0 -490
- package/src/assets/app/locales/ru/messages.po +0 -490
- package/src/assets/app/locales/sv/messages.po +0 -490
- package/src/assets/app/locales/th/messages.po +0 -490
- package/src/assets/app/locales/tr/messages.po +0 -490
- package/src/assets/app/locales/uk/messages.po +0 -490
- package/src/assets/app/locales/vi/messages.po +0 -490
- package/src/assets/app/locales/zh-CN/messages.po +0 -490
- package/src/assets/app/locales/zh-HK/messages.po +0 -490
- package/src/assets/app/locales/zh-TW/messages.po +0 -490
- package/src/assets/app/main.css +0 -33
- package/src/assets/app/main.tsx +0 -44
- package/src/assets/app/views/authorize/accept/accept-form.tsx +0 -150
- package/src/assets/app/views/authorize/accept/accept-view.tsx +0 -70
- package/src/assets/app/views/authorize/authorize-view.tsx +0 -180
- package/src/assets/app/views/authorize/reset-password/reset-password-confirm-form.tsx +0 -88
- package/src/assets/app/views/authorize/reset-password/reset-password-request-form.tsx +0 -80
- package/src/assets/app/views/authorize/reset-password/reset-password-view.tsx +0 -127
- package/src/assets/app/views/authorize/sign-in/sign-in-form.tsx +0 -242
- package/src/assets/app/views/authorize/sign-in/sign-in-picker.tsx +0 -116
- package/src/assets/app/views/authorize/sign-in/sign-in-view.tsx +0 -145
- package/src/assets/app/views/authorize/sign-up/sign-up-account-form.tsx +0 -142
- package/src/assets/app/views/authorize/sign-up/sign-up-disclaimer.tsx +0 -51
- package/src/assets/app/views/authorize/sign-up/sign-up-handle-form.tsx +0 -287
- package/src/assets/app/views/authorize/sign-up/sign-up-hcaptcha-form.tsx +0 -108
- package/src/assets/app/views/authorize/sign-up/sign-up-view.tsx +0 -158
- package/src/assets/app/views/authorize/welcome/welcome-view.tsx +0 -56
- package/src/assets/app/views/error/error-view.tsx +0 -31
- package/src/assets/asset.ts +0 -9
- package/src/assets/index.ts +0 -86
- package/tailwind.config.js +0 -31
- package/tsconfig.frontend.json +0 -11
- package/tsconfig.frontend.tsbuildinfo +0 -1
- package/tsconfig.tools.json +0 -8
- package/tsconfig.tools.tsbuildinfo +0 -1
- package/vite.config.mjs +0 -16
@@ -1,8 +1,10 @@
|
|
1
1
|
import type { ServerResponse } from 'node:http'
|
2
|
-
import {
|
3
|
-
import {
|
2
|
+
import { CustomizationData } from '@atproto/oauth-provider-api'
|
3
|
+
import { assets } from '@atproto/oauth-provider-ui'
|
4
|
+
import { buildAssetUrl } from '../assets/assets-middleware.js'
|
4
5
|
import { CspConfig, mergeCsp } from '../lib/csp/index.js'
|
5
6
|
import {
|
7
|
+
AssetRef,
|
6
8
|
Html,
|
7
9
|
LinkAttrs,
|
8
10
|
MetaAttrs,
|
@@ -10,7 +12,9 @@ import {
|
|
10
12
|
html,
|
11
13
|
isLinkRel,
|
12
14
|
} from '../lib/html/index.js'
|
15
|
+
import { CrossOriginEmbedderPolicy } from '../lib/http/security-headers.js'
|
13
16
|
import { AVAILABLE_LOCALES, Locale, isAvailableLocale } from '../lib/locale.js'
|
17
|
+
import { declareBackendData } from './backend-data.js'
|
14
18
|
import {
|
15
19
|
AuthorizationResultAuthorize,
|
16
20
|
buildAuthorizeData,
|
@@ -21,15 +25,28 @@ import {
|
|
21
25
|
buildCustomizationCss,
|
22
26
|
buildCustomizationData,
|
23
27
|
} from './build-customization-data.js'
|
24
|
-
import {
|
25
|
-
import {
|
28
|
+
import { buildErrorData } from './build-error-data.js'
|
29
|
+
import { buildErrorStatus } from './build-error-payload.js'
|
30
|
+
import { sendWebPage } from './send-web-page.js'
|
31
|
+
|
32
|
+
const BASE_CSP: CspConfig = {
|
33
|
+
// API calls are made to the same origin
|
34
|
+
'connect-src': ["'self'"],
|
35
|
+
// Allow loading of PDS logo & User avatars
|
36
|
+
'img-src': ['data:', 'https:'],
|
37
|
+
// Prevent embedding in iframes
|
38
|
+
'frame-ancestors': ["'none'"],
|
39
|
+
}
|
26
40
|
|
27
|
-
|
41
|
+
/**
|
42
|
+
* @see {@link https://docs.hcaptcha.com/#content-security-policy-settings}
|
43
|
+
*/
|
44
|
+
const HCAPTCHA_CSP: CspConfig = {
|
28
45
|
'script-src': ['https://hcaptcha.com', 'https://*.hcaptcha.com'],
|
29
46
|
'frame-src': ['https://hcaptcha.com', 'https://*.hcaptcha.com'],
|
30
47
|
'style-src': ['https://hcaptcha.com', 'https://*.hcaptcha.com'],
|
31
48
|
'connect-src': ['https://hcaptcha.com', 'https://*.hcaptcha.com'],
|
32
|
-
}
|
49
|
+
}
|
33
50
|
|
34
51
|
export type SendPageOptions = {
|
35
52
|
preferredLocales?: readonly string[]
|
@@ -41,43 +58,57 @@ export class OutputManager {
|
|
41
58
|
{ name: 'robots', content: 'noindex' },
|
42
59
|
{ name: 'description', content: 'ATProto OAuth authorization page' },
|
43
60
|
]
|
44
|
-
readonly scripts: readonly (Asset | Html)[]
|
45
|
-
readonly styles: readonly (Asset | Html)[]
|
46
61
|
readonly csp: CspConfig
|
62
|
+
readonly coep: CrossOriginEmbedderPolicy
|
63
|
+
readonly customizationData: CustomizationData
|
64
|
+
readonly customizationCss: Html
|
47
65
|
|
48
66
|
constructor(customization: Customization) {
|
49
67
|
this.links = customization.branding?.links
|
50
68
|
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
// Note: building scripts/styles/csp here for two reasons:
|
55
|
-
// 1. To avoid re-building it on every request
|
56
|
-
// 2. To throw during init if the customization/config is invalid
|
57
|
-
|
58
|
-
this.scripts = [
|
59
|
-
declareBackendData('__availableLocales', AVAILABLE_LOCALES),
|
60
|
-
declareBackendData(
|
61
|
-
'__customizationData',
|
62
|
-
buildCustomizationData(customization),
|
63
|
-
),
|
64
|
-
// Last (to be able to read the "backend data" variables)
|
65
|
-
...scripts.filter((asset) => asset.isEntry),
|
66
|
-
]
|
67
|
-
|
68
|
-
this.styles = [
|
69
|
-
// First (to be overridden by customization)
|
70
|
-
...styles,
|
71
|
-
cssCode(buildCustomizationCss(customization)),
|
72
|
-
]
|
73
|
-
|
74
|
-
const customizationCsp = customization?.hcaptcha ? HCAPTCHA_CSP : undefined
|
75
|
-
const assetsCsp: CspConfig = {
|
76
|
-
'script-src': scripts.map(assetToCsp),
|
77
|
-
'style-src': styles.map(assetToCsp),
|
78
|
-
}
|
69
|
+
// "cache" these:
|
70
|
+
this.customizationData = buildCustomizationData(customization)
|
71
|
+
this.customizationCss = cssCode(buildCustomizationCss(customization))
|
79
72
|
|
80
|
-
this.csp = mergeCsp(
|
73
|
+
this.csp = mergeCsp(
|
74
|
+
BASE_CSP,
|
75
|
+
customization?.hcaptcha ? HCAPTCHA_CSP : undefined,
|
76
|
+
)
|
77
|
+
// Because we are loading avatar images from external sources, that might
|
78
|
+
// not have CORP headers set, we need to use at least "credentialless".
|
79
|
+
this.coep = customization?.hcaptcha
|
80
|
+
? // https://github.com/hCaptcha/react-hcaptcha/issues/259
|
81
|
+
// @TODO Remove the use of `unsafeNone` once the issue above is resolved
|
82
|
+
CrossOriginEmbedderPolicy.unsafeNone
|
83
|
+
: CrossOriginEmbedderPolicy.credentialless
|
84
|
+
}
|
85
|
+
|
86
|
+
buildAssets(
|
87
|
+
name: string,
|
88
|
+
backendData: Record<string, unknown>,
|
89
|
+
): {
|
90
|
+
scripts: (AssetRef | Html)[]
|
91
|
+
styles: (AssetRef | Html)[]
|
92
|
+
} {
|
93
|
+
return {
|
94
|
+
scripts: [
|
95
|
+
declareBackendData(backendData),
|
96
|
+
// After backend injected data
|
97
|
+
...Array.from(assets)
|
98
|
+
.filter(
|
99
|
+
([, item]) =>
|
100
|
+
item.type === 'chunk' && item.isEntry && item.name === name,
|
101
|
+
)
|
102
|
+
.map(([filename]) => ({ url: buildAssetUrl(filename) })),
|
103
|
+
],
|
104
|
+
styles: [
|
105
|
+
...Array.from(assets)
|
106
|
+
.filter(([, item]) => item.mime === 'text/css')
|
107
|
+
.map(([filename]) => ({ url: buildAssetUrl(filename) })),
|
108
|
+
// Last (to be able to override the default styles)
|
109
|
+
this.customizationCss,
|
110
|
+
],
|
111
|
+
}
|
81
112
|
}
|
82
113
|
|
83
114
|
async sendAuthorizePage(
|
@@ -89,17 +120,21 @@ export class OutputManager {
|
|
89
120
|
data.parameters.ui_locales?.split(' ') ?? options?.preferredLocales,
|
90
121
|
)
|
91
122
|
|
123
|
+
const { scripts, styles } = this.buildAssets('authorization-page', {
|
124
|
+
__availableLocales: AVAILABLE_LOCALES,
|
125
|
+
__customizationData: this.customizationData,
|
126
|
+
__authorizeData: buildAuthorizeData(data),
|
127
|
+
})
|
128
|
+
|
92
129
|
return sendWebPage(res, {
|
93
|
-
scripts
|
94
|
-
|
95
|
-
...this.scripts,
|
96
|
-
],
|
97
|
-
styles: this.styles,
|
130
|
+
scripts,
|
131
|
+
styles,
|
98
132
|
meta: this.meta,
|
99
133
|
links: this.buildLinks(locale),
|
100
134
|
htmlAttrs: { lang: locale },
|
101
135
|
body: html`<div id="root"></div>`,
|
102
136
|
csp: this.csp,
|
137
|
+
coep: this.coep,
|
103
138
|
})
|
104
139
|
}
|
105
140
|
|
@@ -110,18 +145,22 @@ export class OutputManager {
|
|
110
145
|
): Promise<void> {
|
111
146
|
const locale = negotiateLocale(options?.preferredLocales)
|
112
147
|
|
148
|
+
const { scripts, styles } = this.buildAssets('error-page', {
|
149
|
+
__availableLocales: AVAILABLE_LOCALES,
|
150
|
+
__customizationData: this.customizationData,
|
151
|
+
__errorData: buildErrorData(err),
|
152
|
+
})
|
153
|
+
|
113
154
|
return sendWebPage(res, {
|
114
155
|
status: buildErrorStatus(err),
|
115
|
-
scripts
|
116
|
-
|
117
|
-
...this.scripts,
|
118
|
-
],
|
119
|
-
styles: this.styles,
|
156
|
+
scripts,
|
157
|
+
styles,
|
120
158
|
meta: this.meta,
|
121
159
|
links: this.buildLinks(locale),
|
122
160
|
htmlAttrs: { lang: locale },
|
123
161
|
body: html`<div id="root"></div>`,
|
124
162
|
csp: this.csp,
|
163
|
+
coep: this.coep,
|
125
164
|
})
|
126
165
|
}
|
127
166
|
|
@@ -1,82 +1,53 @@
|
|
1
1
|
import { createHash } from 'node:crypto'
|
2
2
|
import type { ServerResponse } from 'node:http'
|
3
|
-
import { CspConfig, CspValue,
|
3
|
+
import { CspConfig, CspValue, mergeCsp } from '../lib/csp/index.js'
|
4
4
|
import {
|
5
5
|
AssetRef,
|
6
6
|
BuildDocumentOptions,
|
7
7
|
Html,
|
8
8
|
buildDocument,
|
9
|
-
js,
|
10
9
|
} from '../lib/html/index.js'
|
11
|
-
import {
|
10
|
+
import { WriteHtmlOptions, writeHtml } from '../lib/http/response.js'
|
12
11
|
|
13
|
-
export
|
14
|
-
|
15
|
-
|
16
|
-
// script will read the global variable and then unset it. See
|
17
|
-
// "readBackendData" in "src/assets/app/backend-types.ts".
|
18
|
-
return js`window[${name}]=${data};document.currentScript.remove();`
|
12
|
+
export const DEFAULT_CSP: CspConfig = {
|
13
|
+
'upgrade-insecure-requests': true,
|
14
|
+
'default-src': ["'none'"],
|
19
15
|
}
|
20
16
|
|
21
|
-
export type SendWebPageOptions = BuildDocumentOptions &
|
22
|
-
WriteResponseOptions & {
|
23
|
-
csp?: CspConfig
|
24
|
-
}
|
17
|
+
export type SendWebPageOptions = BuildDocumentOptions & WriteHtmlOptions
|
25
18
|
|
26
19
|
export async function sendWebPage(
|
27
20
|
res: ServerResponse,
|
28
|
-
options: SendWebPageOptions,
|
21
|
+
{ csp: inputCsp, ...options }: SendWebPageOptions,
|
29
22
|
): Promise<void> {
|
30
|
-
|
31
|
-
|
23
|
+
// @NOTE the csp string might be quite long. In that case it might be tempting
|
24
|
+
// to set it through the http-equiv <meta> in the HTML. However, some
|
25
|
+
// directives cannot be enforced by browsers when set through the meta tag
|
26
|
+
// (e.g. 'frame-ancestors'). Therefore, it's better to set the CSP through the
|
27
|
+
// HTTP header.
|
28
|
+
const csp = mergeCsp(DEFAULT_CSP, inputCsp, {
|
32
29
|
'base-uri': options.base?.origin as undefined | `https://${string}`,
|
33
|
-
'script-src':
|
34
|
-
'style-src':
|
35
|
-
'img-src': ["'self'", 'data:', 'https:'],
|
36
|
-
'connect-src': ["'self'"],
|
37
|
-
'upgrade-insecure-requests': true,
|
38
|
-
|
39
|
-
// Prevents the CSP to be embedded in a page <meta>:
|
40
|
-
'frame-ancestors': ["'none'"],
|
30
|
+
'script-src': options.scripts?.map(assetToCsp),
|
31
|
+
'style-src': options.styles?.map(assetToCsp),
|
41
32
|
})
|
42
33
|
|
43
|
-
|
44
|
-
|
45
|
-
// reason, we won't try to avoid too long headers and let the proxy throw
|
46
|
-
// in case of a too long header.
|
47
|
-
res.setHeader('Content-Security-Policy', buildCsp(csp))
|
48
|
-
|
49
|
-
// @TODO: make these headers configurable (?)
|
50
|
-
res.setHeader('Permissions-Policy', 'otp-credentials=*, document-domain=()')
|
51
|
-
res.setHeader('Cross-Origin-Embedder-Policy', 'credentialless')
|
52
|
-
res.setHeader('Cross-Origin-Resource-Policy', 'same-origin')
|
53
|
-
res.setHeader('Cross-Origin-Opener-Policy', 'same-origin')
|
54
|
-
res.setHeader('Referrer-Policy', 'same-origin')
|
55
|
-
res.setHeader('X-Frame-Options', 'DENY')
|
56
|
-
res.setHeader('X-Content-Type-Options', 'nosniff')
|
57
|
-
res.setHeader('X-XSS-Protection', '0')
|
58
|
-
res.setHeader('Strict-Transport-Security', 'max-age=63072000')
|
59
|
-
|
60
|
-
const html = buildDocument(options)
|
61
|
-
|
62
|
-
return writeHtml(res, html.toString(), options)
|
34
|
+
const html = buildDocument(options).toString()
|
35
|
+
return writeHtml(res, html, { ...options, csp })
|
63
36
|
}
|
64
37
|
|
65
|
-
|
66
|
-
assets?: Iterable<Html | AssetRef>,
|
67
|
-
): Generator<CspValue> {
|
68
|
-
if (assets) {
|
69
|
-
for (const asset of assets) {
|
70
|
-
yield assetToCsp(asset)
|
71
|
-
}
|
72
|
-
}
|
73
|
-
}
|
74
|
-
|
75
|
-
export function assetToCsp(asset: Html | AssetRef): CspValue {
|
38
|
+
function assetToCsp(asset: Html | AssetRef): CspValue {
|
76
39
|
if (asset instanceof Html) {
|
77
|
-
|
78
|
-
|
40
|
+
// Inline assets are "allowed" by their hash
|
41
|
+
const hash = createHash('sha256')
|
42
|
+
for (const fragment of asset) hash.update(fragment)
|
43
|
+
return `'sha256-${hash.digest('base64')}'`
|
79
44
|
} else {
|
80
|
-
|
45
|
+
// External assets are referenced by their origin
|
46
|
+
if (asset.url.startsWith('https:') || asset.url.startsWith('http:')) {
|
47
|
+
return new URL(asset.url).origin as `https:${string}` | `http:${string}`
|
48
|
+
}
|
49
|
+
|
50
|
+
// Internal assets are served from the same origin
|
51
|
+
return `'self'`
|
81
52
|
}
|
82
53
|
}
|
package/tsconfig.backend.json
CHANGED
@@ -1 +1 @@
|
|
1
|
-
{"root":["./src/constants.ts","./src/index.ts","./src/oauth-client.ts","./src/oauth-dpop.ts","./src/oauth-errors.ts","./src/oauth-hooks.ts","./src/oauth-provider.ts","./src/oauth-store.ts","./src/oauth-verifier.ts","./src/access-token/access-token-type.ts","./src/account/account-manager.ts","./src/account/account-store.ts","./src/account/account.ts","./src/account/sign-in-data.ts","./src/account/sign-up-
|
1
|
+
{"root":["./src/constants.ts","./src/index.ts","./src/oauth-client.ts","./src/oauth-dpop.ts","./src/oauth-errors.ts","./src/oauth-hooks.ts","./src/oauth-provider.ts","./src/oauth-store.ts","./src/oauth-verifier.ts","./src/access-token/access-token-type.ts","./src/account/account-manager.ts","./src/account/account-store.ts","./src/account/account.ts","./src/account/sign-in-data.ts","./src/account/sign-up-input.ts","./src/assets/assets-middleware.ts","./src/client/client-auth.ts","./src/client/client-data.ts","./src/client/client-id.ts","./src/client/client-info.ts","./src/client/client-manager.ts","./src/client/client-store.ts","./src/client/client-utils.ts","./src/client/client.ts","./src/device/device-data.ts","./src/device/device-id.ts","./src/device/device-manager.ts","./src/device/device-store.ts","./src/device/session-id.ts","./src/dpop/dpop-manager.ts","./src/dpop/dpop-nonce.ts","./src/errors/access-denied-error.ts","./src/errors/account-selection-required-error.ts","./src/errors/consent-required-error.ts","./src/errors/handle-unavailable-error.ts","./src/errors/invalid-authorization-details-error.ts","./src/errors/invalid-client-error.ts","./src/errors/invalid-client-id-error.ts","./src/errors/invalid-client-metadata-error.ts","./src/errors/invalid-dpop-key-binding-error.ts","./src/errors/invalid-dpop-proof-error.ts","./src/errors/invalid-grant-error.ts","./src/errors/invalid-invite-code-error.ts","./src/errors/invalid-parameters-error.ts","./src/errors/invalid-redirect-uri-error.ts","./src/errors/invalid-request-error.ts","./src/errors/invalid-scope-error.ts","./src/errors/invalid-token-error.ts","./src/errors/login-required-error.ts","./src/errors/oauth-error.ts","./src/errors/second-authentication-factor-required-error.ts","./src/errors/unauthorized-client-error.ts","./src/errors/use-dpop-nonce-error.ts","./src/errors/www-authenticate-error.ts","./src/lib/hcaptcha.ts","./src/lib/locale.ts","./src/lib/redis.ts","./src/lib/csp/index.ts","./src/lib/html/build-document.ts","./src/lib/html/escapers.ts","./src/lib/html/html.ts","./src/lib/html/index.ts","./src/lib/html/tags.ts","./src/lib/html/util.ts","./src/lib/http/accept.ts","./src/lib/http/context.ts","./src/lib/http/index.ts","./src/lib/http/method.ts","./src/lib/http/middleware.ts","./src/lib/http/parser.ts","./src/lib/http/path.ts","./src/lib/http/request.ts","./src/lib/http/response.ts","./src/lib/http/route.ts","./src/lib/http/router.ts","./src/lib/http/security-headers.ts","./src/lib/http/stream.ts","./src/lib/http/types.ts","./src/lib/http/url.ts","./src/lib/util/authorization-header.ts","./src/lib/util/cast.ts","./src/lib/util/crypto.ts","./src/lib/util/date.ts","./src/lib/util/function.ts","./src/lib/util/hostname.ts","./src/lib/util/redirect-uri.ts","./src/lib/util/time.ts","./src/lib/util/type.ts","./src/lib/util/well-known.ts","./src/metadata/build-metadata.ts","./src/oidc/sub.ts","./src/output/backend-data.ts","./src/output/build-authorize-data.ts","./src/output/build-customization-data.ts","./src/output/build-error-data.ts","./src/output/build-error-payload.ts","./src/output/output-manager.ts","./src/output/send-authorize-redirect.ts","./src/output/send-web-page.ts","./src/replay/replay-manager.ts","./src/replay/replay-store-memory.ts","./src/replay/replay-store-redis.ts","./src/replay/replay-store.ts","./src/request/code.ts","./src/request/request-data.ts","./src/request/request-id.ts","./src/request/request-info.ts","./src/request/request-manager.ts","./src/request/request-store-memory.ts","./src/request/request-store-redis.ts","./src/request/request-store.ts","./src/request/request-uri.ts","./src/signer/signed-token-payload.ts","./src/signer/signer.ts","./src/token/refresh-token.ts","./src/token/token-claims.ts","./src/token/token-data.ts","./src/token/token-id.ts","./src/token/token-manager.ts","./src/token/token-store.ts","./src/token/verify-token-claims.ts"],"version":"5.6.3"}
|
package/tsconfig.json
CHANGED
package/.linguirc
DELETED
@@ -1,57 +0,0 @@
|
|
1
|
-
{
|
2
|
-
"format": "po",
|
3
|
-
"sourceLocale": "en",
|
4
|
-
"locales": [
|
5
|
-
"en",
|
6
|
-
"an",
|
7
|
-
"ast",
|
8
|
-
"ca",
|
9
|
-
"da",
|
10
|
-
"de",
|
11
|
-
"el",
|
12
|
-
"en-GB",
|
13
|
-
"es",
|
14
|
-
"eu",
|
15
|
-
"fi",
|
16
|
-
"fr",
|
17
|
-
"ga",
|
18
|
-
"gl",
|
19
|
-
"hi",
|
20
|
-
"hu",
|
21
|
-
"ia",
|
22
|
-
"id",
|
23
|
-
"it",
|
24
|
-
"ja",
|
25
|
-
"km",
|
26
|
-
"ko",
|
27
|
-
"ne",
|
28
|
-
"nl",
|
29
|
-
"pl",
|
30
|
-
"pt-BR",
|
31
|
-
"ro",
|
32
|
-
"ru",
|
33
|
-
"sv",
|
34
|
-
"th",
|
35
|
-
"tr",
|
36
|
-
"uk",
|
37
|
-
"vi",
|
38
|
-
"zh-CN",
|
39
|
-
"zh-HK",
|
40
|
-
"zh-TW"
|
41
|
-
],
|
42
|
-
"fallbackLocales": {
|
43
|
-
"default": "en"
|
44
|
-
},
|
45
|
-
"catalogs": [
|
46
|
-
{
|
47
|
-
"path": "<rootDir>/src/assets/app/locales/{locale}/messages",
|
48
|
-
"include": [
|
49
|
-
"<rootDir>/src/assets/app"
|
50
|
-
],
|
51
|
-
"exclude": [
|
52
|
-
"**/dist/**",
|
53
|
-
"**/node_modules/**"
|
54
|
-
]
|
55
|
-
}
|
56
|
-
]
|
57
|
-
}
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"file":"sign-up-data.d.ts","sourceRoot":"","sources":["../../src/account/sign-up-data.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAA;AAIvB,eAAO,MAAM,gBAAgB;;;;;;;;;;;;;;;;;;;;;;EAIlB,CAAA;AAEX,MAAM,MAAM,UAAU,GAAG,CAAC,CAAC,MAAM,CAAC,OAAO,gBAAgB,CAAC,CAAA"}
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"file":"sign-up-data.js","sourceRoot":"","sources":["../../src/account/sign-up-data.ts"],"names":[],"mappings":";;;AACA,oDAAwD;AACxD,yDAA4D;AAE/C,QAAA,gBAAgB,GAAG,0CAAuB;KACpD,MAAM,CAAC;IACN,aAAa,EAAE,iCAAmB,CAAC,QAAQ,EAAE;CAC9C,CAAC;KACD,MAAM,EAAE,CAAA"}
|