@oxyhq/core 5.5.0 → 6.0.0

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 (181) hide show
  1. package/dist/cjs/.tsbuildinfo +1 -1
  2. package/dist/cjs/HttpService.js +6 -3
  3. package/dist/cjs/OxyServices.base.js +7 -102
  4. package/dist/cjs/boot/coldBootV2.js +350 -0
  5. package/dist/cjs/boot/deviceBootReturn.js +152 -0
  6. package/dist/cjs/crypto/keyManager.js +95 -0
  7. package/dist/cjs/i18n/locales/en-US.json +13 -1
  8. package/dist/cjs/i18n/locales/es-ES.json +13 -1
  9. package/dist/cjs/i18n/locales/locales/en-US.json +13 -1
  10. package/dist/cjs/i18n/locales/locales/es-ES.json +13 -1
  11. package/dist/cjs/index.js +47 -44
  12. package/dist/cjs/mixins/OxyServices.accounts.js +6 -13
  13. package/dist/cjs/mixins/OxyServices.auth.js +66 -201
  14. package/dist/cjs/mixins/OxyServices.authorizedApps.js +38 -0
  15. package/dist/cjs/mixins/OxyServices.deviceBoot.js +119 -0
  16. package/dist/cjs/mixins/index.js +13 -17
  17. package/dist/cjs/session/SessionClient.js +40 -1
  18. package/dist/cjs/session/authStateStore.js +284 -0
  19. package/dist/cjs/session/refresh.js +264 -0
  20. package/dist/cjs/utils/accountUtils.js +1 -55
  21. package/dist/cjs/utils/authWebUrl.js +6 -15
  22. package/dist/cjs/utils/fapiAutoDetect.js +16 -64
  23. package/dist/cjs/utils/platform.js +19 -0
  24. package/dist/cjs/utils/ssoBounce.js +15 -362
  25. package/dist/cjs/utils/validationUtils.js +57 -0
  26. package/dist/esm/.tsbuildinfo +1 -1
  27. package/dist/esm/HttpService.js +6 -3
  28. package/dist/esm/OxyServices.base.js +7 -102
  29. package/dist/esm/boot/coldBootV2.js +344 -0
  30. package/dist/esm/boot/deviceBootReturn.js +146 -0
  31. package/dist/esm/crypto/keyManager.js +95 -0
  32. package/dist/esm/i18n/locales/en-US.json +13 -1
  33. package/dist/esm/i18n/locales/es-ES.json +13 -1
  34. package/dist/esm/i18n/locales/locales/en-US.json +13 -1
  35. package/dist/esm/i18n/locales/locales/es-ES.json +13 -1
  36. package/dist/esm/index.js +28 -18
  37. package/dist/esm/mixins/OxyServices.accounts.js +6 -13
  38. package/dist/esm/mixins/OxyServices.auth.js +66 -201
  39. package/dist/esm/mixins/OxyServices.authorizedApps.js +35 -0
  40. package/dist/esm/mixins/OxyServices.deviceBoot.js +116 -0
  41. package/dist/esm/mixins/index.js +13 -17
  42. package/dist/esm/session/SessionClient.js +40 -1
  43. package/dist/esm/session/authStateStore.js +278 -0
  44. package/dist/esm/session/refresh.js +257 -0
  45. package/dist/esm/utils/accountUtils.js +0 -53
  46. package/dist/esm/utils/authWebUrl.js +6 -14
  47. package/dist/esm/utils/fapiAutoDetect.js +16 -63
  48. package/dist/esm/utils/platform.js +18 -0
  49. package/dist/esm/utils/ssoBounce.js +14 -345
  50. package/dist/esm/utils/validationUtils.js +56 -0
  51. package/dist/types/.tsbuildinfo +1 -1
  52. package/dist/types/HttpService.d.ts +13 -0
  53. package/dist/types/OxyServices.base.d.ts +0 -52
  54. package/dist/types/OxyServices.d.ts +0 -25
  55. package/dist/types/boot/coldBootV2.d.ts +76 -0
  56. package/dist/types/boot/deviceBootReturn.d.ts +83 -0
  57. package/dist/types/crypto/keyManager.d.ts +21 -0
  58. package/dist/types/index.d.ts +15 -21
  59. package/dist/types/mixins/OxyServices.accounts.d.ts +0 -2
  60. package/dist/types/mixins/OxyServices.analytics.d.ts +0 -2
  61. package/dist/types/mixins/OxyServices.appData.d.ts +0 -2
  62. package/dist/types/mixins/OxyServices.assets.d.ts +0 -2
  63. package/dist/types/mixins/OxyServices.auth.d.ts +35 -77
  64. package/dist/types/mixins/{OxyServices.redirect.d.ts → OxyServices.authorizedApps.d.ts} +35 -33
  65. package/dist/types/mixins/OxyServices.civic.d.ts +0 -2
  66. package/dist/types/mixins/OxyServices.connectedApps.d.ts +0 -2
  67. package/dist/types/mixins/OxyServices.contacts.d.ts +0 -2
  68. package/dist/types/mixins/OxyServices.deviceBoot.d.ts +110 -0
  69. package/dist/types/mixins/OxyServices.devices.d.ts +0 -2
  70. package/dist/types/mixins/OxyServices.features.d.ts +0 -2
  71. package/dist/types/mixins/OxyServices.identity.d.ts +0 -2
  72. package/dist/types/mixins/OxyServices.language.d.ts +0 -2
  73. package/dist/types/mixins/OxyServices.links.d.ts +0 -2
  74. package/dist/types/mixins/OxyServices.location.d.ts +0 -2
  75. package/dist/types/mixins/OxyServices.nodes.d.ts +0 -2
  76. package/dist/types/mixins/OxyServices.payment.d.ts +0 -2
  77. package/dist/types/mixins/OxyServices.privacy.d.ts +0 -2
  78. package/dist/types/mixins/OxyServices.reputation.d.ts +0 -2
  79. package/dist/types/mixins/OxyServices.security.d.ts +0 -2
  80. package/dist/types/mixins/OxyServices.topics.d.ts +0 -2
  81. package/dist/types/mixins/OxyServices.user.d.ts +0 -2
  82. package/dist/types/mixins/OxyServices.utility.d.ts +0 -2
  83. package/dist/types/mixins/index.d.ts +6 -9
  84. package/dist/types/models/interfaces.d.ts +0 -67
  85. package/dist/types/session/SessionClient.d.ts +25 -0
  86. package/dist/types/session/authStateStore.d.ts +119 -0
  87. package/dist/types/session/refresh.d.ts +93 -0
  88. package/dist/types/utils/accountUtils.d.ts +0 -14
  89. package/dist/types/utils/authWebUrl.d.ts +6 -12
  90. package/dist/types/utils/fapiAutoDetect.d.ts +15 -38
  91. package/dist/types/utils/platform.d.ts +14 -0
  92. package/dist/types/utils/ssoBounce.d.ts +14 -280
  93. package/dist/types/utils/validationUtils.d.ts +15 -0
  94. package/package.json +2 -2
  95. package/src/HttpService.ts +19 -3
  96. package/src/OxyServices.base.ts +7 -112
  97. package/src/OxyServices.ts +0 -38
  98. package/src/boot/__tests__/coldBootV2.test.ts +317 -0
  99. package/src/boot/__tests__/deviceBootReturn.test.ts +158 -0
  100. package/src/boot/coldBootV2.ts +426 -0
  101. package/src/boot/deviceBootReturn.ts +195 -0
  102. package/src/crypto/__tests__/sharedDeviceToken.test.ts +24 -0
  103. package/src/crypto/keyManager.ts +101 -0
  104. package/src/i18n/locales/en-US.json +13 -1
  105. package/src/i18n/locales/es-ES.json +13 -1
  106. package/src/index.ts +74 -65
  107. package/src/mixins/OxyServices.accounts.ts +6 -13
  108. package/src/mixins/OxyServices.auth.ts +78 -253
  109. package/src/mixins/OxyServices.authorizedApps.ts +75 -0
  110. package/src/mixins/OxyServices.deviceBoot.ts +146 -0
  111. package/src/mixins/__tests__/OxyServices.deviceBoot.test.ts +107 -0
  112. package/src/mixins/__tests__/accounts.test.ts +17 -44
  113. package/src/mixins/__tests__/authorizedApps.test.ts +63 -0
  114. package/src/mixins/__tests__/passwordSignIn.test.ts +91 -0
  115. package/src/mixins/index.ts +16 -22
  116. package/src/models/interfaces.ts +0 -79
  117. package/src/session/SessionClient.ts +52 -1
  118. package/src/session/__tests__/SessionClient.additive.test.ts +92 -0
  119. package/src/session/__tests__/SessionClient.rest.test.ts +25 -0
  120. package/src/session/__tests__/SessionClient.state.test.ts +18 -5
  121. package/src/session/__tests__/authStateStore.test.ts +209 -0
  122. package/src/session/__tests__/refresh.test.ts +256 -0
  123. package/src/session/authStateStore.ts +335 -0
  124. package/src/session/refresh.ts +334 -0
  125. package/src/utils/__tests__/authWebUrl.test.ts +5 -29
  126. package/src/utils/__tests__/fapiAutoDetect.test.ts +5 -126
  127. package/src/utils/__tests__/validationUtils.test.ts +30 -0
  128. package/src/utils/accountUtils.ts +0 -62
  129. package/src/utils/authWebUrl.ts +6 -15
  130. package/src/utils/fapiAutoDetect.ts +16 -60
  131. package/src/utils/platform.ts +21 -0
  132. package/src/utils/ssoBounce.ts +14 -393
  133. package/src/utils/validationUtils.ts +62 -0
  134. package/dist/cjs/AuthManager.js +0 -1110
  135. package/dist/cjs/AuthManagerTypes.js +0 -13
  136. package/dist/cjs/CrossDomainAuth.js +0 -206
  137. package/dist/cjs/mixins/OxyServices.fedcm.js +0 -823
  138. package/dist/cjs/mixins/OxyServices.redirect.js +0 -95
  139. package/dist/cjs/mixins/OxyServices.silent.js +0 -204
  140. package/dist/cjs/mixins/OxyServices.sso.js +0 -208
  141. package/dist/cjs/utils/ssoEstablish.js +0 -110
  142. package/dist/cjs/utils/ssoReturn.js +0 -275
  143. package/dist/esm/AuthManager.js +0 -1105
  144. package/dist/esm/AuthManagerTypes.js +0 -12
  145. package/dist/esm/CrossDomainAuth.js +0 -201
  146. package/dist/esm/mixins/OxyServices.fedcm.js +0 -821
  147. package/dist/esm/mixins/OxyServices.redirect.js +0 -92
  148. package/dist/esm/mixins/OxyServices.silent.js +0 -202
  149. package/dist/esm/mixins/OxyServices.sso.js +0 -204
  150. package/dist/esm/utils/ssoEstablish.js +0 -107
  151. package/dist/esm/utils/ssoReturn.js +0 -271
  152. package/dist/types/AuthManager.d.ts +0 -380
  153. package/dist/types/AuthManagerTypes.d.ts +0 -81
  154. package/dist/types/CrossDomainAuth.d.ts +0 -164
  155. package/dist/types/mixins/OxyServices.fedcm.d.ts +0 -331
  156. package/dist/types/mixins/OxyServices.silent.d.ts +0 -132
  157. package/dist/types/mixins/OxyServices.sso.d.ts +0 -138
  158. package/dist/types/utils/ssoEstablish.d.ts +0 -85
  159. package/dist/types/utils/ssoReturn.d.ts +0 -156
  160. package/src/AuthManager.ts +0 -1269
  161. package/src/AuthManagerTypes.ts +0 -86
  162. package/src/CrossDomainAuth.ts +0 -243
  163. package/src/__tests__/authManager.cookiePath.test.ts +0 -390
  164. package/src/__tests__/authManager.security.test.ts +0 -377
  165. package/src/__tests__/crossDomainAuth.test.ts +0 -116
  166. package/src/__tests__/establishDeviceRefreshSlot.test.ts +0 -221
  167. package/src/mixins/OxyServices.fedcm.ts +0 -1026
  168. package/src/mixins/OxyServices.redirect.ts +0 -122
  169. package/src/mixins/OxyServices.silent.ts +0 -272
  170. package/src/mixins/OxyServices.sso.ts +0 -261
  171. package/src/mixins/__tests__/constructorAuthWebUrl.test.ts +0 -85
  172. package/src/mixins/__tests__/fedcm.test.ts +0 -667
  173. package/src/mixins/__tests__/sessionBaseUrl.test.ts +0 -61
  174. package/src/mixins/__tests__/silent.test.ts +0 -102
  175. package/src/mixins/__tests__/sso.test.ts +0 -228
  176. package/src/utils/__tests__/consumeSsoReturn.test.ts +0 -816
  177. package/src/utils/__tests__/ssoBounce.test.ts +0 -219
  178. package/src/utils/__tests__/ssoEstablish.test.ts +0 -204
  179. package/src/utils/__tests__/ssoReturn.test.ts +0 -276
  180. package/src/utils/ssoEstablish.ts +0 -174
  181. package/src/utils/ssoReturn.ts +0 -389
@@ -53,6 +53,11 @@ const STORAGE_KEYS = {
53
53
  SHARED_PUBLIC_KEY: 'oxy_shared_identity_public_key',
54
54
  SHARED_SESSION_TOKEN: 'oxy_shared_session_token',
55
55
  SHARED_SESSION_ID: 'oxy_shared_session_id',
56
+ // Opaque device-attribution token, shared across all Oxy apps on one device
57
+ // so they all resolve to a SINGLE server-side DeviceSession (device-first
58
+ // session model). Add-only: it never carries session state, only attributes
59
+ // a newly-credentialed session to the shared device set.
60
+ SHARED_DEVICE_TOKEN: 'oxy_shared_device_token',
56
61
  };
57
62
  /**
58
63
  * iOS Keychain Access Group for sharing identities across Oxy apps
@@ -540,6 +545,96 @@ export class KeyManager {
540
545
  return false;
541
546
  }
542
547
  }
548
+ /**
549
+ * Store the opaque device-attribution token in the SHARED keychain so every
550
+ * Oxy app on this device reads the SAME token and therefore resolves to one
551
+ * server-side DeviceSession.
552
+ *
553
+ * Mirrors the shared-session storage options exactly (iOS keychain access
554
+ * group `group.so.oxy.shared`; Android shared secure store). Native-only —
555
+ * a no-op on web (the shared keychain does not exist there; web persists its
556
+ * deviceToken in the per-origin {@link AuthStateStore} instead).
557
+ */
558
+ static async setSharedDeviceToken(deviceToken) {
559
+ if (isWebPlatform()) {
560
+ return; // Not supported on web
561
+ }
562
+ try {
563
+ const store = await initSecureStore();
564
+ if (isIOS()) {
565
+ const opts = {
566
+ keychainAccessible: store.WHEN_UNLOCKED,
567
+ keychainAccessGroup: IOS_KEYCHAIN_GROUP,
568
+ };
569
+ await store.setItemAsync(STORAGE_KEYS.SHARED_DEVICE_TOKEN, deviceToken, opts);
570
+ }
571
+ else if (isAndroid()) {
572
+ await store.setItemAsync(STORAGE_KEYS.SHARED_DEVICE_TOKEN, deviceToken);
573
+ }
574
+ if (isDev()) {
575
+ logger.debug('Shared device token stored successfully', { component: 'KeyManager' });
576
+ }
577
+ }
578
+ catch (error) {
579
+ if (isDev()) {
580
+ logger.error('Failed to store shared device token', error, { component: 'KeyManager' });
581
+ }
582
+ throw error;
583
+ }
584
+ }
585
+ /**
586
+ * Read the shared device-attribution token, or `null` when none is set (or
587
+ * on web). Mirrors {@link getSharedSession}'s keychain-access-group read.
588
+ */
589
+ static async getSharedDeviceToken() {
590
+ if (isWebPlatform()) {
591
+ return null;
592
+ }
593
+ try {
594
+ const store = await initSecureStore();
595
+ if (isIOS()) {
596
+ const opts = { keychainAccessGroup: IOS_KEYCHAIN_GROUP };
597
+ return await store.getItemAsync(STORAGE_KEYS.SHARED_DEVICE_TOKEN, opts);
598
+ }
599
+ if (isAndroid()) {
600
+ return await store.getItemAsync(STORAGE_KEYS.SHARED_DEVICE_TOKEN);
601
+ }
602
+ return null;
603
+ }
604
+ catch (error) {
605
+ if (isDev()) {
606
+ logger.warn('Failed to get shared device token', { component: 'KeyManager' }, error);
607
+ }
608
+ return null;
609
+ }
610
+ }
611
+ /**
612
+ * Delete the shared device-attribution token (device signout-all). Best-effort:
613
+ * a keychain failure is logged, not thrown, so it cannot block a sign-out.
614
+ */
615
+ static async clearSharedDeviceToken() {
616
+ if (isWebPlatform()) {
617
+ return;
618
+ }
619
+ try {
620
+ const store = await initSecureStore();
621
+ if (isIOS()) {
622
+ const opts = { keychainAccessGroup: IOS_KEYCHAIN_GROUP };
623
+ await store.deleteItemAsync(STORAGE_KEYS.SHARED_DEVICE_TOKEN, opts);
624
+ }
625
+ else if (isAndroid()) {
626
+ await store.deleteItemAsync(STORAGE_KEYS.SHARED_DEVICE_TOKEN);
627
+ }
628
+ if (isDev()) {
629
+ logger.debug('Shared device token cleared successfully', { component: 'KeyManager' });
630
+ }
631
+ }
632
+ catch (error) {
633
+ if (isDev()) {
634
+ logger.error('Failed to clear shared device token', error, { component: 'KeyManager' });
635
+ }
636
+ }
637
+ }
543
638
  // ==================== END SHARED IDENTITY METHODS ====================
544
639
  /**
545
640
  * Atomically persist a key pair to secure storage with verification + backup.
@@ -2,6 +2,13 @@
2
2
  "signin": {
3
3
  "title": "Sign In",
4
4
  "subtitle": "Sign in to continue your journey",
5
+ "chooser": {
6
+ "title": "Choose an account",
7
+ "subtitle": "Continue as an account below, or use another.",
8
+ "signedIn": "Signed in",
9
+ "useAnother": "Use another account",
10
+ "continueAs": "Continue as {{name}}"
11
+ },
5
12
  "addAccountTitle": "Add Another Account",
6
13
  "addAccountSubtitle": "Sign in with another account",
7
14
  "username": {
@@ -602,6 +609,7 @@
602
609
  "editProfile": {
603
610
  "title": "Edit Profile",
604
611
  "subtitle": "Manage your profile and preferences",
612
+ "notSet": "Not set",
605
613
  "sections": {
606
614
  "profilePicture": "Profile Picture",
607
615
  "basicInfo": "Basic Information",
@@ -610,6 +618,9 @@
610
618
  "security": "Security"
611
619
  },
612
620
  "items": {
621
+ "avatar": {
622
+ "subtitle": "Update your profile photo"
623
+ },
613
624
  "displayName": {
614
625
  "title": "Display Name",
615
626
  "subtitle": "This is how your name will appear to others",
@@ -617,7 +628,8 @@
617
628
  "firstName": "First Name",
618
629
  "firstNamePlaceholder": "Enter first name",
619
630
  "lastName": "Last Name",
620
- "lastNamePlaceholder": "Enter last name (optional)"
631
+ "lastNamePlaceholder": "Enter last name (optional)",
632
+ "invalidChars": "Use letters and spaces only"
621
633
  },
622
634
  "username": {
623
635
  "title": "Username",
@@ -2,6 +2,13 @@
2
2
  "signin": {
3
3
  "title": "Iniciar sesión",
4
4
  "subtitle": "Inicia sesión para continuar",
5
+ "chooser": {
6
+ "title": "Elige una cuenta",
7
+ "subtitle": "Continúa con una de tus cuentas o usa otra.",
8
+ "signedIn": "Sesión activa",
9
+ "useAnother": "Usar otra cuenta",
10
+ "continueAs": "Continuar como {{name}}"
11
+ },
5
12
  "addAccountTitle": "Agregar otra cuenta",
6
13
  "addAccountSubtitle": "Inicia sesión con otra cuenta",
7
14
  "username": {
@@ -152,6 +159,7 @@
152
159
  "editProfile": {
153
160
  "title": "Editar perfil",
154
161
  "subtitle": "Gestiona tu perfil y preferencias",
162
+ "notSet": "Sin definir",
155
163
  "sections": {
156
164
  "profilePicture": "Foto de perfil",
157
165
  "basicInfo": "Información básica",
@@ -160,6 +168,9 @@
160
168
  "security": "Seguridad"
161
169
  },
162
170
  "items": {
171
+ "avatar": {
172
+ "subtitle": "Actualiza tu foto de perfil"
173
+ },
163
174
  "displayName": {
164
175
  "title": "Nombre para mostrar",
165
176
  "subtitle": "Así aparecerá tu nombre para los demás",
@@ -167,7 +178,8 @@
167
178
  "firstName": "Nombre",
168
179
  "firstNamePlaceholder": "Introduce tu nombre",
169
180
  "lastName": "Apellido",
170
- "lastNamePlaceholder": "Introduce tu apellido (opcional)"
181
+ "lastNamePlaceholder": "Introduce tu apellido (opcional)",
182
+ "invalidChars": "Usa solo letras y espacios"
171
183
  },
172
184
  "username": {
173
185
  "title": "Usuario",
@@ -2,6 +2,13 @@
2
2
  "signin": {
3
3
  "title": "Sign In",
4
4
  "subtitle": "Sign in to continue your journey",
5
+ "chooser": {
6
+ "title": "Choose an account",
7
+ "subtitle": "Continue as an account below, or use another.",
8
+ "signedIn": "Signed in",
9
+ "useAnother": "Use another account",
10
+ "continueAs": "Continue as {{name}}"
11
+ },
5
12
  "addAccountTitle": "Add Another Account",
6
13
  "addAccountSubtitle": "Sign in with another account",
7
14
  "username": {
@@ -602,6 +609,7 @@
602
609
  "editProfile": {
603
610
  "title": "Edit Profile",
604
611
  "subtitle": "Manage your profile and preferences",
612
+ "notSet": "Not set",
605
613
  "sections": {
606
614
  "profilePicture": "Profile Picture",
607
615
  "basicInfo": "Basic Information",
@@ -610,6 +618,9 @@
610
618
  "security": "Security"
611
619
  },
612
620
  "items": {
621
+ "avatar": {
622
+ "subtitle": "Update your profile photo"
623
+ },
613
624
  "displayName": {
614
625
  "title": "Display Name",
615
626
  "subtitle": "This is how your name will appear to others",
@@ -617,7 +628,8 @@
617
628
  "firstName": "First Name",
618
629
  "firstNamePlaceholder": "Enter first name",
619
630
  "lastName": "Last Name",
620
- "lastNamePlaceholder": "Enter last name (optional)"
631
+ "lastNamePlaceholder": "Enter last name (optional)",
632
+ "invalidChars": "Use letters and spaces only"
621
633
  },
622
634
  "username": {
623
635
  "title": "Username",
@@ -2,6 +2,13 @@
2
2
  "signin": {
3
3
  "title": "Iniciar sesión",
4
4
  "subtitle": "Inicia sesión para continuar",
5
+ "chooser": {
6
+ "title": "Elige una cuenta",
7
+ "subtitle": "Continúa con una de tus cuentas o usa otra.",
8
+ "signedIn": "Sesión activa",
9
+ "useAnother": "Usar otra cuenta",
10
+ "continueAs": "Continuar como {{name}}"
11
+ },
5
12
  "addAccountTitle": "Agregar otra cuenta",
6
13
  "addAccountSubtitle": "Inicia sesión con otra cuenta",
7
14
  "username": {
@@ -152,6 +159,7 @@
152
159
  "editProfile": {
153
160
  "title": "Editar perfil",
154
161
  "subtitle": "Gestiona tu perfil y preferencias",
162
+ "notSet": "Sin definir",
155
163
  "sections": {
156
164
  "profilePicture": "Foto de perfil",
157
165
  "basicInfo": "Información básica",
@@ -160,6 +168,9 @@
160
168
  "security": "Seguridad"
161
169
  },
162
170
  "items": {
171
+ "avatar": {
172
+ "subtitle": "Actualiza tu foto de perfil"
173
+ },
163
174
  "displayName": {
164
175
  "title": "Nombre para mostrar",
165
176
  "subtitle": "Así aparecerá tu nombre para los demás",
@@ -167,7 +178,8 @@
167
178
  "firstName": "Nombre",
168
179
  "firstNamePlaceholder": "Introduce tu nombre",
169
180
  "lastName": "Apellido",
170
- "lastNamePlaceholder": "Introduce tu apellido (opcional)"
181
+ "lastNamePlaceholder": "Introduce tu apellido (opcional)",
182
+ "invalidChars": "Usa solo letras y espacios"
171
183
  },
172
184
  "username": {
173
185
  "title": "Usuario",
package/dist/esm/index.js CHANGED
@@ -23,11 +23,6 @@ import './crypto/polyfill.js';
23
23
  // ---------------------------------------------------------------------------
24
24
  export { OxyServices, OxyAuthenticationError, OxyAuthenticationTimeoutError } from './OxyServices.js';
25
25
  export { OXY_CLOUD_URL, oxyClient } from './OxyServices.js';
26
- // ---------------------------------------------------------------------------
27
- // Authentication
28
- // ---------------------------------------------------------------------------
29
- export { AuthManager, createAuthManager } from './AuthManager.js';
30
- export { CrossDomainAuth, createCrossDomainAuth } from './CrossDomainAuth.js';
31
26
  export { ServiceCredentialMismatchError } from './mixins/OxyServices.auth.js';
32
27
  export { OxyAppDataIdentifierError } from './mixins/OxyServices.appData.js';
33
28
  // ---------------------------------------------------------------------------
@@ -80,7 +75,7 @@ export { SUPPORTED_LANGUAGES, getLanguageMetadata, getLanguageName, getNativeLan
80
75
  // ---------------------------------------------------------------------------
81
76
  // Platform detection
82
77
  // ---------------------------------------------------------------------------
83
- export { getPlatformOS, setPlatformOS, isWeb, isNative, isIOS, isAndroid, } from './utils/platform.js';
78
+ export { getPlatformOS, setPlatformOS, isWeb, isNative, isIOS, isAndroid, isWebBrowser, } from './utils/platform.js';
84
79
  // ---------------------------------------------------------------------------
85
80
  // Colour / theme utilities
86
81
  // ---------------------------------------------------------------------------
@@ -105,7 +100,7 @@ export { retryAsync } from './utils/asyncUtils.js';
105
100
  // ---------------------------------------------------------------------------
106
101
  // Validation
107
102
  // ---------------------------------------------------------------------------
108
- export { EMAIL_REGEX, USERNAME_REGEX, PASSWORD_REGEX, isValidEmail, isValidUsername, isValidPassword, isRequiredString, isRequiredNumber, isRequiredBoolean, isValidArray, isValidObject, isValidUUID, isValidURL, isValidDate, isValidFileSize, isValidFileType, sanitizeString, sanitizeHTML, isValidObjectId, validateAndSanitizeUserInput, } from './utils/validationUtils.js';
103
+ export { EMAIL_REGEX, USERNAME_REGEX, PASSWORD_REGEX, isValidEmail, isValidUsername, isValidPassword, isValidDisplayName, isRequiredString, isRequiredNumber, isRequiredBoolean, isValidArray, isValidObject, isValidUUID, isValidURL, isValidDate, isValidFileSize, isValidFileType, sanitizeString, sanitizeHTML, isValidObjectId, validateAndSanitizeUserInput, } from './utils/validationUtils.js';
109
104
  // ---------------------------------------------------------------------------
110
105
  // Logging
111
106
  // ---------------------------------------------------------------------------
@@ -117,19 +112,20 @@ export { updateAvatarVisibility } from './utils/avatarUtils.js';
117
112
  // ---------------------------------------------------------------------------
118
113
  // Accounts
119
114
  // ---------------------------------------------------------------------------
120
- export { buildAccountsArray, createQuickAccount, getAccountDisplayName, getAccountFallbackHandle, formatPublicKeyHandle, mergeAccountsFromRefreshAll, getAccountColor, } from './utils/accountUtils.js';
115
+ export { buildAccountsArray, createQuickAccount, getAccountDisplayName, getAccountFallbackHandle, formatPublicKeyHandle, getAccountColor, } from './utils/accountUtils.js';
121
116
  // ---------------------------------------------------------------------------
122
- // Cross-domain SSO infrastructure
117
+ // Registrable-domain + central-IdP-apex helpers.
118
+ //
119
+ // The client SSO-bounce / silent-iframe / FedCM machinery was removed in the
120
+ // device-first cutover. These three symbols survive because the api SSO surface
121
+ // and the IdP (both lista B, gated on the ecosystem bump) still import them:
122
+ // `registrableApex` (eTLD+1), `CENTRAL_IDP_APEX`, and the `SSO_CALLBACK_PATH`
123
+ // constant. `@oxyhq/core/server` re-exports `registrableApex` + `SSO_CALLBACK_PATH`
124
+ // for the api; the IdP imports all three from here.
123
125
  // ---------------------------------------------------------------------------
124
- export { autoDetectAuthWebUrl, registrableApex } from './utils/fapiAutoDetect.js';
125
- // Central cross-domain SSO (opaque single-use code bounce via auth.oxy.so)
126
- export { CENTRAL_AUTH_URL, CENTRAL_IDP_APEX, resolveCentralAuthUrl } from './utils/authWebUrl.js';
127
- export { parseSsoReturnFragment, consumeSsoReturn } from './utils/ssoReturn.js';
128
- export { generateSsoState } from './mixins/OxyServices.sso.js';
129
- // Post-claim durable-session establish hop (web device-flow / QR sign-in).
130
- export { establishIdpSessionAfterClaim } from './utils/ssoEstablish.js';
131
- // SSO bounce — per-origin sessionStorage keys, bounce URL builder, predicates
132
- export { SSO_CALLBACK_PATH, SSO_GUARD_TTL_MS, ssoStateKey, ssoGuardKey, ssoDestKey, ssoNoSessionKey, ssoAttemptedKey, ssoPriorSessionKey, ssoSignedOutKey, ssoOutcomeKey, ssoCallbackBootstrapKey, ssoNavigate, getSsoCallbackBootstrapScript, buildSsoBounceUrl, isCentralIdPOrigin, guardActive, silentRestoreSuppressed, allowSsoBounce, } from './utils/ssoBounce.js';
126
+ export { registrableApex } from './utils/fapiAutoDetect.js';
127
+ export { CENTRAL_AUTH_URL, CENTRAL_IDP_APEX } from './utils/authWebUrl.js';
128
+ export { SSO_CALLBACK_PATH } from './utils/ssoBounce.js';
133
129
  export { runColdBoot } from './utils/coldBoot.js';
134
130
  // ---------------------------------------------------------------------------
135
131
  // Session sync (device-scoped multi-account session client)
@@ -143,6 +139,20 @@ export { SessionClient } from './session/SessionClient.js';
143
139
  export { createSessionClientHost } from './session/sessionClientHost.js';
144
140
  export { createSessionClient } from './session/createSessionClient.js';
145
141
  export { deviceStateToClientSessions, activeSessionIdOf, activeUserOf, accountIdsOf, } from './session/projectSessionState.js';
142
+ // ---------------------------------------------------------------------------
143
+ // Device-first session machinery (auth centralization, wave 1) — additive.
144
+ // Persisted auth-state store, the unified refresh handler + scheduler, the
145
+ // cold-boot v2 runner, and the device-boot return-fragment consumer. Built ON
146
+ // the existing `runColdBoot` primitive + `SessionClient`; the legacy
147
+ // FedCM/SSO/CrossDomainAuth surface is untouched (cutover happens in F4).
148
+ // ---------------------------------------------------------------------------
149
+ export { createWebAuthStateStore, createNativeAuthStateStore, createMemoryAuthStateStore, AUTH_STATE_STORAGE_KEY, DEVICE_TOKEN_STORAGE_KEY, } from './session/authStateStore.js';
150
+ export { refreshPersistedSession, createAuthRefreshHandler, installAuthRefreshHandler, startTokenRefreshScheduler, TOKEN_REFRESH_LEAD_MS, } from './session/refresh.js';
151
+ export { runSessionColdBoot, createBrowserColdBootDom, isSameApex, BOOT_ATTEMPTED_KEY, } from './boot/coldBootV2.js';
152
+ export { consumeDeviceBootReturn, parseDeviceBootFragment, hashHasBootFragment, BOOT_FRAGMENT_PARAM, BOOT_STATE_SESSION_KEY, } from './boot/deviceBootReturn.js';
153
+ // The web-session result contract (`WebSessionResult`) is owned by
154
+ // `@oxyhq/contracts` — import it directly from there; `@oxyhq/core` does not
155
+ // re-export contract types.
146
156
  // API response contracts (request/response Zod schemas + inferred types) live in
147
157
  // `@oxyhq/contracts` — the single source of truth shared by the backend and every
148
158
  // client SDK. Import them directly from `@oxyhq/contracts`; `@oxyhq/core` does NOT
@@ -83,22 +83,15 @@ export function OxyServicesAccountsMixin(Base) {
83
83
  const res = await this.makeRequest('POST', `/accounts/${encodeURIComponent(accountId)}/switch`, undefined, { cache: false });
84
84
  // Plant the freshly minted session as the ACTIVE session, mirroring
85
85
  // `claimSessionByToken` / `verifyChallenge`: the response body carries
86
- // the first access token. The device refresh cookie is established below.
86
+ // the first access token.
87
87
  if (res?.accessToken) {
88
88
  this.setTokens(res.accessToken);
89
89
  }
90
- // Register the switched session in the device's multi-account set by
91
- // establishing its first-party refresh cookie. This MUST be a separate
92
- // call to `POST /auth/session` (the shared `establishDeviceRefreshSlot`
93
- // primitive): the switch route is at `/accounts/*`, outside the
94
- // `oxy_rt_<authuser>` cookie's `Path=/auth` scope, so it can never read
95
- // the device's existing slots and would overwrite slot 0 (destroying the
96
- // operator's own session). `/auth/session` runs where the cookies ARE
97
- // visible, so the server allocates a NEW slot that coexists with the
98
- // operator's and returns its `authuser`. Web-only; best-effort (the helper
99
- // re-plants the rotated access token and returns `null` on native/failure).
100
- const establishedAuthuser = await this.establishDeviceRefreshSlot();
101
- const authuser = establishedAuthuser ?? res.authuser;
90
+ // The switch route now registers the switched session in the device's
91
+ // server-side DeviceSession set directly (device-first), so there is no
92
+ // client-side refresh-cookie slot to establish the `authuser` comes
93
+ // from the switch response (optional-chained to match `res?.accessToken`).
94
+ const authuser = res?.authuser;
102
95
  // Identity changed → drop the entire GET response cache so no entry
103
96
  // personalised for the previous identity is reused. Cache keys are
104
97
  // identity-scoped, so a different identity could not READ the old