@better-auth-ui/heroui 1.6.2 → 1.6.4

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 (213) hide show
  1. package/dist/components/auth/additional-field.d.ts +4 -0
  2. package/dist/components/auth/additional-field.js +270 -0
  3. package/dist/components/auth/auth-provider.d.ts +4 -6
  4. package/dist/components/auth/auth-provider.js +12 -11
  5. package/dist/components/auth/auth.d.ts +1 -1
  6. package/dist/components/auth/auth.js +54 -28
  7. package/dist/components/{settings/security → auth/delete-user}/danger-zone.d.ts +3 -4
  8. package/dist/components/{settings/security → auth/delete-user}/danger-zone.js +1 -1
  9. package/dist/components/{settings/security → auth/delete-user}/delete-user.d.ts +1 -1
  10. package/dist/components/auth/delete-user/delete-user.js +95 -0
  11. package/dist/components/{email → auth/email}/email-changed-email.d.ts +2 -2
  12. package/dist/components/{email → auth/email}/email-changed-email.js +7 -7
  13. package/dist/components/{email → auth/email}/email-verification-email.d.ts +2 -2
  14. package/dist/components/{email → auth/email}/email-verification-email.js +7 -7
  15. package/dist/components/auth/email/magic-link-email.d.ts +3 -0
  16. package/dist/components/{email → auth/email}/magic-link-email.js +7 -7
  17. package/dist/components/auth/email/new-device-email.d.ts +3 -0
  18. package/dist/components/{email → auth/email}/new-device-email.js +7 -7
  19. package/dist/components/auth/email/otp-email.d.ts +3 -0
  20. package/dist/components/{email → auth/email}/otp-email.js +6 -6
  21. package/dist/components/{email → auth/email}/password-changed-email.d.ts +2 -2
  22. package/dist/components/{email → auth/email}/password-changed-email.js +7 -7
  23. package/dist/components/{email → auth/email}/reset-password-email.d.ts +2 -2
  24. package/dist/components/{email → auth/email}/reset-password-email.js +7 -7
  25. package/dist/components/auth/error-toaster.d.ts +1 -0
  26. package/dist/components/auth/error-toaster.js +17 -0
  27. package/dist/components/auth/forgot-password.d.ts +2 -2
  28. package/dist/components/auth/forgot-password.js +42 -42
  29. package/dist/components/auth/magic-link/magic-link-button.d.ts +11 -0
  30. package/dist/components/auth/magic-link/magic-link-button.js +20 -0
  31. package/dist/components/auth/magic-link/magic-link.d.ts +16 -0
  32. package/dist/components/auth/magic-link/magic-link.js +87 -0
  33. package/dist/components/{settings/account → auth/multi-session}/manage-account.d.ts +2 -6
  34. package/dist/components/auth/multi-session/manage-account.js +49 -0
  35. package/dist/components/{settings/account → auth/multi-session}/manage-accounts.d.ts +1 -1
  36. package/dist/components/auth/multi-session/manage-accounts.js +34 -0
  37. package/dist/components/{user/switch-account-menu.d.ts → auth/multi-session/switch-account-submenu-content.d.ts} +3 -3
  38. package/dist/components/auth/multi-session/switch-account-submenu-content.js +29 -0
  39. package/dist/components/{user/switch-account-item.d.ts → auth/multi-session/switch-account-submenu-item.d.ts} +2 -2
  40. package/dist/components/auth/multi-session/switch-account-submenu-item.js +20 -0
  41. package/dist/components/auth/multi-session/switch-account-submenu.d.ts +13 -0
  42. package/dist/components/auth/multi-session/switch-account-submenu.js +24 -0
  43. package/dist/components/auth/passkey/passkey-button.d.ts +6 -0
  44. package/dist/components/auth/passkey/passkey-button.js +24 -0
  45. package/dist/components/auth/passkey/passkey.js +45 -0
  46. package/dist/components/{settings/security → auth/passkey}/passkeys.d.ts +1 -1
  47. package/dist/components/auth/passkey/passkeys.js +106 -0
  48. package/dist/components/auth/provider-button.d.ts +13 -0
  49. package/dist/components/auth/provider-button.js +25 -0
  50. package/dist/components/auth/provider-buttons.d.ts +3 -10
  51. package/dist/components/auth/provider-buttons.js +14 -22
  52. package/dist/components/auth/reset-password.d.ts +1 -1
  53. package/dist/components/auth/reset-password.js +110 -110
  54. package/dist/components/{settings → auth/settings}/account/account-settings.d.ts +5 -2
  55. package/dist/components/auth/settings/account/account-settings.js +20 -0
  56. package/dist/components/auth/settings/account/change-avatar.js +89 -0
  57. package/dist/components/{settings → auth/settings}/account/change-email.d.ts +1 -1
  58. package/dist/components/{settings → auth/settings}/account/change-email.js +17 -20
  59. package/dist/components/{settings → auth/settings}/account/user-profile.d.ts +3 -4
  60. package/dist/components/auth/settings/account/user-profile.js +86 -0
  61. package/dist/components/auth/settings/security/active-session.js +59 -0
  62. package/dist/components/{settings → auth/settings}/security/active-sessions.d.ts +1 -1
  63. package/dist/components/auth/settings/security/active-sessions.js +34 -0
  64. package/dist/components/{settings → auth/settings}/security/change-password.d.ts +1 -1
  65. package/dist/components/auth/settings/security/change-password.js +189 -0
  66. package/dist/components/auth/settings/security/linked-account.js +56 -0
  67. package/dist/components/{settings → auth/settings}/security/linked-accounts.d.ts +1 -1
  68. package/dist/components/auth/settings/security/linked-accounts.js +45 -0
  69. package/dist/components/{settings → auth/settings}/security/security-settings.d.ts +1 -1
  70. package/dist/components/auth/settings/security/security-settings.js +22 -0
  71. package/dist/components/auth/settings/settings.js +45 -0
  72. package/dist/components/auth/sign-in.d.ts +1 -1
  73. package/dist/components/auth/sign-in.js +64 -100
  74. package/dist/components/auth/sign-out.js +11 -11
  75. package/dist/components/auth/sign-up.d.ts +1 -1
  76. package/dist/components/auth/sign-up.js +123 -157
  77. package/dist/components/{settings/account → auth/theme}/appearance.d.ts +3 -6
  78. package/dist/components/auth/theme/appearance.js +72 -0
  79. package/dist/components/auth/theme/theme-toggle-item.d.ts +5 -0
  80. package/dist/components/auth/theme/theme-toggle-item.js +58 -0
  81. package/dist/components/auth/user/user-avatar.js +29 -0
  82. package/dist/components/{user → auth/user}/user-button.d.ts +2 -6
  83. package/dist/components/auth/user/user-button.js +55 -0
  84. package/dist/components/auth/user/user-view.js +37 -0
  85. package/dist/components/auth/username/sign-in-username.d.ts +14 -0
  86. package/dist/components/auth/username/sign-in-username.js +142 -0
  87. package/dist/components/auth/username/username-field.d.ts +8 -0
  88. package/dist/components/auth/username/username-field.js +51 -0
  89. package/dist/email.d.ts +7 -0
  90. package/dist/email.js +9 -0
  91. package/dist/index.d.ts +13 -27
  92. package/dist/index.js +22 -36
  93. package/dist/lib/auth/auth-plugin.d.ts +44 -0
  94. package/dist/lib/auth/delete-user-plugin.d.ts +17 -0
  95. package/dist/lib/auth/delete-user-plugin.js +10 -0
  96. package/dist/lib/auth/magic-link-plugin.d.ts +31 -0
  97. package/dist/lib/auth/magic-link-plugin.js +13 -0
  98. package/dist/lib/auth/multi-session-plugin.d.ts +18 -0
  99. package/dist/lib/auth/multi-session-plugin.js +12 -0
  100. package/dist/lib/auth/passkey-plugin.d.ts +20 -0
  101. package/dist/lib/auth/passkey-plugin.js +12 -0
  102. package/dist/lib/auth/theme-plugin.d.ts +68 -0
  103. package/dist/lib/auth/theme-plugin.js +23 -0
  104. package/dist/lib/auth/username-plugin.d.ts +63 -0
  105. package/dist/lib/auth/username-plugin.js +18 -0
  106. package/dist/plugins.d.ts +20 -0
  107. package/dist/plugins.js +21 -0
  108. package/package.json +22 -22
  109. package/src/components/auth/additional-field.tsx +554 -0
  110. package/src/components/auth/auth-provider.tsx +8 -5
  111. package/src/components/auth/auth.tsx +100 -36
  112. package/src/components/{settings/security → auth/delete-user}/danger-zone.tsx +3 -10
  113. package/src/components/{settings/security → auth/delete-user}/delete-user.tsx +31 -24
  114. package/src/components/{email → auth/email}/email-changed-email.tsx +2 -2
  115. package/src/components/{email → auth/email}/email-verification-email.tsx +2 -2
  116. package/src/components/{email → auth/email}/magic-link-email.tsx +2 -2
  117. package/src/components/{email → auth/email}/new-device-email.tsx +2 -2
  118. package/src/components/{email → auth/email}/otp-email.tsx +2 -2
  119. package/src/components/{email → auth/email}/password-changed-email.tsx +2 -2
  120. package/src/components/{email → auth/email}/reset-password-email.tsx +2 -2
  121. package/src/components/auth/error-toaster.tsx +25 -0
  122. package/src/components/auth/forgot-password.tsx +15 -13
  123. package/src/components/auth/magic-link/magic-link-button.tsx +61 -0
  124. package/src/components/auth/{magic-link.tsx → magic-link/magic-link.tsx} +52 -57
  125. package/src/components/{settings/account → auth/multi-session}/manage-account.tsx +15 -15
  126. package/src/components/{settings/account → auth/multi-session}/manage-accounts.tsx +16 -12
  127. package/src/components/{user/switch-account-menu.tsx → auth/multi-session/switch-account-submenu-content.tsx} +19 -17
  128. package/src/components/{user/switch-account-item.tsx → auth/multi-session/switch-account-submenu-item.tsx} +18 -8
  129. package/src/components/auth/multi-session/switch-account-submenu.tsx +50 -0
  130. package/src/components/auth/passkey/passkey-button.tsx +56 -0
  131. package/src/components/{settings/security → auth/passkey}/passkey.tsx +21 -9
  132. package/src/components/auth/passkey/passkeys.tsx +196 -0
  133. package/src/components/auth/provider-button.tsx +65 -0
  134. package/src/components/auth/provider-buttons.tsx +23 -45
  135. package/src/components/auth/reset-password.tsx +14 -9
  136. package/src/components/{settings → auth/settings}/account/account-settings.tsx +15 -13
  137. package/src/components/{settings → auth/settings}/account/change-avatar.tsx +4 -5
  138. package/src/components/{settings → auth/settings}/account/change-email.tsx +5 -6
  139. package/src/components/auth/settings/account/user-profile.tsx +171 -0
  140. package/src/components/{settings → auth/settings}/security/active-session.tsx +8 -6
  141. package/src/components/{settings → auth/settings}/security/active-sessions.tsx +5 -10
  142. package/src/components/{settings → auth/settings}/security/change-password.tsx +22 -14
  143. package/src/components/{settings → auth/settings}/security/linked-account.tsx +10 -16
  144. package/src/components/{settings → auth/settings}/security/linked-accounts.tsx +4 -9
  145. package/src/components/{settings → auth/settings}/security/security-settings.tsx +7 -6
  146. package/src/components/{settings → auth/settings}/settings.tsx +2 -2
  147. package/src/components/auth/sign-in.tsx +39 -80
  148. package/src/components/auth/sign-out.tsx +2 -2
  149. package/src/components/auth/sign-up.tsx +110 -147
  150. package/src/components/{settings/account → auth/theme}/appearance.tsx +18 -25
  151. package/src/components/auth/theme/theme-toggle-item.tsx +110 -0
  152. package/src/components/{user → auth/user}/user-avatar.tsx +12 -4
  153. package/src/components/{user → auth/user}/user-button.tsx +15 -88
  154. package/src/components/{user → auth/user}/user-view.tsx +12 -4
  155. package/src/components/auth/username/sign-in-username.tsx +283 -0
  156. package/src/components/auth/username/username-field.tsx +122 -0
  157. package/src/email.ts +9 -0
  158. package/src/index.tsx +13 -27
  159. package/src/lib/auth/auth-plugin.ts +67 -0
  160. package/src/lib/auth/delete-user-plugin.ts +15 -0
  161. package/src/lib/auth/magic-link-plugin.ts +26 -0
  162. package/src/lib/auth/multi-session-plugin.ts +17 -0
  163. package/src/lib/auth/passkey-plugin.ts +17 -0
  164. package/src/lib/auth/theme-plugin.ts +86 -0
  165. package/src/lib/auth/username-plugin.tsx +30 -0
  166. package/src/plugins.ts +23 -0
  167. package/dist/components/auth/magic-link-button.d.ts +0 -13
  168. package/dist/components/auth/magic-link-button.js +0 -16
  169. package/dist/components/auth/magic-link.d.ts +0 -17
  170. package/dist/components/auth/magic-link.js +0 -111
  171. package/dist/components/auth/passkey-button.d.ts +0 -4
  172. package/dist/components/auth/passkey-button.js +0 -24
  173. package/dist/components/email/magic-link-email.d.ts +0 -3
  174. package/dist/components/email/new-device-email.d.ts +0 -3
  175. package/dist/components/email/otp-email.d.ts +0 -3
  176. package/dist/components/settings/account/account-settings.js +0 -23
  177. package/dist/components/settings/account/appearance.js +0 -71
  178. package/dist/components/settings/account/change-avatar.js +0 -89
  179. package/dist/components/settings/account/manage-account.js +0 -51
  180. package/dist/components/settings/account/manage-accounts.js +0 -33
  181. package/dist/components/settings/account/user-profile.js +0 -106
  182. package/dist/components/settings/security/active-session.js +0 -62
  183. package/dist/components/settings/security/active-sessions.js +0 -34
  184. package/dist/components/settings/security/change-password.js +0 -192
  185. package/dist/components/settings/security/delete-user.js +0 -97
  186. package/dist/components/settings/security/linked-account.js +0 -62
  187. package/dist/components/settings/security/linked-accounts.js +0 -45
  188. package/dist/components/settings/security/passkey.js +0 -43
  189. package/dist/components/settings/security/passkeys.js +0 -53
  190. package/dist/components/settings/security/security-settings.js +0 -25
  191. package/dist/components/settings/settings.js +0 -45
  192. package/dist/components/user/switch-account-item.js +0 -20
  193. package/dist/components/user/switch-account-menu.js +0 -28
  194. package/dist/components/user/user-avatar.js +0 -29
  195. package/dist/components/user/user-button.js +0 -91
  196. package/dist/components/user/user-view.js +0 -37
  197. package/dist/core.d.ts +0 -1
  198. package/dist/core.js +0 -1
  199. package/dist/react-exports.d.ts +0 -1
  200. package/dist/react-exports.js +0 -1
  201. package/src/components/auth/magic-link-button.tsx +0 -43
  202. package/src/components/auth/passkey-button.tsx +0 -36
  203. package/src/components/settings/account/user-profile.tsx +0 -218
  204. package/src/components/settings/security/passkeys.tsx +0 -104
  205. package/src/core.ts +0 -1
  206. package/src/react-exports.ts +0 -1
  207. /package/dist/components/{settings/security → auth/passkey}/passkey.d.ts +0 -0
  208. /package/dist/components/{settings → auth/settings}/account/change-avatar.d.ts +0 -0
  209. /package/dist/components/{settings → auth/settings}/security/active-session.d.ts +0 -0
  210. /package/dist/components/{settings → auth/settings}/security/linked-account.d.ts +0 -0
  211. /package/dist/components/{settings → auth/settings}/settings.d.ts +0 -0
  212. /package/dist/components/{user → auth/user}/user-avatar.d.ts +0 -0
  213. /package/dist/components/{user → auth/user}/user-view.d.ts +0 -0
@@ -0,0 +1,89 @@
1
+ import { UserAvatar as e } from "../../user/user-avatar.js";
2
+ import { fileToBase64 as t } from "@better-auth-ui/core";
3
+ import { useAuth as n, useSession as r, useUpdateUser as i } from "@better-auth-ui/react";
4
+ import { CloudArrowUpIn as a, TrashBin as o } from "@gravity-ui/icons";
5
+ import { Button as s, Dropdown as c, Label as l, Spinner as u, cn as d, toast as f } from "@heroui/react";
6
+ import { useRef as p, useState as m } from "react";
7
+ import { jsx as h, jsxs as g } from "react/jsx-runtime";
8
+ //#region src/components/auth/settings/account/change-avatar.tsx
9
+ function _({ className: _ }) {
10
+ let { authClient: v, localization: y, avatar: b } = n(), { data: x } = r(v), { mutate: S, isPending: C } = i(v), w = p(null), [T, E] = m(!1), [D, O] = m(!1), k = C || T || D;
11
+ async function A(e) {
12
+ let n = e.target.files?.[0];
13
+ if (n) {
14
+ e.target.value = "", E(!0);
15
+ try {
16
+ let e = await b.resize?.(n, b.size, b.extension) || n;
17
+ S({ image: await b.upload?.(e) || await t(e) }, { onSuccess: () => f.success(y.settings.avatarChangedSuccess) });
18
+ } catch (e) {
19
+ e instanceof Error && f.danger(e.message);
20
+ }
21
+ E(!1);
22
+ }
23
+ }
24
+ async function j() {
25
+ let e = x?.user.image;
26
+ S({ image: null }, { onSuccess: async () => {
27
+ if (e) {
28
+ O(!0);
29
+ try {
30
+ await b.delete?.(e);
31
+ } finally {
32
+ O(!1);
33
+ }
34
+ }
35
+ f.success(y.settings.avatarDeletedSuccess);
36
+ } });
37
+ }
38
+ return /* @__PURE__ */ g("div", {
39
+ className: d("flex flex-col gap-1", _),
40
+ children: [
41
+ /* @__PURE__ */ h(l, {
42
+ isDisabled: !x,
43
+ children: y.settings.avatar
44
+ }),
45
+ /* @__PURE__ */ h("input", {
46
+ ref: w,
47
+ type: "file",
48
+ accept: "image/*",
49
+ className: "hidden",
50
+ onChange: A
51
+ }),
52
+ /* @__PURE__ */ g("div", {
53
+ className: "flex items-center gap-4",
54
+ children: [/* @__PURE__ */ h(s, {
55
+ type: "button",
56
+ isIconOnly: !0,
57
+ variant: "ghost",
58
+ className: "p-0 h-auto w-auto rounded-full",
59
+ isDisabled: !x || k,
60
+ onPress: () => w.current?.click(),
61
+ children: /* @__PURE__ */ h(e, {
62
+ size: "lg",
63
+ isPending: k
64
+ })
65
+ }), /* @__PURE__ */ g(c, { children: [/* @__PURE__ */ g(s, {
66
+ isDisabled: !x || k,
67
+ size: "sm",
68
+ variant: "secondary",
69
+ children: [k && /* @__PURE__ */ h(u, { size: "sm" }), y.settings.changeAvatar]
70
+ }), /* @__PURE__ */ h(c.Popover, {
71
+ className: "min-w-fit",
72
+ children: /* @__PURE__ */ g(c.Menu, { children: [/* @__PURE__ */ g(c.Item, {
73
+ textValue: y.settings.uploadAvatar,
74
+ onAction: () => w.current?.click(),
75
+ children: [/* @__PURE__ */ h(a, { className: "text-muted" }), /* @__PURE__ */ h(l, { children: y.settings.uploadAvatar })]
76
+ }), /* @__PURE__ */ g(c.Item, {
77
+ textValue: y.settings.deleteAvatar,
78
+ isDisabled: !x?.user.image,
79
+ onAction: j,
80
+ variant: "danger",
81
+ children: [/* @__PURE__ */ h(o, { className: "text-danger" }), /* @__PURE__ */ h(l, { children: y.settings.deleteAvatar })]
82
+ })] })
83
+ })] })]
84
+ })
85
+ ]
86
+ });
87
+ }
88
+ //#endregion
89
+ export { _ as ChangeAvatar };
@@ -12,4 +12,4 @@ export type ChangeEmailProps = {
12
12
  *
13
13
  * @returns A JSX element rendering the change-email card and form
14
14
  */
15
- export declare function ChangeEmail({ className, variant, ...props }: ChangeEmailProps & CardProps): import("react/jsx-runtime").JSX.Element;
15
+ export declare function ChangeEmail({ className, variant, ...props }: ChangeEmailProps & Omit<CardProps, "children">): import("react/jsx-runtime").JSX.Element;
@@ -1,53 +1,50 @@
1
1
  import { useAuth as e, useChangeEmail as t, useSession as n } from "@better-auth-ui/react";
2
2
  import { Button as r, Card as i, FieldError as a, Fieldset as o, Form as s, Input as c, Label as l, Skeleton as u, Spinner as d, TextField as f, cn as p, toast as m } from "@heroui/react";
3
3
  import { jsx as h, jsxs as g } from "react/jsx-runtime";
4
- //#region src/components/settings/account/change-email.tsx
4
+ //#region src/components/auth/settings/account/change-email.tsx
5
5
  function _({ className: _, variant: v, ...y }) {
6
- let { localization: b, baseURL: x, viewPaths: S } = e(), { data: C } = n(), { mutate: w, isPending: T } = t({
7
- onSuccess: () => m.success(b.settings.changeEmailSuccess),
8
- onError: (e) => m.danger(e.error?.message || e.message)
9
- });
10
- function E(e) {
11
- e.preventDefault(), w({
6
+ let { authClient: b, localization: x, baseURL: S, viewPaths: C } = e(), { data: w } = n(b), { mutate: T, isPending: E } = t(b, { onSuccess: () => m.success(x.settings.changeEmailSuccess) });
7
+ function D(e) {
8
+ e.preventDefault(), T({
12
9
  newEmail: new FormData(e.currentTarget).get("email"),
13
- callbackURL: `${x}/${S.settings.account}`
10
+ callbackURL: `${S}/${C.settings.account}`
14
11
  });
15
12
  }
16
13
  return /* @__PURE__ */ g("div", { children: [/* @__PURE__ */ h("h2", {
17
14
  className: p("text-sm font-semibold mb-3"),
18
- children: b.settings.changeEmail
15
+ children: x.settings.changeEmail
19
16
  }), /* @__PURE__ */ h(i, {
20
17
  className: p("p-4 gap-4", _),
21
18
  variant: v,
22
19
  ...y,
23
20
  children: /* @__PURE__ */ h(i.Content, { children: /* @__PURE__ */ h(s, {
24
- onSubmit: E,
21
+ onSubmit: D,
25
22
  children: /* @__PURE__ */ g(o, {
26
23
  className: "w-full gap-4",
27
24
  children: [/* @__PURE__ */ h(o.Group, { children: /* @__PURE__ */ g(f, {
28
25
  name: "email",
29
26
  type: "email",
30
- defaultValue: C?.user.email,
31
- isDisabled: T || !C,
27
+ defaultValue: w?.user.email,
28
+ isDisabled: E || !w,
32
29
  children: [
33
- /* @__PURE__ */ h(l, { children: b.auth.email }),
34
- C ? /* @__PURE__ */ h(c, {
30
+ /* @__PURE__ */ h(l, { children: x.auth.email }),
31
+ w ? /* @__PURE__ */ h(c, {
35
32
  required: !0,
36
33
  variant: v === "transparent" ? "primary" : "secondary",
37
34
  autoComplete: "email",
38
- placeholder: b.auth.emailPlaceholder
35
+ placeholder: x.auth.emailPlaceholder
39
36
  }) : /* @__PURE__ */ h(u, { className: "h-10 md:h-9 w-full rounded-xl" }),
40
37
  /* @__PURE__ */ h(a, {})
41
38
  ]
42
- }, C?.user.email) }), /* @__PURE__ */ h(o.Actions, { children: /* @__PURE__ */ g(r, {
39
+ }, w?.user.email) }), /* @__PURE__ */ h(o.Actions, { children: /* @__PURE__ */ g(r, {
43
40
  type: "submit",
44
- isPending: T,
45
- isDisabled: !C,
41
+ isPending: E,
42
+ isDisabled: !w,
46
43
  size: "sm",
47
- children: [T && /* @__PURE__ */ h(d, {
44
+ children: [E && /* @__PURE__ */ h(d, {
48
45
  color: "current",
49
46
  size: "sm"
50
- }), b.settings.updateEmail]
47
+ }), x.settings.updateEmail]
51
48
  }) })]
52
49
  })
53
50
  }) })
@@ -4,8 +4,7 @@ export type UserProfileProps = {
4
4
  variant?: CardProps["variant"];
5
5
  };
6
6
  /**
7
- * Render a profile card that lets the authenticated user view and update their display name, username, and avatar.
8
- *
9
- * @returns A JSX element containing the user profile card with avatar upload and editable form fields
7
+ * Render a profile card that lets the authenticated user view and update their
8
+ * display name, avatar, and any plugin- or user-supplied additional fields.
10
9
  */
11
- export declare function UserProfile({ className, variant, ...props }: UserProfileProps & CardProps): import("react/jsx-runtime").JSX.Element;
10
+ export declare function UserProfile({ className, variant, ...props }: UserProfileProps & Omit<CardProps, "children">): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,86 @@
1
+ import { AdditionalField as e } from "../../additional-field.js";
2
+ import { ChangeAvatar as t } from "./change-avatar.js";
3
+ import { parseAdditionalFieldValue as n } from "@better-auth-ui/core";
4
+ import { useAuth as r, useSession as i, useUpdateUser as a } from "@better-auth-ui/react";
5
+ import { Button as o, Card as s, FieldError as c, Form as l, Input as u, Label as d, Skeleton as f, Spinner as p, TextField as m, cn as h, toast as g } from "@heroui/react";
6
+ import { jsx as _, jsxs as v } from "react/jsx-runtime";
7
+ //#region src/components/auth/settings/account/user-profile.tsx
8
+ function y({ className: y, variant: b, ...x }) {
9
+ let { additionalFields: S, authClient: C, localization: w } = r(), { data: T } = i(C), { mutate: E, isPending: D } = a(C, { onSuccess: () => g.success(w.settings.profileUpdatedSuccess) });
10
+ async function O(e) {
11
+ e.preventDefault();
12
+ let t = new FormData(e.currentTarget), r = t.get("name"), i = {};
13
+ for (let e of S ?? []) {
14
+ if (e.profile === !1 || e.readOnly) continue;
15
+ let r = n(e, t.get(e.name));
16
+ if (e.validate) try {
17
+ await e.validate(r);
18
+ } catch (e) {
19
+ g.danger(e instanceof Error ? e.message : String(e));
20
+ return;
21
+ }
22
+ r !== void 0 && (i[e.name] = r);
23
+ }
24
+ E({
25
+ name: r,
26
+ ...i
27
+ });
28
+ }
29
+ return /* @__PURE__ */ v("div", { children: [/* @__PURE__ */ _("h2", {
30
+ className: h("text-sm font-semibold mb-3"),
31
+ children: w.settings.profile
32
+ }), /* @__PURE__ */ _(s, {
33
+ className: h("p-4 gap-4", y),
34
+ variant: b,
35
+ ...x,
36
+ children: /* @__PURE__ */ _(s.Content, { children: /* @__PURE__ */ v(l, {
37
+ onSubmit: O,
38
+ className: "flex flex-col gap-4",
39
+ children: [
40
+ /* @__PURE__ */ _(t, {}),
41
+ /* @__PURE__ */ v(m, {
42
+ name: "name",
43
+ defaultValue: T?.user.name,
44
+ isDisabled: D || !T,
45
+ children: [
46
+ /* @__PURE__ */ _(d, { children: w.auth.name }),
47
+ /* @__PURE__ */ _(u, {
48
+ className: h(!T && "hidden"),
49
+ autoComplete: "name",
50
+ placeholder: w.auth.name,
51
+ variant: b === "transparent" ? "primary" : "secondary"
52
+ }),
53
+ !T && /* @__PURE__ */ _(f, { className: "h-10 md:h-9 w-full rounded-xl" }),
54
+ /* @__PURE__ */ _(c, {})
55
+ ]
56
+ }, T?.user?.name),
57
+ S?.filter((e) => e.profile !== !1).map((t) => {
58
+ if (!T) return t.inputType === "hidden" ? null : /* @__PURE__ */ _(f, { className: "h-10 md:h-9 w-full rounded-xl" }, t.name);
59
+ let n = T.user[t.name], r = `${t.name}:${n instanceof Date ? n.toISOString() : String(n ?? "")}`;
60
+ return /* @__PURE__ */ _(e, {
61
+ name: t.name,
62
+ field: {
63
+ ...t,
64
+ defaultValue: n
65
+ },
66
+ isPending: D,
67
+ variant: b
68
+ }, r);
69
+ }),
70
+ /* @__PURE__ */ v(o, {
71
+ type: "submit",
72
+ isPending: D,
73
+ isDisabled: !T,
74
+ size: "sm",
75
+ className: "self-start mt-1",
76
+ children: [D && /* @__PURE__ */ _(p, {
77
+ color: "current",
78
+ size: "sm"
79
+ }), w.settings.saveChanges]
80
+ })
81
+ ]
82
+ }) })
83
+ })] });
84
+ }
85
+ //#endregion
86
+ export { y as UserProfile };
@@ -0,0 +1,59 @@
1
+ import { useAuth as e, useRevokeSession as t, useSession as n } from "@better-auth-ui/react";
2
+ import { ArrowRightFromSquare as r, Display as i, Smartphone as a, Xmark as o } from "@gravity-ui/icons";
3
+ import { Button as s, Chip as c, Spinner as l, toast as u } from "@heroui/react";
4
+ import { jsx as d, jsxs as f } from "react/jsx-runtime";
5
+ import p from "bowser";
6
+ //#region src/components/auth/settings/security/active-session.tsx
7
+ function m(e) {
8
+ let t = Math.floor((Date.now() - e.getTime()) / 1e3), n = new Intl.RelativeTimeFormat(void 0, { numeric: "auto" });
9
+ for (let [e, r] of [
10
+ ["year", 31536e3],
11
+ ["month", 2592e3],
12
+ ["week", 604800],
13
+ ["day", 86400],
14
+ ["hour", 3600],
15
+ ["minute", 60],
16
+ ["second", 1]
17
+ ]) if (t >= r) return n.format(-Math.floor(t / r), e);
18
+ return n.format(0, "second");
19
+ }
20
+ function h({ activeSession: h }) {
21
+ let { authClient: g, basePaths: _, localization: v, viewPaths: y, navigate: b } = e(), { data: x } = n(g, { refetchOnMount: !1 }), { mutate: S, isPending: C } = t(g, { onSuccess: () => u.success(v.settings.revokeSessionSuccess) }), w = h.token === x?.session.token, T = p.parse(h.userAgent || "");
22
+ return /* @__PURE__ */ f("div", {
23
+ className: "flex items-center gap-3",
24
+ children: [
25
+ /* @__PURE__ */ d("div", {
26
+ className: "flex size-10 shrink-0 items-center justify-center rounded-xl bg-surface-secondary",
27
+ children: T.platform.type === "mobile" || T.platform.type === "tablet" ? /* @__PURE__ */ d(a, { className: "size-4.5" }) : /* @__PURE__ */ d(i, { className: "size-4.5" })
28
+ }),
29
+ /* @__PURE__ */ f("div", {
30
+ className: "flex flex-col min-w-0",
31
+ children: [/* @__PURE__ */ f("span", {
32
+ className: "text-sm font-medium truncate",
33
+ children: [T.browser.name || "Unknown Browser", T.os.name ? `, ${T.os.name}` : ""]
34
+ }), w ? /* @__PURE__ */ d(c, {
35
+ color: "accent",
36
+ size: "sm",
37
+ children: v.settings.currentSession
38
+ }) : h.createdAt && /* @__PURE__ */ d("span", {
39
+ className: "text-xs text-muted capitalize",
40
+ children: m(h.createdAt)
41
+ })]
42
+ }),
43
+ /* @__PURE__ */ f(s, {
44
+ className: "ml-auto shrink-0",
45
+ variant: "outline",
46
+ size: "sm",
47
+ onPress: () => w ? b({ to: `${_.auth}/${y.auth.signOut}` }) : S(h),
48
+ isPending: C,
49
+ "aria-label": w ? v.auth.signOut : v.settings.revokeSession,
50
+ children: [C ? /* @__PURE__ */ d(l, {
51
+ color: "current",
52
+ size: "sm"
53
+ }) : d(w ? r : o, {}), w ? v.auth.signOut : v.settings.revoke]
54
+ })
55
+ ]
56
+ });
57
+ }
58
+ //#endregion
59
+ export { h as ActiveSession };
@@ -11,4 +11,4 @@ export type ActiveSessionsProps = {
11
11
  *
12
12
  * @returns A JSX element containing the sessions card
13
13
  */
14
- export declare function ActiveSessions({ className, variant, ...props }: ActiveSessionsProps & CardProps): import("react/jsx-runtime").JSX.Element;
14
+ export declare function ActiveSessions({ className, variant, ...props }: ActiveSessionsProps & Omit<CardProps, "children">): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,34 @@
1
+ import { ActiveSession as e } from "./active-session.js";
2
+ import { useAuth as t, useListSessions as n, useSession as r } from "@better-auth-ui/react";
3
+ import { Card as i, Skeleton as a, cn as o } from "@heroui/react";
4
+ import { jsx as s, jsxs as c } from "react/jsx-runtime";
5
+ //#region src/components/auth/settings/security/active-sessions.tsx
6
+ function l({ className: a, variant: l, ...d }) {
7
+ let { authClient: f, localization: p } = t(), { data: m } = r(f), { data: h, isPending: g } = n(f), _ = h?.toSorted((e) => e.id === m?.session.id ? -1 : 1);
8
+ return /* @__PURE__ */ c("div", { children: [/* @__PURE__ */ s("h2", {
9
+ className: o("text-sm font-semibold mb-3"),
10
+ children: p.settings.activeSessions
11
+ }), /* @__PURE__ */ s(i, {
12
+ className: o(a),
13
+ variant: l,
14
+ ...d,
15
+ children: /* @__PURE__ */ s(i.Content, {
16
+ className: "gap-0",
17
+ children: g ? /* @__PURE__ */ s(u, {}) : _?.map((t, n) => /* @__PURE__ */ c("div", { children: [n > 0 && /* @__PURE__ */ s("div", { className: "border-b border-dashed -mx-4 md:-mx-6 my-4" }), /* @__PURE__ */ s(e, { activeSession: t })] }, t.id))
18
+ })
19
+ })] });
20
+ }
21
+ function u() {
22
+ return /* @__PURE__ */ s("div", {
23
+ className: "flex items-center justify-between",
24
+ children: /* @__PURE__ */ c("div", {
25
+ className: "flex items-center gap-3",
26
+ children: [/* @__PURE__ */ s(a, { className: "size-10 rounded-xl" }), /* @__PURE__ */ c("div", {
27
+ className: "flex flex-col gap-1",
28
+ children: [/* @__PURE__ */ s(a, { className: "h-4 w-32 rounded-lg" }), /* @__PURE__ */ s(a, { className: "h-3 w-24 rounded-lg" })]
29
+ })]
30
+ })
31
+ });
32
+ }
33
+ //#endregion
34
+ export { l as ActiveSessions };
@@ -12,4 +12,4 @@ export type ChangePasswordProps = {
12
12
  *
13
13
  * @returns A JSX element containing the change-password or set-password card
14
14
  */
15
- export declare function ChangePassword({ className, variant, ...props }: ChangePasswordProps & CardProps): import("react/jsx-runtime").JSX.Element;
15
+ export declare function ChangePassword({ className, variant, ...props }: ChangePasswordProps & Omit<CardProps, "children">): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,189 @@
1
+ import { useAuth as e, useChangePassword as t, useListAccounts as n, useRequestPasswordReset as r, useSession as i } from "@better-auth-ui/react";
2
+ import { Eye as a, EyeSlash as o } from "@gravity-ui/icons";
3
+ import { Button as s, Card as c, FieldError as l, Fieldset as u, Form as d, Input as f, InputGroup as p, Label as m, Skeleton as h, Spinner as g, TextField as _, cn as v, toast as y } from "@heroui/react";
4
+ import { useState as b } from "react";
5
+ import { jsx as x, jsxs as S } from "react/jsx-runtime";
6
+ //#region src/components/auth/settings/security/change-password.tsx
7
+ function C({ className: t, variant: r, ...a }) {
8
+ let { authClient: o, emailAndPassword: s, localization: c } = e(), { data: l } = i(o), { data: u, isPending: d } = n(o), f = u?.some((e) => e.providerId === "credential");
9
+ return !d && !f ? /* @__PURE__ */ x(w, {
10
+ className: t,
11
+ variant: r,
12
+ ...a
13
+ }) : /* @__PURE__ */ x(T, {
14
+ className: t,
15
+ variant: r,
16
+ emailAndPassword: s,
17
+ localization: c,
18
+ session: d ? void 0 : l,
19
+ ...a
20
+ });
21
+ }
22
+ function w({ className: t, variant: n, ...a }) {
23
+ let { authClient: o, localization: l } = e(), { data: u } = i(o), { mutate: d, isPending: f } = r(o, { onSuccess: () => y.success(l.auth.passwordResetEmailSent) }), p = () => {
24
+ u?.user.email && d({ email: u.user.email });
25
+ };
26
+ return /* @__PURE__ */ S("div", { children: [/* @__PURE__ */ x("h2", {
27
+ className: v("text-sm font-semibold mb-3"),
28
+ children: l.settings.changePassword
29
+ }), /* @__PURE__ */ x(c, {
30
+ className: v(t),
31
+ variant: n,
32
+ ...a,
33
+ children: /* @__PURE__ */ S(c.Content, {
34
+ className: "flex flex-col gap-4 sm:flex-row sm:items-center sm:justify-between",
35
+ children: [/* @__PURE__ */ S("div", { children: [/* @__PURE__ */ x("p", {
36
+ className: "text-sm font-medium leading-tight",
37
+ children: l.settings.setPassword
38
+ }), /* @__PURE__ */ x("p", {
39
+ className: "text-muted text-xs mt-0.5",
40
+ children: l.settings.setPasswordDescription
41
+ })] }), /* @__PURE__ */ S(s, {
42
+ size: "sm",
43
+ isPending: f,
44
+ isDisabled: !u,
45
+ onPress: p,
46
+ children: [f && /* @__PURE__ */ x(g, {
47
+ color: "current",
48
+ size: "sm"
49
+ }), l.auth.sendResetLink]
50
+ })]
51
+ })
52
+ })] });
53
+ }
54
+ function T({ className: n, variant: r, emailAndPassword: i, localization: C, session: w, ...T }) {
55
+ let { authClient: E } = e(), [D, O] = b(""), [k, A] = b(""), [j, M] = b(""), { mutate: N, isPending: P } = t(E, {
56
+ onError: (e) => {
57
+ O(""), A(""), M(""), y.danger(e.error?.message || e.message);
58
+ },
59
+ onSuccess: () => {
60
+ O(""), A(""), M(""), y.success(C.settings.changePasswordSuccess);
61
+ }
62
+ }), [F, I] = b(!1), [L, R] = b(!1), z = (e) => {
63
+ if (e.preventDefault(), i?.confirmPassword && k !== j) {
64
+ O(""), A(""), M(""), y.danger(C.auth.passwordsDoNotMatch);
65
+ return;
66
+ }
67
+ N({
68
+ currentPassword: D,
69
+ newPassword: k,
70
+ revokeOtherSessions: !0
71
+ });
72
+ };
73
+ return /* @__PURE__ */ S("div", { children: [/* @__PURE__ */ x("h2", {
74
+ className: v("text-sm font-semibold mb-3"),
75
+ children: C.settings.changePassword
76
+ }), /* @__PURE__ */ x(c, {
77
+ className: v("p-4 gap-4", n),
78
+ variant: r,
79
+ ...T,
80
+ children: /* @__PURE__ */ x(c.Content, { children: /* @__PURE__ */ x(d, {
81
+ onSubmit: z,
82
+ children: /* @__PURE__ */ S(u, {
83
+ className: "w-full gap-4",
84
+ children: [/* @__PURE__ */ S(u.Group, { children: [
85
+ /* @__PURE__ */ S(_, {
86
+ name: "currentPassword",
87
+ type: "password",
88
+ isDisabled: P || !w,
89
+ defaultValue: "",
90
+ value: D,
91
+ onChange: O,
92
+ children: [
93
+ /* @__PURE__ */ x(m, { children: C.settings.currentPassword }),
94
+ /* @__PURE__ */ x(f, {
95
+ className: v(!w && "hidden"),
96
+ autoComplete: "current-password",
97
+ placeholder: C.settings.currentPasswordPlaceholder,
98
+ required: !0,
99
+ variant: r === "transparent" ? "primary" : "secondary"
100
+ }),
101
+ !w && /* @__PURE__ */ x(h, { className: "h-10 md:h-9 w-full rounded-xl" }),
102
+ /* @__PURE__ */ x(l, {})
103
+ ]
104
+ }),
105
+ /* @__PURE__ */ S(_, {
106
+ minLength: i?.minPasswordLength,
107
+ maxLength: i?.maxPasswordLength,
108
+ isDisabled: P || !w,
109
+ value: k,
110
+ onChange: A,
111
+ children: [
112
+ /* @__PURE__ */ x(m, { children: C.auth.newPassword }),
113
+ /* @__PURE__ */ S(p, {
114
+ className: v(!w && "hidden"),
115
+ variant: r === "transparent" ? "primary" : "secondary",
116
+ children: [/* @__PURE__ */ x(p.Input, {
117
+ name: "newPassword",
118
+ type: F ? "text" : "password",
119
+ autoComplete: "new-password",
120
+ placeholder: C.auth.newPasswordPlaceholder,
121
+ required: !0
122
+ }), /* @__PURE__ */ x(p.Suffix, {
123
+ className: "px-0",
124
+ children: /* @__PURE__ */ x(s, {
125
+ isIconOnly: !0,
126
+ "aria-label": F ? C.auth.hidePassword : C.auth.showPassword,
127
+ size: "sm",
128
+ variant: "ghost",
129
+ onPress: () => I(!F),
130
+ isDisabled: P,
131
+ children: x(F ? o : a, {})
132
+ })
133
+ })]
134
+ }),
135
+ !w && /* @__PURE__ */ x(h, { className: "h-10 md:h-9 w-full rounded-xl" }),
136
+ /* @__PURE__ */ x(l, {})
137
+ ]
138
+ }),
139
+ i?.confirmPassword && /* @__PURE__ */ S(_, {
140
+ minLength: i?.minPasswordLength,
141
+ maxLength: i?.maxPasswordLength,
142
+ isDisabled: P || !w,
143
+ isRequired: !0,
144
+ value: j,
145
+ onChange: M,
146
+ children: [
147
+ /* @__PURE__ */ x(m, { children: C.auth.confirmPassword }),
148
+ /* @__PURE__ */ S(p, {
149
+ className: v(!w && "hidden"),
150
+ variant: r === "transparent" ? "primary" : "secondary",
151
+ children: [/* @__PURE__ */ x(p.Input, {
152
+ name: "confirmPassword",
153
+ type: L ? "text" : "password",
154
+ autoComplete: "new-password",
155
+ placeholder: C.auth.confirmPasswordPlaceholder,
156
+ required: !0
157
+ }), /* @__PURE__ */ x(p.Suffix, {
158
+ className: "px-0",
159
+ children: /* @__PURE__ */ x(s, {
160
+ isIconOnly: !0,
161
+ "aria-label": L ? C.auth.hidePassword : C.auth.showPassword,
162
+ size: "sm",
163
+ variant: "ghost",
164
+ onPress: () => R(!L),
165
+ isDisabled: P,
166
+ children: x(L ? o : a, {})
167
+ })
168
+ })]
169
+ }),
170
+ !w && /* @__PURE__ */ x(h, { className: "h-10 md:h-9 w-full rounded-xl" }),
171
+ /* @__PURE__ */ x(l, {})
172
+ ]
173
+ })
174
+ ] }), /* @__PURE__ */ x(u.Actions, { children: /* @__PURE__ */ S(s, {
175
+ type: "submit",
176
+ isPending: P,
177
+ isDisabled: !w,
178
+ size: "sm",
179
+ children: [P && /* @__PURE__ */ x(g, {
180
+ color: "current",
181
+ size: "sm"
182
+ }), C.settings.updatePassword]
183
+ }) })]
184
+ })
185
+ }) })
186
+ })] });
187
+ }
188
+ //#endregion
189
+ export { C as ChangePassword };
@@ -0,0 +1,56 @@
1
+ import { getProviderName as e } from "@better-auth-ui/core";
2
+ import { providerIcons as t, useAccountInfo as n, useAuth as r, useLinkSocial as i, useUnlinkAccount as a } from "@better-auth-ui/react";
3
+ import { Link as o, LinkSlash as s, PlugConnection as c } from "@gravity-ui/icons";
4
+ import { Button as l, Skeleton as u, Spinner as d, cn as f, toast as p } from "@heroui/react";
5
+ import { jsx as m, jsxs as h } from "react/jsx-runtime";
6
+ //#region src/components/auth/settings/security/linked-account.tsx
7
+ function g({ account: g, provider: _ }) {
8
+ let { authClient: v, baseURL: y, localization: b } = r(), { data: x, isPending: S } = n(v, { query: { accountId: g?.accountId } }), { mutate: C, isPending: w } = i(v), { mutate: T, isPending: E } = a(v, { onSuccess: () => p.success(b.settings.accountUnlinked) }), D = t[_], O = e(_), k = x?.data?.login || x?.data?.username || x?.user?.email || x?.user?.name || g?.accountId;
9
+ return /* @__PURE__ */ h("div", {
10
+ className: "flex items-center gap-3",
11
+ children: [
12
+ /* @__PURE__ */ m("div", {
13
+ className: f("flex size-10 shrink-0 items-center justify-center rounded-xl bg-surface-secondary"),
14
+ children: m(D || c, { className: f("size-4.5", !g && "opacity-50") })
15
+ }),
16
+ /* @__PURE__ */ h("div", {
17
+ className: "flex flex-col min-w-0",
18
+ children: [/* @__PURE__ */ m("span", {
19
+ className: "text-sm font-medium leading-tight",
20
+ children: O
21
+ }), g && S ? /* @__PURE__ */ m(u, { className: "h-3 w-24 my-0.5 rounded-lg" }) : /* @__PURE__ */ m("span", {
22
+ className: "text-xs text-muted truncate",
23
+ children: g ? k : b.settings.linkProvider.replace("{{provider}}", O)
24
+ })]
25
+ }),
26
+ g ? /* @__PURE__ */ h(l, {
27
+ className: "ml-auto shrink-0",
28
+ variant: "outline",
29
+ size: "sm",
30
+ onPress: () => T({ providerId: g.providerId }),
31
+ isPending: E,
32
+ "aria-label": b.settings.unlinkProvider.replace("{{provider}}", O),
33
+ children: [E ? /* @__PURE__ */ m(d, {
34
+ color: "current",
35
+ size: "sm"
36
+ }) : /* @__PURE__ */ m(s, {}), b.settings.unlinkProvider.replace("{{provider}}", "").trim()]
37
+ }) : /* @__PURE__ */ h(l, {
38
+ className: "ml-auto shrink-0",
39
+ variant: "outline",
40
+ size: "sm",
41
+ onPress: () => C({
42
+ provider: _,
43
+ callbackURL: `${y}${window.location.pathname}`
44
+ }),
45
+ isPending: w,
46
+ "aria-label": b.settings.linkProvider.replace("{{provider}}", O),
47
+ children: [w ? /* @__PURE__ */ m(d, {
48
+ color: "current",
49
+ size: "sm"
50
+ }) : /* @__PURE__ */ m(o, {}), b.settings.link]
51
+ })
52
+ ]
53
+ });
54
+ }
55
+ //#endregion
56
+ export { g as LinkedAccount };
@@ -12,4 +12,4 @@ export type LinkedAccountsProps = {
12
12
  *
13
13
  * @returns A JSX element containing the linked accounts card
14
14
  */
15
- export declare function LinkedAccounts({ className, variant, ...props }: LinkedAccountsProps & CardProps): import("react/jsx-runtime").JSX.Element;
15
+ export declare function LinkedAccounts({ className, variant, ...props }: LinkedAccountsProps & Omit<CardProps, "children">): import("react/jsx-runtime").JSX.Element;