@digitaldefiance/express-suite-react-components 5.0.2 → 5.0.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 (314) hide show
  1. package/package.json +5 -4
  2. package/src/auth/AdminRoute.d.ts +8 -0
  3. package/src/auth/AdminRoute.d.ts.map +1 -0
  4. package/src/auth/AdminRoute.js +28 -0
  5. package/src/auth/Private.d.ts +6 -0
  6. package/src/auth/Private.d.ts.map +1 -0
  7. package/src/auth/Private.js +14 -0
  8. package/src/auth/PrivateRoute.d.ts +8 -0
  9. package/src/auth/PrivateRoute.d.ts.map +1 -0
  10. package/src/auth/PrivateRoute.js +23 -0
  11. package/src/auth/UnAuth.d.ts +6 -0
  12. package/src/auth/UnAuth.d.ts.map +1 -0
  13. package/src/auth/UnAuth.js +14 -0
  14. package/src/auth/UnAuthRoute.d.ts +8 -0
  15. package/src/auth/UnAuthRoute.d.ts.map +1 -0
  16. package/src/auth/UnAuthRoute.js +22 -0
  17. package/src/auth/{index.ts → index.d.ts} +3 -2
  18. package/src/auth/index.d.ts.map +1 -0
  19. package/src/auth/index.js +12 -0
  20. package/src/components/ApiAccess.d.ts +16 -0
  21. package/src/components/ApiAccess.d.ts.map +1 -0
  22. package/src/components/ApiAccess.js +77 -0
  23. package/src/components/BackupCodeLoginForm.d.ts +43 -0
  24. package/src/components/BackupCodeLoginForm.d.ts.map +1 -0
  25. package/src/components/BackupCodeLoginForm.js +139 -0
  26. package/src/components/BackupCodesForm.d.ts +26 -0
  27. package/src/components/BackupCodesForm.d.ts.map +1 -0
  28. package/src/components/BackupCodesForm.js +120 -0
  29. package/src/components/CategoryMenu.d.ts +17 -0
  30. package/src/components/CategoryMenu.d.ts.map +1 -0
  31. package/src/components/CategoryMenu.js +65 -0
  32. package/src/components/ChangePasswordForm.d.ts +26 -0
  33. package/src/components/ChangePasswordForm.d.ts.map +1 -0
  34. package/src/components/ChangePasswordForm.js +78 -0
  35. package/src/components/ConfirmationDialog.d.ts +13 -0
  36. package/src/components/ConfirmationDialog.d.ts.map +1 -0
  37. package/src/components/ConfirmationDialog.js +10 -0
  38. package/src/components/CurrencyCodeSelector.d.ts +9 -0
  39. package/src/components/CurrencyCodeSelector.d.ts.map +1 -0
  40. package/src/components/CurrencyCodeSelector.js +31 -0
  41. package/src/components/CurrencyInput.d.ts +13 -0
  42. package/src/components/CurrencyInput.d.ts.map +1 -0
  43. package/src/components/CurrencyInput.js +22 -0
  44. package/src/components/DashboardPage.d.ts +8 -0
  45. package/src/components/DashboardPage.d.ts.map +1 -0
  46. package/src/components/DashboardPage.js +10 -0
  47. package/src/components/DropdownMenu.d.ts +13 -0
  48. package/src/components/DropdownMenu.d.ts.map +1 -0
  49. package/src/components/DropdownMenu.js +63 -0
  50. package/src/components/ExpirationSecondsSelector.d.ts +13 -0
  51. package/src/components/ExpirationSecondsSelector.d.ts.map +1 -0
  52. package/src/components/ExpirationSecondsSelector.js +32 -0
  53. package/src/components/FakeEmailAdminPanel.d.ts +23 -0
  54. package/src/components/FakeEmailAdminPanel.d.ts.map +1 -0
  55. package/src/components/FakeEmailAdminPanel.js +147 -0
  56. package/src/components/Flag.d.ts +20 -0
  57. package/src/components/Flag.d.ts.map +1 -0
  58. package/src/components/Flag.js +43 -0
  59. package/src/components/ForgotPasswordForm.d.ts +18 -0
  60. package/src/components/ForgotPasswordForm.d.ts.map +1 -0
  61. package/src/components/ForgotPasswordForm.js +61 -0
  62. package/src/components/LoginForm.d.ts +44 -0
  63. package/src/components/LoginForm.d.ts.map +1 -0
  64. package/src/components/LoginForm.js +123 -0
  65. package/src/components/LogoutPage.d.ts +8 -0
  66. package/src/components/LogoutPage.d.ts.map +1 -0
  67. package/src/components/LogoutPage.js +16 -0
  68. package/src/components/RegisterForm.d.ts +100 -0
  69. package/src/components/RegisterForm.d.ts.map +1 -0
  70. package/src/components/RegisterForm.js +306 -0
  71. package/src/components/ResetPasswordForm.d.ts +23 -0
  72. package/src/components/ResetPasswordForm.d.ts.map +1 -0
  73. package/src/components/ResetPasswordForm.js +78 -0
  74. package/src/components/SideMenu.d.ts +8 -0
  75. package/src/components/SideMenu.d.ts.map +1 -0
  76. package/src/components/SideMenu.js +25 -0
  77. package/src/components/SideMenuListItem.d.ts +13 -0
  78. package/src/components/SideMenuListItem.d.ts.map +1 -0
  79. package/src/components/SideMenuListItem.js +44 -0
  80. package/src/components/T.d.ts +7 -0
  81. package/src/components/T.d.ts.map +1 -0
  82. package/src/components/T.js +13 -0
  83. package/src/components/TDiv.d.ts +9 -0
  84. package/src/components/TDiv.d.ts.map +1 -0
  85. package/src/components/TDiv.js +14 -0
  86. package/src/components/TImgAlt.d.ts +10 -0
  87. package/src/components/TImgAlt.d.ts.map +1 -0
  88. package/src/components/TImgAlt.js +14 -0
  89. package/src/components/TopMenu.d.ts +50 -0
  90. package/src/components/TopMenu.d.ts.map +1 -0
  91. package/src/components/TopMenu.js +79 -0
  92. package/src/components/TotpSetupForm.d.ts +24 -0
  93. package/src/components/TotpSetupForm.d.ts.map +1 -0
  94. package/src/components/TotpSetupForm.js +82 -0
  95. package/src/components/TotpVerificationForm.d.ts +23 -0
  96. package/src/components/TotpVerificationForm.d.ts.map +1 -0
  97. package/src/components/TotpVerificationForm.js +66 -0
  98. package/src/components/TranslatedTitle.d.ts +8 -0
  99. package/src/components/TranslatedTitle.d.ts.map +1 -0
  100. package/src/components/TranslatedTitle.js +15 -0
  101. package/src/components/UserLanguageSelector.d.ts +4 -0
  102. package/src/components/UserLanguageSelector.d.ts.map +1 -0
  103. package/src/components/UserLanguageSelector.js +31 -0
  104. package/src/components/UserMenu.d.ts +4 -0
  105. package/src/components/UserMenu.d.ts.map +1 -0
  106. package/src/components/UserMenu.js +12 -0
  107. package/src/components/UserSettingsForm.d.ts +113 -0
  108. package/src/components/UserSettingsForm.d.ts.map +1 -0
  109. package/src/components/UserSettingsForm.js +269 -0
  110. package/src/components/VerifyEmailPage.d.ts +24 -0
  111. package/src/components/VerifyEmailPage.d.ts.map +1 -0
  112. package/src/components/VerifyEmailPage.js +81 -0
  113. package/src/components/{index.ts → index.d.ts} +1 -1
  114. package/src/components/index.d.ts.map +1 -0
  115. package/src/components/index.js +35 -0
  116. package/src/contexts/AuthProvider.d.ts +19 -0
  117. package/src/contexts/AuthProvider.d.ts.map +1 -0
  118. package/src/contexts/AuthProvider.js +514 -0
  119. package/src/contexts/I18nProvider.d.ts +27 -0
  120. package/src/contexts/I18nProvider.d.ts.map +1 -0
  121. package/src/contexts/I18nProvider.js +60 -0
  122. package/src/contexts/MenuContext.d.ts +28 -0
  123. package/src/contexts/MenuContext.d.ts.map +1 -0
  124. package/src/contexts/MenuContext.js +307 -0
  125. package/src/contexts/SuiteConfigProvider.d.ts +44 -0
  126. package/src/contexts/SuiteConfigProvider.d.ts.map +1 -0
  127. package/src/contexts/SuiteConfigProvider.js +43 -0
  128. package/src/contexts/ThemeProvider.d.ts +15 -0
  129. package/src/contexts/ThemeProvider.d.ts.map +1 -0
  130. package/src/contexts/ThemeProvider.js +36 -0
  131. package/src/contexts/auth-context.d.ts +172 -0
  132. package/src/contexts/auth-context.d.ts.map +1 -0
  133. package/src/contexts/auth-context.js +13 -0
  134. package/src/contexts/{index.ts → index.d.ts} +1 -0
  135. package/src/contexts/index.d.ts.map +1 -0
  136. package/src/contexts/index.js +8 -0
  137. package/src/hooks/{index.ts → index.d.ts} +1 -0
  138. package/src/hooks/index.d.ts.map +1 -0
  139. package/src/hooks/index.js +9 -0
  140. package/src/hooks/useAuthenticatedApi.d.ts +34 -0
  141. package/src/hooks/useAuthenticatedApi.d.ts.map +1 -0
  142. package/src/hooks/useAuthenticatedApi.js +46 -0
  143. package/src/hooks/useBackupCodes.d.ts +15 -0
  144. package/src/hooks/useBackupCodes.d.ts.map +1 -0
  145. package/src/hooks/useBackupCodes.js +74 -0
  146. package/src/hooks/useEmailVerification.d.ts +10 -0
  147. package/src/hooks/useEmailVerification.d.ts.map +1 -0
  148. package/src/hooks/useEmailVerification.js +40 -0
  149. package/src/hooks/useExpiringValue.d.ts +14 -0
  150. package/src/hooks/useExpiringValue.d.ts.map +1 -0
  151. package/src/hooks/useExpiringValue.js +53 -0
  152. package/src/hooks/useLocalStorage.d.ts +2 -0
  153. package/src/hooks/useLocalStorage.d.ts.map +1 -0
  154. package/src/hooks/useLocalStorage.js +15 -0
  155. package/src/hooks/useUserSettings.d.ts +48 -0
  156. package/src/hooks/useUserSettings.d.ts.map +1 -0
  157. package/src/hooks/useUserSettings.js +171 -0
  158. package/src/{index.ts → index.d.ts} +1 -1
  159. package/src/index.d.ts.map +1 -0
  160. package/src/index.js +12 -0
  161. package/src/interfaces/IAppConfig.d.ts +8 -0
  162. package/src/interfaces/IAppConfig.d.ts.map +1 -0
  163. package/src/interfaces/IAppConfig.js +2 -0
  164. package/src/interfaces/ICategoryConfig.d.ts +41 -0
  165. package/src/interfaces/ICategoryConfig.d.ts.map +1 -0
  166. package/src/interfaces/ICategoryConfig.js +2 -0
  167. package/src/interfaces/IMenuConfig.d.ts +28 -0
  168. package/src/interfaces/IMenuConfig.d.ts.map +1 -0
  169. package/src/interfaces/IMenuConfig.js +2 -0
  170. package/src/interfaces/IMenuOption.d.ts +82 -0
  171. package/src/interfaces/IMenuOption.d.ts.map +1 -0
  172. package/src/interfaces/IMenuOption.js +2 -0
  173. package/src/interfaces/{index.ts → index.d.ts} +1 -0
  174. package/src/interfaces/index.d.ts.map +1 -0
  175. package/src/interfaces/index.js +7 -0
  176. package/src/services/__mocks__/authService.d.ts +21 -0
  177. package/src/services/__mocks__/authService.d.ts.map +1 -0
  178. package/src/services/__mocks__/authService.js +15 -0
  179. package/src/services/api.d.ts +3 -0
  180. package/src/services/api.d.ts.map +1 -0
  181. package/src/services/api.js +14 -0
  182. package/src/services/authService.d.ts +126 -0
  183. package/src/services/authService.d.ts.map +1 -0
  184. package/src/services/authService.js +471 -0
  185. package/src/services/authenticatedApi.d.ts +3 -0
  186. package/src/services/authenticatedApi.d.ts.map +1 -0
  187. package/src/services/authenticatedApi.js +18 -0
  188. package/src/services/index.d.ts +4 -0
  189. package/src/services/index.d.ts.map +1 -0
  190. package/src/services/index.js +6 -0
  191. package/src/types/MenuType.d.ts +11 -0
  192. package/src/types/MenuType.d.ts.map +1 -0
  193. package/src/types/MenuType.js +12 -0
  194. package/src/types/expirationSeconds.d.ts +3 -0
  195. package/src/types/expirationSeconds.d.ts.map +1 -0
  196. package/src/types/expirationSeconds.js +17 -0
  197. package/src/types/index.d.ts +2 -0
  198. package/src/types/index.d.ts.map +1 -0
  199. package/src/types/index.js +4 -0
  200. package/src/types/translation.d.ts +10 -0
  201. package/src/types/translation.d.ts.map +1 -0
  202. package/src/types/translation.js +9 -0
  203. package/src/wrappers/BackupCodeLoginWrapper.d.ts +8 -0
  204. package/src/wrappers/BackupCodeLoginWrapper.d.ts.map +1 -0
  205. package/src/wrappers/BackupCodeLoginWrapper.js +20 -0
  206. package/src/wrappers/BackupCodesWrapper.d.ts +7 -0
  207. package/src/wrappers/BackupCodesWrapper.d.ts.map +1 -0
  208. package/src/wrappers/BackupCodesWrapper.js +17 -0
  209. package/src/wrappers/ChangePasswordFormWrapper.d.ts +8 -0
  210. package/src/wrappers/ChangePasswordFormWrapper.d.ts.map +1 -0
  211. package/src/wrappers/ChangePasswordFormWrapper.js +21 -0
  212. package/src/wrappers/ForgotPasswordFormWrapper.d.ts +8 -0
  213. package/src/wrappers/ForgotPasswordFormWrapper.d.ts.map +1 -0
  214. package/src/wrappers/ForgotPasswordFormWrapper.js +29 -0
  215. package/src/wrappers/LoginFormWrapper.d.ts +21 -0
  216. package/src/wrappers/LoginFormWrapper.d.ts.map +1 -0
  217. package/src/wrappers/LoginFormWrapper.js +72 -0
  218. package/src/wrappers/LogoutPageWrapper.d.ts +9 -0
  219. package/src/wrappers/LogoutPageWrapper.d.ts.map +1 -0
  220. package/src/wrappers/LogoutPageWrapper.js +21 -0
  221. package/src/wrappers/RegisterFormWrapper.d.ts +20 -0
  222. package/src/wrappers/RegisterFormWrapper.d.ts.map +1 -0
  223. package/src/wrappers/RegisterFormWrapper.js +51 -0
  224. package/src/wrappers/ResetPasswordFormWrapper.d.ts +9 -0
  225. package/src/wrappers/ResetPasswordFormWrapper.d.ts.map +1 -0
  226. package/src/wrappers/ResetPasswordFormWrapper.js +34 -0
  227. package/src/wrappers/UserSettingsFormWrapper.d.ts +29 -0
  228. package/src/wrappers/UserSettingsFormWrapper.d.ts.map +1 -0
  229. package/src/wrappers/UserSettingsFormWrapper.js +95 -0
  230. package/src/wrappers/VerifyEmailPageWrapper.d.ts +8 -0
  231. package/src/wrappers/VerifyEmailPageWrapper.d.ts.map +1 -0
  232. package/src/wrappers/VerifyEmailPageWrapper.js +21 -0
  233. package/src/wrappers/{index.tsx → index.d.ts} +1 -10
  234. package/src/wrappers/index.d.ts.map +1 -0
  235. package/src/wrappers/index.js +24 -0
  236. package/LICENSE +0 -21
  237. package/src/auth/AdminRoute.tsx +0 -54
  238. package/src/auth/Private.tsx +0 -17
  239. package/src/auth/PrivateRoute.tsx +0 -28
  240. package/src/auth/UnAuth.tsx +0 -16
  241. package/src/auth/UnAuthRoute.tsx +0 -30
  242. package/src/components/ApiAccess.tsx +0 -175
  243. package/src/components/BackupCodeLoginForm.tsx +0 -489
  244. package/src/components/BackupCodesForm.tsx +0 -287
  245. package/src/components/CategoryMenu.tsx +0 -155
  246. package/src/components/ChangePasswordForm.tsx +0 -273
  247. package/src/components/ConfirmationDialog.tsx +0 -48
  248. package/src/components/CurrencyCodeSelector.tsx +0 -60
  249. package/src/components/CurrencyInput.tsx +0 -80
  250. package/src/components/DashboardPage.tsx +0 -24
  251. package/src/components/DropdownMenu.tsx +0 -105
  252. package/src/components/ExpirationSecondsSelector.tsx +0 -60
  253. package/src/components/FakeEmailAdminPanel.tsx +0 -374
  254. package/src/components/Flag.tsx +0 -52
  255. package/src/components/ForgotPasswordForm.tsx +0 -174
  256. package/src/components/LoginForm.tsx +0 -468
  257. package/src/components/LogoutPage.tsx +0 -21
  258. package/src/components/RegisterForm.tsx +0 -1169
  259. package/src/components/ResetPasswordForm.tsx +0 -247
  260. package/src/components/SideMenu.tsx +0 -46
  261. package/src/components/SideMenuListItem.tsx +0 -75
  262. package/src/components/T.tsx +0 -24
  263. package/src/components/TDiv.tsx +0 -26
  264. package/src/components/TImgAlt.tsx +0 -28
  265. package/src/components/TopMenu.tsx +0 -252
  266. package/src/components/TotpSetupForm.tsx +0 -188
  267. package/src/components/TotpVerificationForm.tsx +0 -148
  268. package/src/components/TranslatedTitle.tsx +0 -31
  269. package/src/components/UserLanguageSelector.tsx +0 -45
  270. package/src/components/UserMenu.tsx +0 -15
  271. package/src/components/UserSettingsForm.tsx +0 -904
  272. package/src/components/VerifyEmailPage.tsx +0 -222
  273. package/src/components/__tests__/RegisterForm.totp.spec.tsx +0 -377
  274. package/src/components/__tests__/TotpSetupForm.spec.tsx +0 -258
  275. package/src/components/__tests__/TotpVerificationForm.spec.tsx +0 -259
  276. package/src/components/__tests__/UserSettingsForm.totp.spec.tsx +0 -396
  277. package/src/contexts/AuthProvider.spec.tsx +0 -1284
  278. package/src/contexts/AuthProvider.tsx +0 -977
  279. package/src/contexts/I18nProvider.tsx +0 -164
  280. package/src/contexts/MenuContext.tsx +0 -426
  281. package/src/contexts/SuiteConfigProvider.tsx +0 -93
  282. package/src/contexts/ThemeProvider.tsx +0 -67
  283. package/src/hooks/useAuthenticatedApi.tsx +0 -67
  284. package/src/hooks/useBackupCodes.ts +0 -105
  285. package/src/hooks/useEmailVerification.ts +0 -54
  286. package/src/hooks/useExpiringValue.ts +0 -78
  287. package/src/hooks/useLocalStorage.ts +0 -18
  288. package/src/hooks/useUserSettings.ts +0 -271
  289. package/src/interfaces/IAppConfig.ts +0 -7
  290. package/src/interfaces/ICategoryConfig.ts +0 -41
  291. package/src/interfaces/IMenuConfig.ts +0 -28
  292. package/src/interfaces/IMenuOption.ts +0 -79
  293. package/src/services/__mocks__/authService.ts +0 -14
  294. package/src/services/__tests__/authService.totp.property.spec.ts +0 -360
  295. package/src/services/__tests__/authService.totp.spec.ts +0 -439
  296. package/src/services/api.ts +0 -13
  297. package/src/services/authService.ts +0 -692
  298. package/src/services/authenticatedApi.ts +0 -17
  299. package/src/services/index.ts +0 -3
  300. package/src/types/MenuType.ts +0 -15
  301. package/src/types/expirationSeconds.ts +0 -18
  302. package/src/types/index.ts +0 -1
  303. package/src/types/translation.ts +0 -20
  304. package/src/wrappers/BackupCodeLoginWrapper.tsx +0 -34
  305. package/src/wrappers/BackupCodesWrapper.tsx +0 -28
  306. package/src/wrappers/ChangePasswordFormWrapper.tsx +0 -34
  307. package/src/wrappers/ForgotPasswordFormWrapper.tsx +0 -45
  308. package/src/wrappers/LoginFormWrapper.tsx +0 -108
  309. package/src/wrappers/LogoutPageWrapper.tsx +0 -30
  310. package/src/wrappers/RegisterFormWrapper.tsx +0 -109
  311. package/src/wrappers/ResetPasswordFormWrapper.tsx +0 -57
  312. package/src/wrappers/UserSettingsFormWrapper.tsx +0 -140
  313. package/src/wrappers/VerifyEmailPageWrapper.tsx +0 -27
  314. package/src/wrappers/__tests__/LoginFormWrapper.totp.spec.tsx +0 -339
@@ -1,977 +0,0 @@
1
- import {
2
- AESGCMService,
3
- Constants as AppConstants,
4
- ECIESService,
5
- EmailString,
6
- Member as FrontendMember,
7
- IECIESConfig,
8
- PasswordLoginService,
9
- Pbkdf2Service,
10
- SecureString,
11
- } from '@digitaldefiance/ecies-lib';
12
- import {
13
- CoreLanguageCode,
14
- CurrencyCode,
15
- Timezone,
16
- } from '@digitaldefiance/i18n-lib';
17
- import {
18
- IConstants,
19
- IRequestUserDTO,
20
- ISuccessMessage,
21
- IUserSettings,
22
- SuiteCoreComponentId,
23
- SuiteCoreStringKey,
24
- SuiteCoreStringKeyValue,
25
- } from '@digitaldefiance/suite-core-lib';
26
- import { Wallet } from '@ethereumjs/wallet';
27
- import { PaletteMode } from '@mui/material';
28
- import {
29
- createContext,
30
- ReactNode,
31
- useCallback,
32
- useContext,
33
- useEffect,
34
- useMemo,
35
- useState,
36
- } from 'react';
37
- import { useExpiringValue } from '../hooks/useExpiringValue';
38
- import { useLocalStorage } from '../hooks/useLocalStorage';
39
- import { useUserSettings } from '../hooks/useUserSettings';
40
- import { createAuthService } from '../services/authService';
41
- import { createAuthenticatedApiClient } from '../services/authenticatedApi';
42
- import { useI18n } from './I18nProvider';
43
- import { useTheme } from './ThemeProvider';
44
-
45
- export interface AuthContextData {
46
- /**
47
- * True if the user has a global admin role
48
- */
49
- admin: boolean;
50
- /**
51
- * Counter that increments on login/logout to trigger effects in dependent components
52
- */
53
- authState: number;
54
- /**
55
- * Performs a server side backup-code login
56
- * @param identifier
57
- * @param code
58
- * @param isEmail
59
- * @param recoverMnemonic
60
- * @param newPassword
61
- * @returns
62
- */
63
- backupCodeLogin: (
64
- identifier: string,
65
- code: string,
66
- isEmail: boolean,
67
- recoverMnemonic: boolean,
68
- newPassword?: string
69
- ) => Promise<
70
- | { token: string; codeCount: number; mnemonic?: string; message?: string }
71
- | { error: string; status?: number }
72
- >;
73
- /**
74
- * Verifies the stored token (if any) and updates auth state
75
- * @returns void
76
- */
77
- checkAuth: () => void;
78
- /**
79
- * Changes the stored browser password login mnemonic
80
- * @param currentPassword
81
- * @param newPassword
82
- * @returns
83
- */
84
- changePassword: (
85
- currentPassword: string,
86
- newPassword: string
87
- ) => Promise<
88
- | ISuccessMessage
89
- | {
90
- error: string;
91
- errorType?: string | undefined;
92
- }
93
- >;
94
- clearMnemonic: () => void;
95
- clearWallet: () => void;
96
- colorMode?: PaletteMode;
97
- currencyCode?: CurrencyCode;
98
- directLogin: (
99
- mnemonic: SecureString,
100
- username?: string,
101
- email?: EmailString,
102
- expireMnemonicSeconds?: number,
103
- expireWalletSeconds?: number
104
- ) => Promise<
105
- | { token: string; user: IRequestUserDTO; wallet: Wallet }
106
- | { pendingTotpToken: string }
107
- | { error: string; errorType?: string }
108
- >;
109
- emailChallengeLogin: (
110
- mnemonic: SecureString,
111
- token: string,
112
- username?: string,
113
- email?: EmailString,
114
- expireMnemonicSeconds?: number,
115
- expireWalletSeconds?: number
116
- ) => Promise<
117
- | { token: string; user: IRequestUserDTO; wallet: Wallet; message: string }
118
- | { pendingTotpToken: string }
119
- | { error: string; errorType?: string }
120
- >;
121
- isAuthenticated: boolean;
122
- // True only while the app is determining initial auth state (e.g., on first load or refresh)
123
- isCheckingAuth: boolean;
124
- isBrowserPasswordLoginAvailable?: () => boolean;
125
- loading: boolean;
126
- logout: () => void;
127
- mnemonic?: SecureString;
128
- mnemonicExpirationSeconds: number;
129
- passwordLogin: (
130
- password: SecureString,
131
- username?: string,
132
- email?: EmailString
133
- ) => Promise<
134
- | { token: string; user: IRequestUserDTO; wallet: Wallet }
135
- | { pendingTotpToken: string }
136
- | { error: string; errorType?: string }
137
- >;
138
- requestEmailLogin: (
139
- username?: string,
140
- email?: EmailString
141
- ) => Promise<string | { error: string; errorType?: string }>;
142
- refreshToken: () => Promise<{ token: string; user: IRequestUserDTO }>;
143
- register: (
144
- username: string,
145
- email: string,
146
- timezone: string,
147
- password?: string,
148
- mnemonic?: string,
149
- displayName?: string,
150
- directChallenge?: boolean
151
- ) => Promise<
152
- | {
153
- success: boolean;
154
- message: string;
155
- mnemonic: string;
156
- }
157
- | {
158
- error: string;
159
- errorType?: string;
160
- field?: string;
161
- errors?: Array<{ path: string; msg: string }>;
162
- }
163
- >;
164
- serverPublicKey: string | null;
165
- /**
166
- * Gets the remaining time in seconds for the mnemonic expiration
167
- * @returns Number of seconds remaining, or 0 if no mnemonic is set
168
- */
169
- getMnemonicRemainingTime: () => number;
170
- /**
171
- * Gets the remaining time in seconds for the wallet expiration
172
- * @returns Number of seconds remaining, or 0 if no wallet is set
173
- */
174
- getWalletRemainingTime: () => number;
175
- setMnemonic: (mnemonic: SecureString, durationSeconds?: number) => void;
176
- setMnemonicExpirationSeconds: (seconds: number) => void;
177
- setWalletExpirationSeconds: (seconds: number) => void;
178
- setUpBrowserPasswordLogin: (
179
- mnemonic: SecureString,
180
- password: SecureString,
181
- username?: string,
182
- email?: EmailString
183
- ) => Promise<
184
- | { success: boolean; message: string }
185
- | { error: string; errorType?: string }
186
- >;
187
- setUser: (user: IRequestUserDTO | null) => Promise<void>;
188
- setUserSetting: (setting?: Partial<IUserSettings>) => Promise<void>;
189
- setWallet: (wallet: Wallet, durationSeconds?: number) => void;
190
- user: FrontendMember | null;
191
- userData: IRequestUserDTO | null;
192
- userSettings: IUserSettings | undefined;
193
- token: string | null;
194
- wallet?: Wallet;
195
- walletExpirationSeconds: number;
196
- verifyToken: (token: string) => Promise<boolean>;
197
- /**
198
- * Initiates TOTP setup for the authenticated user.
199
- * Returns the provisioning URI and raw base32 secret on success.
200
- */
201
- setupTotp: () => Promise<
202
- { provisioningUri: string; secret: string } | { error: string }
203
- >;
204
- /**
205
- * Confirms TOTP setup with a 6-digit code.
206
- */
207
- confirmTotp: (
208
- code: string
209
- ) => Promise<{ success: boolean } | { error: string }>;
210
- /**
211
- * Completes TOTP login by verifying a 6-digit code against a pending TOTP token.
212
- */
213
- verifyTotpLogin: (
214
- pendingTotpToken: string,
215
- code: string
216
- ) => Promise<{ token: string; user: IRequestUserDTO } | { error: string }>;
217
- }
218
-
219
- export type AuthProviderProps = {
220
- children: ReactNode;
221
- baseUrl: string;
222
- constants: IConstants;
223
- eciesConfig: IECIESConfig;
224
- /**
225
- * Optional callback to handle navigation after logout
226
- * If not provided, logout will only clear auth state without navigation
227
- */
228
- onLogout?: () => void;
229
- emailDomain: string;
230
- };
231
-
232
- export const AuthContext = createContext<AuthContextData>(
233
- {} as AuthContextData
234
- );
235
-
236
- const AuthProviderInner = ({
237
- children,
238
- baseUrl,
239
- constants,
240
- eciesConfig,
241
- onLogout,
242
- emailDomain,
243
- }: AuthProviderProps) => {
244
- const { tComponent, changeLanguage: i18nChangeLanguage } = useI18n();
245
- const { setColorMode: themeSetPaletteMode, mode: colorMode } = useTheme();
246
-
247
- const authService = useMemo(
248
- () => createAuthService(constants, baseUrl, eciesConfig, emailDomain),
249
- [constants, baseUrl, eciesConfig, emailDomain]
250
- );
251
- const authenticatedApi = useMemo(
252
- () => createAuthenticatedApiClient(baseUrl),
253
- [baseUrl]
254
- );
255
-
256
- // Use the custom hooks for expiring values
257
- const mnemonicManager = useExpiringValue<SecureString>(
258
- constants.DefaultExpireMemoryMnemonicSeconds,
259
- 'mnemonicExpirationSeconds'
260
- );
261
- const walletManager = useExpiringValue<Wallet>(
262
- constants.DefaultExpireMemoryWalletSeconds,
263
- 'walletExpirationSeconds'
264
- );
265
-
266
- // Use localStorage hook for expiration settings
267
- const [mnemonicExpirationSeconds, _setMnemonicExpirationSeconds] =
268
- useLocalStorage(
269
- 'mnemonicExpirationSeconds',
270
- constants.DefaultExpireMemoryMnemonicSeconds
271
- );
272
- const [walletExpirationSeconds, _setWalletExpirationSeconds] =
273
- useLocalStorage(
274
- 'walletExpirationSeconds',
275
- constants.DefaultExpireMemoryWalletSeconds
276
- );
277
- const [serverPublicKey, setServerPublicKey] = useState<string | null>(null);
278
- const [user, setUser] = useState<IRequestUserDTO | null>(null);
279
- const [frontendUser, setFrontendUser] = useState<FrontendMember | null>(null);
280
- const [isAuthenticated, setIsAuthenticated] = useState(false);
281
- const [isGlobalAdmin, setIsGlobalAdmin] = useState(false);
282
- const [loading, setLoading] = useState(true);
283
- // Separate flag so route guards don't unmount during actions (e.g., register/login)
284
- const [isCheckingAuth, setIsCheckingAuth] = useState(true);
285
- const [token, setToken] = useState<string | null>(null);
286
- const [authState, setAuthState] = useState(0);
287
-
288
- // Use the user settings hook for settings management
289
- const { userSettings, setUserSettingAndUpdateSettings } = useUserSettings({
290
- authenticatedApi,
291
- isAuthenticated,
292
- });
293
-
294
- // Helper functions to calculate remaining time (now provided by the hooks)
295
- const getMnemonicRemainingTime = mnemonicManager.getRemainingTime;
296
- const getWalletRemainingTime = walletManager.getRemainingTime;
297
-
298
- // Wrapper functions to match the interface (the localStorage hook handles storage automatically)
299
- const setMnemonicExpirationSeconds = _setMnemonicExpirationSeconds;
300
- const setWalletExpirationSeconds = _setWalletExpirationSeconds;
301
-
302
- // Sync user language with i18n provider when the user's saved language changes.
303
- // Only update the i18n engine — do NOT call setUserSettingAndUpdateSettings
304
- // here because its merge with defaults can overwrite other settings (e.g.
305
- // timezone) with default values when the closure captures stale userSettings.
306
- useEffect(() => {
307
- if (user?.siteLanguage) {
308
- i18nChangeLanguage(user.siteLanguage);
309
- }
310
- // eslint-disable-next-line react-hooks/exhaustive-deps
311
- }, [user?.siteLanguage]);
312
-
313
- const setMnemonic = useCallback(
314
- (mnemonic: SecureString, durationSeconds?: number) => {
315
- const finalDurationSeconds = durationSeconds ?? mnemonicExpirationSeconds;
316
-
317
- // Store the duration to localStorage if provided
318
- if (durationSeconds !== undefined) {
319
- _setMnemonicExpirationSeconds(durationSeconds);
320
- }
321
-
322
- // Only save to storage if a custom duration was provided
323
- return mnemonicManager.setValue(
324
- mnemonic,
325
- finalDurationSeconds,
326
- durationSeconds !== undefined
327
- );
328
- },
329
- // mnemonicManager is intentionally excluded as it's a stable reference from useExpiringValue
330
- // eslint-disable-next-line react-hooks/exhaustive-deps
331
- [
332
- mnemonicExpirationSeconds,
333
- mnemonicManager.setValue,
334
- _setMnemonicExpirationSeconds,
335
- ]
336
- );
337
-
338
- const setWallet = useCallback(
339
- (wallet: Wallet, durationSeconds?: number) => {
340
- const finalDurationSeconds = durationSeconds ?? walletExpirationSeconds;
341
-
342
- // Store the duration to localStorage if provided
343
- if (durationSeconds !== undefined) {
344
- _setWalletExpirationSeconds(durationSeconds);
345
- }
346
-
347
- // Only save to storage if a custom duration was provided
348
- return walletManager.setValue(
349
- wallet,
350
- finalDurationSeconds,
351
- durationSeconds !== undefined
352
- );
353
- },
354
- // walletManager is intentionally excluded as it's a stable reference from useExpiringValue
355
- // eslint-disable-next-line react-hooks/exhaustive-deps
356
- [
357
- walletExpirationSeconds,
358
- walletManager.setValue,
359
- _setWalletExpirationSeconds,
360
- ]
361
- );
362
-
363
- const clearMnemonic = mnemonicManager.clearValue;
364
- const clearWallet = walletManager.clearValue;
365
-
366
- const checkAuth = useCallback(async () => {
367
- const token = localStorage.getItem('authToken');
368
- if (!token) {
369
- setUser(null);
370
- setIsAuthenticated(false);
371
- setLoading(false);
372
- setIsCheckingAuth(false);
373
- setToken(null);
374
- setFrontendUser(null);
375
- setServerPublicKey(null);
376
- await setUserSettingAndUpdateSettings(undefined);
377
- themeSetPaletteMode('light');
378
- clearMnemonic();
379
- clearWallet();
380
- return;
381
- }
382
-
383
- try {
384
- const userData = await authService.verifyToken(token);
385
- if ('error' in userData && typeof userData.error === 'string') {
386
- setIsAuthenticated(false);
387
- setToken(null);
388
- } else if ('id' in userData && 'email' in userData) {
389
- const userDataDTO: IRequestUserDTO = userData as IRequestUserDTO;
390
- setUser(userDataDTO);
391
- setIsGlobalAdmin(userDataDTO.roles.some((r) => r.admin));
392
- setIsAuthenticated(true);
393
- setToken(token);
394
- await setUserSettingAndUpdateSettings({
395
- darkMode: userDataDTO.darkMode,
396
- currency: new CurrencyCode(userDataDTO.currency),
397
- timezone: new Timezone(userDataDTO.timezone),
398
- siteLanguage: userDataDTO.siteLanguage as CoreLanguageCode,
399
- email: new EmailString(userDataDTO.email),
400
- directChallenge: userDataDTO.directChallenge,
401
- ...(userDataDTO.displayName !== undefined
402
- ? { displayName: userDataDTO.displayName }
403
- : {}),
404
- });
405
- }
406
- } catch (error) {
407
- console.error('Token verification failed:', error);
408
- setUser(null);
409
- setIsAuthenticated(false);
410
- await setUserSettingAndUpdateSettings(undefined);
411
- localStorage.removeItem('authToken');
412
- } finally {
413
- setLoading(false);
414
- setIsCheckingAuth(false);
415
- }
416
- }, [
417
- authService,
418
- clearMnemonic,
419
- clearWallet,
420
- setUserSettingAndUpdateSettings,
421
- themeSetPaletteMode,
422
- ]);
423
-
424
- useEffect(() => {
425
- const token = localStorage.getItem('authToken');
426
- if (token) {
427
- (async () => {
428
- await checkAuth();
429
- })();
430
- } else {
431
- setLoading(false);
432
- setIsCheckingAuth(false);
433
- }
434
- // eslint-disable-next-line react-hooks/exhaustive-deps
435
- }, [authState]); // Only run when authState changes (login/logout), not when checkAuth is recreated
436
-
437
- const directLogin: AuthContextData['directLogin'] = useCallback(
438
- async (
439
- mnemonic,
440
- username,
441
- email,
442
- expireMnemonicSeconds,
443
- expireWalletSeconds
444
- ) => {
445
- setLoading(true);
446
- const loginResult = await authService.directLogin(
447
- mnemonic,
448
- username,
449
- email
450
- );
451
- setLoading(false);
452
- if (
453
- typeof loginResult === 'object' &&
454
- 'token' in loginResult &&
455
- 'user' in loginResult &&
456
- 'wallet' in loginResult
457
- ) {
458
- setMnemonic(mnemonic, expireMnemonicSeconds);
459
- setUser(loginResult.user);
460
- setWallet(loginResult.wallet, expireWalletSeconds);
461
- setIsAuthenticated(true);
462
- setAuthState((prev) => prev + 1);
463
- localStorage.setItem('authToken', loginResult.token);
464
- localStorage.setItem('user', JSON.stringify(loginResult.user));
465
- await setUserSettingAndUpdateSettings({
466
- darkMode: loginResult.user.darkMode,
467
- currency: new CurrencyCode(loginResult.user.currency),
468
- timezone: new Timezone(loginResult.user.timezone),
469
- siteLanguage: loginResult.user.siteLanguage as CoreLanguageCode,
470
- email: new EmailString(loginResult.user.email),
471
- directChallenge: loginResult.user.directChallenge,
472
- ...(loginResult.user.displayName !== undefined
473
- ? { displayName: loginResult.user.displayName }
474
- : {}),
475
- });
476
- return loginResult;
477
- }
478
- return loginResult;
479
- },
480
- [authService, setMnemonic, setWallet, setUserSettingAndUpdateSettings]
481
- );
482
-
483
- const emailChallengeLogin: AuthContextData['emailChallengeLogin'] =
484
- useCallback(
485
- async (
486
- mnemonic,
487
- token,
488
- username,
489
- email,
490
- expireMnemonicSeconds,
491
- expireWalletSeconds
492
- ) => {
493
- setLoading(true);
494
- const loginResult = await authService.emailChallengeLogin(
495
- mnemonic,
496
- token,
497
- username,
498
- email
499
- );
500
- setLoading(false);
501
- if (
502
- typeof loginResult === 'object' &&
503
- 'token' in loginResult &&
504
- 'user' in loginResult &&
505
- 'wallet' in loginResult
506
- ) {
507
- setMnemonic(mnemonic, expireMnemonicSeconds);
508
- setUser(loginResult.user);
509
- setWallet(loginResult.wallet, expireWalletSeconds);
510
- setIsAuthenticated(true);
511
- setAuthState((prev) => prev + 1);
512
- localStorage.setItem('authToken', loginResult.token);
513
- localStorage.setItem('user', JSON.stringify(loginResult.user));
514
- await setUserSettingAndUpdateSettings({
515
- darkMode: loginResult.user.darkMode,
516
- currency: new CurrencyCode(loginResult.user.currency),
517
- timezone: new Timezone(loginResult.user.timezone),
518
- siteLanguage: loginResult.user.siteLanguage as CoreLanguageCode,
519
- email: new EmailString(loginResult.user.email),
520
- directChallenge: loginResult.user.directChallenge,
521
- ...(loginResult.user.displayName !== undefined
522
- ? { displayName: loginResult.user.displayName }
523
- : {}),
524
- });
525
- return loginResult;
526
- }
527
- return loginResult;
528
- },
529
- [authService, setMnemonic, setWallet, setUserSettingAndUpdateSettings]
530
- );
531
- const getPasswordLoginService = useCallback(() => {
532
- const eciesService: ECIESService = new ECIESService(eciesConfig);
533
- const aesGcmService = new AESGCMService();
534
- return new PasswordLoginService(
535
- aesGcmService,
536
- eciesService,
537
- new Pbkdf2Service(
538
- AppConstants.PBKDF2_PROFILES,
539
- AppConstants.ECIES,
540
- AppConstants.PBKDF2
541
- )
542
- );
543
- }, [eciesConfig]);
544
-
545
- const isBrowserPasswordLoginAvailable = useCallback(() => {
546
- const storedEncryptedPrivateKey = localStorage.getItem(
547
- PasswordLoginService.privateKeyStorageKey
548
- );
549
- return !!storedEncryptedPrivateKey;
550
- }, []);
551
-
552
- const passwordLogin: AuthContextData['passwordLogin'] = useCallback(
553
- async (password: SecureString, username?: string, email?: EmailString) => {
554
- if (!isBrowserPasswordLoginAvailable()) {
555
- return {
556
- error: tComponent<SuiteCoreStringKeyValue>(
557
- SuiteCoreComponentId,
558
- SuiteCoreStringKey.Error_Login_PasswordLoginNotSetup
559
- ),
560
- errorType: 'PasswordLoginNotSetup',
561
- };
562
- }
563
- setLoading(true);
564
- const passwordLoginService: PasswordLoginService =
565
- getPasswordLoginService();
566
- const { wallet, mnemonic } =
567
- await passwordLoginService.getWalletAndMnemonicFromLocalStorageBundle(
568
- password
569
- );
570
- const loginResult = await authService.directLogin(
571
- mnemonic,
572
- username,
573
- email
574
- );
575
- setLoading(false);
576
- setWallet(wallet);
577
- setMnemonic(mnemonic);
578
- // Set theme based on user's darkMode preference if login succeeded
579
- if ('user' in loginResult) {
580
- await setUserSettingAndUpdateSettings({
581
- darkMode: loginResult.user.darkMode,
582
- currency: new CurrencyCode(loginResult.user.currency),
583
- timezone: new Timezone(loginResult.user.timezone),
584
- siteLanguage: loginResult.user.siteLanguage as CoreLanguageCode,
585
- email: new EmailString(loginResult.user.email),
586
- directChallenge: loginResult.user.directChallenge,
587
- ...(loginResult.user.displayName !== undefined
588
- ? { displayName: loginResult.user.displayName }
589
- : {}),
590
- });
591
- }
592
- return loginResult;
593
- },
594
- [
595
- authService,
596
- getPasswordLoginService,
597
- setMnemonic,
598
- setWallet,
599
- tComponent,
600
- isBrowserPasswordLoginAvailable,
601
- setUserSettingAndUpdateSettings,
602
- ]
603
- );
604
-
605
- const refreshToken: AuthContextData['refreshToken'] =
606
- useCallback(async () => {
607
- try {
608
- const result = await authService.refreshToken();
609
- localStorage.setItem('authToken', result.token);
610
- localStorage.setItem('user', JSON.stringify(result.user));
611
- setUser(result.user);
612
- setIsAuthenticated(true);
613
- return result;
614
- } catch (error) {
615
- setUser(null);
616
- setIsAuthenticated(false);
617
- localStorage.removeItem('authToken');
618
- localStorage.removeItem('user');
619
- throw error;
620
- }
621
- }, [authService]);
622
-
623
- const register: AuthContextData['register'] = useCallback(
624
- async (
625
- username: string,
626
- email: string,
627
- timezone: string,
628
- password?: string,
629
- mnemonic?: string,
630
- displayName?: string,
631
- directChallenge?: boolean
632
- ) => {
633
- const registerResult = await authService.register(
634
- username,
635
- email,
636
- timezone,
637
- password,
638
- mnemonic,
639
- displayName,
640
- directChallenge
641
- );
642
- return registerResult as Awaited<ReturnType<AuthContextData['register']>>;
643
- },
644
- [authService]
645
- );
646
-
647
- const requestEmailLogin = useCallback(
648
- async (
649
- username?: string,
650
- email?: EmailString
651
- ): Promise<string | { error: string; errorType?: string }> => {
652
- setLoading(true);
653
- const result = await authService.requestEmailLogin(username, email);
654
- setLoading(false);
655
- return result;
656
- },
657
- [authService]
658
- );
659
-
660
- const setUpBrowserPasswordLogin = useCallback(
661
- async (
662
- mnemonic: SecureString,
663
- password: SecureString
664
- ): Promise<
665
- | { success: boolean; message: string }
666
- | { error: string; errorType?: string }
667
- > => {
668
- setLoading(true);
669
- const passwordLoginService: PasswordLoginService =
670
- getPasswordLoginService();
671
- try {
672
- const wallet =
673
- await passwordLoginService.setupPasswordLoginLocalStorageBundle(
674
- mnemonic,
675
- password
676
- );
677
- setLoading(false);
678
- setWallet(wallet);
679
- setMnemonic(mnemonic);
680
- return {
681
- success: true,
682
- message: tComponent<SuiteCoreStringKeyValue>(
683
- SuiteCoreComponentId,
684
- SuiteCoreStringKey.PasswordLogin_Setup_Success
685
- ),
686
- };
687
- } catch {
688
- setLoading(false);
689
- return {
690
- success: false,
691
- message: tComponent<SuiteCoreStringKeyValue>(
692
- SuiteCoreComponentId,
693
- SuiteCoreStringKey.PasswordLogin_Setup_Failure
694
- ),
695
- };
696
- }
697
- },
698
- [getPasswordLoginService, setMnemonic, setWallet, tComponent]
699
- );
700
-
701
- const backupCodeLogin = useCallback(
702
- async (
703
- identifier: string,
704
- code: string,
705
- isEmail: boolean,
706
- recoverMnemonic: boolean,
707
- newPassword?: string
708
- ): Promise<
709
- | {
710
- token: string;
711
- codeCount: number;
712
- mnemonic?: string;
713
- message?: string;
714
- }
715
- | { error: string; status?: number }
716
- > => {
717
- setLoading(true);
718
- const loginResult = await authService.backupCodeLogin(
719
- identifier,
720
- code,
721
- isEmail,
722
- recoverMnemonic,
723
- newPassword
724
- );
725
- setLoading(false);
726
- if (typeof loginResult === 'object' && 'token' in loginResult) {
727
- localStorage.setItem('authToken', loginResult.token);
728
- if (loginResult.user) {
729
- setUser(loginResult.user);
730
- setIsAuthenticated(true);
731
- await setUserSettingAndUpdateSettings({
732
- darkMode: loginResult.user.darkMode,
733
- currency: new CurrencyCode(loginResult.user.currency),
734
- timezone: new Timezone(loginResult.user.timezone),
735
- siteLanguage: loginResult.user.siteLanguage as CoreLanguageCode,
736
- email: new EmailString(loginResult.user.email),
737
- directChallenge: loginResult.user.directChallenge,
738
- ...(loginResult.user.displayName !== undefined
739
- ? { displayName: loginResult.user.displayName }
740
- : {}),
741
- });
742
- }
743
- setAuthState((prev) => prev + 1);
744
- return {
745
- token: loginResult.token,
746
- mnemonic: loginResult.mnemonic,
747
- message: loginResult.message,
748
- codeCount: loginResult.codeCount,
749
- };
750
- }
751
- return loginResult;
752
- },
753
- [authService, setUserSettingAndUpdateSettings]
754
- );
755
-
756
- const logout = useCallback(async () => {
757
- localStorage.removeItem('user');
758
- localStorage.removeItem('authToken');
759
- clearMnemonic();
760
- setUser(null);
761
- clearWallet();
762
- setIsAuthenticated(false);
763
- await setUserSettingAndUpdateSettings(undefined);
764
- setAuthState((prev) => prev + 1);
765
-
766
- // Call the optional navigation callback if provided
767
- if (onLogout) {
768
- onLogout();
769
- }
770
- }, [onLogout, clearMnemonic, clearWallet, setUserSettingAndUpdateSettings]);
771
-
772
- const verifyToken = useCallback(
773
- async (token: string) => {
774
- const requestUser = await authService.verifyToken(token);
775
- if (typeof requestUser === 'object' && 'error' in requestUser) {
776
- setIsAuthenticated(false);
777
- await setUserSettingAndUpdateSettings(undefined);
778
- return false;
779
- } else {
780
- setUser(requestUser);
781
- setIsAuthenticated(true);
782
- return true;
783
- }
784
- },
785
- [authService, setUserSettingAndUpdateSettings]
786
- );
787
-
788
- const changePassword = useCallback(
789
- async (
790
- currentPassword: string,
791
- newPassword: string
792
- ): Promise<
793
- | ISuccessMessage
794
- | {
795
- error: string;
796
- errorType?: string | undefined;
797
- }
798
- > => {
799
- if (!isBrowserPasswordLoginAvailable()) {
800
- return {
801
- error: tComponent<SuiteCoreStringKeyValue>(
802
- SuiteCoreComponentId,
803
- SuiteCoreStringKey.Error_Login_PasswordLoginNotSetup
804
- ),
805
- errorType: 'PasswordLoginNotSetup',
806
- };
807
- }
808
- setLoading(true);
809
- try {
810
- const passwordLoginService: PasswordLoginService =
811
- getPasswordLoginService();
812
- const { mnemonic, wallet } =
813
- await passwordLoginService.getWalletAndMnemonicFromLocalStorageBundle(
814
- new SecureString(currentPassword)
815
- );
816
- if (!mnemonic) {
817
- setLoading(false);
818
- return {
819
- error: tComponent<SuiteCoreStringKeyValue>(
820
- SuiteCoreComponentId,
821
- SuiteCoreStringKey.PasswordLogin_InvalidCurrentPassword
822
- ),
823
- errorType: 'InvalidCurrentPassword',
824
- };
825
- }
826
- await passwordLoginService.setupPasswordLoginLocalStorageBundle(
827
- mnemonic,
828
- new SecureString(newPassword)
829
- );
830
- setLoading(false);
831
- setWallet(wallet);
832
- setMnemonic(mnemonic);
833
- return {
834
- success: true,
835
- message: tComponent<SuiteCoreStringKeyValue>(
836
- SuiteCoreComponentId,
837
- SuiteCoreStringKey.PasswordChange_Success
838
- ),
839
- };
840
- } catch {
841
- setLoading(false);
842
- return { error: 'Password change failed' };
843
- }
844
- },
845
- [
846
- getPasswordLoginService,
847
- setMnemonic,
848
- setWallet,
849
- tComponent,
850
- isBrowserPasswordLoginAvailable,
851
- ]
852
- );
853
-
854
- const contextValue = useMemo(() => {
855
- const setUserAndIsAuthenticated = async (
856
- newUser: IRequestUserDTO | null
857
- ) => {
858
- setUser(newUser);
859
- setIsAuthenticated(!!newUser);
860
- };
861
-
862
- return {
863
- admin: isGlobalAdmin,
864
- authState,
865
- backupCodeLogin,
866
- changePassword,
867
- checkAuth,
868
- clearMnemonic,
869
- clearWallet,
870
- colorMode,
871
- currencyCode: userSettings?.currency,
872
- directLogin,
873
- emailChallengeLogin,
874
- getMnemonicRemainingTime,
875
- getWalletRemainingTime,
876
- isAuthenticated,
877
- isCheckingAuth,
878
- isBrowserPasswordLoginAvailable,
879
- loading,
880
- logout,
881
- mnemonic: mnemonicManager.value,
882
- mnemonicExpirationSeconds,
883
- passwordLogin,
884
- refreshToken,
885
- register,
886
- requestEmailLogin,
887
- serverPublicKey,
888
- setMnemonic,
889
- setMnemonicExpirationSeconds,
890
- setUpBrowserPasswordLogin,
891
- setUser: setUserAndIsAuthenticated,
892
- setUserSetting: setUserSettingAndUpdateSettings,
893
- setWallet,
894
- setWalletExpirationSeconds,
895
- setupTotp: () => authService.setupTotp(),
896
- confirmTotp: (code: string) => authService.confirmTotp(code),
897
- verifyTotpLogin: (pendingTotpToken: string, code: string) =>
898
- authService.verifyTotpLogin(pendingTotpToken, code),
899
- token,
900
- user: frontendUser,
901
- userData: user,
902
- userSettings,
903
- verifyToken,
904
- wallet: walletManager.value,
905
- walletExpirationSeconds,
906
- };
907
- // authenticatedApi is intentionally excluded as it's a stable reference from useMemo
908
- // eslint-disable-next-line react-hooks/exhaustive-deps
909
- }, [
910
- authState,
911
- backupCodeLogin,
912
- changePassword,
913
- checkAuth,
914
- clearMnemonic,
915
- clearWallet,
916
- colorMode,
917
- directLogin,
918
- emailChallengeLogin,
919
- frontendUser,
920
- getMnemonicRemainingTime,
921
- getWalletRemainingTime,
922
- isAuthenticated,
923
- isCheckingAuth,
924
- isGlobalAdmin,
925
- isBrowserPasswordLoginAvailable,
926
- loading,
927
- logout,
928
- mnemonicManager.value,
929
- mnemonicExpirationSeconds,
930
- passwordLogin,
931
- refreshToken,
932
- register,
933
- requestEmailLogin,
934
- serverPublicKey,
935
- setMnemonic,
936
- setMnemonicExpirationSeconds,
937
- setUpBrowserPasswordLogin,
938
- setUserSettingAndUpdateSettings,
939
- setWallet,
940
- setWalletExpirationSeconds,
941
- token,
942
- user,
943
- userSettings,
944
- verifyToken,
945
- walletManager.value,
946
- walletExpirationSeconds,
947
- ]);
948
-
949
- return (
950
- <AuthContext.Provider value={contextValue}>{children}</AuthContext.Provider>
951
- );
952
- };
953
-
954
- export const AuthProvider = ({
955
- children,
956
- baseUrl,
957
- constants,
958
- eciesConfig,
959
- onLogout,
960
- emailDomain,
961
- }: AuthProviderProps) => {
962
- return (
963
- <AuthProviderInner
964
- baseUrl={baseUrl}
965
- constants={constants}
966
- eciesConfig={eciesConfig}
967
- onLogout={onLogout}
968
- emailDomain={emailDomain}
969
- >
970
- {children}
971
- </AuthProviderInner>
972
- );
973
- };
974
-
975
- export const useAuth = () => {
976
- return useContext(AuthContext);
977
- };