@entropy-softworks/ui 2026.7.31 → 2026.8.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.
Files changed (104) hide show
  1. package/CHANGELOG.md +15 -0
  2. package/lib/components/button.d.ts +11 -2
  3. package/lib/components/button.d.ts.map +1 -1
  4. package/lib/components/button.jsx +14 -4
  5. package/lib/components/button.jsx.map +1 -1
  6. package/lib/context/AppConfigContext.d.ts +19 -0
  7. package/lib/context/AppConfigContext.d.ts.map +1 -1
  8. package/lib/context/AppConfigContext.jsx.map +1 -1
  9. package/lib/index.d.ts +1 -0
  10. package/lib/index.d.ts.map +1 -1
  11. package/lib/index.js +2 -0
  12. package/lib/index.js.map +1 -1
  13. package/lib/screens/auth/AccountPickerScreen.d.ts.map +1 -1
  14. package/lib/screens/auth/AccountPickerScreen.jsx +3 -2
  15. package/lib/screens/auth/AccountPickerScreen.jsx.map +1 -1
  16. package/lib/screens/auth/AuthScreen.d.ts +45 -1
  17. package/lib/screens/auth/AuthScreen.d.ts.map +1 -1
  18. package/lib/screens/auth/AuthScreen.jsx +69 -27
  19. package/lib/screens/auth/AuthScreen.jsx.map +1 -1
  20. package/lib/screens/auth/ConsentScreen.d.ts.map +1 -1
  21. package/lib/screens/auth/ConsentScreen.jsx +2 -2
  22. package/lib/screens/auth/ConsentScreen.jsx.map +1 -1
  23. package/lib/screens/auth/ErrorScreen.d.ts.map +1 -1
  24. package/lib/screens/auth/ErrorScreen.jsx +2 -2
  25. package/lib/screens/auth/ErrorScreen.jsx.map +1 -1
  26. package/lib/screens/auth/ExpiredLinkScreen.d.ts.map +1 -1
  27. package/lib/screens/auth/ExpiredLinkScreen.jsx +2 -2
  28. package/lib/screens/auth/ExpiredLinkScreen.jsx.map +1 -1
  29. package/lib/screens/auth/ForgotPasswordScreen.d.ts.map +1 -1
  30. package/lib/screens/auth/ForgotPasswordScreen.jsx +7 -6
  31. package/lib/screens/auth/ForgotPasswordScreen.jsx.map +1 -1
  32. package/lib/screens/auth/ImportDataScreen.d.ts.map +1 -1
  33. package/lib/screens/auth/ImportDataScreen.jsx +1 -1
  34. package/lib/screens/auth/ImportDataScreen.jsx.map +1 -1
  35. package/lib/screens/auth/LoginScreen.d.ts.map +1 -1
  36. package/lib/screens/auth/LoginScreen.jsx +7 -6
  37. package/lib/screens/auth/LoginScreen.jsx.map +1 -1
  38. package/lib/screens/auth/MfaChallengeScreen.d.ts.map +1 -1
  39. package/lib/screens/auth/MfaChallengeScreen.jsx +3 -2
  40. package/lib/screens/auth/MfaChallengeScreen.jsx.map +1 -1
  41. package/lib/screens/auth/MfaEnrollScreen.d.ts.map +1 -1
  42. package/lib/screens/auth/MfaEnrollScreen.jsx +9 -8
  43. package/lib/screens/auth/MfaEnrollScreen.jsx.map +1 -1
  44. package/lib/screens/auth/PasskeyEnrollScreen.d.ts.map +1 -1
  45. package/lib/screens/auth/PasskeyEnrollScreen.jsx +2 -2
  46. package/lib/screens/auth/PasskeyEnrollScreen.jsx.map +1 -1
  47. package/lib/screens/auth/PrivacyPolicyScreen.d.ts.map +1 -1
  48. package/lib/screens/auth/PrivacyPolicyScreen.jsx +3 -2
  49. package/lib/screens/auth/PrivacyPolicyScreen.jsx.map +1 -1
  50. package/lib/screens/auth/RegisterScreen.d.ts.map +1 -1
  51. package/lib/screens/auth/RegisterScreen.jsx +6 -5
  52. package/lib/screens/auth/RegisterScreen.jsx.map +1 -1
  53. package/lib/screens/auth/ResetPasswordScreen.d.ts.map +1 -1
  54. package/lib/screens/auth/ResetPasswordScreen.jsx +6 -5
  55. package/lib/screens/auth/ResetPasswordScreen.jsx.map +1 -1
  56. package/lib/screens/auth/ServerConfigScreen.d.ts.map +1 -1
  57. package/lib/screens/auth/ServerConfigScreen.jsx +6 -5
  58. package/lib/screens/auth/ServerConfigScreen.jsx.map +1 -1
  59. package/lib/screens/auth/TermsOfServiceScreen.d.ts.map +1 -1
  60. package/lib/screens/auth/TermsOfServiceScreen.jsx +3 -2
  61. package/lib/screens/auth/TermsOfServiceScreen.jsx.map +1 -1
  62. package/lib/screens/auth/VerifyEmailScreen.d.ts.map +1 -1
  63. package/lib/screens/auth/VerifyEmailScreen.jsx +5 -4
  64. package/lib/screens/auth/VerifyEmailScreen.jsx.map +1 -1
  65. package/lib/screens/auth/WelcomeScreen.d.ts.map +1 -1
  66. package/lib/screens/auth/WelcomeScreen.jsx +2 -2
  67. package/lib/screens/auth/WelcomeScreen.jsx.map +1 -1
  68. package/lib/services/auth.service.d.ts +9 -0
  69. package/lib/services/auth.service.d.ts.map +1 -1
  70. package/lib/services/auth.service.js.map +1 -1
  71. package/lib/services/index.d.ts +1 -0
  72. package/lib/services/index.d.ts.map +1 -1
  73. package/lib/services/index.js +2 -0
  74. package/lib/services/index.js.map +1 -1
  75. package/lib/services/telemetry.d.ts +30 -0
  76. package/lib/services/telemetry.d.ts.map +1 -0
  77. package/lib/services/telemetry.js +72 -0
  78. package/lib/services/telemetry.js.map +1 -0
  79. package/package.json +1 -1
  80. package/src/components/button.tsx +32 -1
  81. package/src/context/AppConfigContext.tsx +19 -0
  82. package/src/index.ts +9 -0
  83. package/src/screens/auth/AccountPickerScreen.tsx +4 -2
  84. package/src/screens/auth/AuthScreen.tsx +159 -31
  85. package/src/screens/auth/ConsentScreen.tsx +4 -2
  86. package/src/screens/auth/ErrorScreen.tsx +4 -2
  87. package/src/screens/auth/ExpiredLinkScreen.tsx +4 -2
  88. package/src/screens/auth/ForgotPasswordScreen.tsx +10 -6
  89. package/src/screens/auth/ImportDataScreen.tsx +2 -1
  90. package/src/screens/auth/LoginScreen.tsx +10 -6
  91. package/src/screens/auth/MfaChallengeScreen.tsx +3 -2
  92. package/src/screens/auth/MfaEnrollScreen.tsx +15 -8
  93. package/src/screens/auth/PasskeyEnrollScreen.tsx +4 -2
  94. package/src/screens/auth/PrivacyPolicyScreen.tsx +4 -2
  95. package/src/screens/auth/RegisterScreen.tsx +8 -5
  96. package/src/screens/auth/ResetPasswordScreen.tsx +9 -5
  97. package/src/screens/auth/ServerConfigScreen.tsx +6 -5
  98. package/src/screens/auth/TermsOfServiceScreen.tsx +4 -2
  99. package/src/screens/auth/VerifyEmailScreen.tsx +8 -4
  100. package/src/screens/auth/WelcomeScreen.tsx +4 -2
  101. package/src/services/__tests__/telemetry.test.ts +81 -0
  102. package/src/services/auth.service.ts +9 -0
  103. package/src/services/index.ts +9 -0
  104. package/src/services/telemetry.ts +107 -0
package/CHANGELOG.md CHANGED
@@ -7,6 +7,21 @@ are CalVer — `YYYY.M.D` of the publish date, with leading zeros dropped (npm's
7
7
  them), matching the `entropy-auth` crate. The `0.1.0` entry below predates the switch and was never
8
8
  published to npm.
9
9
 
10
+ ## 2026.8.1
11
+
12
+ ### Added
13
+
14
+ - Telemetry registry (`registerTelemetry`, `trackClick`, `withClickTracking`). The
15
+ package reports interactions to a sink the host app supplies; it knows nothing
16
+ about batching, authentication or transport. No sink registered means every
17
+ entry point is a no-op, so consumers that do not opt in are unaffected.
18
+ - `telemetryId` prop on `Button` and `IconButton`. Reports a stable,
19
+ author-assigned id when the control is activated. Wired through `onPress`, so
20
+ a disabled or loading button records nothing.
21
+ - All 69 interactive controls across the 18 auth screens carry a `telemetryId`,
22
+ making sign-in, sign-up, MFA and consent measurable by consuming apps without
23
+ each of them re-tagging the packaged screens.
24
+
10
25
  ## [Unreleased]
11
26
 
12
27
  ## [2026.7.31] — 2026-07-31
@@ -10,7 +10,16 @@ export interface ButtonProps extends Omit<PressableProps, "className" | "style">
10
10
  disabled?: boolean;
11
11
  /** Override the loading spinner colour (otherwise derived from the variant). */
12
12
  spinnerColor?: string;
13
+ /**
14
+ * Stable, author-assigned id reported when this control is activated, e.g.
15
+ * `"login.submit"`. Omit it and nothing is tracked.
16
+ *
17
+ * Deliberately not derived from the button's label: copy changes over time,
18
+ * differs per locale, and can interpolate user data — all of which would
19
+ * either break a dashboard or leak into one.
20
+ */
21
+ telemetryId?: string;
13
22
  }
14
- export declare function Button({ variant, size, className, textClassName, children, isLoading, disabled, spinnerColor, onPressIn, onPressOut, ...props }: ButtonProps): React.JSX.Element;
15
- export declare function IconButton({ size, children, className, ...props }: ButtonProps): React.JSX.Element;
23
+ export declare function Button({ variant, size, className, textClassName, children, isLoading, disabled, spinnerColor, telemetryId, onPress, onPressIn, onPressOut, ...props }: ButtonProps): React.JSX.Element;
24
+ export declare function IconButton({ size, children, className, telemetryId, onPress, ...props }: ButtonProps): React.JSX.Element;
16
25
  //# sourceMappingURL=button.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"button.d.ts","sourceRoot":"","sources":["../../src/components/button.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,EAAgC,KAAK,cAAc,EAAkB,MAAM,cAAc,CAAC;AAKjG,MAAM,WAAW,WAAY,SAAQ,IAAI,CAAC,cAAc,EAAE,WAAW,GAAG,OAAO,CAAC;IAC9E,OAAO,CAAC,EAAE,SAAS,GAAG,OAAO,GAAG,SAAS,GAAG,aAAa,CAAC;IAC1D,IAAI,CAAC,EAAE,IAAI,GAAG,SAAS,GAAG,IAAI,CAAC;IAC/B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC3B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,gFAAgF;IAChF,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAsBD,wBAAgB,MAAM,CAAC,EACrB,OAAmB,EACnB,IAAgB,EAChB,SAAS,EACT,aAAa,EACb,QAAQ,EACR,SAAiB,EACjB,QAAgB,EAChB,YAAY,EACZ,SAAS,EACT,UAAU,EACV,GAAG,KAAK,EACT,EAAE,WAAW,qBAgEb;AAED,wBAAgB,UAAU,CAAC,EAAE,IAAgB,EAAE,QAAQ,EAAE,SAAS,EAAE,GAAG,KAAK,EAAE,EAAE,WAAW,qBA2B1F"}
1
+ {"version":3,"file":"button.d.ts","sourceRoot":"","sources":["../../src/components/button.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,EAAgC,KAAK,cAAc,EAAkB,MAAM,cAAc,CAAC;AAMjG,MAAM,WAAW,WAAY,SAAQ,IAAI,CAAC,cAAc,EAAE,WAAW,GAAG,OAAO,CAAC;IAC9E,OAAO,CAAC,EAAE,SAAS,GAAG,OAAO,GAAG,SAAS,GAAG,aAAa,CAAC;IAC1D,IAAI,CAAC,EAAE,IAAI,GAAG,SAAS,GAAG,IAAI,CAAC;IAC/B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC3B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,gFAAgF;IAChF,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB;;;;;;;OAOG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAsBD,wBAAgB,MAAM,CAAC,EACrB,OAAmB,EACnB,IAAgB,EAChB,SAAS,EACT,aAAa,EACb,QAAQ,EACR,SAAiB,EACjB,QAAgB,EAChB,YAAY,EACZ,WAAW,EACX,OAAO,EACP,SAAS,EACT,UAAU,EACV,GAAG,KAAK,EACT,EAAE,WAAW,qBAuEb;AAED,wBAAgB,UAAU,CAAC,EACzB,IAAgB,EAChB,QAAQ,EACR,SAAS,EACT,WAAW,EACX,OAAO,EACP,GAAG,KAAK,EACT,EAAE,WAAW,qBAgCb"}
@@ -3,6 +3,7 @@ import { ActivityIndicator, Pressable, Text as RNText } from "react-native";
3
3
  import Animated, { useAnimatedStyle, useSharedValue, withTiming } from "react-native-reanimated";
4
4
  import { useColorScheme } from "nativewind";
5
5
  import { cn } from "../utils/cn";
6
+ import { withClickTracking } from "../services/telemetry";
6
7
  const sizeClass = { sm: "h-10 px-4", default: "h-12 px-4", lg: "h-14 px-6" };
7
8
  const textSizeClass = { sm: "text-sm", default: "text-base", lg: "text-lg" };
8
9
  // Colours are driven by the active theme's CSS variables (`--primary`,
@@ -20,10 +21,15 @@ const fgClass = {
20
21
  outline: "text-foreground",
21
22
  ghost: "text-foreground",
22
23
  };
23
- export function Button({ variant = "default", size = "default", className, textClassName, children, isLoading = false, disabled = false, spinnerColor, onPressIn, onPressOut, ...props }) {
24
+ export function Button({ variant = "default", size = "default", className, textClassName, children, isLoading = false, disabled = false, spinnerColor, telemetryId, onPress, onPressIn, onPressOut, ...props }) {
24
25
  const { colorScheme } = useColorScheme();
25
26
  const isDark = colorScheme === "dark";
26
27
  const isDisabled = disabled || isLoading;
28
+ // Wrapped rather than reported from a press listener so a disabled or
29
+ // loading button records nothing: Pressable does not fire onPress in either
30
+ // state, and counting presses the user never actually completed would
31
+ // overstate every funnel it appears in.
32
+ const handlePress = withClickTracking(telemetryId, onPress);
27
33
  // Reanimated feedback shared by every button: hover (web) lifts slightly,
28
34
  // press dips + dims — two distinct, layered responses.
29
35
  const pressed = useSharedValue(0);
@@ -43,7 +49,7 @@ export function Button({ variant = "default", size = "default", className, textC
43
49
  ? "#FFFFFF"
44
50
  : "#000000");
45
51
  return (<Animated.View style={pressStyle} className={isDisabled ? "opacity-50" : undefined}>
46
- <Pressable className={cn("flex-row items-center justify-center rounded-lg", sizeClass[size], bgClass[variant], className)} disabled={isDisabled} onPressIn={(e) => {
52
+ <Pressable className={cn("flex-row items-center justify-center rounded-lg", sizeClass[size], bgClass[variant], className)} disabled={isDisabled} onPress={handlePress} onPressIn={(e) => {
47
53
  pressed.value = withTiming(1, { duration: 90 });
48
54
  onPressIn?.(e);
49
55
  }} onPressOut={(e) => {
@@ -56,7 +62,11 @@ export function Button({ variant = "default", size = "default", className, textC
56
62
  </Pressable>
57
63
  </Animated.View>);
58
64
  }
59
- export function IconButton({ size = "default", children, className, ...props }) {
65
+ export function IconButton({ size = "default", children, className, telemetryId, onPress, ...props }) {
66
+ // IconButton accepts ButtonProps, so telemetryId type-checks on it whether or
67
+ // not it is honoured. Wiring it here means a tagged icon button reports,
68
+ // rather than silently being the one control that never appears.
69
+ const handlePress = withClickTracking(telemetryId, onPress);
60
70
  const dim = { sm: 40, default: 48, lg: 56 }[size];
61
71
  const isDisabled = props.disabled || props.isLoading;
62
72
  const pressed = useSharedValue(0);
@@ -65,7 +75,7 @@ export function IconButton({ size = "default", children, className, ...props })
65
75
  transform: [{ scale: 1 + hovered.value * 0.06 - pressed.value * 0.08 }],
66
76
  }));
67
77
  return (<Animated.View style={pressStyle} className={isDisabled ? "opacity-50" : undefined}>
68
- <Pressable className={cn("items-center justify-center rounded-lg", className)} style={{ width: dim, height: dim }} disabled={isDisabled} onPressIn={() => (pressed.value = withTiming(1, { duration: 90 }))} onPressOut={() => (pressed.value = withTiming(0, { duration: 150 }))} onHoverIn={() => (hovered.value = withTiming(1, { duration: 120 }))} onHoverOut={() => (hovered.value = withTiming(0, { duration: 160 }))} {...props} focusable={!isDisabled} accessibilityState={{ disabled: isDisabled, busy: props.isLoading }}>
78
+ <Pressable className={cn("items-center justify-center rounded-lg", className)} style={{ width: dim, height: dim }} disabled={isDisabled} onPress={handlePress} onPressIn={() => (pressed.value = withTiming(1, { duration: 90 }))} onPressOut={() => (pressed.value = withTiming(0, { duration: 150 }))} onHoverIn={() => (hovered.value = withTiming(1, { duration: 120 }))} onHoverOut={() => (hovered.value = withTiming(0, { duration: 160 }))} {...props} focusable={!isDisabled} accessibilityState={{ disabled: isDisabled, busy: props.isLoading }}>
69
79
  {children}
70
80
  </Pressable>
71
81
  </Animated.View>);
@@ -1 +1 @@
1
- {"version":3,"file":"button.jsx","sourceRoot":"","sources":["../../src/components/button.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"button.jsx","sourceRoot":"","sources":["../../src/components/button.tsx"],"names":[],"mappings":"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"}
@@ -25,6 +25,12 @@ export interface AppRoutes {
25
25
  export type LogoComponent = React.ComponentType<{
26
26
  width?: number;
27
27
  height?: number;
28
+ /**
29
+ * Ink colour for a monochrome mark. The auth screen passes the resolved
30
+ * theme foreground, so a single-colour logo inverts with the theme instead
31
+ * of each logo having to resolve the colour scheme for itself.
32
+ */
33
+ color?: string;
28
34
  style?: StyleProp<ViewStyle> | StyleProp<ImageStyle>;
29
35
  }>;
30
36
  export interface AppConfig {
@@ -47,6 +53,19 @@ export interface AppConfig {
47
53
  termsText?: string;
48
54
  /** Optional privacy-policy markdown / plain text. */
49
55
  privacyText?: string;
56
+ /**
57
+ * The logo already spells the product name (a wordmark rather than a glyph).
58
+ *
59
+ * When true the auth screen renders the mark on its own, at its natural
60
+ * aspect ratio, instead of pairing a square glyph with the app name — which
61
+ * would otherwise print the name twice and squash a wide mark into a square.
62
+ */
63
+ logoIsWordmark?: boolean;
64
+ /**
65
+ * Rendered width of a wordmark logo, in px. Defaults to 160. Only consulted
66
+ * when `logoIsWordmark` is set; a glyph logo keeps its square 72px pairing.
67
+ */
68
+ logoWidth?: number;
50
69
  }
51
70
  export declare function AppConfigProvider({ config, children, }: {
52
71
  config: AppConfig;
@@ -1 +1 @@
1
- {"version":3,"file":"AppConfigContext.d.ts","sourceRoot":"","sources":["../../src/context/AppConfigContext.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA6C,MAAM,OAAO,CAAC;AAClE,OAAO,EAAE,KAAK,IAAI,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EAAE,KAAK,UAAU,EAAE,KAAK,SAAS,EAAE,KAAK,SAAS,EAAE,MAAM,cAAc,CAAC;AAE/E;;;;GAIG;AACH,MAAM,WAAW,SAAS;IACxB,OAAO,EAAE,IAAI,CAAC;IACd,KAAK,EAAE,IAAI,CAAC;IACZ,QAAQ,EAAE,IAAI,CAAC;IACf,cAAc,EAAE,IAAI,CAAC;IACrB,aAAa,EAAE,IAAI,CAAC;IACpB,WAAW,EAAE,IAAI,CAAC;IAClB,YAAY,EAAE,IAAI,CAAC;IACnB,SAAS,EAAE,IAAI,CAAC;IAChB,cAAc,EAAE,IAAI,CAAC;IACrB,aAAa,EAAE,IAAI,CAAC;IACpB,YAAY,EAAE,IAAI,CAAC;IACnB,UAAU,EAAE,IAAI,CAAC;IACjB,yEAAyE;IACzE,IAAI,EAAE,IAAI,CAAC;CACZ;AAED,MAAM,MAAM,aAAa,GAAG,KAAK,CAAC,aAAa,CAAC;IAC9C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,GAAG,SAAS,CAAC,UAAU,CAAC,CAAC;CACtD,CAAC,CAAC;AAEH,MAAM,WAAW,SAAS;IACxB,4EAA4E;IAC5E,OAAO,EAAE,MAAM,CAAC;IAChB,qDAAqD;IACrD,IAAI,EAAE,aAAa,CAAC;IACpB,yBAAyB;IACzB,MAAM,EAAE,SAAS,CAAC;IAClB;;;OAGG;IACH,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,qDAAqD;IACrD,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAID,wBAAgB,iBAAiB,CAAC,EAChC,MAAM,EACN,QAAQ,GACT,EAAE;IACD,MAAM,EAAE,SAAS,CAAC;IAClB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B,qBAGA;AAED,wBAAgB,YAAY,IAAI,SAAS,CAQxC"}
1
+ {"version":3,"file":"AppConfigContext.d.ts","sourceRoot":"","sources":["../../src/context/AppConfigContext.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA6C,MAAM,OAAO,CAAC;AAClE,OAAO,EAAE,KAAK,IAAI,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EAAE,KAAK,UAAU,EAAE,KAAK,SAAS,EAAE,KAAK,SAAS,EAAE,MAAM,cAAc,CAAC;AAE/E;;;;GAIG;AACH,MAAM,WAAW,SAAS;IACxB,OAAO,EAAE,IAAI,CAAC;IACd,KAAK,EAAE,IAAI,CAAC;IACZ,QAAQ,EAAE,IAAI,CAAC;IACf,cAAc,EAAE,IAAI,CAAC;IACrB,aAAa,EAAE,IAAI,CAAC;IACpB,WAAW,EAAE,IAAI,CAAC;IAClB,YAAY,EAAE,IAAI,CAAC;IACnB,SAAS,EAAE,IAAI,CAAC;IAChB,cAAc,EAAE,IAAI,CAAC;IACrB,aAAa,EAAE,IAAI,CAAC;IACpB,YAAY,EAAE,IAAI,CAAC;IACnB,UAAU,EAAE,IAAI,CAAC;IACjB,yEAAyE;IACzE,IAAI,EAAE,IAAI,CAAC;CACZ;AAED,MAAM,MAAM,aAAa,GAAG,KAAK,CAAC,aAAa,CAAC;IAC9C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB;;;;OAIG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,GAAG,SAAS,CAAC,UAAU,CAAC,CAAC;CACtD,CAAC,CAAC;AAEH,MAAM,WAAW,SAAS;IACxB,4EAA4E;IAC5E,OAAO,EAAE,MAAM,CAAC;IAChB,qDAAqD;IACrD,IAAI,EAAE,aAAa,CAAC;IACpB,yBAAyB;IACzB,MAAM,EAAE,SAAS,CAAC;IAClB;;;OAGG;IACH,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,qDAAqD;IACrD,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;;;;OAMG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAID,wBAAgB,iBAAiB,CAAC,EAChC,MAAM,EACN,QAAQ,GACT,EAAE;IACD,MAAM,EAAE,SAAS,CAAC;IAClB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B,qBAGA;AAED,wBAAgB,YAAY,IAAI,SAAS,CAQxC"}
@@ -1 +1 @@
1
- {"version":3,"file":"AppConfigContext.jsx","sourceRoot":"","sources":["../../src/context/AppConfigContext.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,aAAa,EAAE,UAAU,EAAE,OAAO,EAAE,MAAM,OAAO,CAAC;AAsDlE,MAAM,gBAAgB,GAAG,aAAa,CAAmB,IAAI,CAAC,CAAC;AAE/D,MAAM,UAAU,iBAAiB,CAAC,EAChC,MAAM,EACN,QAAQ,GAIT;IACC,MAAM,KAAK,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC,CAAC,CAAC;IAC9C,OAAO,CAAC,gBAAgB,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,EAAE,gBAAgB,CAAC,QAAQ,CAAC,CAAC;AACzF,CAAC;AAED,MAAM,UAAU,YAAY;IAC1B,MAAM,GAAG,GAAG,UAAU,CAAC,gBAAgB,CAAC,CAAC;IACzC,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,MAAM,IAAI,KAAK,CACb,gFAAgF,CACjF,CAAC;IACJ,CAAC;IACD,OAAO,GAAG,CAAC;AACb,CAAC"}
1
+ {"version":3,"file":"AppConfigContext.jsx","sourceRoot":"","sources":["../../src/context/AppConfigContext.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,aAAa,EAAE,UAAU,EAAE,OAAO,EAAE,MAAM,OAAO,CAAC;AAyElE,MAAM,gBAAgB,GAAG,aAAa,CAAmB,IAAI,CAAC,CAAC;AAE/D,MAAM,UAAU,iBAAiB,CAAC,EAChC,MAAM,EACN,QAAQ,GAIT;IACC,MAAM,KAAK,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC,CAAC,CAAC;IAC9C,OAAO,CAAC,gBAAgB,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,EAAE,gBAAgB,CAAC,QAAQ,CAAC,CAAC;AACzF,CAAC;AAED,MAAM,UAAU,YAAY;IAC1B,MAAM,GAAG,GAAG,UAAU,CAAC,gBAAgB,CAAC,CAAC;IACzC,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,MAAM,IAAI,KAAK,CACb,gFAAgF,CACjF,CAAC;IACJ,CAAC;IACD,OAAO,GAAG,CAAC;AACb,CAAC"}
package/lib/index.d.ts CHANGED
@@ -7,4 +7,5 @@ export * from "./forms";
7
7
  export * from "./hooks";
8
8
  export * from "./services";
9
9
  export * from "./utils";
10
+ export { registerTelemetry, trackClick, withClickTracking, __resetTelemetryForTests, type TelemetrySink, } from "./services/telemetry";
10
11
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAuCA,cAAc,cAAc,CAAC;AAC7B,cAAc,mBAAmB,CAAC;AAClC,cAAc,uBAAuB,CAAC;AACtC,cAAc,WAAW,CAAC;AAC1B,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,YAAY,CAAC;AAC3B,cAAc,SAAS,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAuCA,cAAc,cAAc,CAAC;AAC7B,cAAc,mBAAmB,CAAC;AAClC,cAAc,uBAAuB,CAAC;AACtC,cAAc,WAAW,CAAC;AAC1B,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,YAAY,CAAC;AAC3B,cAAc,SAAS,CAAC;AAGxB,OAAO,EACL,iBAAiB,EACjB,UAAU,EACV,iBAAiB,EACjB,wBAAwB,EACxB,KAAK,aAAa,GACnB,MAAM,sBAAsB,CAAC"}
package/lib/index.js CHANGED
@@ -44,4 +44,6 @@ export * from "./forms";
44
44
  export * from "./hooks";
45
45
  export * from "./services";
46
46
  export * from "./utils";
47
+ // Telemetry registry. No-op until a host app calls registerTelemetry.
48
+ export { registerTelemetry, trackClick, withClickTracking, __resetTelemetryForTests, } from "./services/telemetry";
47
49
  //# sourceMappingURL=index.js.map
package/lib/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,0CAA0C;AAE1C,4EAA4E;AAC5E,2CAA2C;AAC3C,EAAE;AACF,2DAA2D;AAC3D,+EAA+E;AAC/E,0EAA0E;AAC1E,EAAE;AACF,qEAAqE;AACrE,wEAAwE;AACxE,iEAAiE;AACjE,uEAAuE;AACvE,mDAAmD;AAEnD,oEAAoE;AACpE,kEAAkE;AAClE,qEAAqE;AACrE,iEAAiE;AACjE,sEAAsE;AACtE,sEAAsE;AACtE,+CAA+C;AAC/C,qEAAqE;AACrE,uEAAuE;AACvE,qEAAqE;AACrE,oCAAoC;AACpC,mEAAmE;AACnE,yDAAyD;AACzD,mEAAmE;AACnE,kEAAkE;AAClE,kEAAkE;AAClE,yBAAyB;AACzB,EAAE;AACF,oEAAoE;AACpE,kEAAkE;AAClE,mEAAmE;AACnE,oEAAoE;AACpE,oEAAoE;AACpE,+DAA+D;AAC/D,cAAc,cAAc,CAAC;AAC7B,cAAc,mBAAmB,CAAC;AAClC,cAAc,uBAAuB,CAAC;AACtC,cAAc,WAAW,CAAC;AAC1B,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,YAAY,CAAC;AAC3B,cAAc,SAAS,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,0CAA0C;AAE1C,4EAA4E;AAC5E,2CAA2C;AAC3C,EAAE;AACF,2DAA2D;AAC3D,+EAA+E;AAC/E,0EAA0E;AAC1E,EAAE;AACF,qEAAqE;AACrE,wEAAwE;AACxE,iEAAiE;AACjE,uEAAuE;AACvE,mDAAmD;AAEnD,oEAAoE;AACpE,kEAAkE;AAClE,qEAAqE;AACrE,iEAAiE;AACjE,sEAAsE;AACtE,sEAAsE;AACtE,+CAA+C;AAC/C,qEAAqE;AACrE,uEAAuE;AACvE,qEAAqE;AACrE,oCAAoC;AACpC,mEAAmE;AACnE,yDAAyD;AACzD,mEAAmE;AACnE,kEAAkE;AAClE,kEAAkE;AAClE,yBAAyB;AACzB,EAAE;AACF,oEAAoE;AACpE,kEAAkE;AAClE,mEAAmE;AACnE,oEAAoE;AACpE,oEAAoE;AACpE,+DAA+D;AAC/D,cAAc,cAAc,CAAC;AAC7B,cAAc,mBAAmB,CAAC;AAClC,cAAc,uBAAuB,CAAC;AACtC,cAAc,WAAW,CAAC;AAC1B,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,YAAY,CAAC;AAC3B,cAAc,SAAS,CAAC;AAExB,sEAAsE;AACtE,OAAO,EACL,iBAAiB,EACjB,UAAU,EACV,iBAAiB,EACjB,wBAAwB,GAEzB,MAAM,sBAAsB,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"AccountPickerScreen.d.ts","sourceRoot":"","sources":["../../../src/screens/auth/AccountPickerScreen.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAgB1B,iDAAiD;AACjD,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,wBAAwB;IACvC,QAAQ,EAAE,eAAe,EAAE,CAAC;IAC5B,sCAAsC;IACtC,QAAQ,EAAE,CAAC,OAAO,EAAE,eAAe,KAAK,IAAI,CAAC;IAC7C,wCAAwC;IACxC,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB;AAED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,EAClC,QAAQ,EACR,QAAQ,EACR,YAAY,EACZ,SAAS,GACV,EAAE,wBAAwB,qBAyD1B;AAED,eAAe,mBAAmB,CAAC"}
1
+ {"version":3,"file":"AccountPickerScreen.d.ts","sourceRoot":"","sources":["../../../src/screens/auth/AccountPickerScreen.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAiB1B,iDAAiD;AACjD,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,wBAAwB;IACvC,QAAQ,EAAE,eAAe,EAAE,CAAC;IAC5B,sCAAsC;IACtC,QAAQ,EAAE,CAAC,OAAO,EAAE,eAAe,KAAK,IAAI,CAAC;IAC7C,wCAAwC;IACxC,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB;AAED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,EAClC,QAAQ,EACR,QAAQ,EACR,YAAY,EACZ,SAAS,GACV,EAAE,wBAAwB,qBA0D1B;AAED,eAAe,mBAAmB,CAAC"}
@@ -6,6 +6,7 @@ import { useColorScheme } from "nativewind";
6
6
  import { MutedText, Text } from "../../components/text";
7
7
  import { Button } from "../../components/button";
8
8
  import { Card, CardContent, CardDescription, CardFooter, CardHeader, CardTitle, } from "../../components/card";
9
+ import { withClickTracking } from "../../services/telemetry";
9
10
  /**
10
11
  * "Choose an account" screen for multi-session SSO (OIDC `prompt=select_account`
11
12
  * style). Presentational: the host app supplies the accounts and handles the
@@ -26,7 +27,7 @@ export function AccountPickerScreen({ accounts, onSelect, onUseAnother, isLoadin
26
27
  </CardHeader>
27
28
 
28
29
  <CardContent className="gap-2">
29
- {accounts.length === 0 ? (<MutedText className="text-sm">No signed-in accounts.</MutedText>) : (accounts.map((a) => (<Pressable key={a.userId} onPress={() => onSelect(a)} disabled={isLoading} accessibilityRole="button" accessibilityLabel={`Continue as ${a.username}`} className="rounded-md border border-border px-3 py-3">
30
+ {accounts.length === 0 ? (<MutedText className="text-sm">No signed-in accounts.</MutedText>) : (accounts.map((a) => (<Pressable key={a.userId} onPress={withClickTracking("auth.account_picker.on_select", () => onSelect(a))} disabled={isLoading} accessibilityRole="button" accessibilityLabel={`Continue as ${a.username}`} className="rounded-md border border-border px-3 py-3">
30
31
  <Text className="text-sm text-foreground">
31
32
  {a.displayName || a.username}
32
33
  </Text>
@@ -35,7 +36,7 @@ export function AccountPickerScreen({ accounts, onSelect, onUseAnother, isLoadin
35
36
  </CardContent>
36
37
 
37
38
  <CardFooter className="border-t-0">
38
- <Button className="w-full" variant="outline" onPress={onUseAnother} accessibilityLabel="Use another account" accessibilityRole="button">
39
+ <Button className="w-full" variant="outline" telemetryId="auth.account_picker.use_another" onPress={onUseAnother} accessibilityLabel="Use another account" accessibilityRole="button">
39
40
  Use another account
40
41
  </Button>
41
42
  </CardFooter>
@@ -1 +1 @@
1
- {"version":3,"file":"AccountPickerScreen.jsx","sourceRoot":"","sources":["../../../src/screens/auth/AccountPickerScreen.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"AccountPickerScreen.jsx","sourceRoot":"","sources":["../../../src/screens/auth/AccountPickerScreen.tsx"],"names":[],"mappings":"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"}
@@ -46,6 +46,50 @@ export interface AuthScreenProps {
46
46
  decoration?: React.ReactNode;
47
47
  /** Welcome-view tagline/subtitle. Defaults to AppConfig `tagline`. */
48
48
  welcomeCtaLabel?: string;
49
+ /**
50
+ * Show the Sign Up half of the toggle. Defaults to `true`.
51
+ *
52
+ * Set `false` where the server has no self-service registration — an
53
+ * identity provider whose tenant is `closed`, for instance. The toggle is
54
+ * hidden rather than disabled, because a control that cannot ever succeed is
55
+ * worse than no control.
56
+ */
57
+ signUpEnabled?: boolean;
58
+ /**
59
+ * Collect an invite code on the Sign Up form and require it. For servers
60
+ * whose registration is invite-only.
61
+ */
62
+ requireInviteCode?: boolean;
63
+ /**
64
+ * Override registration entirely. When provided this runs instead of
65
+ * `useAuth().register`, and the screen shows `signUpSuccessMessage` rather
66
+ * than assuming the user is now signed in.
67
+ *
68
+ * This exists because registration is not uniform across the estate: the
69
+ * single-tenant apps sign you straight in, while the multi-tenant IdP creates
70
+ * an unverified account, emails a link, and leaves you signed out. Reshaping
71
+ * the shared `AuthService.register` to cover both would have changed the
72
+ * contract vault and simple-finance already depend on.
73
+ */
74
+ onSignUp?: (input: {
75
+ email: string;
76
+ username: string;
77
+ password: string;
78
+ displayName: string;
79
+ inviteCode?: string;
80
+ }) => Promise<void>;
81
+ /** Shown after a successful `onSignUp`. */
82
+ signUpSuccessMessage?: string;
83
+ /**
84
+ * Render the welcome stage (logo, decoration, "Get Started") before the form.
85
+ * Defaults to `true`.
86
+ *
87
+ * Set `false` to land straight on the form. An app whose only purpose at this
88
+ * URL is to authenticate has nothing to introduce, and a button that only
89
+ * reveals the form it precedes is pure friction. The in-card "← Back" is
90
+ * hidden too, since there is no stage behind it.
91
+ */
92
+ showWelcome?: boolean;
49
93
  }
50
94
  /**
51
95
  * Single consolidated unauthenticated screen with three animated stages:
@@ -54,6 +98,6 @@ export interface AuthScreenProps {
54
98
  * are themed popups and a connection-settings dialog can be folded in. Preserves
55
99
  * the passkey ceremony + non-PRF unlock and the HIBP/strength checks.
56
100
  */
57
- export declare function AuthScreen({ passwordLabel, passwordPlaceholder, socialAuth, passkeyEnabled, passkeyUnlockPlaceholder, passkeyUnlockTitle, passkeyUnlockDescription, settings, transition, decoration, welcomeCtaLabel, }?: AuthScreenProps): React.JSX.Element;
101
+ export declare function AuthScreen({ passwordLabel, passwordPlaceholder, socialAuth, passkeyEnabled, passkeyUnlockPlaceholder, passkeyUnlockTitle, passkeyUnlockDescription, settings, transition, decoration, welcomeCtaLabel, signUpEnabled, requireInviteCode, onSignUp, signUpSuccessMessage, showWelcome, }?: AuthScreenProps): React.JSX.Element;
58
102
  export default AuthScreen;
59
103
  //# sourceMappingURL=AuthScreen.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"AuthScreen.d.ts","sourceRoot":"","sources":["../../../src/screens/auth/AuthScreen.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA4D,MAAM,OAAO,CAAC;AAGjF,OAAO,QASN,MAAM,yBAAyB,CAAC;AAqCjC,KAAK,iBAAiB,GAAG,KAAK,CAAC,cAAc,CAAC,OAAO,QAAQ,CAAC,IAAI,CAAC,CAAC;AAEpE;;;;;;GAMG;AACH,MAAM,WAAW,kBAAkB;IACjC,MAAM,CAAC,EAAE,iBAAiB,CAAC,QAAQ,CAAC,CAAC;IACrC,QAAQ,CAAC,EAAE,iBAAiB,CAAC,UAAU,CAAC,CAAC;IACzC,OAAO,CAAC,EAAE,iBAAiB,CAAC,SAAS,CAAC,CAAC;CACxC;AAaD,MAAM,WAAW,eAAe;IAC9B,mCAAmC;IACnC,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,yCAAyC;IACzC,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,kEAAkE;IAClE,UAAU,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC7B;;;OAGG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC;;;OAGG;IACH,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE;QAAE,OAAO,EAAE,OAAO,CAAC;QAAC,OAAO,EAAE,MAAM,IAAI,CAAA;KAAE,KAAK,KAAK,CAAC,SAAS,CAAC;IACjF,yDAAyD;IACzD,UAAU,CAAC,EAAE,kBAAkB,CAAC;IAChC;;;;OAIG;IACH,UAAU,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC7B,sEAAsE;IACtE,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,EACzB,aAA0B,EAC1B,mBAA2C,EAC3C,UAAU,EACV,cAAsB,EACtB,wBAAuD,EACvD,kBAAwC,EACxC,wBAAsJ,EACtJ,QAAQ,EACR,UAAU,EACV,UAAU,EACV,eAA+B,GAChC,GAAE,eAAoB,qBA4yBtB;AAED,eAAe,UAAU,CAAC"}
1
+ {"version":3,"file":"AuthScreen.d.ts","sourceRoot":"","sources":["../../../src/screens/auth/AuthScreen.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA4D,MAAM,OAAO,CAAC;AAGjF,OAAO,QASN,MAAM,yBAAyB,CAAC;AAsCjC,KAAK,iBAAiB,GAAG,KAAK,CAAC,cAAc,CAAC,OAAO,QAAQ,CAAC,IAAI,CAAC,CAAC;AAEpE;;;;;;GAMG;AACH,MAAM,WAAW,kBAAkB;IACjC,MAAM,CAAC,EAAE,iBAAiB,CAAC,QAAQ,CAAC,CAAC;IACrC,QAAQ,CAAC,EAAE,iBAAiB,CAAC,UAAU,CAAC,CAAC;IACzC,OAAO,CAAC,EAAE,iBAAiB,CAAC,SAAS,CAAC,CAAC;CACxC;AAaD,MAAM,WAAW,eAAe;IAC9B,mCAAmC;IACnC,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,yCAAyC;IACzC,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,kEAAkE;IAClE,UAAU,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC7B;;;OAGG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC;;;OAGG;IACH,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE;QAAE,OAAO,EAAE,OAAO,CAAC;QAAC,OAAO,EAAE,MAAM,IAAI,CAAA;KAAE,KAAK,KAAK,CAAC,SAAS,CAAC;IACjF,yDAAyD;IACzD,UAAU,CAAC,EAAE,kBAAkB,CAAC;IAChC;;;;OAIG;IACH,UAAU,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC7B,sEAAsE;IACtE,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB;;;;;;;OAOG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB;;;OAGG;IACH,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B;;;;;;;;;;OAUG;IACH,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE;QACjB,KAAK,EAAE,MAAM,CAAC;QACd,QAAQ,EAAE,MAAM,CAAC;QACjB,QAAQ,EAAE,MAAM,CAAC;QACjB,WAAW,EAAE,MAAM,CAAC;QACpB,UAAU,CAAC,EAAE,MAAM,CAAC;KACrB,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACpB,2CAA2C;IAC3C,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B;;;;;;;;OAQG;IACH,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,EACzB,aAA0B,EAC1B,mBAA2C,EAC3C,UAAU,EACV,cAAsB,EACtB,wBAAuD,EACvD,kBAAwC,EACxC,wBAAsJ,EACtJ,QAAQ,EACR,UAAU,EACV,UAAU,EACV,eAA+B,EAC/B,aAAoB,EACpB,iBAAyB,EACzB,QAAQ,EACR,oBAA+F,EAC/F,WAAkB,GACnB,GAAE,eAAoB,qBA03BtB;AAED,eAAe,UAAU,CAAC"}
@@ -2,6 +2,7 @@ import React, { useCallback, useEffect, useMemo, useRef, useState } from "react"
2
2
  import { KeyboardAvoidingView, Platform, ScrollView, View } from "react-native";
3
3
  import { SafeAreaView } from "react-native-safe-area-context";
4
4
  import Animated, { Easing, FadeInDown, FadeOutUp, LinearTransition, runOnJS, useAnimatedStyle, useSharedValue, withTiming, } from "react-native-reanimated";
5
+ import { withClickTracking } from "../../services/telemetry";
5
6
  import { StatusBar } from "expo-status-bar";
6
7
  import { Ionicons } from "@expo/vector-icons";
7
8
  import { useColorScheme } from "nativewind";
@@ -45,21 +46,23 @@ const STAGE_IN_MS = 360;
45
46
  * are themed popups and a connection-settings dialog can be folded in. Preserves
46
47
  * the passkey ceremony + non-PRF unlock and the HIBP/strength checks.
47
48
  */
48
- export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "Enter your password", socialAuth, passkeyEnabled = false, passkeyUnlockPlaceholder = "Enter your master password", passkeyUnlockTitle = "Unlock your vault", passkeyUnlockDescription = "Signed in successfully. This passkey can't unlock the vault on its own — enter your master password to decrypt your data.", settings, transition, decoration, welcomeCtaLabel = "Get Started", } = {}) {
49
+ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "Enter your password", socialAuth, passkeyEnabled = false, passkeyUnlockPlaceholder = "Enter your master password", passkeyUnlockTitle = "Unlock your vault", passkeyUnlockDescription = "Signed in successfully. This passkey can't unlock the vault on its own — enter your master password to decrypt your data.", settings, transition, decoration, welcomeCtaLabel = "Get Started", signUpEnabled = true, requireInviteCode = false, onSignUp, signUpSuccessMessage = "Account created. Check your email to verify the address, then sign in.", showWelcome = true, } = {}) {
49
50
  const { login: authLogin, register: authRegister, loginWithPasskey, unlockWithPassword, } = useAuth();
50
51
  const router = useNavigation();
51
- const { appName, Logo, tagline, routes, termsText, privacyText } = useAppConfig();
52
+ const { appName, Logo, tagline, routes, termsText, privacyText, logoIsWordmark, logoWidth, } = useAppConfig();
52
53
  const { colorScheme } = useColorScheme();
53
54
  const isDark = colorScheme === "dark";
54
55
  const t = useMemo(() => ({ ...DEFAULT_TRANSITION, ...transition }), [transition]);
55
56
  const [mode, setMode] = useState("signin");
56
- const [stage, setStage] = useState("welcome");
57
+ const [inviteCode, setInviteCode] = useState("");
58
+ const [signedUp, setSignedUp] = useState(null);
59
+ const [stage, setStage] = useState(showWelcome ? "welcome" : "auth");
57
60
  const isSignup = mode === "signup";
58
61
  // Stage morph: `stage` is the target; `displayStage` is what's rendered.
59
62
  // On a stage change we fade/scale the content out, swap displayStage at zero
60
63
  // opacity (so the centered-welcome → top-anchored-form layout change is
61
64
  // invisible — no teleport, no overlap of the two states), then fade in.
62
- const [displayStage, setDisplayStage] = useState("welcome");
65
+ const [displayStage, setDisplayStage] = useState(showWelcome ? "welcome" : "auth");
63
66
  // Fade-through: `stage` is the target, `displayStage` is what's rendered. On
64
67
  // a change the content fades/scales out, swaps at zero opacity (so the
65
68
  // position change between stages is never seen), then fades back in.
@@ -153,6 +156,9 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
153
156
  else if (password !== confirmPassword) {
154
157
  next.confirmPassword = "Passwords do not match";
155
158
  }
159
+ if (requireInviteCode && !inviteCode.trim()) {
160
+ next.inviteCode = "An invite code is required to create an account here";
161
+ }
156
162
  }
157
163
  return next;
158
164
  };
@@ -220,7 +226,26 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
220
226
  }
221
227
  try {
222
228
  const username = (email.split("@")[0] || "user").replace(/[^a-zA-Z0-9_]/g, "_").toLowerCase();
223
- await authRegister(email.trim().toLowerCase(), username, password, displayName.trim());
229
+ if (onSignUp) {
230
+ // The host owns the contract. It may leave the user signed out (the
231
+ // IdP emails a verification link), so show the notice rather than
232
+ // assuming a session now exists.
233
+ await onSignUp({
234
+ email: email.trim().toLowerCase(),
235
+ username,
236
+ password,
237
+ displayName: displayName.trim(),
238
+ inviteCode: requireInviteCode ? inviteCode.trim() : undefined,
239
+ });
240
+ setSignedUp(signUpSuccessMessage);
241
+ setPassword("");
242
+ setConfirmPassword("");
243
+ setInviteCode("");
244
+ setMode("signin");
245
+ }
246
+ else {
247
+ await authRegister(email.trim().toLowerCase(), username, password, displayName.trim());
248
+ }
224
249
  await Haptics.notificationAsync(Haptics.NotificationFeedbackType.Success);
225
250
  }
226
251
  catch (error) {
@@ -370,7 +395,7 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
370
395
  (thumb-reachable) so users don't stretch to the corner. */}
371
396
  <View className="mt-4 h-10 flex-row items-center justify-between">
372
397
  <View />
373
- {settings ? (<IconButton variant="ghost" size="sm" onPress={() => setSettingsOpen(true)} accessibilityLabel="Connection settings" accessibilityRole="button">
398
+ {settings ? (<IconButton variant="ghost" size="sm" telemetryId="auth.auth.settings_open" onPress={() => setSettingsOpen(true)} accessibilityLabel="Connection settings" accessibilityRole="button">
374
399
  <Ionicons name="settings-outline" size={22} color={isDark ? "#A3A3A3" : "#737373"}/>
375
400
  </IconButton>) : (<View />)}
376
401
  </View>
@@ -385,10 +410,14 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
385
410
  morphStyle,
386
411
  ]}>
387
412
  <View className="mb-6 items-center">
388
- <View className="flex-row items-center">
389
- <Logo width={72} height={72} style={{ marginRight: -2 }}/>
390
- <Heading className="text-4xl">{appName}</Heading>
391
- </View>
413
+ {logoIsWordmark ? (
414
+ // The mark carries the name; height is left to the
415
+ // component so a wide wordmark keeps its aspect ratio, and
416
+ // the ink colour comes from the already-resolved theme.
417
+ <Logo width={logoWidth ?? 160} color={isDark ? "#FFFFFF" : "#000000"}/>) : (<View className="flex-row items-center">
418
+ <Logo width={72} height={72} style={{ marginRight: -2 }}/>
419
+ <Heading className="text-4xl">{appName}</Heading>
420
+ </View>)}
392
421
  {tagline ? (<Text className="mt-1 font-mono text-base text-muted-foreground">
393
422
  {tagline}
394
423
  </Text>) : null}
@@ -397,7 +426,7 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
397
426
  {onWelcome ? (<View style={{ width: "100%", alignItems: "center" }}>
398
427
  {decoration ? (<View className="mb-6 w-full items-center">{decoration}</View>) : null}
399
428
  <View style={{ width: "100%", maxWidth: 320 }}>
400
- <Button className="w-full" onPress={() => setStage("auth")} accessibilityLabel={welcomeCtaLabel} accessibilityRole="button" testID="welcome-get-started">
429
+ <Button className="w-full" telemetryId="auth.auth.stage" onPress={() => setStage("auth")} accessibilityLabel={welcomeCtaLabel} accessibilityRole="button" testID="welcome-get-started">
401
430
  {welcomeCtaLabel}
402
431
  </Button>
403
432
  </View>
@@ -426,23 +455,24 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
426
455
  </>)}
427
456
  </CardContent>
428
457
  <CardFooter className="flex-col gap-3 border-t-0 pt-0">
429
- {forgotSent ? (<Button className="w-full" onPress={goAuth} accessibilityLabel="Back to sign in">
458
+ {forgotSent ? (<Button className="w-full" telemetryId="auth.auth.go_auth" onPress={goAuth} accessibilityLabel="Back to sign in">
430
459
  Back to Sign In
431
460
  </Button>) : (<>
432
- <Button className="w-full" onPress={handleForgot} isLoading={isLoading} accessibilityLabel="Send reset link">
461
+ <Button className="w-full" telemetryId="auth.auth.forgot" onPress={handleForgot} isLoading={isLoading} accessibilityLabel="Send reset link">
433
462
  Send reset link
434
463
  </Button>
435
- <Text className="mt-1 text-center font-mono text-sm text-muted-foreground" onPress={goAuth} accessibilityRole="button" accessibilityLabel="Back to sign in">
464
+ <Text className="mt-1 text-center font-mono text-sm text-muted-foreground" onPress={withClickTracking("auth.auth.go_auth_2", goAuth)} accessibilityRole="button" accessibilityLabel="Back to sign in">
436
465
  ← Back
437
466
  </Text>
438
467
  </>)}
439
468
  </CardFooter>
440
469
  </>) : (<>
441
470
  <CardHeader className="gap-4">
442
- <SegmentedToggle value={mode} onChange={switchMode} options={[
443
- { key: "signin", label: "Sign In" },
444
- { key: "signup", label: "Sign Up" },
445
- ]}/>
471
+ {signUpEnabled ? (<SegmentedToggle value={mode} onChange={switchMode} options={[
472
+ { key: "signin", label: "Sign In" },
473
+ { key: "signup", label: "Sign Up" },
474
+ ]}/>) : null}
475
+ {signedUp ? (<MutedText className="text-sm leading-5">{signedUp}</MutedText>) : null}
446
476
  <CardTitle>
447
477
  {isSignup ? "Create your account" : `Sign in to ${appName}`}
448
478
  </CardTitle>
@@ -452,7 +482,7 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
452
482
  <Animated.View layout={t.layout}>
453
483
  <CardContent className="gap-3 pb-3">
454
484
  {!isSignup && passkeyEnabled ? (<Animated.View entering={t.entering} exiting={t.exiting} layout={t.layout}>
455
- <Button variant="outline" className="w-full" onPress={handlePasskeyLogin} isLoading={passkeyStep === "passkey-loading"} accessibilityLabel="Sign in with passkey" accessibilityRole="button" testID="login-passkey-button">
485
+ <Button variant="outline" className="w-full" telemetryId="auth.auth.passkey_login" onPress={handlePasskeyLogin} isLoading={passkeyStep === "passkey-loading"} accessibilityLabel="Sign in with passkey" accessibilityRole="button" testID="login-passkey-button">
456
486
  <View className="flex-row items-center justify-center">
457
487
  <Ionicons name="key-outline" size={20} color={isDark ? "#FFFFFF" : "#000000"} className="mr-2"/>
458
488
  <Text className="text-base font-medium">
@@ -503,12 +533,21 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
503
533
  clearField("confirmPassword");
504
534
  }} placeholder="Re-enter your password" autoComplete="password-new" returnKeyType="done" onSubmitEditing={handleSubmit} invalid={!!errors.confirmPassword} accessibilityLabel="Confirm password" testID="auth-confirm-password-input"/>
505
535
  </ShakeField>
536
+ {requireInviteCode ? (<View className="mt-3">
537
+ <ShakeField shake={confirmShake} label="Invite code">
538
+ <Input value={inviteCode} onChangeText={(text) => {
539
+ setInviteCode(text);
540
+ clearField("inviteCode");
541
+ }} placeholder="Paste your invite code" autoCapitalize="none" autoCorrect={false} returnKeyType="done" onSubmitEditing={handleSubmit} invalid={!!errors.inviteCode} accessibilityLabel="Invite code" testID="auth-invite-code-input"/>
542
+ </ShakeField>
543
+ <FormError message={errors.inviteCode}/>
544
+ </View>) : null}
506
545
  </Animated.View>) : (<Animated.View key="forgot" entering={t.entering} exiting={t.exiting} layout={t.layout} className="items-end">
507
- <Text className="font-mono text-sm underline" onPress={() => {
546
+ <Text className="font-mono text-sm underline" onPress={withClickTracking("auth.auth.stage_2", () => {
508
547
  setStage("forgot");
509
548
  setForgotSent(false);
510
549
  setErrors({});
511
- }} accessibilityRole="link" accessibilityLabel="Forgot password">
550
+ })} accessibilityRole="link" accessibilityLabel="Forgot password">
512
551
  Forgot password?
513
552
  </Text>
514
553
  </Animated.View>)}
@@ -517,7 +556,7 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
517
556
  <CardFooter className="flex-col gap-3 border-t-0 pt-0">
518
557
  <FormError message={firstError}/>
519
558
 
520
- <Button className="w-full" onPress={handleSubmit} isLoading={isLoading} accessibilityLabel={isSignup ? "Create account" : "Sign in"} accessibilityRole="button" testID="auth-submit">
559
+ <Button className="w-full" telemetryId="auth.auth.submit" onPress={handleSubmit} isLoading={isLoading} accessibilityLabel={isSignup ? "Create account" : "Sign in"} accessibilityRole="button" testID="auth-submit">
521
560
  {isSignup ? "Create Account" : "Sign In"}
522
561
  </Button>
523
562
 
@@ -527,8 +566,11 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
527
566
  </>) : null}
528
567
 
529
568
  {/* In-card back — thumb-reachable, so users don't
530
- have to stretch to the top-left corner arrow. */}
531
- <Text className="mt-1 text-center font-mono text-sm text-muted-foreground" onPress={() => setStage("welcome")} accessibilityRole="button" accessibilityLabel="Back">
569
+ have to stretch to the top-left corner arrow.
570
+ Hidden when there is no welcome stage behind it. */}
571
+ <Text className={showWelcome
572
+ ? "mt-1 text-center font-mono text-sm text-muted-foreground"
573
+ : "hidden"} onPress={withClickTracking("auth.auth.stage_3", () => setStage("welcome"))} accessibilityRole="button" accessibilityLabel="Back">
532
574
  ← Back
533
575
  </Text>
534
576
  </CardFooter>
@@ -542,11 +584,11 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
542
584
  <View className="mb-6 mt-4">
543
585
  <MutedText className="text-center text-xs leading-5">
544
586
  By continuing, you agree to our{" "}
545
- <Text className="text-xs text-foreground underline" onPress={() => setLegal("terms")} accessibilityRole="link" accessibilityLabel="Terms of Service">
587
+ <Text className="text-xs text-foreground underline" onPress={withClickTracking("auth.auth.legal", () => setLegal("terms"))} accessibilityRole="link" accessibilityLabel="Terms of Service">
546
588
  Terms of Service
547
589
  </Text>{" "}
548
590
  and{" "}
549
- <Text className="text-xs text-foreground underline" onPress={() => setLegal("privacy")} accessibilityRole="link" accessibilityLabel="Privacy Policy">
591
+ <Text className="text-xs text-foreground underline" onPress={withClickTracking("auth.auth.legal_2", () => setLegal("privacy"))} accessibilityRole="link" accessibilityLabel="Privacy Policy">
550
592
  Privacy Policy
551
593
  </Text>
552
594
  </MutedText>
@@ -576,7 +618,7 @@ export function AuthScreen({ passwordLabel = "Password", passwordPlaceholder = "
576
618
  }} placeholder={passkeyUnlockPlaceholder} error={unlockError} autoComplete="password" returnKeyType="done" onSubmitEditing={handleUnlockAfterPasskey} accessibilityLabel="Master password" testID="login-passkey-unlock-input"/>
577
619
  </View>
578
620
  <DialogFooter style={{ justifyContent: "center" }}>
579
- <DialogButton variant="primary" onPress={isLoading ? () => { } : handleUnlockAfterPasskey} accessibilityLabel="Unlock" accessibilityRole="button">
621
+ <DialogButton variant="primary" onPress={withClickTracking("auth.auth.action", isLoading ? () => { } : handleUnlockAfterPasskey)} accessibilityLabel="Unlock" accessibilityRole="button">
580
622
  {isLoading ? "Unlocking…" : "Unlock"}
581
623
  </DialogButton>
582
624
  </DialogFooter>