@owlmeans/web-panel 0.1.18-rc.19 → 0.1.18-rc.20
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/agent-meta/manifest.json +2 -2
- package/agent-meta/skills/web-panel/SKILL.md +1 -1
- package/build/auth/plugins/basic-ed25519.js +1 -1
- package/build/auth/plugins/basic-ed25519.js.map +1 -1
- package/build/components/index.d.ts +1 -0
- package/build/components/index.d.ts.map +1 -1
- package/build/components/index.js +1 -0
- package/build/components/index.js.map +1 -1
- package/build/components/login/append.d.ts +22 -0
- package/build/components/login/append.d.ts.map +1 -0
- package/build/components/login/append.js +21 -0
- package/build/components/login/append.js.map +1 -0
- package/build/components/login/credit.d.ts +17 -0
- package/build/components/login/credit.d.ts.map +1 -0
- package/build/components/login/credit.js +17 -0
- package/build/components/login/credit.js.map +1 -0
- package/build/components/login/icons.d.ts +14 -0
- package/build/components/login/icons.d.ts.map +1 -0
- package/build/components/login/icons.js +29 -0
- package/build/components/login/icons.js.map +1 -0
- package/build/components/login/index.d.ts +6 -0
- package/build/components/login/index.d.ts.map +1 -0
- package/build/components/login/index.js +6 -0
- package/build/components/login/index.js.map +1 -0
- package/build/components/login/screen.d.ts +23 -0
- package/build/components/login/screen.d.ts.map +1 -0
- package/build/components/login/screen.js +54 -0
- package/build/components/login/screen.js.map +1 -0
- package/build/components/login/terms.d.ts +9 -0
- package/build/components/login/terms.d.ts.map +1 -0
- package/build/components/login/terms.js +30 -0
- package/build/components/login/terms.js.map +1 -0
- package/build/consent/component.d.ts +11 -0
- package/build/consent/component.d.ts.map +1 -0
- package/build/consent/component.js +53 -0
- package/build/consent/component.js.map +1 -0
- package/build/consent/index.d.ts +4 -0
- package/build/consent/index.d.ts.map +1 -0
- package/build/consent/index.js +3 -0
- package/build/consent/index.js.map +1 -0
- package/build/context.d.ts.map +1 -1
- package/build/context.js +4 -0
- package/build/context.js.map +1 -1
- package/package.json +30 -22
- package/src/auth/plugins/basic-ed25519.tsx +1 -1
- package/src/components/index.ts +1 -0
- package/src/components/login/append.ts +34 -0
- package/src/components/login/credit.tsx +34 -0
- package/src/components/login/icons.tsx +39 -0
- package/src/components/login/index.ts +5 -0
- package/src/components/login/screen.tsx +110 -0
- package/src/components/login/terms.tsx +71 -0
- package/src/consent/component.tsx +62 -0
- package/src/consent/index.ts +11 -0
- package/src/context.ts +5 -0
- package/tests/harness/mount.tsx +48 -1
- package/tests/login.spec.ts +115 -0
package/agent-meta/manifest.json
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
{
|
|
2
2
|
"schemaVersion": 2,
|
|
3
3
|
"package": "@owlmeans/web-panel",
|
|
4
|
-
"version": "0.1.18-rc.
|
|
5
|
-
"generatedAt": "2026-08-30T20:53:
|
|
4
|
+
"version": "0.1.18-rc.19",
|
|
5
|
+
"generatedAt": "2026-08-30T20:53:43.839Z",
|
|
6
6
|
"canonicalRepo": "https://github.com/owlmeans/common",
|
|
7
7
|
"entries": [
|
|
8
8
|
{
|
|
@@ -22,7 +22,7 @@ export const Ed22519BasicAuthUIPlugin = ({ type, stage, control }) => {
|
|
|
22
22
|
};
|
|
23
23
|
const createSubmit = (context, control) => async (data) => {
|
|
24
24
|
const token = await control.authenticate({
|
|
25
|
-
|
|
25
|
+
entitySlug: data.entityId,
|
|
26
26
|
userId: data.address,
|
|
27
27
|
credential: data.privateKey
|
|
28
28
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"basic-ed25519.js","sourceRoot":"","sources":["../../../src/auth/plugins/basic-ed25519.tsx"],"names":[],"mappings":";AAMA,OAAO,EAAE,kCAAkC,IAAI,MAAM,EAAE,MAAM,qCAAqC,CAAA;AAClG,OAAO,EAAE,mBAAmB,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAA;AAChE,OAAO,EAAE,IAAI,EAAE,MAAM,gCAAgC,CAAA;AACrD,OAAO,EAAE,SAAS,EAAE,MAAM,qCAAqC,CAAA;AAC/D,OAAO,EAAE,WAAW,EAAE,MAAM,OAAO,CAAA;AACnC,OAAO,EAAE,QAAQ,EAAE,MAAM,0BAA0B,CAAA;AACnD,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAA;AACrD,OAAO,EAAE,UAAU,EAAE,MAAM,sBAAsB,CAAA;AAEjD,MAAM,CAAC,MAAM,wBAAwB,GAA2B,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE,EAAE;IAC3F,MAAM,OAAO,GAAG,UAAU,EAAE,CAAA;IAC5B,MAAM,MAAM,GAAG,WAAW,CAAC,YAAY,CAAC,OAAgC,EAAE,OAAO,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,CAAA;IAE3F,MAAM,OAAO,GAAG,WAAW,CAAC,GAAG,EAAE;QAC/B,QAAQ,KAAK,EAAE,CAAC;YACd,KAAK,mBAAmB,CAAC,YAAY;gBACnC,OAAO,CAAC,UAAU,EAAE,SAAS,EAAE,YAAY,CAAC,CAAC,GAAG,CAC9C,IAAI,CAAC,EAAE,CAAC,KAAC,SAAS,IAAY,IAAI,EAAE,IAAI,EAAE,KAAK,UAAvB,IAAI,CAAsB,CACnD,CAAA;YACH;gBACE,OAAO,KAAC,QAAQ,KAAG,CAAA;QACvB,CAAC;IACH,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC,CAAA;IAEX,OAAO,KAAC,IAAI,IAAC,QAAQ,QAAC,IAAI,EAAC,eAAe,EAAC,UAAU,EAAE,YAAY,CAAC,IAAI,EACtE,IAAI,EAAE,EAAE,EAAE,EAAE,KAAK,EAAE,QAAQ,EAAE,mBAAmB,EAAE,EAClD,UAAU,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,YACpC,KAAC,OAAO,KAAG,GACN,CAAA;AACT,CAAC,CAAA;AAED,MAAM,YAAY,GAAG,CAAC,OAAmB,EAAE,OAA8B,EAAE,EAAE,CAAC,KAAK,EAAE,IAAc,EAAE,EAAE;IACrG,MAAM,KAAK,GAAG,MAAM,OAAO,CAAC,YAAY,CAAC;QACvC,
|
|
1
|
+
{"version":3,"file":"basic-ed25519.js","sourceRoot":"","sources":["../../../src/auth/plugins/basic-ed25519.tsx"],"names":[],"mappings":";AAMA,OAAO,EAAE,kCAAkC,IAAI,MAAM,EAAE,MAAM,qCAAqC,CAAA;AAClG,OAAO,EAAE,mBAAmB,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAA;AAChE,OAAO,EAAE,IAAI,EAAE,MAAM,gCAAgC,CAAA;AACrD,OAAO,EAAE,SAAS,EAAE,MAAM,qCAAqC,CAAA;AAC/D,OAAO,EAAE,WAAW,EAAE,MAAM,OAAO,CAAA;AACnC,OAAO,EAAE,QAAQ,EAAE,MAAM,0BAA0B,CAAA;AACnD,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAA;AACrD,OAAO,EAAE,UAAU,EAAE,MAAM,sBAAsB,CAAA;AAEjD,MAAM,CAAC,MAAM,wBAAwB,GAA2B,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE,EAAE;IAC3F,MAAM,OAAO,GAAG,UAAU,EAAE,CAAA;IAC5B,MAAM,MAAM,GAAG,WAAW,CAAC,YAAY,CAAC,OAAgC,EAAE,OAAO,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,CAAA;IAE3F,MAAM,OAAO,GAAG,WAAW,CAAC,GAAG,EAAE;QAC/B,QAAQ,KAAK,EAAE,CAAC;YACd,KAAK,mBAAmB,CAAC,YAAY;gBACnC,OAAO,CAAC,UAAU,EAAE,SAAS,EAAE,YAAY,CAAC,CAAC,GAAG,CAC9C,IAAI,CAAC,EAAE,CAAC,KAAC,SAAS,IAAY,IAAI,EAAE,IAAI,EAAE,KAAK,UAAvB,IAAI,CAAsB,CACnD,CAAA;YACH;gBACE,OAAO,KAAC,QAAQ,KAAG,CAAA;QACvB,CAAC;IACH,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC,CAAA;IAEX,OAAO,KAAC,IAAI,IAAC,QAAQ,QAAC,IAAI,EAAC,eAAe,EAAC,UAAU,EAAE,YAAY,CAAC,IAAI,EACtE,IAAI,EAAE,EAAE,EAAE,EAAE,KAAK,EAAE,QAAQ,EAAE,mBAAmB,EAAE,EAClD,UAAU,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,YACpC,KAAC,OAAO,KAAG,GACN,CAAA;AACT,CAAC,CAAA;AAED,MAAM,YAAY,GAAG,CAAC,OAAmB,EAAE,OAA8B,EAAE,EAAE,CAAC,KAAK,EAAE,IAAc,EAAE,EAAE;IACrG,MAAM,KAAK,GAAG,MAAM,OAAO,CAAC,YAAY,CAAC;QACvC,UAAU,EAAE,IAAI,CAAC,QAAQ;QACzB,MAAM,EAAE,IAAI,CAAC,OAAO;QACpB,UAAU,EAAE,IAAI,CAAC,UAAU;KAC5B,CAAC,CAAA;IAEF,IAAI,KAAK,CAAC,KAAK,KAAK,EAAE,EAAE,CAAC;QACvB,OAAM;IACR,CAAC;IAED,MAAM,CAAC,GAAG,CAAC,GAAG,MAAM,OAAO,CAAC,MAAM,CAAwC,UAAU,CAAC;SAClF,IAAI,CAAC,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAA;IAEzB,OAAO,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,KAAK,GAAG,mBAAmB,CAAC,aAAa,CAAC,CAAA;IACrE,oEAAoE;IACpE,6CAA6C;IAC7C,+FAA+F;IAC/F,UAAU,CAAC,GAAG,EAAE,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,GAAG,GAAG,EAAE,GAAG,CAAC,CAAA;AACnD,CAAC,CAAA"}
|
|
@@ -3,6 +3,7 @@ export * from './panel-app/index.js';
|
|
|
3
3
|
export * from './layout/index.js';
|
|
4
4
|
export * from './nav/index.js';
|
|
5
5
|
export * from './footer/index.js';
|
|
6
|
+
export * from './login/index.js';
|
|
6
7
|
export * from './form/index.js';
|
|
7
8
|
export * from './form/text/index.js';
|
|
8
9
|
export * from './form/button/index.js';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/components/index.ts"],"names":[],"mappings":"AAAA,mBAAmB,YAAY,CAAA;AAE/B,cAAc,sBAAsB,CAAA;AACpC,cAAc,mBAAmB,CAAA;AACjC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/components/index.ts"],"names":[],"mappings":"AAAA,mBAAmB,YAAY,CAAA;AAE/B,cAAc,sBAAsB,CAAA;AACpC,cAAc,mBAAmB,CAAA;AACjC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAEhC,cAAc,iBAAiB,CAAA;AAC/B,cAAc,sBAAsB,CAAA;AACpC,cAAc,wBAAwB,CAAA;AACtC,cAAc,qBAAqB,CAAA;AAEnC,cAAc,mBAAmB,CAAA;AAEjC,cAAc,YAAY,CAAA;AAC1B,cAAc,WAAW,CAAA;AACzB,cAAc,WAAW,CAAA;AACzB,cAAc,aAAa,CAAA;AAC3B,cAAc,aAAa,CAAA;AAC3B,cAAc,cAAc,CAAA"}
|
|
@@ -2,6 +2,7 @@ export * from './panel-app/index.js';
|
|
|
2
2
|
export * from './layout/index.js';
|
|
3
3
|
export * from './nav/index.js';
|
|
4
4
|
export * from './footer/index.js';
|
|
5
|
+
export * from './login/index.js';
|
|
5
6
|
export * from './form/index.js';
|
|
6
7
|
export * from './form/text/index.js';
|
|
7
8
|
export * from './form/button/index.js';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/components/index.ts"],"names":[],"mappings":"AAEA,cAAc,sBAAsB,CAAA;AACpC,cAAc,mBAAmB,CAAA;AACjC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/components/index.ts"],"names":[],"mappings":"AAEA,cAAc,sBAAsB,CAAA;AACpC,cAAc,mBAAmB,CAAA;AACjC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAEhC,cAAc,iBAAiB,CAAA;AAC/B,cAAc,sBAAsB,CAAA;AACpC,cAAc,wBAAwB,CAAA;AACtC,cAAc,qBAAqB,CAAA;AAEnC,cAAc,mBAAmB,CAAA;AAEjC,cAAc,YAAY,CAAA;AAC1B,cAAc,WAAW,CAAA;AACzB,cAAc,WAAW,CAAA;AACzB,cAAc,aAAa,CAAA;AAC3B,cAAc,aAAa,CAAA;AAC3B,cAAc,cAAc,CAAA"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import type { ComponentType, ReactNode } from 'react';
|
|
2
|
+
import type { LoginScreenProps } from '@owlmeans/client-auth/login';
|
|
3
|
+
import type { BasicConfig, BasicContext } from '@owlmeans/context';
|
|
4
|
+
export interface LoginScreenSetup extends Omit<LoginScreenProps, 'translate'> {
|
|
5
|
+
/** The one thing an application is expected to supply. */
|
|
6
|
+
Logo?: ComponentType<{
|
|
7
|
+
className?: string;
|
|
8
|
+
}> | ReactNode;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Give this context the shadcn sign-in screen, with the application's own logo and copy on it.
|
|
12
|
+
*
|
|
13
|
+
* Registered on the login SERVICE rather than imported by a dispatcher, because a relying party
|
|
14
|
+
* (`web-oidc-rp`, `mui-oidc-rp`) must never depend on a UI family — that edge would make every
|
|
15
|
+
* relying party pick one, and there are two. The dispatcher asks `login().screen()` and falls back
|
|
16
|
+
* to the plain screen `@owlmeans/client-auth` ships, so an app that never calls this still gets a
|
|
17
|
+
* chooser rather than an auto-redirect.
|
|
18
|
+
*
|
|
19
|
+
* Idempotent: called by `makeContext` with defaults, and again by the app with its own logo.
|
|
20
|
+
*/
|
|
21
|
+
export declare const appendLoginScreen: <C extends BasicConfig, T extends BasicContext<C>>(ctx: T, setup?: LoginScreenSetup) => T;
|
|
22
|
+
//# sourceMappingURL=append.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"append.d.ts","sourceRoot":"","sources":["../../../src/components/login/append.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,SAAS,EAAE,MAAM,OAAO,CAAA;AAErD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,6BAA6B,CAAA;AACnE,OAAO,KAAK,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAA;AAGlE,MAAM,WAAW,gBAAiB,SAAQ,IAAI,CAAC,gBAAgB,EAAE,WAAW,CAAC;IAC3E,0DAA0D;IAC1D,IAAI,CAAC,EAAE,aAAa,CAAC;QAAE,SAAS,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,GAAG,SAAS,CAAA;CACzD;AAED;;;;;;;;;;GAUG;AACH,eAAO,MAAM,iBAAiB,GAAI,CAAC,SAAS,WAAW,EAAE,CAAC,SAAS,YAAY,CAAC,CAAC,CAAC,OAC3E,CAAC,UAAU,gBAAgB,KAC/B,CASF,CAAA"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { ensureLoginService } from '@owlmeans/client-auth/login';
|
|
2
|
+
import { LocalizedLoginScreen } from './screen.js';
|
|
3
|
+
/**
|
|
4
|
+
* Give this context the shadcn sign-in screen, with the application's own logo and copy on it.
|
|
5
|
+
*
|
|
6
|
+
* Registered on the login SERVICE rather than imported by a dispatcher, because a relying party
|
|
7
|
+
* (`web-oidc-rp`, `mui-oidc-rp`) must never depend on a UI family — that edge would make every
|
|
8
|
+
* relying party pick one, and there are two. The dispatcher asks `login().screen()` and falls back
|
|
9
|
+
* to the plain screen `@owlmeans/client-auth` ships, so an app that never calls this still gets a
|
|
10
|
+
* chooser rather than an auto-redirect.
|
|
11
|
+
*
|
|
12
|
+
* Idempotent: called by `makeContext` with defaults, and again by the app with its own logo.
|
|
13
|
+
*/
|
|
14
|
+
export const appendLoginScreen = (ctx, setup) => {
|
|
15
|
+
const service = ensureLoginService(ctx);
|
|
16
|
+
service.registerScreen(setup == null || Object.keys(setup).length < 1
|
|
17
|
+
? LocalizedLoginScreen
|
|
18
|
+
: props => LocalizedLoginScreen({ ...setup, ...props }));
|
|
19
|
+
return ctx;
|
|
20
|
+
};
|
|
21
|
+
//# sourceMappingURL=append.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"append.js","sourceRoot":"","sources":["../../../src/components/login/append.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,kBAAkB,EAAE,MAAM,6BAA6B,CAAA;AAGhE,OAAO,EAAE,oBAAoB,EAAE,MAAM,aAAa,CAAA;AAOlD;;;;;;;;;;GAUG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAAG,CAC/B,GAAM,EAAE,KAAwB,EAC7B,EAAE;IACL,MAAM,OAAO,GAAG,kBAAkB,CAAC,GAAG,CAAC,CAAA;IACvC,OAAO,CAAC,cAAc,CACpB,KAAK,IAAI,IAAI,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,GAAG,CAAC;QAC5C,CAAC,CAAC,oBAAoB;QACtB,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,oBAAoB,CAAC,EAAE,GAAG,KAAK,EAAE,GAAG,KAAK,EAAE,CAAC,CAC1D,CAAA;IAED,OAAO,GAAG,CAAA;AACZ,CAAC,CAAA"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { FC } from 'react';
|
|
2
|
+
import type { LoginCreditModel } from '@owlmeans/client-panel/auth';
|
|
3
|
+
export interface LoginCreditProps {
|
|
4
|
+
model: LoginCreditModel;
|
|
5
|
+
translate: (key: string, defaultValue: string) => string;
|
|
6
|
+
className?: string;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* The line at the bottom of a sign-in screen.
|
|
10
|
+
*
|
|
11
|
+
* Two halves, and each may stand alone: the platform credit, and who the application belongs to.
|
|
12
|
+
* A generated application shows both — "Powered by OwlMeans" beside its own product and
|
|
13
|
+
* organization — and an application whose owner has paid to drop the credit shows only the second.
|
|
14
|
+
* Rendering nothing at all is also correct, for an app that is neither.
|
|
15
|
+
*/
|
|
16
|
+
export declare const LoginCredit: FC<LoginCreditProps>;
|
|
17
|
+
//# sourceMappingURL=credit.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"credit.d.ts","sourceRoot":"","sources":["../../../src/components/login/credit.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAA;AAE/B,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,6BAA6B,CAAA;AAEnE,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,gBAAgB,CAAA;IACvB,SAAS,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,KAAK,MAAM,CAAA;IACxD,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAED;;;;;;;GAOG;AACH,eAAO,MAAM,WAAW,EAAE,EAAE,CAAC,gBAAgB,CAe5C,CAAA"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { cn } from '@/lib/utils';
|
|
3
|
+
/**
|
|
4
|
+
* The line at the bottom of a sign-in screen.
|
|
5
|
+
*
|
|
6
|
+
* Two halves, and each may stand alone: the platform credit, and who the application belongs to.
|
|
7
|
+
* A generated application shows both — "Powered by OwlMeans" beside its own product and
|
|
8
|
+
* organization — and an application whose owner has paid to drop the credit shows only the second.
|
|
9
|
+
* Rendering nothing at all is also correct, for an app that is neither.
|
|
10
|
+
*/
|
|
11
|
+
export const LoginCredit = ({ model, translate, className }) => {
|
|
12
|
+
if (!model.poweredBy && model.line == null) {
|
|
13
|
+
return null;
|
|
14
|
+
}
|
|
15
|
+
return _jsxs("p", { "data-login-credit": true, className: cn('text-center text-xs text-muted-foreground', className), children: [model.poweredBy && _jsx("span", { "data-login-powered": true, children: translate('login.credit.powered', 'Powered by OwlMeans') }), model.poweredBy && model.line != null && _jsx("span", { "aria-hidden": "true", children: " \u00B7 " }), model.line != null && _jsx("span", { children: model.line })] });
|
|
16
|
+
};
|
|
17
|
+
//# sourceMappingURL=credit.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"credit.js","sourceRoot":"","sources":["../../../src/components/login/credit.tsx"],"names":[],"mappings":";AACA,OAAO,EAAE,EAAE,EAAE,MAAM,aAAa,CAAA;AAShC;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,WAAW,GAAyB,CAAC,EAAE,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,EAAE,EAAE;IACnF,IAAI,CAAC,KAAK,CAAC,SAAS,IAAI,KAAK,CAAC,IAAI,IAAI,IAAI,EAAE,CAAC;QAC3C,OAAO,IAAI,CAAA;IACb,CAAC;IAED,OAAO,wCAEL,SAAS,EAAE,EAAE,CAAC,2CAA2C,EAAE,SAAS,CAAC,aAEpE,KAAK,CAAC,SAAS,IAAI,qDACjB,SAAS,CAAC,sBAAsB,EAAE,qBAAqB,CAAC,GACpD,EACN,KAAK,CAAC,SAAS,IAAI,KAAK,CAAC,IAAI,IAAI,IAAI,IAAI,8BAAkB,MAAM,yBAAW,EAC5E,KAAK,CAAC,IAAI,IAAI,IAAI,IAAI,yBAAO,KAAK,CAAC,IAAI,GAAQ,IAC9C,CAAA;AACN,CAAC,CAAA"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { FC } from 'react';
|
|
2
|
+
/**
|
|
3
|
+
* A method's icon, resolved from a NAME.
|
|
4
|
+
*
|
|
5
|
+
* The registry carries names rather than components so that `@owlmeans/client-auth` and
|
|
6
|
+
* `@owlmeans/oidc` — neither of which may depend on an icon library — can describe a method
|
|
7
|
+
* completely. An unknown name renders the generic sign-in glyph rather than nothing, because a row
|
|
8
|
+
* of buttons where one has no icon reads as a rendering fault.
|
|
9
|
+
*/
|
|
10
|
+
export declare const LoginMethodIcon: FC<{
|
|
11
|
+
name?: string;
|
|
12
|
+
className?: string;
|
|
13
|
+
}>;
|
|
14
|
+
//# sourceMappingURL=icons.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"icons.d.ts","sourceRoot":"","sources":["../../../src/components/login/icons.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAA;AA0B/B;;;;;;;GAOG;AACH,eAAO,MAAM,eAAe,EAAE,EAAE,CAAC;IAAE,IAAI,CAAC,EAAE,MAAM,CAAC;IAAC,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,CAIrE,CAAA"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { KeyRound, LogIn, Mail, ShieldCheck, Wallet } from 'lucide-react';
|
|
3
|
+
/**
|
|
4
|
+
* Google's mark, inline.
|
|
5
|
+
*
|
|
6
|
+
* Lucide carries no brand marks, and a remote image on a sign-in screen is a third-party request
|
|
7
|
+
* before consent. Four paths cost less than either.
|
|
8
|
+
*/
|
|
9
|
+
const GoogleMark = ({ className }) => (_jsxs("svg", { className: className, viewBox: "0 0 48 48", "aria-hidden": "true", role: "presentation", children: [_jsx("path", { fill: "#EA4335", d: "M24 9.5c3.54 0 6.71 1.22 9.21 3.6l6.85-6.85C35.9 2.38 30.47 0 24 0 14.62 0 6.51 5.38 2.56 13.22l7.98 6.19C12.43 13.72 17.74 9.5 24 9.5z" }), _jsx("path", { fill: "#4285F4", d: "M46.98 24.55c0-1.57-.15-3.09-.38-4.55H24v9.02h12.94c-.58 2.96-2.26 5.48-4.78 7.18l7.73 6c4.51-4.18 7.09-10.36 7.09-17.65z" }), _jsx("path", { fill: "#FBBC05", d: "M10.53 28.59c-.48-1.45-.76-2.99-.76-4.59s.27-3.14.76-4.59l-7.98-6.19C.92 16.46 0 20.12 0 24c0 3.88.92 7.54 2.56 10.78l7.97-6.19z" }), _jsx("path", { fill: "#34A853", d: "M24 48c6.48 0 11.93-2.13 15.89-5.81l-7.73-6c-2.15 1.45-4.92 2.3-8.16 2.3-6.26 0-11.57-4.22-13.47-9.91l-7.98 6.19C6.51 42.62 14.62 48 24 48z" })] }));
|
|
10
|
+
const ICONS = {
|
|
11
|
+
google: GoogleMark,
|
|
12
|
+
key: KeyRound,
|
|
13
|
+
shield: ShieldCheck,
|
|
14
|
+
wallet: Wallet,
|
|
15
|
+
mail: Mail,
|
|
16
|
+
};
|
|
17
|
+
/**
|
|
18
|
+
* A method's icon, resolved from a NAME.
|
|
19
|
+
*
|
|
20
|
+
* The registry carries names rather than components so that `@owlmeans/client-auth` and
|
|
21
|
+
* `@owlmeans/oidc` — neither of which may depend on an icon library — can describe a method
|
|
22
|
+
* completely. An unknown name renders the generic sign-in glyph rather than nothing, because a row
|
|
23
|
+
* of buttons where one has no icon reads as a rendering fault.
|
|
24
|
+
*/
|
|
25
|
+
export const LoginMethodIcon = ({ name, className }) => {
|
|
26
|
+
const Icon = (name != null ? ICONS[name] : undefined) ?? LogIn;
|
|
27
|
+
return _jsx(Icon, { className: className });
|
|
28
|
+
};
|
|
29
|
+
//# sourceMappingURL=icons.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"icons.js","sourceRoot":"","sources":["../../../src/components/login/icons.tsx"],"names":[],"mappings":";AACA,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,cAAc,CAAA;AAEzE;;;;;GAKG;AACH,MAAM,UAAU,GAA+B,CAAC,EAAE,SAAS,EAAE,EAAE,EAAE,CAAC,CAChE,eAAK,SAAS,EAAE,SAAS,EAAE,OAAO,EAAC,WAAW,iBAAa,MAAM,EAAC,IAAI,EAAC,cAAc,aACnF,eAAM,IAAI,EAAC,SAAS,EAAC,CAAC,EAAC,yIAAyI,GAAG,EACnK,eAAM,IAAI,EAAC,SAAS,EAAC,CAAC,EAAC,2HAA2H,GAAG,EACrJ,eAAM,IAAI,EAAC,SAAS,EAAC,CAAC,EAAC,kIAAkI,GAAG,EAC5J,eAAM,IAAI,EAAC,SAAS,EAAC,CAAC,EAAC,6IAA6I,GAAG,IACnK,CACP,CAAA;AAED,MAAM,KAAK,GAA+C;IACxD,MAAM,EAAE,UAAU;IAClB,GAAG,EAAE,QAAQ;IACb,MAAM,EAAE,WAAW;IACnB,MAAM,EAAE,MAAM;IACd,IAAI,EAAE,IAAI;CACX,CAAA;AAED;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,eAAe,GAA8C,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,EAAE,EAAE;IAChG,MAAM,IAAI,GAAG,CAAC,IAAI,IAAI,IAAI,CAAC,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,IAAI,KAAK,CAAA;IAE9D,OAAO,KAAC,IAAI,IAAC,SAAS,EAAE,SAAS,GAAI,CAAA;AACvC,CAAC,CAAA"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/login/index.ts"],"names":[],"mappings":"AAAA,cAAc,aAAa,CAAA;AAC3B,cAAc,YAAY,CAAA;AAC1B,cAAc,aAAa,CAAA;AAC3B,cAAc,YAAY,CAAA;AAC1B,cAAc,aAAa,CAAA"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/login/index.ts"],"names":[],"mappings":"AAAA,cAAc,aAAa,CAAA;AAC3B,cAAc,YAAY,CAAA;AAC1B,cAAc,aAAa,CAAA;AAC3B,cAAc,YAAY,CAAA;AAC1B,cAAc,aAAa,CAAA"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import type { FC } from 'react';
|
|
2
|
+
import type { LoginScreenProps } from '@owlmeans/client-auth/login';
|
|
3
|
+
/**
|
|
4
|
+
* The sign-in screen: which identity provider, confirmed against which documents.
|
|
5
|
+
*
|
|
6
|
+
* It never starts anything by itself. Every flow leaves from a click — which is the requirement,
|
|
7
|
+
* and also what makes framed sign-in work at all, because the window a framed application has to
|
|
8
|
+
* open can only be opened inside a user gesture.
|
|
9
|
+
*
|
|
10
|
+
* Pure with respect to i18n: `translate` is a prop. {@link LocalizedLoginScreen} is the wrapper
|
|
11
|
+
* that binds it to the app's own resources, so an application mounted without an i18n provider can
|
|
12
|
+
* still render this one with a resolver of its own.
|
|
13
|
+
*/
|
|
14
|
+
export declare const LoginScreen: FC<LoginScreenProps>;
|
|
15
|
+
/**
|
|
16
|
+
* {@link LoginScreen} bound to the application's own translations.
|
|
17
|
+
*
|
|
18
|
+
* The split exists because the house rule is that a reusable component takes `translate` as a prop
|
|
19
|
+
* and never reaches for a context — but the ordinary case is an app that has one, and making every
|
|
20
|
+
* app write the resolver would guarantee some of them ship English.
|
|
21
|
+
*/
|
|
22
|
+
export declare const LocalizedLoginScreen: FC<LoginScreenProps>;
|
|
23
|
+
//# sourceMappingURL=screen.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"screen.d.ts","sourceRoot":"","sources":["../../../src/components/login/screen.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAA;AAO/B,OAAO,KAAK,EAAe,gBAAgB,EAAE,MAAM,6BAA6B,CAAA;AAWhF;;;;;;;;;;GAUG;AACH,eAAO,MAAM,WAAW,EAAE,EAAE,CAAC,gBAAgB,CA+D5C,CAAA;AAED;;;;;;GAMG;AACH,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,gBAAgB,CAOrD,CAAA"}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { isValidElement } from 'react';
|
|
3
|
+
import { Loader2 } from 'lucide-react';
|
|
4
|
+
import { Button } from '@/components/ui/button';
|
|
5
|
+
import { Card, CardContent, CardHeader, CardTitle, CardDescription } from '@/components/ui/card';
|
|
6
|
+
import { cn } from '@/lib/utils';
|
|
7
|
+
import { useI18nLib } from '@owlmeans/client-i18n';
|
|
8
|
+
import { useLoginMethods } from '@owlmeans/client-panel/auth';
|
|
9
|
+
import { LoginMethodIcon } from './icons.js';
|
|
10
|
+
import { LoginTerms } from './terms.js';
|
|
11
|
+
import { LoginCredit } from './credit.js';
|
|
12
|
+
const VARIANT = {
|
|
13
|
+
primary: 'default',
|
|
14
|
+
secondary: 'outline',
|
|
15
|
+
link: 'link',
|
|
16
|
+
};
|
|
17
|
+
/**
|
|
18
|
+
* The sign-in screen: which identity provider, confirmed against which documents.
|
|
19
|
+
*
|
|
20
|
+
* It never starts anything by itself. Every flow leaves from a click — which is the requirement,
|
|
21
|
+
* and also what makes framed sign-in work at all, because the window a framed application has to
|
|
22
|
+
* open can only be opened inside a user gesture.
|
|
23
|
+
*
|
|
24
|
+
* Pure with respect to i18n: `translate` is a prop. {@link LocalizedLoginScreen} is the wrapper
|
|
25
|
+
* that binds it to the app's own resources, so an application mounted without an i18n provider can
|
|
26
|
+
* still render this one with a resolver of its own.
|
|
27
|
+
*/
|
|
28
|
+
export const LoginScreen = props => {
|
|
29
|
+
const t = props.translate ?? ((_key, defaultValue) => defaultValue);
|
|
30
|
+
const model = useLoginMethods({
|
|
31
|
+
...(props.config != null ? { config: props.config } : {}),
|
|
32
|
+
...(props.terms !== undefined ? { terms: props.terms } : {}),
|
|
33
|
+
...(props.methods != null ? { methods: props.methods } : {}),
|
|
34
|
+
});
|
|
35
|
+
const Logo = props.Logo;
|
|
36
|
+
return _jsx("div", { className: cn('flex min-h-full w-full items-center justify-center p-4', props.className), children: _jsxs(Card, { className: cn('w-full max-w-sm', props.containerClassName), children: [_jsxs(CardHeader, { className: "items-center gap-2 text-center", children: [Logo != null && _jsx("div", { className: "flex justify-center pb-2", children: isValidElement(Logo) ? Logo : typeof Logo === 'function'
|
|
37
|
+
? _jsx(Logo, { className: "h-10 w-auto" }) : Logo }), _jsx(CardTitle, { className: "text-xl", children: props.title ?? t('login.title', 'Sign in') }), _jsx(CardDescription, { children: props.subtitle ?? t('login.subtitle', 'Choose how you would like to continue.') })] }), _jsxs(CardContent, { className: "flex flex-col gap-4", children: [model.methods.length < 1
|
|
38
|
+
? _jsx("p", { role: "status", className: "text-sm text-muted-foreground text-center", children: t('login.empty', 'No sign-in method is configured for this application.') })
|
|
39
|
+
: _jsx("div", { className: "flex flex-col gap-2", children: model.methods.map((method) => _jsxs(Button, { type: "button", "data-login-method": method.id, variant: VARIANT[method.emphasis ?? 'secondary'] ?? 'outline', "aria-disabled": model.blocked, "data-blocked": model.blocked ? 'true' : undefined, className: cn('w-full justify-center gap-2', model.blocked && 'opacity-60'), autoFocus: method.id === model.primary?.id, onClick: () => model.select(method), children: [model.busy === method.id
|
|
40
|
+
? _jsx(Loader2, { className: "size-4 animate-spin" })
|
|
41
|
+
: _jsx(LoginMethodIcon, { name: method.icon, className: "size-4" }), method.label ?? t(`login.method.${method.i18nKey ?? method.id}`, method.id)] }, method.id)) }), model.terms.required && _jsx(LoginTerms, { model: model.terms, translate: t }), model.error != null && _jsx("p", { role: "alert", className: "text-sm text-destructive", children: model.error })] }), _jsx("div", { className: "px-6", children: props.footer ?? _jsx(LoginCredit, { model: model.credit, translate: t }) })] }) });
|
|
42
|
+
};
|
|
43
|
+
/**
|
|
44
|
+
* {@link LoginScreen} bound to the application's own translations.
|
|
45
|
+
*
|
|
46
|
+
* The split exists because the house rule is that a reusable component takes `translate` as a prop
|
|
47
|
+
* and never reaches for a context — but the ordinary case is an app that has one, and making every
|
|
48
|
+
* app write the resolver would guarantee some of them ship English.
|
|
49
|
+
*/
|
|
50
|
+
export const LocalizedLoginScreen = props => {
|
|
51
|
+
const t = useI18nLib('auth');
|
|
52
|
+
return _jsx(LoginScreen, { ...props, translate: props.translate ?? ((key, defaultValue) => t(key, { defaultValue })) });
|
|
53
|
+
};
|
|
54
|
+
//# sourceMappingURL=screen.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"screen.js","sourceRoot":"","sources":["../../../src/components/login/screen.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { FC } from 'react';
|
|
2
|
+
import type { LoginTermsModel } from '@owlmeans/client-panel/auth';
|
|
3
|
+
export interface LoginTermsProps {
|
|
4
|
+
model: LoginTermsModel;
|
|
5
|
+
translate: (key: string, defaultValue: string) => string;
|
|
6
|
+
className?: string;
|
|
7
|
+
}
|
|
8
|
+
export declare const LoginTerms: FC<LoginTermsProps>;
|
|
9
|
+
//# sourceMappingURL=terms.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"terms.d.ts","sourceRoot":"","sources":["../../../src/components/login/terms.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAa,MAAM,OAAO,CAAA;AAE1C,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,6BAA6B,CAAA;AAElE,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,eAAe,CAAA;IACtB,SAAS,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,KAAK,MAAM,CAAA;IACxD,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAuBD,eAAO,MAAM,UAAU,EAAE,EAAE,CAAC,eAAe,CAuC1C,CAAA"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { cn } from '@/lib/utils';
|
|
3
|
+
/**
|
|
4
|
+
* Split a translated sentence around its two link placeholders.
|
|
5
|
+
*
|
|
6
|
+
* The sentence is translated as ONE string with `{{terms}}` and `{{privacy}}` in it, rather than
|
|
7
|
+
* assembled from fragments, because word order differs between languages and an assembled sentence
|
|
8
|
+
* forces every translator into English's. Splitting the already-translated string keeps that
|
|
9
|
+
* freedom while keeping the i18n contract at `(key, defaultValue) => string` — no ReactNode ever
|
|
10
|
+
* comes out of a translation, so an app with no i18n provider still renders a correct sentence.
|
|
11
|
+
*/
|
|
12
|
+
const interpolate = (sentence, slots) => sentence
|
|
13
|
+
.split(/(\{\{[a-z]+\}\})/i)
|
|
14
|
+
.map((part, index) => {
|
|
15
|
+
const match = /^\{\{([a-z]+)\}\}$/i.exec(part);
|
|
16
|
+
return match != null
|
|
17
|
+
? _jsx("span", { children: slots[match[1]] ?? part }, index)
|
|
18
|
+
: _jsx("span", { children: part }, index);
|
|
19
|
+
});
|
|
20
|
+
export const LoginTerms = ({ model, translate, className }) => {
|
|
21
|
+
const link = (href, label) => _jsx("a", { href: href, target: "_blank", rel: "noreferrer noopener", className: "underline underline-offset-2 hover:text-foreground", children: label });
|
|
22
|
+
return _jsxs("div", { className: cn('flex flex-col gap-1.5', className), children: [_jsxs("label", { className: "flex items-start gap-2 text-sm text-muted-foreground cursor-pointer", children: [_jsx("input", { type: "checkbox", "data-login-terms": true, className: "mt-0.5 size-4 shrink-0 accent-primary", checked: model.accepted, "aria-invalid": model.attempted && !model.accepted, onChange: event => model.accept(event.target.checked) }), _jsx("span", { children: interpolate(translate('login.terms.agreement', 'I have read and agree to the {{terms}} and the {{privacy}}.'), {
|
|
23
|
+
terms: link(model.urls.terms, translate('login.terms.terms', 'Terms & Conditions')),
|
|
24
|
+
privacy: link(model.urls.privacy, translate('login.terms.privacy', 'Privacy Policy')),
|
|
25
|
+
cookies: model.urls.cookies != null
|
|
26
|
+
? link(model.urls.cookies, translate('login.terms.cookies', 'Cookie Policy'))
|
|
27
|
+
: null,
|
|
28
|
+
}) })] }), model.attempted && !model.accepted && _jsx("p", { role: "alert", className: "text-sm text-destructive", children: translate('login.terms.required', 'Please confirm the Terms & Conditions and the Privacy Policy to continue.') })] });
|
|
29
|
+
};
|
|
30
|
+
//# sourceMappingURL=terms.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"terms.js","sourceRoot":"","sources":["../../../src/components/login/terms.tsx"],"names":[],"mappings":";AACA,OAAO,EAAE,EAAE,EAAE,MAAM,aAAa,CAAA;AAShC;;;;;;;;GAQG;AACH,MAAM,WAAW,GAAG,CAClB,QAAgB,EAAE,KAAgC,EACrC,EAAE,CAAC,QAAQ;KACvB,KAAK,CAAC,mBAAmB,CAAC;KAC1B,GAAG,CAAC,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE;IACnB,MAAM,KAAK,GAAG,qBAAqB,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;IAE9C,OAAO,KAAK,IAAI,IAAI;QAClB,CAAC,CAAC,yBAAmB,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,IAAI,IAA/B,KAAK,CAAkC;QACpD,CAAC,CAAC,yBAAmB,IAAI,IAAZ,KAAK,CAAe,CAAA;AACrC,CAAC,CAAC,CAAA;AAEJ,MAAM,CAAC,MAAM,UAAU,GAAwB,CAAC,EAAE,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,EAAE,EAAE;IACjF,MAAM,IAAI,GAAG,CAAC,IAAY,EAAE,KAAa,EAAa,EAAE,CACtD,YAAG,IAAI,EAAE,IAAI,EAAE,MAAM,EAAC,QAAQ,EAAC,GAAG,EAAC,qBAAqB,EACtD,SAAS,EAAC,oDAAoD,YAAE,KAAK,GAAK,CAAA;IAE9E,OAAO,eAAK,SAAS,EAAE,EAAE,CAAC,uBAAuB,EAAE,SAAS,CAAC,aAC3D,iBAAO,SAAS,EAAC,qEAAqE,aAOpF,gBACE,IAAI,EAAC,UAAU,4BACf,SAAS,EAAC,uCAAuC,EACjD,OAAO,EAAE,KAAK,CAAC,QAAQ,kBACT,KAAK,CAAC,SAAS,IAAI,CAAC,KAAK,CAAC,QAAQ,EAChD,QAAQ,EAAE,KAAK,CAAC,EAAE,CAAC,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,OAAO,CAAC,GACrD,EACF,yBACG,WAAW,CACV,SAAS,CAAC,uBAAuB,EAC/B,6DAA6D,CAAC,EAChE;4BACE,KAAK,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,KAAK,EAAE,SAAS,CAAC,mBAAmB,EAAE,oBAAoB,CAAC,CAAC;4BACnF,OAAO,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,qBAAqB,EAAE,gBAAgB,CAAC,CAAC;4BACrF,OAAO,EAAE,KAAK,CAAC,IAAI,CAAC,OAAO,IAAI,IAAI;gCACjC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,qBAAqB,EAAE,eAAe,CAAC,CAAC;gCAC7E,CAAC,CAAC,IAAI;yBACT,CACF,GACI,IACD,EACP,KAAK,CAAC,SAAS,IAAI,CAAC,KAAK,CAAC,QAAQ,IAAI,YAAG,IAAI,EAAC,OAAO,EAAC,SAAS,EAAC,0BAA0B,YACxF,SAAS,CAAC,sBAAsB,EAC/B,2EAA2E,CAAC,GAC5E,IACA,CAAA;AACR,CAAC,CAAA"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { FC } from 'react';
|
|
2
|
+
import type { CookieConsentProps, CookiePolicyProps } from '@owlmeans/web-consent';
|
|
3
|
+
/**
|
|
4
|
+
* The consent dialog, bound to this application's language and translations.
|
|
5
|
+
*
|
|
6
|
+
* `@owlmeans/web-consent` deliberately knows nothing about OwlMeans i18n — one of its consumers is
|
|
7
|
+
* an Astro site with none — so this is where the two meet.
|
|
8
|
+
*/
|
|
9
|
+
export declare const PanelCookieConsent: FC<CookieConsentProps>;
|
|
10
|
+
export declare const PanelCookiePolicy: FC<CookiePolicyProps>;
|
|
11
|
+
//# sourceMappingURL=component.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"component.d.ts","sourceRoot":"","sources":["../../src/consent/component.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAA;AAE/B,OAAO,KAAK,EAAE,kBAAkB,EAAE,iBAAiB,EAAiB,MAAM,uBAAuB,CAAA;AA6BjG;;;;;GAKG;AACH,eAAO,MAAM,kBAAkB,EAAE,EAAE,CAAC,kBAAkB,CAMrD,CAAA;AAED,eAAO,MAAM,iBAAiB,EAAE,EAAE,CAAC,iBAAiB,CAMnD,CAAA"}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { useCallback } from 'react';
|
|
3
|
+
import { CookieConsent, CookiePolicy, defaultConsentTranslate } from '@owlmeans/web-consent';
|
|
4
|
+
import { useI18nLib, useLanguage } from '@owlmeans/client-i18n';
|
|
5
|
+
import { SUPPORTED_LNGS } from '@owlmeans/i18n';
|
|
6
|
+
/**
|
|
7
|
+
* Resolve consent copy through the application first, and the packaged bundle second.
|
|
8
|
+
*
|
|
9
|
+
* The chain matters. `@owlmeans/web-consent` takes `translate` as a prop and, once given one,
|
|
10
|
+
* stops consulting its own translations — so a wrapper that forwarded the framework resolver
|
|
11
|
+
* alone would render the ENGLISH default for every key the application had not overridden, in
|
|
12
|
+
* every language. Falling through to the packaged bundle for the current locale means an
|
|
13
|
+
* application overrides what it wants to and inherits seven languages for the rest.
|
|
14
|
+
*/
|
|
15
|
+
const useConsentTranslate = (locale, override) => {
|
|
16
|
+
const t = useI18nLib('consent');
|
|
17
|
+
return useCallback((key, defaultValue) => {
|
|
18
|
+
if (override != null) {
|
|
19
|
+
return override(key, defaultValue);
|
|
20
|
+
}
|
|
21
|
+
const packaged = defaultConsentTranslate(locale)(key, defaultValue);
|
|
22
|
+
// `t` answers with whatever it is given when the key is unknown, so the packaged string is
|
|
23
|
+
// what it is given — an application's override wins, and everything else stays translated.
|
|
24
|
+
return t(key, { defaultValue: packaged });
|
|
25
|
+
}, [t, locale, override]);
|
|
26
|
+
};
|
|
27
|
+
/**
|
|
28
|
+
* The consent dialog, bound to this application's language and translations.
|
|
29
|
+
*
|
|
30
|
+
* `@owlmeans/web-consent` deliberately knows nothing about OwlMeans i18n — one of its consumers is
|
|
31
|
+
* an Astro site with none — so this is where the two meet.
|
|
32
|
+
*/
|
|
33
|
+
export const PanelCookieConsent = props => {
|
|
34
|
+
const [lng] = useLanguage();
|
|
35
|
+
const locale = props.locale ?? lng;
|
|
36
|
+
const translate = useConsentTranslate(locale, props.translate);
|
|
37
|
+
return _jsx(CookieConsent, { ...props, locale: locale, translate: translate });
|
|
38
|
+
};
|
|
39
|
+
export const PanelCookiePolicy = props => {
|
|
40
|
+
const [lng] = useLanguage();
|
|
41
|
+
const locale = props.locale ?? lng;
|
|
42
|
+
const translate = useConsentTranslate(locale, props.translate);
|
|
43
|
+
return _jsx(CookiePolicy, { ...props, locale: locale, translate: translate });
|
|
44
|
+
};
|
|
45
|
+
/**
|
|
46
|
+
* The consent package carries its own locale list because it must build with no dependency on the
|
|
47
|
+
* i18n package at all. This assertion is what keeps the two from drifting: a language added to the
|
|
48
|
+
* framework and not to the bundle fails here, at build time, rather than as a dialog rendering
|
|
49
|
+
* English to the one reader who cannot report it.
|
|
50
|
+
*/
|
|
51
|
+
const _localeParity = SUPPORTED_LNGS;
|
|
52
|
+
void _localeParity;
|
|
53
|
+
//# sourceMappingURL=component.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"component.js","sourceRoot":"","sources":["../../src/consent/component.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,OAAO,CAAA;AAEnC,OAAO,EAAE,aAAa,EAAE,YAAY,EAAE,uBAAuB,EAAE,MAAM,uBAAuB,CAAA;AAE5F,OAAO,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAA;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAA;AAE/C;;;;;;;;GAQG;AACH,MAAM,mBAAmB,GAAG,CAC1B,MAAc,EAAE,QAAwD,EACvB,EAAE;IACnD,MAAM,CAAC,GAAG,UAAU,CAAC,SAAS,CAAC,CAAA;IAE/B,OAAO,WAAW,CAAC,CAAC,GAAW,EAAE,YAAoB,EAAE,EAAE;QACvD,IAAI,QAAQ,IAAI,IAAI,EAAE,CAAC;YACrB,OAAO,QAAQ,CAAC,GAAG,EAAE,YAAY,CAAC,CAAA;QACpC,CAAC;QACD,MAAM,QAAQ,GAAG,uBAAuB,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,YAAY,CAAC,CAAA;QACnE,2FAA2F;QAC3F,2FAA2F;QAC3F,OAAO,CAAC,CAAC,GAAG,EAAE,EAAE,YAAY,EAAE,QAAQ,EAAE,CAAC,CAAA;IAC3C,CAAC,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC,CAAA;AAC3B,CAAC,CAAA;AAED;;;;;GAKG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAA2B,KAAK,CAAC,EAAE;IAChE,MAAM,CAAC,GAAG,CAAC,GAAG,WAAW,EAAE,CAAA;IAC3B,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM,IAAI,GAAG,CAAA;IAClC,MAAM,SAAS,GAAG,mBAAmB,CAAC,MAAM,EAAE,KAAK,CAAC,SAAS,CAAC,CAAA;IAE9D,OAAO,KAAC,aAAa,OAAK,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,SAAS,GAAI,CAAA;AAC3E,CAAC,CAAA;AAED,MAAM,CAAC,MAAM,iBAAiB,GAA0B,KAAK,CAAC,EAAE;IAC9D,MAAM,CAAC,GAAG,CAAC,GAAG,WAAW,EAAE,CAAA;IAC3B,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM,IAAI,GAAG,CAAA;IAClC,MAAM,SAAS,GAAG,mBAAmB,CAAC,MAAM,EAAE,KAAK,CAAC,SAAS,CAAC,CAAA;IAE9D,OAAO,KAAC,YAAY,OAAK,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,SAAS,GAAI,CAAA;AAC1E,CAAC,CAAA;AAED;;;;;GAKG;AACH,MAAM,aAAa,GAA6B,cAA0C,CAAA;AAC1F,KAAK,aAAa,CAAA"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
export * from './component.js';
|
|
2
|
+
export { useConsent, useConsentCategory, consentStore, openConsent, isConsented, readConsent, writeConsent, clearConsent, DEFAULT_CONSENT_CATEGORIES, CONSENT_KEY, CONSENT_ESSENTIAL, CONSENT_ANALYTICS, CONSENT_MARKETING, consentBootstrapScript, } from '@owlmeans/web-consent';
|
|
3
|
+
export type { ConsentCategory, ConsentOptions, ConsentRecord, ConsentSignal, ConsentState, CookieConsentProps, CookiePolicyProps, } from '@owlmeans/web-consent';
|
|
4
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/consent/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAA;AAC9B,OAAO,EACL,UAAU,EAAE,kBAAkB,EAAE,YAAY,EAAE,WAAW,EAAE,WAAW,EACtE,WAAW,EAAE,YAAY,EAAE,YAAY,EAAE,0BAA0B,EACnE,WAAW,EAAE,iBAAiB,EAAE,iBAAiB,EAAE,iBAAiB,EACpE,sBAAsB,GACvB,MAAM,uBAAuB,CAAA;AAC9B,YAAY,EACV,eAAe,EAAE,cAAc,EAAE,aAAa,EAAE,aAAa,EAAE,YAAY,EAC3E,kBAAkB,EAAE,iBAAiB,GACtC,MAAM,uBAAuB,CAAA"}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export * from './component.js';
|
|
2
|
+
export { useConsent, useConsentCategory, consentStore, openConsent, isConsented, readConsent, writeConsent, clearConsent, DEFAULT_CONSENT_CATEGORIES, CONSENT_KEY, CONSENT_ESSENTIAL, CONSENT_ANALYTICS, CONSENT_MARKETING, consentBootstrapScript, } from '@owlmeans/web-consent';
|
|
3
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/consent/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAA;AAC9B,OAAO,EACL,UAAU,EAAE,kBAAkB,EAAE,YAAY,EAAE,WAAW,EAAE,WAAW,EACtE,WAAW,EAAE,YAAY,EAAE,YAAY,EAAE,0BAA0B,EACnE,WAAW,EAAE,iBAAiB,EAAE,iBAAiB,EAAE,iBAAiB,EACpE,sBAAsB,GACvB,MAAM,uBAAuB,CAAA"}
|
package/build/context.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAG,UAAU,EAAE,MAAM,YAAY,CAAA;
|
|
1
|
+
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAG,UAAU,EAAE,MAAM,YAAY,CAAA;AAKxD,eAAO,MAAM,WAAW,GAAI,CAAC,SAAS,SAAS,EAAE,CAAC,SAAS,UAAU,CAAC,CAAC,CAAC,OAAO,CAAC,KAAG,CAalF,CAAA;AAED,eAAO,MAAM,UAAU,GAAI,CAAC,SAAS,SAAS,GAAG,SAAS,EAAC,CAAC,SAAS,UAAU,CAAC,CAAC,CAAC,GAAG,UAAU,CAAC,CAAC,CAAC,QACnF,CAAA"}
|
package/build/context.js
CHANGED
|
@@ -1,11 +1,15 @@
|
|
|
1
1
|
import { appendFlowService } from '@owlmeans/web-flow';
|
|
2
2
|
import { makeContext as makeClientContext, useContext as useCtx } from '@owlmeans/web-client';
|
|
3
3
|
import { apiConfigMiddleware } from '@owlmeans/api-config-client';
|
|
4
|
+
import { appendLoginScreen } from './components/login/append.js';
|
|
4
5
|
export const makeContext = (cfg) => {
|
|
5
6
|
const context = makeClientContext(cfg);
|
|
6
7
|
context.registerMiddleware(apiConfigMiddleware);
|
|
7
8
|
appendFlowService(context);
|
|
8
9
|
context.flow = () => context.service('flow');
|
|
10
|
+
// Every app on this package gets the shadcn sign-in screen with no wiring of its own; one that
|
|
11
|
+
// wants its logo on it calls `appendLoginScreen` again, which is idempotent.
|
|
12
|
+
appendLoginScreen(context);
|
|
9
13
|
return context;
|
|
10
14
|
};
|
|
11
15
|
export const useContext = () => useCtx();
|
package/build/context.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context.js","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAA;AAEtD,OAAO,EAAE,WAAW,IAAI,iBAAiB,EAAE,UAAU,IAAI,MAAM,EAAE,MAAM,sBAAsB,CAAA;AAC7F,OAAO,EAAE,mBAAmB,EAAE,MAAM,6BAA6B,CAAA;
|
|
1
|
+
{"version":3,"file":"context.js","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAA;AAEtD,OAAO,EAAE,WAAW,IAAI,iBAAiB,EAAE,UAAU,IAAI,MAAM,EAAE,MAAM,sBAAsB,CAAA;AAC7F,OAAO,EAAE,mBAAmB,EAAE,MAAM,6BAA6B,CAAA;AACjE,OAAO,EAAE,iBAAiB,EAAE,MAAM,8BAA8B,CAAA;AAEhE,MAAM,CAAC,MAAM,WAAW,GAAG,CAA+C,GAAM,EAAK,EAAE;IACrF,MAAM,OAAO,GAAG,iBAAiB,CAAC,GAAG,CAAM,CAAA;IAE3C,OAAO,CAAC,kBAAkB,CAAC,mBAAmB,CAAC,CAAA;IAE/C,iBAAiB,CAAO,OAAO,CAAC,CAAA;IAChC,OAAO,CAAC,IAAI,GAAG,GAAG,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,MAAM,CAAC,CAAA;IAE5C,+FAA+F;IAC/F,6EAA6E;IAC7E,iBAAiB,CAAO,OAAO,CAAC,CAAA;IAEhC,OAAO,OAAO,CAAA;AAChB,CAAC,CAAA;AAED,MAAM,CAAC,MAAM,UAAU,GAAG,GAA4E,EAAE,CACtG,MAAM,EAAO,CAAA"}
|