@onairos/react-native 3.1.12 → 3.1.13

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 (604) hide show
  1. package/lib/commonjs/api/index.js +75 -1
  2. package/lib/commonjs/api/index.js.map +1 -1
  3. package/lib/commonjs/assets/fonts/EBGaramond-VariableFont_wght.ttf +0 -0
  4. package/lib/commonjs/assets/fonts/IBMPlexSans-VariableFont_wdth,wght.ttf +0 -0
  5. package/lib/commonjs/assets/icons/Facebookicon.png +0 -0
  6. package/lib/commonjs/assets/icons/Gmail.png +0 -0
  7. package/lib/commonjs/assets/icons/Linkedinicon.png +0 -0
  8. package/lib/commonjs/assets/icons/Redditicon.png +0 -0
  9. package/lib/commonjs/assets/icons/YouTubeicon2.png +0 -0
  10. package/lib/commonjs/assets/icons/YouTubeicon3.png +0 -0
  11. package/lib/commonjs/assets/icons/farcaster.png +0 -0
  12. package/lib/commonjs/assets/icons/instagram.png +0 -0
  13. package/lib/commonjs/assets/icons/pinterest.png +0 -0
  14. package/lib/commonjs/assets/icons/swerv_logo.png +0 -0
  15. package/lib/commonjs/assets/icons/twitter.jpg +0 -0
  16. package/lib/commonjs/assets/images/Checkbox.svg +3 -0
  17. package/lib/commonjs/assets/images/EnochE.svg +19 -0
  18. package/lib/commonjs/assets/images/Enochicon1.png +0 -0
  19. package/lib/commonjs/assets/images/Face_ID_logo.png +0 -0
  20. package/lib/commonjs/assets/images/Facebookicon.png +0 -0
  21. package/lib/commonjs/assets/images/Gmail.png +0 -0
  22. package/lib/commonjs/assets/images/Googlelogo.png +0 -0
  23. package/lib/commonjs/assets/images/Linkedinicon.png +0 -0
  24. package/lib/commonjs/assets/images/Onairoslogo.png +0 -0
  25. package/lib/commonjs/assets/images/Personalityprofile.svg +3 -0
  26. package/lib/commonjs/assets/images/Personalitytraits.svg +3 -0
  27. package/lib/commonjs/assets/images/Redditicon.png +0 -0
  28. package/lib/commonjs/assets/images/Userpreferences.svg +3 -0
  29. package/lib/commonjs/assets/images/YouTubeicon3.png +0 -0
  30. package/lib/commonjs/assets/images/arrow.svg +20 -0
  31. package/lib/commonjs/assets/images/basicproficon.svg +43 -0
  32. package/lib/commonjs/assets/images/basicprofile.svg +3 -0
  33. package/lib/commonjs/assets/images/checkmark.svg +4 -0
  34. package/lib/commonjs/assets/images/contentanalysis.svg +3 -0
  35. package/lib/commonjs/assets/images/contenticon.svg +23 -0
  36. package/lib/commonjs/assets/images/persona1.png +0 -0
  37. package/lib/commonjs/assets/images/persona2.png +0 -0
  38. package/lib/commonjs/assets/images/persona3.png +0 -0
  39. package/lib/commonjs/assets/images/persona4.png +0 -0
  40. package/lib/commonjs/assets/images/persona5.png +0 -0
  41. package/lib/commonjs/assets/images/personalityicon.svg +18 -0
  42. package/lib/commonjs/assets/images/x-close.svg +3 -0
  43. package/lib/commonjs/components/BodyText.js +27 -0
  44. package/lib/commonjs/components/BodyText.js.map +1 -0
  45. package/lib/commonjs/components/BrandMark.js +44 -0
  46. package/lib/commonjs/components/BrandMark.js.map +1 -0
  47. package/lib/commonjs/components/CodeInput.js +30 -0
  48. package/lib/commonjs/components/CodeInput.js.map +1 -0
  49. package/lib/commonjs/components/EmailInput.js +30 -0
  50. package/lib/commonjs/components/EmailInput.js.map +1 -0
  51. package/lib/commonjs/components/ExistingUserDataConfirmation.js +474 -0
  52. package/lib/commonjs/components/ExistingUserDataConfirmation.js.map +1 -0
  53. package/lib/commonjs/components/GoogleButton.js +55 -0
  54. package/lib/commonjs/components/GoogleButton.js.map +1 -0
  55. package/lib/commonjs/components/HeadingGroup.js +43 -0
  56. package/lib/commonjs/components/HeadingGroup.js.map +1 -0
  57. package/lib/commonjs/components/ModalHeader.js +99 -0
  58. package/lib/commonjs/components/ModalHeader.js.map +1 -0
  59. package/lib/commonjs/components/ModalSheet.js +41 -0
  60. package/lib/commonjs/components/ModalSheet.js.map +1 -0
  61. package/lib/commonjs/components/Onairos.js +1 -3
  62. package/lib/commonjs/components/Onairos.js.map +1 -1
  63. package/lib/commonjs/components/OnairosButton.js +171 -190
  64. package/lib/commonjs/components/OnairosButton.js.map +1 -1
  65. package/lib/commonjs/components/OnairosSignInButton.js +169 -0
  66. package/lib/commonjs/components/OnairosSignInButton.js.map +1 -0
  67. package/lib/commonjs/components/Overlay.js +5 -5
  68. package/lib/commonjs/components/Overlay.js.map +1 -1
  69. package/lib/commonjs/components/PersonaImage.js +60 -0
  70. package/lib/commonjs/components/PersonaImage.js.map +1 -0
  71. package/lib/commonjs/components/PersonaLoadingScreen.js +156 -0
  72. package/lib/commonjs/components/PersonaLoadingScreen.js.map +1 -0
  73. package/lib/commonjs/components/PersonalizationConsentScreen.js +316 -0
  74. package/lib/commonjs/components/PersonalizationConsentScreen.js.map +1 -0
  75. package/lib/commonjs/components/PinCreationScreen.js +393 -0
  76. package/lib/commonjs/components/PinCreationScreen.js.map +1 -0
  77. package/lib/commonjs/components/PinInput.js +282 -120
  78. package/lib/commonjs/components/PinInput.js.map +1 -1
  79. package/lib/commonjs/components/PlatformConnectorsStep.js +828 -0
  80. package/lib/commonjs/components/PlatformConnectorsStep.js.map +1 -0
  81. package/lib/commonjs/components/PlatformToggle.js +180 -0
  82. package/lib/commonjs/components/PlatformToggle.js.map +1 -0
  83. package/lib/commonjs/components/PrimaryButton.js +180 -0
  84. package/lib/commonjs/components/PrimaryButton.js.map +1 -0
  85. package/lib/commonjs/components/SignInMatchAnimation.js +197 -0
  86. package/lib/commonjs/components/SignInMatchAnimation.js.map +1 -0
  87. package/lib/commonjs/components/SignInStep.js +179 -0
  88. package/lib/commonjs/components/SignInStep.js.map +1 -0
  89. package/lib/commonjs/components/TrainingModal.js +808 -563
  90. package/lib/commonjs/components/TrainingModal.js.map +1 -1
  91. package/lib/commonjs/components/UniversalOnboarding.js +2304 -1283
  92. package/lib/commonjs/components/UniversalOnboarding.js.map +1 -1
  93. package/lib/commonjs/components/VerificationStep.js +154 -0
  94. package/lib/commonjs/components/VerificationStep.js.map +1 -0
  95. package/lib/commonjs/components/WelcomeScreen.js +385 -0
  96. package/lib/commonjs/components/WelcomeScreen.js.map +1 -0
  97. package/lib/commonjs/components/icons/Basicproficon.js +37 -0
  98. package/lib/commonjs/components/icons/Basicproficon.js.map +1 -0
  99. package/lib/commonjs/components/icons/Basicprofile.js +21 -0
  100. package/lib/commonjs/components/icons/Basicprofile.js.map +1 -0
  101. package/lib/commonjs/components/icons/Checkbox.js +21 -0
  102. package/lib/commonjs/components/icons/Checkbox.js.map +1 -0
  103. package/lib/commonjs/components/icons/Checkmark.js +27 -0
  104. package/lib/commonjs/components/icons/Checkmark.js.map +1 -0
  105. package/lib/commonjs/components/icons/Contentanalysis.js +21 -0
  106. package/lib/commonjs/components/icons/Contentanalysis.js.map +1 -0
  107. package/lib/commonjs/components/icons/Contenticon.js +39 -0
  108. package/lib/commonjs/components/icons/Contenticon.js.map +1 -0
  109. package/lib/commonjs/components/icons/EnochE.js +41 -0
  110. package/lib/commonjs/components/icons/EnochE.js.map +1 -0
  111. package/lib/commonjs/components/icons/Personalityicon.js +30 -0
  112. package/lib/commonjs/components/icons/Personalityicon.js.map +1 -0
  113. package/lib/commonjs/components/icons/Personalityprofile.js +21 -0
  114. package/lib/commonjs/components/icons/Personalityprofile.js.map +1 -0
  115. package/lib/commonjs/components/icons/Personalitytraits.js +21 -0
  116. package/lib/commonjs/components/icons/Personalitytraits.js.map +1 -0
  117. package/lib/commonjs/components/icons/Userpreferences.js +21 -0
  118. package/lib/commonjs/components/icons/Userpreferences.js.map +1 -0
  119. package/lib/commonjs/components/icons/index.js +84 -0
  120. package/lib/commonjs/components/icons/index.js.map +1 -0
  121. package/lib/commonjs/components/onboarding/OAuthWebView.js +134 -743
  122. package/lib/commonjs/components/onboarding/OAuthWebView.js.map +1 -1
  123. package/lib/commonjs/config/api.js +34 -0
  124. package/lib/commonjs/config/api.js.map +1 -0
  125. package/lib/commonjs/context/AuthContext.js +345 -0
  126. package/lib/commonjs/context/AuthContext.js.map +1 -0
  127. package/lib/commonjs/hooks/useConnectedAccounts.js +111 -0
  128. package/lib/commonjs/hooks/useConnectedAccounts.js.map +1 -0
  129. package/lib/commonjs/hooks/useConnections.js +120 -125
  130. package/lib/commonjs/hooks/useConnections.js.map +1 -1
  131. package/lib/commonjs/hooks/useUserConnections.js +148 -0
  132. package/lib/commonjs/hooks/useUserConnections.js.map +1 -0
  133. package/lib/commonjs/index.js +149 -27
  134. package/lib/commonjs/index.js.map +1 -1
  135. package/lib/commonjs/services/apiClient.js +302 -0
  136. package/lib/commonjs/services/apiClient.js.map +1 -0
  137. package/lib/commonjs/services/apiKeyService.js +8 -9
  138. package/lib/commonjs/services/apiKeyService.js.map +1 -1
  139. package/lib/commonjs/services/authService.js +935 -0
  140. package/lib/commonjs/services/authService.js.map +1 -0
  141. package/lib/commonjs/services/biometricPinService.js +184 -0
  142. package/lib/commonjs/services/biometricPinService.js.map +1 -0
  143. package/lib/commonjs/services/connectedAccountsService.js +268 -0
  144. package/lib/commonjs/services/connectedAccountsService.js.map +1 -0
  145. package/lib/commonjs/services/googleAuthService.js +268 -0
  146. package/lib/commonjs/services/googleAuthService.js.map +1 -0
  147. package/lib/commonjs/services/imageCompressionService.js +260 -0
  148. package/lib/commonjs/services/imageCompressionService.js.map +1 -0
  149. package/lib/commonjs/services/jwtStorageService.js +256 -0
  150. package/lib/commonjs/services/jwtStorageService.js.map +1 -0
  151. package/lib/commonjs/services/mobileTrainingService.js +185 -0
  152. package/lib/commonjs/services/mobileTrainingService.js.map +1 -0
  153. package/lib/commonjs/services/pinEncryptionService.js +84 -0
  154. package/lib/commonjs/services/pinEncryptionService.js.map +1 -0
  155. package/lib/commonjs/services/pinStorageUtils.js +105 -0
  156. package/lib/commonjs/services/pinStorageUtils.js.map +1 -0
  157. package/lib/commonjs/services/platformAuthService.js +956 -722
  158. package/lib/commonjs/services/platformAuthService.js.map +1 -1
  159. package/lib/commonjs/services/storageService.js +404 -0
  160. package/lib/commonjs/services/storageService.js.map +1 -0
  161. package/lib/commonjs/services/trainingApiHelpers.js +73 -0
  162. package/lib/commonjs/services/trainingApiHelpers.js.map +1 -0
  163. package/lib/commonjs/services/userConnectionsService.js +486 -0
  164. package/lib/commonjs/services/userConnectionsService.js.map +1 -0
  165. package/lib/commonjs/services/youtubeMigrationService.js +415 -0
  166. package/lib/commonjs/services/youtubeMigrationService.js.map +1 -0
  167. package/lib/commonjs/theme/index.js +249 -0
  168. package/lib/commonjs/theme/index.js.map +1 -0
  169. package/lib/commonjs/utils/eventUtils.js +288 -0
  170. package/lib/commonjs/utils/eventUtils.js.map +1 -0
  171. package/lib/commonjs/utils/haptics.js +66 -0
  172. package/lib/commonjs/utils/haptics.js.map +1 -0
  173. package/lib/commonjs/utils/imagePreloader.js +6 -0
  174. package/lib/commonjs/utils/imagePreloader.js.map +1 -0
  175. package/lib/module/api/index.js +72 -0
  176. package/lib/module/api/index.js.map +1 -1
  177. package/lib/module/assets/fonts/EBGaramond-VariableFont_wght.ttf +0 -0
  178. package/lib/module/assets/fonts/IBMPlexSans-VariableFont_wdth,wght.ttf +0 -0
  179. package/lib/module/assets/icons/Facebookicon.png +0 -0
  180. package/lib/module/assets/icons/Gmail.png +0 -0
  181. package/lib/module/assets/icons/Linkedinicon.png +0 -0
  182. package/lib/module/assets/icons/Redditicon.png +0 -0
  183. package/lib/module/assets/icons/YouTubeicon2.png +0 -0
  184. package/lib/module/assets/icons/YouTubeicon3.png +0 -0
  185. package/lib/module/assets/icons/farcaster.png +0 -0
  186. package/lib/module/assets/icons/instagram.png +0 -0
  187. package/lib/module/assets/icons/pinterest.png +0 -0
  188. package/lib/module/assets/icons/swerv_logo.png +0 -0
  189. package/lib/module/assets/icons/twitter.jpg +0 -0
  190. package/lib/module/assets/images/Checkbox.svg +3 -0
  191. package/lib/module/assets/images/EnochE.svg +19 -0
  192. package/lib/module/assets/images/Enochicon1.png +0 -0
  193. package/lib/module/assets/images/Face_ID_logo.png +0 -0
  194. package/lib/module/assets/images/Facebookicon.png +0 -0
  195. package/lib/module/assets/images/Gmail.png +0 -0
  196. package/lib/module/assets/images/Googlelogo.png +0 -0
  197. package/lib/module/assets/images/Linkedinicon.png +0 -0
  198. package/lib/module/assets/images/Onairoslogo.png +0 -0
  199. package/lib/module/assets/images/Personalityprofile.svg +3 -0
  200. package/lib/module/assets/images/Personalitytraits.svg +3 -0
  201. package/lib/module/assets/images/Redditicon.png +0 -0
  202. package/lib/module/assets/images/Userpreferences.svg +3 -0
  203. package/lib/module/assets/images/YouTubeicon3.png +0 -0
  204. package/lib/module/assets/images/arrow.svg +20 -0
  205. package/lib/module/assets/images/basicproficon.svg +43 -0
  206. package/lib/module/assets/images/basicprofile.svg +3 -0
  207. package/lib/module/assets/images/checkmark.svg +4 -0
  208. package/lib/module/assets/images/contentanalysis.svg +3 -0
  209. package/lib/module/assets/images/contenticon.svg +23 -0
  210. package/lib/module/assets/images/persona1.png +0 -0
  211. package/lib/module/assets/images/persona2.png +0 -0
  212. package/lib/module/assets/images/persona3.png +0 -0
  213. package/lib/module/assets/images/persona4.png +0 -0
  214. package/lib/module/assets/images/persona5.png +0 -0
  215. package/lib/module/assets/images/personalityicon.svg +18 -0
  216. package/lib/module/assets/images/x-close.svg +3 -0
  217. package/lib/module/components/BodyText.js +20 -0
  218. package/lib/module/components/BodyText.js.map +1 -0
  219. package/lib/module/components/BrandMark.js +37 -0
  220. package/lib/module/components/BrandMark.js.map +1 -0
  221. package/lib/module/components/CodeInput.js +23 -0
  222. package/lib/module/components/CodeInput.js.map +1 -0
  223. package/lib/module/components/EmailInput.js +23 -0
  224. package/lib/module/components/EmailInput.js.map +1 -0
  225. package/lib/module/components/ExistingUserDataConfirmation.js +465 -0
  226. package/lib/module/components/ExistingUserDataConfirmation.js.map +1 -0
  227. package/lib/module/components/GoogleButton.js +48 -0
  228. package/lib/module/components/GoogleButton.js.map +1 -0
  229. package/lib/module/components/HeadingGroup.js +36 -0
  230. package/lib/module/components/HeadingGroup.js.map +1 -0
  231. package/lib/module/components/ModalHeader.js +92 -0
  232. package/lib/module/components/ModalHeader.js.map +1 -0
  233. package/lib/module/components/ModalSheet.js +34 -0
  234. package/lib/module/components/ModalSheet.js.map +1 -0
  235. package/lib/module/components/Onairos.js +1 -3
  236. package/lib/module/components/Onairos.js.map +1 -1
  237. package/lib/module/components/OnairosButton.js +172 -192
  238. package/lib/module/components/OnairosButton.js.map +1 -1
  239. package/lib/module/components/OnairosSignInButton.js +160 -0
  240. package/lib/module/components/OnairosSignInButton.js.map +1 -0
  241. package/lib/module/components/Overlay.js +5 -5
  242. package/lib/module/components/Overlay.js.map +1 -1
  243. package/lib/module/components/PersonaImage.js +53 -0
  244. package/lib/module/components/PersonaImage.js.map +1 -0
  245. package/lib/module/components/PersonaLoadingScreen.js +148 -0
  246. package/lib/module/components/PersonaLoadingScreen.js.map +1 -0
  247. package/lib/module/components/PersonalizationConsentScreen.js +309 -0
  248. package/lib/module/components/PersonalizationConsentScreen.js.map +1 -0
  249. package/lib/module/components/PinCreationScreen.js +386 -0
  250. package/lib/module/components/PinCreationScreen.js.map +1 -0
  251. package/lib/module/components/PinInput.js +283 -120
  252. package/lib/module/components/PinInput.js.map +1 -1
  253. package/lib/module/components/PlatformConnectorsStep.js +820 -0
  254. package/lib/module/components/PlatformConnectorsStep.js.map +1 -0
  255. package/lib/module/components/PlatformToggle.js +173 -0
  256. package/lib/module/components/PlatformToggle.js.map +1 -0
  257. package/lib/module/components/PrimaryButton.js +172 -0
  258. package/lib/module/components/PrimaryButton.js.map +1 -0
  259. package/lib/module/components/SignInMatchAnimation.js +189 -0
  260. package/lib/module/components/SignInMatchAnimation.js.map +1 -0
  261. package/lib/module/components/SignInStep.js +171 -0
  262. package/lib/module/components/SignInStep.js.map +1 -0
  263. package/lib/module/components/TrainingModal.js +809 -565
  264. package/lib/module/components/TrainingModal.js.map +1 -1
  265. package/lib/module/components/UniversalOnboarding.js +2307 -1284
  266. package/lib/module/components/UniversalOnboarding.js.map +1 -1
  267. package/lib/module/components/VerificationStep.js +146 -0
  268. package/lib/module/components/VerificationStep.js.map +1 -0
  269. package/lib/module/components/WelcomeScreen.js +378 -0
  270. package/lib/module/components/WelcomeScreen.js.map +1 -0
  271. package/lib/module/components/icons/Basicproficon.js +30 -0
  272. package/lib/module/components/icons/Basicproficon.js.map +1 -0
  273. package/lib/module/components/icons/Basicprofile.js +14 -0
  274. package/lib/module/components/icons/Basicprofile.js.map +1 -0
  275. package/lib/module/components/icons/Checkbox.js +14 -0
  276. package/lib/module/components/icons/Checkbox.js.map +1 -0
  277. package/lib/module/components/icons/Checkmark.js +20 -0
  278. package/lib/module/components/icons/Checkmark.js.map +1 -0
  279. package/lib/module/components/icons/Contentanalysis.js +14 -0
  280. package/lib/module/components/icons/Contentanalysis.js.map +1 -0
  281. package/lib/module/components/icons/Contenticon.js +32 -0
  282. package/lib/module/components/icons/Contenticon.js.map +1 -0
  283. package/lib/module/components/icons/EnochE.js +34 -0
  284. package/lib/module/components/icons/EnochE.js.map +1 -0
  285. package/lib/module/components/icons/Personalityicon.js +23 -0
  286. package/lib/module/components/icons/Personalityicon.js.map +1 -0
  287. package/lib/module/components/icons/Personalityprofile.js +14 -0
  288. package/lib/module/components/icons/Personalityprofile.js.map +1 -0
  289. package/lib/module/components/icons/Personalitytraits.js +14 -0
  290. package/lib/module/components/icons/Personalitytraits.js.map +1 -0
  291. package/lib/module/components/icons/Userpreferences.js +14 -0
  292. package/lib/module/components/icons/Userpreferences.js.map +1 -0
  293. package/lib/module/components/icons/index.js +13 -0
  294. package/lib/module/components/icons/index.js.map +1 -0
  295. package/lib/module/components/onboarding/OAuthWebView.js +136 -744
  296. package/lib/module/components/onboarding/OAuthWebView.js.map +1 -1
  297. package/lib/module/config/api.js +26 -0
  298. package/lib/module/config/api.js.map +1 -0
  299. package/lib/module/context/AuthContext.js +335 -0
  300. package/lib/module/context/AuthContext.js.map +1 -0
  301. package/lib/module/hooks/useConnectedAccounts.js +106 -0
  302. package/lib/module/hooks/useConnectedAccounts.js.map +1 -0
  303. package/lib/module/hooks/useConnections.js +119 -125
  304. package/lib/module/hooks/useConnections.js.map +1 -1
  305. package/lib/module/hooks/useUserConnections.js +140 -0
  306. package/lib/module/hooks/useUserConnections.js.map +1 -0
  307. package/lib/module/index.js +51 -15
  308. package/lib/module/index.js.map +1 -1
  309. package/lib/module/services/apiClient.js +298 -0
  310. package/lib/module/services/apiClient.js.map +1 -0
  311. package/lib/module/services/apiKeyService.js +8 -9
  312. package/lib/module/services/apiKeyService.js.map +1 -1
  313. package/lib/module/services/authService.js +905 -0
  314. package/lib/module/services/authService.js.map +1 -0
  315. package/lib/module/services/biometricPinService.js +173 -0
  316. package/lib/module/services/biometricPinService.js.map +1 -0
  317. package/lib/module/services/connectedAccountsService.js +255 -0
  318. package/lib/module/services/connectedAccountsService.js.map +1 -0
  319. package/lib/module/services/googleAuthService.js +258 -0
  320. package/lib/module/services/googleAuthService.js.map +1 -0
  321. package/lib/module/services/imageCompressionService.js +250 -0
  322. package/lib/module/services/imageCompressionService.js.map +1 -0
  323. package/lib/module/services/jwtStorageService.js +239 -0
  324. package/lib/module/services/jwtStorageService.js.map +1 -0
  325. package/lib/module/services/mobileTrainingService.js +172 -0
  326. package/lib/module/services/mobileTrainingService.js.map +1 -0
  327. package/lib/module/services/pinEncryptionService.js +75 -0
  328. package/lib/module/services/pinEncryptionService.js.map +1 -0
  329. package/lib/module/services/pinStorageUtils.js +93 -0
  330. package/lib/module/services/pinStorageUtils.js.map +1 -0
  331. package/lib/module/services/platformAuthService.js +943 -704
  332. package/lib/module/services/platformAuthService.js.map +1 -1
  333. package/lib/module/services/storageService.js +383 -0
  334. package/lib/module/services/storageService.js.map +1 -0
  335. package/lib/module/services/trainingApiHelpers.js +67 -0
  336. package/lib/module/services/trainingApiHelpers.js.map +1 -0
  337. package/lib/module/services/userConnectionsService.js +476 -0
  338. package/lib/module/services/userConnectionsService.js.map +1 -0
  339. package/lib/module/services/youtubeMigrationService.js +404 -0
  340. package/lib/module/services/youtubeMigrationService.js.map +1 -0
  341. package/lib/module/theme/index.js +244 -0
  342. package/lib/module/theme/index.js.map +1 -0
  343. package/lib/module/utils/eventUtils.js +270 -0
  344. package/lib/module/utils/eventUtils.js.map +1 -0
  345. package/lib/module/utils/haptics.js +59 -0
  346. package/lib/module/utils/haptics.js.map +1 -0
  347. package/lib/module/utils/imagePreloader.js +3 -0
  348. package/lib/module/utils/imagePreloader.js.map +1 -0
  349. package/lib/typescript/api/index.d.ts +8 -0
  350. package/lib/typescript/api/index.d.ts.map +1 -1
  351. package/lib/typescript/components/BodyText.d.ts +10 -0
  352. package/lib/typescript/components/BodyText.d.ts.map +1 -0
  353. package/lib/typescript/components/BrandMark.d.ts +11 -0
  354. package/lib/typescript/components/BrandMark.d.ts.map +1 -0
  355. package/lib/typescript/components/CodeInput.d.ts +10 -0
  356. package/lib/typescript/components/CodeInput.d.ts.map +1 -0
  357. package/lib/typescript/components/EmailInput.d.ts +8 -0
  358. package/lib/typescript/components/EmailInput.d.ts.map +1 -0
  359. package/lib/typescript/components/ExistingUserDataConfirmation.d.ts +12 -0
  360. package/lib/typescript/components/ExistingUserDataConfirmation.d.ts.map +1 -0
  361. package/lib/typescript/components/GoogleButton.d.ts +11 -0
  362. package/lib/typescript/components/GoogleButton.d.ts.map +1 -0
  363. package/lib/typescript/components/HeadingGroup.d.ts +11 -0
  364. package/lib/typescript/components/HeadingGroup.d.ts.map +1 -0
  365. package/lib/typescript/components/ModalHeader.d.ts +11 -0
  366. package/lib/typescript/components/ModalHeader.d.ts.map +1 -0
  367. package/lib/typescript/components/ModalSheet.d.ts +13 -0
  368. package/lib/typescript/components/ModalSheet.d.ts.map +1 -0
  369. package/lib/typescript/components/Onairos.d.ts.map +1 -1
  370. package/lib/typescript/components/OnairosButton.d.ts +29 -4
  371. package/lib/typescript/components/OnairosButton.d.ts.map +1 -1
  372. package/lib/typescript/components/OnairosSignInButton.d.ts +14 -0
  373. package/lib/typescript/components/OnairosSignInButton.d.ts.map +1 -0
  374. package/lib/typescript/components/PersonaImage.d.ts +8 -0
  375. package/lib/typescript/components/PersonaImage.d.ts.map +1 -0
  376. package/lib/typescript/components/PersonaLoadingScreen.d.ts +10 -0
  377. package/lib/typescript/components/PersonaLoadingScreen.d.ts.map +1 -0
  378. package/lib/typescript/components/PersonalizationConsentScreen.d.ts +10 -0
  379. package/lib/typescript/components/PersonalizationConsentScreen.d.ts.map +1 -0
  380. package/lib/typescript/components/PinCreationScreen.d.ts +10 -0
  381. package/lib/typescript/components/PinCreationScreen.d.ts.map +1 -0
  382. package/lib/typescript/components/PinInput.d.ts +11 -1
  383. package/lib/typescript/components/PinInput.d.ts.map +1 -1
  384. package/lib/typescript/components/PlatformConnectorsStep.d.ts +11 -0
  385. package/lib/typescript/components/PlatformConnectorsStep.d.ts.map +1 -0
  386. package/lib/typescript/components/PlatformToggle.d.ts +20 -0
  387. package/lib/typescript/components/PlatformToggle.d.ts.map +1 -0
  388. package/lib/typescript/components/PrimaryButton.d.ts +22 -0
  389. package/lib/typescript/components/PrimaryButton.d.ts.map +1 -0
  390. package/lib/typescript/components/SignInMatchAnimation.d.ts +9 -0
  391. package/lib/typescript/components/SignInMatchAnimation.d.ts.map +1 -0
  392. package/lib/typescript/components/SignInStep.d.ts +12 -0
  393. package/lib/typescript/components/SignInStep.d.ts.map +1 -0
  394. package/lib/typescript/components/TrainingModal.d.ts +12 -1
  395. package/lib/typescript/components/TrainingModal.d.ts.map +1 -1
  396. package/lib/typescript/components/UniversalOnboarding.d.ts +14 -1
  397. package/lib/typescript/components/UniversalOnboarding.d.ts.map +1 -1
  398. package/lib/typescript/components/VerificationStep.d.ts +13 -0
  399. package/lib/typescript/components/VerificationStep.d.ts.map +1 -0
  400. package/lib/typescript/components/WelcomeScreen.d.ts +9 -0
  401. package/lib/typescript/components/WelcomeScreen.d.ts.map +1 -0
  402. package/lib/typescript/components/icons/Basicproficon.d.ts +5 -0
  403. package/lib/typescript/components/icons/Basicproficon.d.ts.map +1 -0
  404. package/lib/typescript/components/icons/Basicprofile.d.ts +5 -0
  405. package/lib/typescript/components/icons/Basicprofile.d.ts.map +1 -0
  406. package/lib/typescript/components/icons/Checkbox.d.ts +5 -0
  407. package/lib/typescript/components/icons/Checkbox.d.ts.map +1 -0
  408. package/lib/typescript/components/icons/Checkmark.d.ts +5 -0
  409. package/lib/typescript/components/icons/Checkmark.d.ts.map +1 -0
  410. package/lib/typescript/components/icons/Contentanalysis.d.ts +5 -0
  411. package/lib/typescript/components/icons/Contentanalysis.d.ts.map +1 -0
  412. package/lib/typescript/components/icons/Contenticon.d.ts +5 -0
  413. package/lib/typescript/components/icons/Contenticon.d.ts.map +1 -0
  414. package/lib/typescript/components/icons/EnochE.d.ts +5 -0
  415. package/lib/typescript/components/icons/EnochE.d.ts.map +1 -0
  416. package/lib/typescript/components/icons/Personalityicon.d.ts +5 -0
  417. package/lib/typescript/components/icons/Personalityicon.d.ts.map +1 -0
  418. package/lib/typescript/components/icons/Personalityprofile.d.ts +5 -0
  419. package/lib/typescript/components/icons/Personalityprofile.d.ts.map +1 -0
  420. package/lib/typescript/components/icons/Personalitytraits.d.ts +5 -0
  421. package/lib/typescript/components/icons/Personalitytraits.d.ts.map +1 -0
  422. package/lib/typescript/components/icons/Userpreferences.d.ts +5 -0
  423. package/lib/typescript/components/icons/Userpreferences.d.ts.map +1 -0
  424. package/lib/typescript/components/icons/index.d.ts +12 -0
  425. package/lib/typescript/components/icons/index.d.ts.map +1 -0
  426. package/lib/typescript/components/onboarding/OAuthWebView.d.ts.map +1 -1
  427. package/lib/typescript/config/api.d.ts +24 -0
  428. package/lib/typescript/config/api.d.ts.map +1 -0
  429. package/lib/typescript/context/AuthContext.d.ts +34 -0
  430. package/lib/typescript/context/AuthContext.d.ts.map +1 -0
  431. package/lib/typescript/hooks/useConnectedAccounts.d.ts +11 -0
  432. package/lib/typescript/hooks/useConnectedAccounts.d.ts.map +1 -0
  433. package/lib/typescript/hooks/useConnections.d.ts +10 -5
  434. package/lib/typescript/hooks/useConnections.d.ts.map +1 -1
  435. package/lib/typescript/hooks/useUserConnections.d.ts +12 -0
  436. package/lib/typescript/hooks/useUserConnections.d.ts.map +1 -0
  437. package/lib/typescript/index.d.ts +24 -6
  438. package/lib/typescript/index.d.ts.map +1 -1
  439. package/lib/typescript/services/apiClient.d.ts +91 -0
  440. package/lib/typescript/services/apiClient.d.ts.map +1 -0
  441. package/lib/typescript/services/apiKeyService.d.ts.map +1 -1
  442. package/lib/typescript/services/authService.d.ts +216 -0
  443. package/lib/typescript/services/authService.d.ts.map +1 -0
  444. package/lib/typescript/services/biometricPinService.d.ts +29 -0
  445. package/lib/typescript/services/biometricPinService.d.ts.map +1 -0
  446. package/lib/typescript/services/connectedAccountsService.d.ts +56 -0
  447. package/lib/typescript/services/connectedAccountsService.d.ts.map +1 -0
  448. package/lib/typescript/services/googleAuthService.d.ts +63 -0
  449. package/lib/typescript/services/googleAuthService.d.ts.map +1 -0
  450. package/lib/typescript/services/imageCompressionService.d.ts +37 -0
  451. package/lib/typescript/services/imageCompressionService.d.ts.map +1 -0
  452. package/lib/typescript/services/jwtStorageService.d.ts +86 -0
  453. package/lib/typescript/services/jwtStorageService.d.ts.map +1 -0
  454. package/lib/typescript/services/mobileTrainingService.d.ts +45 -0
  455. package/lib/typescript/services/mobileTrainingService.d.ts.map +1 -0
  456. package/lib/typescript/services/pinEncryptionService.d.ts +17 -0
  457. package/lib/typescript/services/pinEncryptionService.d.ts.map +1 -0
  458. package/lib/typescript/services/pinStorageUtils.d.ts +25 -0
  459. package/lib/typescript/services/pinStorageUtils.d.ts.map +1 -0
  460. package/lib/typescript/services/platformAuthService.d.ts +34 -109
  461. package/lib/typescript/services/platformAuthService.d.ts.map +1 -1
  462. package/lib/typescript/services/storageService.d.ts +128 -0
  463. package/lib/typescript/services/storageService.d.ts.map +1 -0
  464. package/lib/typescript/services/trainingApiHelpers.d.ts +38 -0
  465. package/lib/typescript/services/trainingApiHelpers.d.ts.map +1 -0
  466. package/lib/typescript/services/userConnectionsService.d.ts +90 -0
  467. package/lib/typescript/services/userConnectionsService.d.ts.map +1 -0
  468. package/lib/typescript/services/youtubeMigrationService.d.ts +12 -0
  469. package/lib/typescript/services/youtubeMigrationService.d.ts.map +1 -0
  470. package/lib/typescript/theme/index.d.ts +416 -0
  471. package/lib/typescript/theme/index.d.ts.map +1 -0
  472. package/lib/typescript/types/index.d.ts +39 -0
  473. package/lib/typescript/types/index.d.ts.map +1 -1
  474. package/lib/typescript/utils/eventUtils.d.ts +108 -0
  475. package/lib/typescript/utils/eventUtils.d.ts.map +1 -0
  476. package/lib/typescript/utils/haptics.d.ts +11 -0
  477. package/lib/typescript/utils/haptics.d.ts.map +1 -0
  478. package/lib/typescript/utils/imagePreloader.d.ts +2 -0
  479. package/lib/typescript/utils/imagePreloader.d.ts.map +1 -0
  480. package/package.json +158 -145
  481. package/src/api/index.ts +41 -0
  482. package/src/assets/fonts/EBGaramond-VariableFont_wght.ttf +0 -0
  483. package/src/assets/fonts/IBMPlexSans-VariableFont_wdth,wght.ttf +0 -0
  484. package/src/assets/icons/Facebookicon.png +0 -0
  485. package/src/assets/icons/Gmail.png +0 -0
  486. package/src/assets/icons/Linkedinicon.png +0 -0
  487. package/src/assets/icons/Redditicon.png +0 -0
  488. package/src/assets/icons/YouTubeicon2.png +0 -0
  489. package/src/assets/icons/YouTubeicon3.png +0 -0
  490. package/src/assets/icons/farcaster.png +0 -0
  491. package/src/assets/icons/instagram.png +0 -0
  492. package/src/assets/icons/pinterest.png +0 -0
  493. package/src/assets/icons/swerv_logo.png +0 -0
  494. package/src/assets/icons/twitter.jpg +0 -0
  495. package/src/assets/images/Checkbox.svg +3 -0
  496. package/src/assets/images/EnochE.svg +19 -0
  497. package/src/assets/images/Enochicon1.png +0 -0
  498. package/src/assets/images/Face_ID_logo.png +0 -0
  499. package/src/assets/images/Facebookicon.png +0 -0
  500. package/src/assets/images/Gmail.png +0 -0
  501. package/src/assets/images/Googlelogo.png +0 -0
  502. package/src/assets/images/Linkedinicon.png +0 -0
  503. package/src/assets/images/Onairoslogo.png +0 -0
  504. package/src/assets/images/Personalityprofile.svg +3 -0
  505. package/src/assets/images/Personalitytraits.svg +3 -0
  506. package/src/assets/images/Redditicon.png +0 -0
  507. package/src/assets/images/Userpreferences.svg +3 -0
  508. package/src/assets/images/YouTubeicon3.png +0 -0
  509. package/src/assets/images/arrow.svg +20 -0
  510. package/src/assets/images/basicproficon.svg +43 -0
  511. package/src/assets/images/basicprofile.svg +3 -0
  512. package/src/assets/images/checkmark.svg +4 -0
  513. package/src/assets/images/contentanalysis.svg +3 -0
  514. package/src/assets/images/contenticon.svg +23 -0
  515. package/src/assets/images/persona1.png +0 -0
  516. package/src/assets/images/persona2.png +0 -0
  517. package/src/assets/images/persona3.png +0 -0
  518. package/src/assets/images/persona4.png +0 -0
  519. package/src/assets/images/persona5.png +0 -0
  520. package/src/assets/images/personalityicon.svg +18 -0
  521. package/src/assets/images/x-close.svg +3 -0
  522. package/src/components/BodyText.tsx +33 -0
  523. package/src/components/BrandMark.tsx +62 -0
  524. package/src/components/CodeInput.tsx +32 -0
  525. package/src/components/EmailInput.tsx +31 -0
  526. package/src/components/ExistingUserDataConfirmation.tsx +507 -0
  527. package/src/components/GoogleButton.tsx +55 -0
  528. package/src/components/HeadingGroup.tsx +49 -0
  529. package/src/components/ModalHeader.tsx +125 -0
  530. package/src/components/ModalSheet.tsx +57 -0
  531. package/src/components/Onairos.tsx +422 -424
  532. package/src/components/OnairosButton.tsx +339 -359
  533. package/src/components/OnairosSignInButton.tsx +166 -0
  534. package/src/components/Overlay.tsx +506 -506
  535. package/src/components/PersonaImage.tsx +79 -0
  536. package/src/components/PersonaLoadingScreen.tsx +201 -0
  537. package/src/components/PersonalizationConsentScreen.tsx +410 -0
  538. package/src/components/PinCreationScreen.tsx +492 -0
  539. package/src/components/PinInput.tsx +555 -343
  540. package/src/components/PlatformConnectorsStep.tsx +892 -0
  541. package/src/components/PlatformToggle.tsx +226 -0
  542. package/src/components/PrimaryButton.tsx +214 -0
  543. package/src/components/SignInMatchAnimation.tsx +225 -0
  544. package/src/components/SignInStep.tsx +217 -0
  545. package/src/components/TrainingModal.tsx +1047 -737
  546. package/src/components/UniversalOnboarding.tsx +2888 -1820
  547. package/src/components/VerificationStep.tsx +198 -0
  548. package/src/components/WelcomeScreen.tsx +473 -0
  549. package/src/components/icons/Basicproficon.tsx +30 -0
  550. package/src/components/icons/Basicprofile.tsx +17 -0
  551. package/src/components/icons/Checkbox.tsx +17 -0
  552. package/src/components/icons/Checkmark.tsx +24 -0
  553. package/src/components/icons/Contentanalysis.tsx +17 -0
  554. package/src/components/icons/Contenticon.tsx +30 -0
  555. package/src/components/icons/EnochE.tsx +39 -0
  556. package/src/components/icons/Personalityicon.tsx +22 -0
  557. package/src/components/icons/Personalityprofile.tsx +17 -0
  558. package/src/components/icons/Personalitytraits.tsx +17 -0
  559. package/src/components/icons/Userpreferences.tsx +17 -0
  560. package/src/components/icons/index.ts +12 -0
  561. package/src/components/onboarding/OAuthWebView.tsx +232 -838
  562. package/src/config/api.ts +25 -0
  563. package/src/context/AuthContext.tsx +393 -0
  564. package/src/hooks/useConnectedAccounts.ts +139 -0
  565. package/src/hooks/useConnections.ts +129 -131
  566. package/src/hooks/useUserConnections.ts +166 -0
  567. package/src/index.ts +94 -49
  568. package/src/services/apiClient.ts +337 -0
  569. package/src/services/apiKeyService.ts +9 -11
  570. package/src/services/authService.ts +1008 -0
  571. package/src/services/biometricPinService.ts +193 -0
  572. package/src/services/connectedAccountsService.ts +290 -0
  573. package/src/services/googleAuthService.ts +279 -0
  574. package/src/services/imageCompressionService.ts +303 -0
  575. package/src/services/jwtStorageService.ts +257 -0
  576. package/src/services/mobileTrainingService.ts +204 -0
  577. package/src/services/pinEncryptionService.ts +76 -0
  578. package/src/services/pinStorageUtils.ts +97 -0
  579. package/src/services/platformAuthService.ts +1346 -1113
  580. package/src/services/storageService.ts +452 -0
  581. package/src/services/trainingApiHelpers.ts +67 -0
  582. package/src/services/userConnectionsService.ts +557 -0
  583. package/src/services/youtubeMigrationService.ts +454 -0
  584. package/src/theme/index.ts +239 -0
  585. package/src/types/index.ts +265 -238
  586. package/src/utils/eventUtils.ts +303 -0
  587. package/src/utils/haptics.ts +59 -0
  588. package/src/utils/imagePreloader.ts +2 -0
  589. package/README.md +0 -375
  590. package/lib/commonjs/assets/images/email.png +0 -0
  591. package/lib/commonjs/assets/images/linkedin.png +0 -0
  592. package/lib/commonjs/assets/images/reddit.png +0 -0
  593. package/lib/commonjs/assets/images/youtube.png +0 -0
  594. package/lib/commonjs/components/UniversalOnboarding.tsx.new +0 -455
  595. package/lib/module/assets/images/email.png +0 -0
  596. package/lib/module/assets/images/linkedin.png +0 -0
  597. package/lib/module/assets/images/reddit.png +0 -0
  598. package/lib/module/assets/images/youtube.png +0 -0
  599. package/lib/module/components/UniversalOnboarding.tsx.new +0 -455
  600. package/src/assets/images/email.png +0 -0
  601. package/src/assets/images/linkedin.png +0 -0
  602. package/src/assets/images/reddit.png +0 -0
  603. package/src/assets/images/youtube.png +0 -0
  604. package/src/components/UniversalOnboarding.tsx.new +0 -455
@@ -6,391 +6,575 @@ Object.defineProperty(exports, "__esModule", {
6
6
  exports.UniversalOnboarding = void 0;
7
7
  var _react = _interopRequireWildcard(require("react"));
8
8
  var _reactNative = require("react-native");
9
- var _MaterialIcons = _interopRequireDefault(require("react-native-vector-icons/MaterialIcons"));
9
+ var _asyncStorage = _interopRequireDefault(require("@react-native-async-storage/async-storage"));
10
10
  var _PinInput = require("./PinInput");
11
- var _TrainingModal = require("./TrainingModal");
12
- var _DataRequestScreen = require("./DataRequestScreen");
13
11
  var _OAuthWebView = require("./onboarding/OAuthWebView");
14
- var _useConnections = require("../hooks/useConnections");
15
- var _constants = require("../constants");
16
12
  var _platformAuthService = require("../services/platformAuthService");
13
+ var _haptics = require("../utils/haptics");
14
+ var _authService = require("../services/authService");
15
+ var _socket = require("socket.io-client");
16
+ var _pinStorageUtils = require("../services/pinStorageUtils");
17
+ var _pinEncryptionService = require("../services/pinEncryptionService");
18
+ var _mobileTrainingService = require("../services/mobileTrainingService");
17
19
  function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
18
- function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function (e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (const t in e) "default" !== t && {}.hasOwnProperty.call(e, t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, t)) && (i.get || i.set) ? o(f, t, i) : f[t] = e[t]); return f; })(e, t); }
19
- // Optional Opacity SDK imports with error handling
20
- let opacityInit = null;
21
- let OpacityEnvironment = null;
22
- let opacityGet = null;
23
- try {
24
- const opacitySDK = require('@opacity-labs/react-native-opacity');
25
- opacityInit = opacitySDK.init;
26
- OpacityEnvironment = opacitySDK.OpacityEnvironment;
27
- opacityGet = opacitySDK.get;
28
- } catch (error) {
29
- console.warn('Opacity SDK not available:', error);
30
- // Opacity SDK will be disabled if not available
31
- }
20
+ function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function (e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (const t in e) "default" !== t && {}.hasOwnProperty.call(e, t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, t)) && (i.get || i.set) ? o(f, t, i) : f[t] = e[t]); return f; })(e, t); } // Removed navigation dependencies for SDK compatibility
21
+ // Import components and hooks
22
+ // import { useConnections } from '../../hooks/useConnections'; // Commented out - file path issue
23
+ // import { useAuth } from '../../context/AuthContext'; // Commented out - file path issue
24
+ // Import types
25
+ // import type { ConnectionStatus } from '../../hooks/useConnections'; // Commented out - file path issue
26
+ // Removed App-specific navigation types
27
+
32
28
  const {
33
29
  height,
34
30
  width
35
31
  } = _reactNative.Dimensions.get('window');
32
+ // ConnectionStatus interface is now imported from hooks/useConnections
33
+
36
34
  const UniversalOnboarding = ({
37
35
  visible,
38
36
  onClose,
39
37
  AppName,
40
- appIcon,
41
38
  requestData,
42
39
  returnLink,
43
40
  onComplete,
44
41
  embedd = false,
45
42
  debug = false,
46
- testMode = false,
43
+ test = false,
47
44
  preferredPlatform,
48
- inferenceData,
49
- auto = false,
50
- partner
45
+ primaryAuthOnly = false
51
46
  }) => {
52
- const [step, setStep] = (0, _react.useState)('email');
47
+ var _existingUserInfo$exi;
48
+ const [step, setStep] = (0, _react.useState)(primaryAuthOnly ? 'persona' : 'connect');
53
49
  const [connections, setConnections] = (0, _react.useState)({});
54
50
  const [pin, setPin] = (0, _react.useState)('');
55
51
  const [selectedTier, setSelectedTier] = (0, _react.useState)('Medium');
56
- const [training, setTraining] = (0, _react.useState)({
57
- progress: 0,
58
- eta: ''
59
- });
60
- const [slideAnim] = (0, _react.useState)(new _reactNative.Animated.Value(height));
52
+ // Training state is now handled by TrainingModal
53
+ const [slideAnim] = (0, _react.useState)(new _reactNative.Animated.Value(height * 0.5));
61
54
  const [platformToggles, setPlatformToggles] = (0, _react.useState)({});
62
55
  const [oauthUrl, setOauthUrl] = (0, _react.useState)('');
63
56
  const [currentPlatform, setCurrentPlatform] = (0, _react.useState)('');
64
- const [username, setUsername] = (0, _react.useState)('Avatar');
65
- const [isConnectingPlatform, setIsConnectingPlatform] = (0, _react.useState)(false);
66
- const [showLoginWebView, setShowLoginWebView] = (0, _react.useState)(false);
67
57
  const [email, setEmail] = (0, _react.useState)('');
68
- const [verificationCode, setVerificationCode] = (0, _react.useState)('');
69
- const [isVerifyingCode, setIsVerifyingCode] = (0, _react.useState)(false);
70
- const [isExistingUser, setIsExistingUser] = (0, _react.useState)(false);
58
+ const [longPressTimer, setLongPressTimer] = (0, _react.useState)(null);
59
+ const [modalVisible, setModalVisible] = (0, _react.useState)(visible);
71
60
 
72
- // Add refs for cleanup and code inputs
73
- const successTimeoutRef = (0, _react.useRef)(null);
74
- const isMountedRef = (0, _react.useRef)(true);
75
- const codeInputRefs = (0, _react.useRef)([]);
61
+ // Debug logging for modal visibility
62
+ (0, _react.useEffect)(() => {
63
+ console.log('🔍 UniversalOnboarding: visible prop changed to:', visible);
64
+ console.log('🔍 UniversalOnboarding: modalVisible state is:', modalVisible);
65
+ console.log('🔍 UniversalOnboarding: current step is:', step);
66
+ console.log('🔍 UniversalOnboarding: primaryAuthOnly is:', primaryAuthOnly);
67
+ }, [visible, modalVisible, step, primaryAuthOnly]);
68
+ const isCompletingRef = (0, _react.useRef)(false);
69
+ const [connectionsCount, setConnectionsCount] = (0, _react.useState)(5); // Simulated connections count
76
70
 
77
71
  // Add state for showing additional platforms
78
- const [showAllPlatforms, setShowAllPlatforms] = (0, _react.useState)(false);
79
-
80
- // Parse test mode options
81
- const testModeOptions = typeof testMode === 'object' ? testMode : {};
82
- const isTestMode = testMode === true || typeof testMode === 'object' && testMode !== null;
83
- const showTestControls = (debug || isTestMode) && requestData;
84
-
85
- // Simple 2-flow system
86
- const isExistingUserFlow = testModeOptions.existingUser || false;
87
- const isNewUserFlow = testModeOptions.newUser || false;
88
- const platforms = [{
89
- id: 'instagram',
90
- name: 'Instagram',
91
- icon: require('../assets/images/instagram.png')
72
+ const [showAdditionalPlatforms, setShowAdditionalPlatforms] = (0, _react.useState)(false);
73
+ const [additionalPlatformsOpacity] = (0, _react.useState)(new _reactNative.Animated.Value(0));
74
+
75
+ // Add ref for ScrollView to control scroll position
76
+ const scrollViewRef = (0, _react.useRef)(null);
77
+ // Get the authenticated user from auth context
78
+ // const { user } = useAuth(); // Hook not available
79
+ const user = null;
80
+
81
+ // State for storing the correct username
82
+ const [username, setUsername] = (0, _react.useState)('');
83
+
84
+ // Real training state variables (replacing fake persona state)
85
+ const [personaProgress, setPersonaProgress] = (0, _react.useState)(0);
86
+ const [personaStatus, setPersonaStatus] = (0, _react.useState)('Initializing...');
87
+ const [isPersonaComplete, setIsPersonaComplete] = (0, _react.useState)(false);
88
+ const [socketConnected, setSocketConnected] = (0, _react.useState)(false);
89
+ const [hasError, setHasError] = (0, _react.useState)(false);
90
+ const [userTraits, setUserTraits] = (0, _react.useState)(null);
91
+ const [inferenceResults, setInferenceResults] = (0, _react.useState)(null);
92
+ const [userToken, setUserToken] = (0, _react.useState)(null);
93
+ const [userInfo, setUserInfo] = (0, _react.useState)(null);
94
+ const [animatedDots, setAnimatedDots] = (0, _react.useState)('');
95
+ const socketRef = (0, _react.useRef)(null);
96
+ const dotsAnimationRef = (0, _react.useRef)(null);
97
+
98
+ // Existing user state
99
+ const [isExistingUser, setIsExistingUser] = (0, _react.useState)(false);
100
+ const [existingUserToken, setExistingUserToken] = (0, _react.useState)(null);
101
+ const [existingUserInfo, setExistingUserInfo] = (0, _react.useState)(null);
102
+
103
+ // Data scenario states
104
+ const [dataScenario, setDataScenario] = (0, _react.useState)(null);
105
+ const [dataDetails, setDataDetails] = (0, _react.useState)(null);
106
+ const [showDataWarning, setShowDataWarning] = (0, _react.useState)(false);
107
+
108
+ // ✅ NEW: Background training state
109
+ const [isBackgroundTrainingStarted, setIsBackgroundTrainingStarted] = (0, _react.useState)(false);
110
+ const [backgroundTrainingProgress, setBackgroundTrainingProgress] = (0, _react.useState)('');
111
+ const [backgroundSocketId, setBackgroundSocketId] = (0, _react.useState)(null);
112
+
113
+ // Function to store connected platforms
114
+ const storeConnectedPlatform = async platformId => {
115
+ try {
116
+ const storedPlatforms = await _asyncStorage.default.getItem('connectedPlatforms');
117
+ let platforms = storedPlatforms ? JSON.parse(storedPlatforms) : [];
118
+
119
+ // Add platform if not already in the list
120
+ if (!platforms.includes(platformId)) {
121
+ platforms.push(platformId);
122
+ await _asyncStorage.default.setItem('connectedPlatforms', JSON.stringify(platforms));
123
+ console.log('📱 Stored connected platform:', platformId, 'Total platforms:', platforms);
124
+ }
125
+ } catch (error) {
126
+ console.error('Error storing connected platform:', error);
127
+ }
128
+ };
129
+
130
+ // Function to remove connected platform from storage
131
+ const removeConnectedPlatform = async platformId => {
132
+ try {
133
+ const storedPlatforms = await _asyncStorage.default.getItem('connectedPlatforms');
134
+ let platforms = storedPlatforms ? JSON.parse(storedPlatforms) : [];
135
+
136
+ // Remove platform from the list
137
+ platforms = platforms.filter(platform => platform !== platformId);
138
+ await _asyncStorage.default.setItem('connectedPlatforms', JSON.stringify(platforms));
139
+ console.log('📱 Removed connected platform:', platformId, 'Remaining platforms:', platforms);
140
+ } catch (error) {
141
+ console.error('Error removing connected platform:', error);
142
+ }
143
+ };
144
+
145
+ // Function to handle disconnect confirmation
146
+ const handleDisconnectPlatform = (platformId, platformName) => {
147
+ _reactNative.Alert.alert('Disconnect Platform', `Are you sure you want to disconnect ${platformName}?`, [{
148
+ text: 'No',
149
+ style: 'cancel'
150
+ }, {
151
+ text: 'Yes',
152
+ style: 'destructive',
153
+ onPress: async () => {
154
+ try {
155
+ // Update local state to show disconnected
156
+ setConnectionStatuses(prev => ({
157
+ ...prev,
158
+ [platformId]: 'disconnected'
159
+ }));
160
+ setConnections(prev => {
161
+ const newConnections = {
162
+ ...prev
163
+ };
164
+ delete newConnections[platformId];
165
+ return newConnections;
166
+ });
167
+ setPlatformToggles(prev => ({
168
+ ...prev,
169
+ [platformId]: false
170
+ }));
171
+
172
+ // Remove from storage
173
+ await removeConnectedPlatform(platformId);
174
+
175
+ // Call the disconnect function from the hook
176
+ await disconnectPlatform();
177
+ console.log('🔌 Disconnected platform:', platformId);
178
+ } catch (error) {
179
+ console.error('Error disconnecting platform:', error);
180
+ }
181
+ }
182
+ }]);
183
+ };
184
+
185
+ // Function to start animated dots
186
+ const startDotsAnimation = () => {
187
+ if (dotsAnimationRef.current) {
188
+ clearInterval(dotsAnimationRef.current);
189
+ }
190
+ let dotCount = 0;
191
+ dotsAnimationRef.current = setInterval(() => {
192
+ dotCount = (dotCount + 1) % 4; // 0, 1, 2, 3, then back to 0
193
+ if (dotCount === 0) {
194
+ setAnimatedDots('');
195
+ } else {
196
+ setAnimatedDots('.'.repeat(dotCount));
197
+ }
198
+ }, 500); // Change every 500ms
199
+ };
200
+
201
+ // Function to stop animated dots
202
+ const stopDotsAnimation = () => {
203
+ if (dotsAnimationRef.current) {
204
+ clearInterval(dotsAnimationRef.current);
205
+ dotsAnimationRef.current = null;
206
+ }
207
+ setAnimatedDots('');
208
+ };
209
+
210
+ // Split platforms into main and additional
211
+ const mainPlatforms = [{
212
+ id: 'pinterest',
213
+ name: 'Pinterest',
214
+ color: '#E60023'
92
215
  }, {
93
216
  id: 'youtube',
94
217
  name: 'YouTube',
95
- icon: require('../assets/images/youtube.png')
96
- }, {
97
- id: 'email',
98
- name: 'Gmail',
99
- icon: require('../assets/images/email.png')
218
+ color: '#FFFFFF'
100
219
  }, {
220
+ id: 'linkedin',
221
+ name: 'LinkedIn',
222
+ color: '#0077B5'
223
+ }];
224
+ const additionalPlatforms = [{
101
225
  id: 'reddit',
102
226
  name: 'Reddit',
103
- icon: require('../assets/images/reddit.png')
227
+ color: '#FFFFFF'
104
228
  }, {
105
- id: 'pinterest',
106
- name: 'Pinterest',
107
- icon: require('../assets/images/pinterest.png')
229
+ id: 'gmail',
230
+ name: 'Gmail',
231
+ color: '#EA4335'
108
232
  }];
109
233
 
110
- // Define primary platforms (shown by default)
111
- const primaryPlatforms = platforms.slice(0, 3); // Instagram, YouTube, Gmail
112
- const additionalPlatforms = platforms.slice(3); // Reddit, Pinterest
113
-
114
- // Get platforms to display based on showAllPlatforms state
115
- const platformsToDisplay = showAllPlatforms ? platforms : primaryPlatforms;
116
- const {
117
- connectPlatform,
118
- disconnectPlatform,
119
- getConnectionStatus,
120
- isConnecting
121
- } = (0, _useConnections.useConnections)();
234
+ // Keep the original platforms array for compatibility
235
+ const platforms = [...mainPlatforms, ...additionalPlatforms];
236
+
237
+ // const {
238
+ // connectPlatform,
239
+ // disconnectPlatform,
240
+ // getConnectionStatus,
241
+ // isConnecting,
242
+ // } = useConnections(); // Hook not available
243
+ const connectPlatform = async () => {};
244
+ const disconnectPlatform = async () => {};
245
+ const getConnectionStatus = () => 'disconnected';
246
+ const isConnecting = false;
247
+ const isConnected = () => false;
248
+
249
+ // Track connection statuses and currently connecting platform
250
+ const [connectionStatuses, setConnectionStatuses] = (0, _react.useState)({});
251
+ const [connectingPlatform, setConnectingPlatform] = (0, _react.useState)(null);
252
+
253
+ // Function to get the platform icon based on platform ID
254
+ const getPlatformIcon = platformId => {
255
+ switch (platformId) {
256
+ case 'instagram':
257
+ return require('../assets/icons/instagram.png');
258
+ case 'youtube':
259
+ return require('../assets/icons/YouTubeicon2.png');
260
+ case 'reddit':
261
+ return require('../assets/icons/Redditicon.png');
262
+ case 'pinterest':
263
+ return require('../assets/icons/pinterest.png');
264
+ case 'facebook':
265
+ return require('../assets/icons/Facebookicon.png');
266
+ case 'linkedin':
267
+ return require('../assets/icons/Linkedinicon.png');
268
+ case 'gmail':
269
+ return require('../assets/icons/Gmail.png');
270
+ }
271
+ };
272
+
273
+ // Track if the modal has ever been visible to prevent initial onClose call
274
+ const hasBeenVisibleRef = (0, _react.useRef)(false);
122
275
  (0, _react.useEffect)(() => {
123
- // Set mounted flag
124
- isMountedRef.current = true;
125
276
  if (visible) {
277
+ hasBeenVisibleRef.current = true; // Mark that modal has been visible
278
+ isCompletingRef.current = false; // Reset flag when becoming visible
279
+ setModalVisible(true);
126
280
  loadInitialStatus();
127
281
  // Animate in
128
282
  _reactNative.Animated.spring(slideAnim, {
129
283
  toValue: 0,
130
- useNativeDriver: true,
131
- bounciness: 0
284
+ friction: 8,
285
+ tension: 40,
286
+ useNativeDriver: true
132
287
  }).start();
133
-
134
- // Set up deep link listener for OAuth callbacks
135
- // Using the subscription pattern for React Native's Linking API
136
- const subscription = _reactNative.Linking.addListener('url', ({
137
- url
138
- }) => {
139
- if ((0, _platformAuthService.isOAuthCallback)(url)) {
140
- handleOAuthCallback(url);
141
- }
142
- });
143
-
144
- // Check for initial URL (app was opened via deep link)
145
- _reactNative.Linking.getInitialURL().then(initialUrl => {
146
- if (initialUrl && (0, _platformAuthService.isOAuthCallback)(initialUrl)) {
147
- handleOAuthCallback(initialUrl);
148
- }
149
- });
150
-
151
- // Initialize platform toggles
152
- const initialToggles = {};
153
- platforms.forEach(platform => {
154
- initialToggles[platform.id] = false;
155
- });
156
- setPlatformToggles(initialToggles);
157
-
158
- // Debug mode for Expo Go
159
- if (debug || _reactNative.Platform.OS === 'web') {
160
- console.log('Debug mode enabled - Using mock data for onboarding');
161
- console.log('Configuration:', {
162
- auto,
163
- partner,
164
- hasInferenceData: !!inferenceData,
165
- inferenceDataType: typeof inferenceData
166
- });
167
-
168
- // Pre-populate with mock connections in debug mode
169
- if (testMode || _reactNative.Platform.OS === 'web') {
170
- setConnections({
171
- instagram: {
172
- userName: 'instagram_user',
173
- connected: true
174
- },
175
- youtube: {
176
- userName: 'youtube_user',
177
- connected: true
178
- }
179
- });
180
- }
181
- }
182
-
183
- // If there's a preferred platform, pre-connect
184
- if (preferredPlatform && debug) {
185
- setConnections(prev => ({
186
- ...prev,
187
- [preferredPlatform]: {
188
- userName: `${preferredPlatform}_user`,
189
- connected: true
190
- }
191
- }));
192
- }
193
-
194
- // Return cleanup function
288
+ const subscription = _reactNative.Linking.addEventListener('url', handleUrl);
195
289
  return () => {
196
- // Remove event listener using the subscription
197
290
  subscription.remove();
198
291
  };
199
- } else {
200
- // Animate out
292
+ } else if (hasBeenVisibleRef.current && !isCompletingRef.current) {
293
+ // Only animate out if NOT completing - prevents flicker during successful completion
201
294
  _reactNative.Animated.timing(slideAnim, {
202
295
  toValue: height,
203
- duration: 250,
204
- useNativeDriver: true
296
+ useNativeDriver: true,
297
+ duration: 500,
298
+ // Longer duration for a more elegant exit
299
+ easing: _reactNative.Easing.bezier(0.16, 1, 0.3, 1) // Custom bezier curve for a luxurious, smooth exit
205
300
  }).start(() => {
206
- // Reset state if needed
301
+ // Use a timeout to prevent animation state updates during unmount
302
+ setTimeout(() => {
303
+ setModalVisible(false);
304
+ onClose(); // Call onClose from props
305
+ }, 16);
207
306
  });
307
+ } else if (hasBeenVisibleRef.current && isCompletingRef.current) {
308
+ // If completing, hide modal immediately without any animation or delay
309
+ setModalVisible(false);
310
+ // Don't call onClose() when completing - let parent handle the navigation
311
+ isCompletingRef.current = false; // Reset for next time
208
312
  }
209
- }, [visible, preferredPlatform]);
313
+ }, [visible, onClose]); // Removed isCompleting from dependency array
210
314
 
211
- // Cleanup effect for unmounting
315
+ // Cleanup socket connection and dots animation when component unmounts or becomes invisible
212
316
  (0, _react.useEffect)(() => {
213
317
  return () => {
214
- // Set mounted flag to false
215
- isMountedRef.current = false;
216
-
217
- // Clear any pending timeouts
218
- if (successTimeoutRef.current) {
219
- clearTimeout(successTimeoutRef.current);
220
- successTimeoutRef.current = null;
318
+ if (socketRef.current) {
319
+ console.log('🔌 Cleaning up socket connection...');
320
+ socketRef.current.disconnect();
321
+ socketRef.current = null;
221
322
  }
323
+ stopDotsAnimation();
222
324
  };
325
+ }, [visible]);
326
+
327
+ // Set up deep link listener for OAuth callbacks
328
+ const handleUrl = (0, _react.useCallback)(({
329
+ url
330
+ }) => {
331
+ if ((0, _platformAuthService.isOAuthCallback)(url)) {
332
+ handleOAuthCallback(url);
333
+ }
223
334
  }, []);
224
- const handleClose = () => {
225
- // Clear any pending timeouts before closing
226
- if (successTimeoutRef.current) {
227
- clearTimeout(successTimeoutRef.current);
228
- successTimeoutRef.current = null;
335
+
336
+ // Load user data and authentication token when modal becomes visible
337
+ (0, _react.useEffect)(() => {
338
+ const loadUserData = async () => {
339
+ try {
340
+ // Check for existing user info first
341
+ const existingToken = await _asyncStorage.default.getItem('existing_user_token');
342
+ const existingInfo = await _asyncStorage.default.getItem('existing_user_info');
343
+ if (existingToken && existingInfo) {
344
+ console.log('🔍 Found existing user info - user wants to add more data');
345
+ setIsExistingUser(true);
346
+ setExistingUserToken(existingToken);
347
+ setExistingUserInfo(JSON.parse(existingInfo));
348
+
349
+ // Clear the temporary storage
350
+ await _asyncStorage.default.removeItem('existing_user_token');
351
+ await _asyncStorage.default.removeItem('existing_user_info');
352
+ }
353
+ const token = (await _asyncStorage.default.getItem('onairos_jwt_token')) || (await _asyncStorage.default.getItem('auth_token'));
354
+ setUserToken(token);
355
+ if (token) {
356
+ var _user$email;
357
+ // Use provided username or get stored username
358
+ const storedUsername = await (0, _authService.getOnairosUsername)();
359
+ const fallbackUsername = storedUsername || (user === null || user === void 0 || (_user$email = user.email) === null || _user$email === void 0 ? void 0 : _user$email.split('@')[0]) || (user === null || user === void 0 ? void 0 : user.name) || 'mobile_user';
360
+ console.log('🔍 Using username for training:', fallbackUsername);
361
+ setUserInfo({
362
+ username: fallbackUsername,
363
+ email: (user === null || user === void 0 ? void 0 : user.email) || null,
364
+ id: null // Will be filled by backend during training
365
+ });
366
+ setUsername(fallbackUsername);
367
+ }
368
+ } catch (error) {
369
+ var _user$email2;
370
+ console.error('Error loading user data:', error);
371
+ // Fallback user info
372
+ const fallbackUsername = (user === null || user === void 0 || (_user$email2 = user.email) === null || _user$email2 === void 0 ? void 0 : _user$email2.split('@')[0]) || (user === null || user === void 0 ? void 0 : user.name) || 'mobile_user';
373
+ setUserInfo({
374
+ username: fallbackUsername,
375
+ email: (user === null || user === void 0 ? void 0 : user.email) || null,
376
+ id: null
377
+ });
378
+ setUsername(fallbackUsername);
379
+ }
380
+ };
381
+ if (visible) {
382
+ loadUserData();
229
383
  }
384
+ }, [visible, user]);
385
+ const loadInitialStatus = async () => {
386
+ try {
387
+ // Get the stored Onairos username first
388
+ const storedUsername = await (0, _authService.getOnairosUsername)();
389
+ const fallbackUsername = (user === null || user === void 0 ? void 0 : user.email) || (user === null || user === void 0 ? void 0 : user.name) || `user_${Math.floor(Math.random() * 10000)}`;
390
+ const finalUsername = storedUsername || fallbackUsername;
391
+ console.log('🔍 Loading username for data connections:', {
392
+ storedUsername,
393
+ fallbackUsername,
394
+ finalUsername
395
+ });
396
+ setUsername(finalUsername);
397
+
398
+ // Initialize connection statuses
399
+ const connectionStatus = await getConnectionStatus();
400
+ console.log('Initial connection status:', connectionStatus);
401
+
402
+ // Update the main connections state
403
+ setConnections(connectionStatus);
404
+
405
+ // Convert connections object to status strings
406
+ const statuses = {};
407
+ Object.keys(connectionStatus).forEach(platform => {
408
+ var _connectionStatus$pla;
409
+ statuses[platform] = (_connectionStatus$pla = connectionStatus[platform]) !== null && _connectionStatus$pla !== void 0 && _connectionStatus$pla.connected ? 'connected' : 'disconnected';
410
+ });
411
+ setConnectionStatuses(statuses);
230
412
 
231
- // Set mounted flag to false
232
- isMountedRef.current = false;
413
+ // Initialize platform toggles based on connection statuses
414
+ const toggles = {};
415
+ Object.keys(connectionStatus).forEach(platform => {
416
+ var _connectionStatus$pla2;
417
+ toggles[platform] = ((_connectionStatus$pla2 = connectionStatus[platform]) === null || _connectionStatus$pla2 === void 0 ? void 0 : _connectionStatus$pla2.connected) || false;
418
+ });
419
+ setPlatformToggles(toggles);
420
+ console.log('Connection statuses set:', statuses);
421
+ console.log('Platform toggles set:', toggles);
422
+ } catch (error) {
423
+ console.error('Error loading initial connection status:', error);
424
+ // Set empty objects as fallback
425
+ setConnections({});
426
+ setConnectionStatuses({});
427
+ setPlatformToggles({});
428
+
429
+ // Still set a fallback username even if other loading fails
430
+ const fallbackUsername = (user === null || user === void 0 ? void 0 : user.email) || (user === null || user === void 0 ? void 0 : user.name) || `user_${Math.floor(Math.random() * 10000)}`;
431
+ setUsername(fallbackUsername);
432
+ }
433
+ };
434
+ const handleClose = () => {
435
+ const currentlyCompleting = isCompletingRef.current; // Capture ref's current value
233
436
 
234
- // Animate out and then call onClose
437
+ // Animate out with a luxurious, smooth motion
235
438
  _reactNative.Animated.timing(slideAnim, {
236
439
  toValue: height,
237
- duration: 250,
238
- useNativeDriver: true
440
+ // Full slide down
441
+ useNativeDriver: true,
442
+ duration: 500,
443
+ // Longer duration for a more elegant exit
444
+ easing: _reactNative.Easing.bezier(0.16, 1, 0.3, 1) // Custom bezier curve for a luxurious, smooth exit
239
445
  }).start(() => {
240
- // Only call onClose if component is still meant to be mounted
241
- // This prevents the "User closed onboarding" error
242
- onClose();
446
+ // Small delay before closing modal to ensure animation completes fully
447
+ setTimeout(() => {
448
+ setModalVisible(false);
449
+ if (!currentlyCompleting) {
450
+ // Use the captured value
451
+ onClose();
452
+ }
453
+ // Do NOT reset isCompletingRef.current here. The useEffect watching props.visible is responsible for that.
454
+ }, 100);
243
455
  });
244
456
  };
245
- const loadInitialStatus = (0, _react.useCallback)(async () => {
457
+ const handleConnectPlatform = async platformId => {
458
+ // Trigger haptic feedback when connect button is pressed
459
+ (0, _haptics.triggerHaptic)(_haptics.HapticType.BUTTON_PRESS);
460
+ setConnectingPlatform(platformId);
246
461
  try {
247
- console.log('🔄 Loading initial connection status...');
248
- const status = await getConnectionStatus();
249
- console.log('✅ Connection status loaded:', status);
250
- setConnections(status || {});
462
+ // Check if the platform has a native SDK
463
+ if ((0, _platformAuthService.hasNativeSDK)(platformId)) {
464
+ // Use native SDK authentication
465
+ setCurrentPlatform(platformId);
466
+ const success = await (0, _platformAuthService.initiateNativeAuth)(platformId, username);
467
+ if (success) {
468
+ // Update connections state
469
+ setConnections(prev => ({
470
+ ...prev,
471
+ [platformId]: {
472
+ userName: username,
473
+ connected: true
474
+ }
475
+ }));
476
+
477
+ // Update platform toggles
478
+ setPlatformToggles(prev => ({
479
+ ...prev,
480
+ [platformId]: true
481
+ }));
482
+
483
+ // Update connection statuses
484
+ setConnectionStatuses(prev => ({
485
+ ...prev,
486
+ [platformId]: 'connected'
487
+ }));
488
+
489
+ // Store the connected platform
490
+ await storeConnectedPlatform(platformId);
491
+ }
492
+ } else {
493
+ // For other platforms, use the web OAuth flow
494
+ setCurrentPlatform(platformId);
495
+ const oauthUrl = await (0, _platformAuthService.initiateOAuth)(platformId, username);
496
+ if (oauthUrl) {
497
+ setOauthUrl(oauthUrl);
498
+ setStep('oauth');
499
+ }
500
+ }
251
501
  } catch (error) {
252
- console.error('❌ Failed to load connection status:', error);
253
- // Set empty connections to prevent crashes
254
- setConnections({});
502
+ console.error(`Error connecting to ${platformId}:`, error);
503
+ } finally {
504
+ setConnectingPlatform(null);
255
505
  }
256
- }, [getConnectionStatus]);
506
+ };
257
507
  const togglePlatform = (0, _react.useCallback)(async platformId => {
508
+ // If toggling on, initiate the OAuth flow for the platform
258
509
  if (!platformToggles[platformId]) {
259
- // Attempt to connect platform
260
510
  try {
261
- setIsConnectingPlatform(true);
262
- console.log(`🔌 Initiating connection for ${platformId}`);
263
-
264
- // Test API connectivity first
265
- console.log('🔍 Testing API connectivity...');
266
- const connectivityTest = await (0, _platformAuthService.testApiConnectivity)();
267
- if (!connectivityTest.success) {
268
- console.error('❌ API connectivity test failed:', connectivityTest.error);
269
- _reactNative.Alert.alert('Network Error', `${connectivityTest.error}\n\nPlease check your internet connection and try again.`);
511
+ // Special case for Instagram which uses the existing flow
512
+ if (platformId === 'instagram') {
513
+ setPlatformToggles(prev => ({
514
+ ...prev,
515
+ [platformId]: !prev[platformId]
516
+ }));
517
+ setConnections(prev => ({
518
+ ...prev,
519
+ [platformId]: {
520
+ userName: `${platformId}_user`,
521
+ connected: true
522
+ }
523
+ }));
524
+ // Store the connected platform
525
+ await storeConnectedPlatform(platformId);
270
526
  return;
271
527
  }
272
- console.log('✅ API connectivity confirmed');
273
-
274
- // Instagram: Use Opacity SDK exclusively
275
- if (platformId === 'instagram') {
276
- // Check if Opacity SDK is available
277
- if (!opacityInit || !OpacityEnvironment || !opacityGet) {
278
- console.error('❌ Opacity SDK not available for Instagram');
279
- throw new Error('Instagram connection requires the Opacity SDK. Please ensure @opacity-labs/react-native-opacity is properly installed and configured.');
280
- }
281
- console.log('🔌 Initializing Opacity SDK for Instagram...');
282
-
283
- // Initialize Opacity SDK with your API key
284
- const apiKey = 'OsamaTest-7bde2407-7360-462a-86b4-b26d7f890cbb';
285
- await opacityInit({
286
- apiKey,
287
- environment: OpacityEnvironment.Production,
288
- shouldShowErrorsInWebView: true
289
- });
290
- console.log('✅ Opacity SDK initialized successfully');
291
- console.log('📱 Fetching Instagram profile...');
292
528
 
293
- // Fetch Instagram profile using Opacity SDK
294
- const profile = await opacityGet('flow:instagram:profile');
295
- if (profile && typeof profile === 'object') {
296
- console.log('✅ Instagram profile retrieved:', profile);
297
-
298
- // Extract username from profile or use fallback
299
- const instagramUsername = profile.username || profile.name || username;
529
+ // Check if the platform has a native SDK
530
+ if ((0, _platformAuthService.hasNativeSDK)(platformId)) {
531
+ // Use native SDK authentication
532
+ setCurrentPlatform(platformId);
533
+ const success = await (0, _platformAuthService.initiateNativeAuth)(platformId, username);
534
+ if (success) {
535
+ // Update connections state
536
+ setConnections(prev => ({
537
+ ...prev,
538
+ [platformId]: {
539
+ userName: username,
540
+ connected: true
541
+ }
542
+ }));
300
543
 
301
- // Update platform toggle state
544
+ // Update platform toggles
302
545
  setPlatformToggles(prev => ({
303
546
  ...prev,
304
547
  [platformId]: true
305
548
  }));
306
549
 
307
- // Update connections state with Instagram data
308
- setConnections(prev => ({
309
- ...prev,
310
- [platformId]: {
311
- userName: instagramUsername,
312
- connected: true,
313
- profileData: profile // Store additional profile data
314
- }
315
- }));
316
- console.log(`✅ Instagram successfully connected for user: ${instagramUsername}`);
317
- } else {
318
- throw new Error('Invalid or empty Instagram profile data returned from Opacity SDK');
319
- }
320
- } else {
321
- // For all other platforms (non-Instagram), check if they have native SDK
322
- if ((0, _platformAuthService.hasNativeSDK)(platformId)) {
323
- console.log(`📱 Using native SDK for ${platformId}`);
324
- // Use native SDK for authentication
325
- const success = await (0, _platformAuthService.initiateNativeAuth)(platformId, username);
326
- if (success) {
327
- console.log(`✅ Native authentication successful for ${platformId}`);
328
- // Update platform toggle state
329
- setPlatformToggles(prev => ({
330
- ...prev,
331
- [platformId]: true
332
- }));
333
-
334
- // Update connections state
335
- setConnections(prev => ({
336
- ...prev,
337
- [platformId]: {
338
- userName: username,
339
- connected: true
340
- }
341
- }));
342
- } else {
343
- throw new Error(`Native authentication failed for ${platformId}`);
344
- }
345
- } else {
346
- // Use OAuth WebView flow
347
- console.log(`🌐 Initiating OAuth flow for ${platformId}`);
348
- const oauthUrl = await (0, _platformAuthService.initiateOAuth)(platformId, username, AppName);
349
- if (oauthUrl) {
350
- console.log(`✅ Received OAuth URL for ${platformId}:`, oauthUrl);
351
- setCurrentPlatform(platformId);
352
- setOauthUrl(oauthUrl);
353
- setStep('oauth');
354
- } else {
355
- console.error(`❌ No OAuth URL returned for ${platformId}`);
356
- throw new Error(`Failed to get authorization URL for ${platformId}. Please try again.`);
357
- }
550
+ // Store the connected platform
551
+ await storeConnectedPlatform(platformId);
358
552
  }
553
+ return;
359
554
  }
360
- } catch (error) {
361
- console.error(`❌ Error connecting ${platformId}:`, error);
362
-
363
- // Provide user-friendly error messages based on platform
364
- let errorMessage = 'Unknown error occurred';
365
- if (error instanceof Error) {
366
- if (platformId === 'instagram') {
367
- if (error.message.includes('Initialize')) {
368
- errorMessage = 'Failed to initialize Instagram connection. Please check your internet connection.';
369
- } else if (error.message.includes('profile')) {
370
- errorMessage = 'Unable to retrieve Instagram profile. Please try again or check your Instagram account permissions.';
371
- } else {
372
- errorMessage = error.message;
373
- }
374
- } else {
375
- errorMessage = error.message;
376
- }
555
+
556
+ // For other platforms, use the web OAuth flow
557
+ setCurrentPlatform(platformId);
558
+ const oauthUrl = await (0, _platformAuthService.initiateOAuth)(platformId, username);
559
+
560
+ // If oauthUrl is null, it means we should use native SDK (which should have been caught above)
561
+ if (oauthUrl) {
562
+ setOauthUrl(oauthUrl);
563
+ setStep('oauth');
377
564
  }
378
- _reactNative.Alert.alert(`${platformId.charAt(0).toUpperCase() + platformId.slice(1)} Connection Failed`, errorMessage, [{
379
- text: 'OK',
380
- style: 'default'
381
- }]);
382
- } finally {
383
- setIsConnectingPlatform(false);
565
+ } catch (error) {
566
+ console.error(`Error initiating OAuth for ${platformId}:`, error);
567
+ // If there's an error, don't toggle the platform
568
+ return;
384
569
  }
385
570
  } else {
386
- // Disconnect platform
387
- console.log(`🔌 Disconnecting ${platformId}`);
571
+ // If toggling off, just update the state
388
572
  setPlatformToggles(prev => ({
389
573
  ...prev,
390
- [platformId]: false
574
+ [platformId]: !prev[platformId]
391
575
  }));
392
576
 
393
- // Update connections state
577
+ // Remove connection
394
578
  setConnections(prev => {
395
579
  const newConnections = {
396
580
  ...prev
@@ -399,50 +583,50 @@ const UniversalOnboarding = ({
399
583
  return newConnections;
400
584
  });
401
585
  }
402
- }, [platformToggles, username, AppName]);
586
+ }, [platformToggles, username]);
403
587
 
404
- /**
405
- * Handles OAuth callback URLs
588
+ /**
589
+ * Handles OAuth callback URLs
406
590
  */
407
591
  const handleOAuthCallback = (0, _react.useCallback)(url => {
408
- console.log('🔗 OAuth callback received:', url);
409
- const result = (0, _platformAuthService.handleOAuthCallbackUrl)(url);
410
- if (result.success && result.platform && result.code) {
411
- console.log(`✅ OAuth successful for ${result.platform}`);
412
-
413
- // Update connections state
414
- setConnections(prev => ({
415
- ...prev,
416
- [result.platform]: {
417
- userName: username,
418
- connected: true
419
- }
420
- }));
592
+ try {
593
+ // Extract the authorization code from the URL
594
+ const parsedUrl = new URL(url);
595
+ const code = parsedUrl.searchParams.get('code');
596
+ const platform = parsedUrl.searchParams.get('platform') || currentPlatform;
597
+ if (code && platform) {
598
+ // Update connections state
599
+ setConnections(prev => ({
600
+ ...prev,
601
+ [platform]: {
602
+ userName: username,
603
+ connected: true
604
+ }
605
+ }));
421
606
 
422
- // Update platform toggles
423
- setPlatformToggles(prev => ({
424
- ...prev,
425
- [result.platform]: true
426
- }));
607
+ // Update platform toggles
608
+ setPlatformToggles(prev => ({
609
+ ...prev,
610
+ [platform]: true
611
+ }));
427
612
 
428
- // Close OAuth window and return to connect step
429
- setOauthUrl('');
430
- setCurrentPlatform('');
431
- setStep('connect');
432
- console.log(`🎉 ${result.platform} successfully connected via OAuth`);
433
- } else {
434
- console.error('❌ OAuth callback failed or incomplete');
613
+ // Return to the connect step
614
+ setStep('connect');
615
+ }
616
+ } catch (error) {
617
+ console.error('Error handling OAuth callback:', error);
435
618
  }
436
- }, [username]);
619
+ }, [currentPlatform, username]);
437
620
 
438
- /**
439
- * Handles completion of the OAuth flow
621
+ /**
622
+ * Handles successful OAuth authentication from the OAuthWebView
440
623
  */
441
- const handleOAuthSuccess = (0, _react.useCallback)(code => {
442
- console.log(`OAuth success for ${currentPlatform} with code: ${code}`);
443
-
444
- // Update connections for the current platform
624
+ const handleOAuthSuccess = (0, _react.useCallback)(async code => {
625
+ console.log(`🎉 OAuth success for ${currentPlatform} - backend callback completed`);
626
+ console.log(`📝 Received result:`, code);
445
627
  if (currentPlatform) {
628
+ console.log(`✅ Updating connection state for ${currentPlatform}`);
629
+
446
630
  // Update connections state
447
631
  setConnections(prev => ({
448
632
  ...prev,
@@ -457,513 +641,893 @@ const UniversalOnboarding = ({
457
641
  ...prev,
458
642
  [currentPlatform]: true
459
643
  }));
460
- console.log(`Successfully connected ${currentPlatform} for user ${username}`);
644
+
645
+ // Update connection statuses
646
+ setConnectionStatuses(prev => ({
647
+ ...prev,
648
+ [currentPlatform]: 'connected'
649
+ }));
650
+
651
+ // Store the connected platform
652
+ await storeConnectedPlatform(currentPlatform);
653
+ console.log(`💾 ${currentPlatform} connection stored successfully`);
461
654
  }
462
655
 
463
- // Close OAuth window and return to connect step
656
+ // Close the OAuth window by returning to the connect step
657
+ console.log('🔄 Returning to connect step');
464
658
  setOauthUrl('');
465
- setCurrentPlatform('');
466
659
  setStep('connect');
467
- }, [currentPlatform, username]);
468
-
469
- // Function to check for existing account (spoofed for now)
470
- const checkExistingAccount = (0, _react.useCallback)(async () => {
471
- console.log('Checking for existing account...');
472
- // TODO: Implement actual logic to check cookies/storage for existing account
473
- // For now, this is spoofed and doesn't do anything
474
- return false;
475
- }, []);
476
-
477
- // Function to handle email submission
478
- const handleEmailSubmit = (0, _react.useCallback)(async () => {
479
- console.log('🚀 handleEmailSubmit called with email:', email);
480
- console.log('🧪 testMode value:', testMode);
481
- console.log('🧪 isTestMode computed:', isTestMode);
482
- try {
483
- if (!email || !email.trim()) {
484
- console.log('❌ No email provided');
485
- _reactNative.Alert.alert('Error', 'Please enter your email address');
486
- return;
487
- }
488
-
489
- // Basic email validation
490
- const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
491
- if (!emailRegex.test(email.trim())) {
492
- console.log('❌ Invalid email format');
493
- _reactNative.Alert.alert('Error', 'Please enter a valid email address');
494
- return;
495
- }
496
- console.log('📧 Email validation passed, proceeding...');
497
-
498
- // Check if we should skip API calls entirely (only for specific test scenarios)
499
- const shouldSkipApiCalls = typeof testMode === 'object' && testMode !== null && testMode.skipApiCalls === true;
500
- if (shouldSkipApiCalls) {
501
- console.log('🧪 Test mode with skipApiCalls: true - Skipping API call, proceeding to verification');
502
- setStep('verify');
503
- return;
504
- }
660
+ }, [currentPlatform, username, storeConnectedPlatform]);
661
+ const handlePinSubmit = (0, _react.useCallback)(async userPin => {
662
+ setPin(userPin);
505
663
 
506
- // Add loading state to prevent multiple submissions
507
- if (isVerifyingCode) {
508
- console.log('⚠️ Email verification already in progress');
509
- return;
510
- }
511
- setIsVerifyingCode(true);
512
- console.log('🔄 Starting email verification process...');
513
- console.log('📡 Will make API call with testMode flag:', isTestMode);
664
+ // Store PIN temporarily for training component access
665
+ (0, _pinStorageUtils.setTemporaryPin)(userPin);
666
+ console.log('🔐 [PIN SUBMIT] PIN submitted, checking for background training...');
514
667
 
515
- // Wrap the entire API call in a timeout to prevent hanging
516
- const timeoutPromise = new Promise((_, reject) => {
517
- setTimeout(() => reject(new Error('Request timeout')), 10000); // 10 second timeout
518
- });
519
- try {
520
- // Safety check for function availability with detailed debugging
521
- console.log('🔍 Checking requestEmailVerification function availability...');
522
- console.log('🔍 Type of requestEmailVerification:', typeof _platformAuthService.requestEmailVerification);
523
- console.log('🔍 requestEmailVerification function:', _platformAuthService.requestEmailVerification);
524
- if (typeof _platformAuthService.requestEmailVerification !== 'function') {
525
- console.error('❌ requestEmailVerification function not available');
526
- console.error('❌ Available functions from platformAuthService:', {
527
- requestEmailVerification: typeof _platformAuthService.requestEmailVerification,
528
- verifyEmailCode: typeof _platformAuthService.verifyEmailCode,
529
- checkEmailVerificationStatus: typeof _platformAuthService.checkEmailVerificationStatus
530
- });
531
- // In development, just proceed anyway
532
- console.log('🧪 Proceeding without API call in development mode');
533
- setStep('verify');
534
- return;
535
- }
536
- console.log('✅ requestEmailVerification function is available');
537
- console.log('🔄 Making API call to requestEmailVerification...');
538
-
539
- // Race between API call and timeout
540
- const result = await Promise.race([(0, _platformAuthService.requestEmailVerification)(email.trim(), isTestMode), timeoutPromise]);
541
- console.log('📡 Email verification API result:', result);
542
- if (result && result.success) {
543
- console.log('✅ Verification code requested successfully');
544
- setStep('verify');
545
- } else {
546
- console.warn('⚠️ Email verification request failed, but proceeding anyway:', result);
547
- // In development mode, proceed even if API fails
548
- setStep('verify');
549
- }
550
- } catch (verificationError) {
551
- console.error('❌ Error in email verification API call:', verificationError);
552
- // In development mode, proceed even if API fails
553
- console.log('🧪 API failed but proceeding to verification step in development mode');
554
- setStep('verify');
555
- } finally {
556
- setIsVerifyingCode(false);
557
- }
558
- } catch (error) {
559
- console.error('❌ Unexpected error in email submission:', error);
560
- setIsVerifyingCode(false);
668
+ // NEW: Check if background training is already running
669
+ if (isBackgroundTrainingStarted && backgroundSocketId) {
670
+ console.log('✅ [PIN SUBMIT] Background training detected, continuing with PIN validation...');
561
671
 
562
- // In development mode, still try to proceed
563
- console.log('🧪 Error occurred but attempting to proceed to verification step');
672
+ // Continue with existing training by sending PIN validation
564
673
  try {
565
- setStep('verify');
566
- } catch (stepError) {
567
- console.error('❌ Failed to set step to verify:', stepError);
568
- _reactNative.Alert.alert('Error', 'An unexpected error occurred. Please try again.');
674
+ await continueBackgroundTrainingWithPin(userPin);
675
+ setStep('persona'); // Move to persona step to show training progress
676
+ } catch (error) {
677
+ console.error(' [PIN SUBMIT] Failed to continue background training:', error);
678
+ // ❌ DISABLED: Don't start new training when PIN is submitted
679
+ // Just show persona step with error state
680
+ setStep('persona');
681
+ setPersonaStatus('Error: Failed to continue training');
682
+ setHasError(true);
569
683
  }
684
+ } else {
685
+ console.log('ℹ️ [PIN SUBMIT] No background training detected');
686
+ // ❌ DISABLED: Don't start training when PIN is submitted
687
+ // Training should only start during connector→PIN transition
688
+ setStep('persona');
689
+ setPersonaStatus('No training in progress. Please restart the flow.');
690
+ setHasError(true);
570
691
  }
571
- }, [email, isVerifyingCode, debug, testMode, isTestMode]);
692
+ console.log('🔐 [PIN SUBMIT] PIN stored securely, moved to persona step');
693
+ }, [isBackgroundTrainingStarted, backgroundSocketId]);
572
694
 
573
- // Function to handle verification code submission
574
- const handleVerificationSubmit = (0, _react.useCallback)(async () => {
575
- if (!verificationCode.trim() || verificationCode.trim().length !== 6) {
576
- _reactNative.Alert.alert('Error', 'Please enter a 6-digit verification code');
577
- return;
578
- }
579
- setIsVerifyingCode(true);
695
+ // Start real Enoch training via API (restored for backwards compatibility)
696
+ const startEnochTraining = async (socketId, authToken) => {
580
697
  try {
581
- // Safety check for function availability
582
- if (typeof _platformAuthService.verifyEmailCode !== 'function') {
583
- throw new Error('Email verification service not available');
698
+ setPersonaStatus('Starting training...');
699
+ setPersonaProgress(15);
700
+
701
+ // Use provided token or get from AsyncStorage to avoid state timing issues
702
+ const token = authToken || (await _asyncStorage.default.getItem('onairos_jwt_token')) || (await _asyncStorage.default.getItem('auth_token'));
703
+ if (!token) {
704
+ console.error('❌ No authentication token available');
705
+ throw new Error('No authentication token available');
584
706
  }
707
+ console.log('🚀 Starting Enoch training with socketId:', socketId);
708
+ console.log('🔑 Using auth token:', token ? `${token.substring(0, 20)}...` : 'None');
709
+
710
+ // Get stored Onairos username for API calls
711
+ const storedUsername = await (0, _authService.getOnairosUsername)();
712
+ const finalUsername = storedUsername || (userInfo === null || userInfo === void 0 ? void 0 : userInfo.username) || (userInfo === null || userInfo === void 0 ? void 0 : userInfo.name) || username || 'mobile_user';
713
+
714
+ // Get connected platforms information
715
+ const connectedPlatforms = await _asyncStorage.default.getItem('connectedPlatforms');
716
+ const platformsList = connectedPlatforms ? JSON.parse(connectedPlatforms) : [];
717
+ console.log('📱 Connected platforms for training:', platformsList);
718
+
719
+ // Get encrypted PIN for training (if available)
720
+ const encryptedPin = await (0, _pinEncryptionService.getEncryptedPinForAPI)().catch(error => {
721
+ console.warn('⚠️ Could not get encrypted PIN for training:', error);
722
+ return null;
723
+ });
585
724
 
586
- // Test Mode: Use specific flows
587
- if (isTestMode) {
588
- console.log('🧪 Test mode verification - simulating success');
589
- if (isExistingUserFlow) {
590
- // Flow 1: Existing User Data Request Close (return API URL)
591
- console.log('🧪 Test Flow 1: Existing User → Show Data Request');
592
- setIsExistingUser(true);
593
- setStep('dataRequest');
594
- return;
595
- } else if (isNewUserFlow) {
596
- // Flow 2: New User → Platform Connect → PIN → Training
597
- console.log('🧪 Test Flow 2: New User → Platform Connect');
598
- const emailPrefix = email.trim().split('@')[0] || 'TestUser';
599
- setUsername(emailPrefix);
600
- setStep('connect');
601
- return;
602
- }
725
+ // Prepare user data for training - match backend expected format
726
+ const trainingData = {
727
+ socketId,
728
+ username: finalUsername,
729
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || null,
730
+ modelKey: null,
731
+ connectedPlatforms: platformsList,
732
+ platformConnections: connections,
733
+ ...(encryptedPin && {
734
+ encryptedPin: encryptedPin,
735
+ hasPinData: true
736
+ })
737
+ };
738
+ console.log('📤 Sending training data to /mobile-training/enoch:', trainingData);
739
+
740
+ // Use the new training function that includes YouTube migration check
741
+ const result = await (0, _mobileTrainingService.startEnochTrainingWithYouTubeCheck)(trainingData);
742
+ console.log('📡 Training API response:', result);
743
+
744
+ // Handle CONNECTIONS_REQUIRED scenario (pre-training validation)
745
+ if (result.requiresConnections || result.code === 'CONNECTIONS_REQUIRED') {
746
+ console.log('🔗 Connections required detected from HTTP response');
747
+ setDataScenario('CONNECTIONS_REQUIRED');
748
+ setDataDetails(result);
749
+ setShowDataWarning(true);
750
+ setPersonaStatus('Connections required');
751
+ setHasError(true);
752
+ stopDotsAnimation();
753
+ return;
603
754
  }
604
-
605
- // Real API call (production) or test mode
606
- const result = await (0, _platformAuthService.verifyEmailCode)(email.trim(), verificationCode.trim(), isTestMode);
607
755
  if (result.success) {
608
- console.log(' Email verification successful');
609
-
610
- // Check if user exists in backend (properly typed now)
611
- const existingUser = result.existingUser || false;
612
- setIsExistingUser(existingUser);
613
- if (existingUser) {
614
- console.log('👤 Existing user detected, showing data request screen');
615
- setStep('dataRequest');
616
- } else {
617
- console.log('🆕 New user, proceeding to platform connection');
618
- // Safely set username from email prefix
619
- try {
620
- const emailPrefix = email.trim().split('@')[0];
621
- if (emailPrefix && emailPrefix.length > 0) {
622
- setUsername(emailPrefix);
623
- } else {
624
- setUsername('User'); // Fallback username
625
- }
626
- } catch (usernameError) {
627
- console.warn('Failed to extract username from email, using fallback:', usernameError);
628
- setUsername('User');
629
- }
630
- setStep('connect');
756
+ console.log('🚀 Training Started:', result.message);
757
+ console.log('🎯 Training Features:', result.features);
758
+
759
+ // Log the new features from the spec
760
+ if (result.features) {
761
+ console.log('✅ Inference enabled:', result.features.inference);
762
+ console.log('💾 Storage method:', result.features.storage);
763
+ console.log('🔒 Compression enabled:', result.features.compression);
764
+ console.log('🔐 Encryption enabled:', result.features.encryption);
765
+ console.log('📊 Training type:', result.features.type);
766
+ console.log('🗄️ Databases:', result.features.databases);
767
+ console.log('📈 Query scores enabled:', result.features.queryScores);
631
768
  }
769
+ setPersonaStatus('Training model...');
770
+ setPersonaProgress(25);
632
771
  } else {
633
- _reactNative.Alert.alert('Verification Failed', result.error || 'Invalid verification code');
772
+ console.error(' Training start failed:', result.error);
773
+ setPersonaStatus(`Error: ${result.error || 'Training failed to start'}`);
774
+ setHasError(true);
775
+ stopDotsAnimation();
634
776
  }
635
777
  } catch (error) {
636
- console.error('❌ Error verifying code:', error);
637
- _reactNative.Alert.alert('Error', 'Failed to verify code');
638
- } finally {
639
- setIsVerifyingCode(false);
778
+ console.error('❌ Training start error:', error);
779
+ setPersonaStatus(`Error: ${error instanceof Error ? error.message : 'Unknown error'}`);
780
+ setHasError(true);
781
+ stopDotsAnimation();
640
782
  }
641
- }, [email, verificationCode]);
642
- const handlePinSubmit = (0, _react.useCallback)(async userPin => {
643
- setPin(userPin);
644
- setStep('training');
783
+ };
645
784
 
646
- // Save session data for "Never Connect Again" functionality
785
+ // NEW: Continue background training with PIN validation
786
+ const continueBackgroundTrainingWithPin = async userPin => {
647
787
  try {
648
- const sessionData = {
649
- pin: userPin,
650
- connections,
651
- platformToggles,
652
- selectedTier,
653
- username,
654
- timestamp: Date.now(),
655
- appName: AppName,
656
- inferenceData: auto ? inferenceData : undefined,
657
- partner
658
- };
788
+ console.log('🔐 [BACKGROUND] Continuing existing background training with PIN validation');
789
+ console.log('🔑 Using auth token:', `${userToken === null || userToken === void 0 ? void 0 : userToken.substring(0, 20)}...`);
659
790
 
660
- // Store session data in secure storage for future use
661
- console.log('Saving session data for future "Never Connect Again" functionality:', sessionData);
791
+ // Check if we have a valid socket ID
792
+ if (!backgroundSocketId) {
793
+ throw new Error('No background socket ID available');
794
+ }
795
+
796
+ // ❌ REMOVED: Don't send new training signal - training already started!
797
+ // We should just validate the PIN with the existing training, not start new training
662
798
 
663
- // TODO: Implement actual secure storage of session data
664
- // This would typically involve:
665
- // 1. Storing encrypted session data locally
666
- // 2. Setting cookies in WebView for onairos.uk domain
667
- // 3. Storing authentication tokens securely
799
+ console.log('🔐 [BACKGROUND] PIN validation - continuing with existing training session');
800
+ console.log('🔌 [BACKGROUND] Using existing socket ID:', backgroundSocketId);
668
801
 
669
- // For now, we'll simulate this with console logging
670
- console.log('Session data saved - future apps will detect existing account');
802
+ // Just log that we're continuing - the existing training should handle PIN internally
803
+ console.log(' [BACKGROUND] PIN submitted for existing training session');
671
804
  } catch (error) {
672
- console.error('Failed to save session data:', error);
805
+ console.error('❌ [BACKGROUND] Failed to continue background training:', error);
806
+ throw error;
673
807
  }
674
- }, [connections, selectedTier, platformToggles, username, AppName, auto, inferenceData, partner]);
675
- const handleTrainingComplete = (0, _react.useCallback)(async () => {
676
- console.log('🎉 Training completed successfully');
677
- console.log('🔍 Auto mode enabled:', auto);
678
- console.log('🔍 Inference data available:', !!inferenceData);
679
- try {
680
- if (auto && inferenceData) {
681
- console.log('🤖 Auto mode: Making API request to get URL and perform inference');
808
+ };
682
809
 
683
- // First, get the API URL from backend
684
- const apiUrlResponse = await fetch('https://api2.onairos.uk/', {
685
- method: 'POST',
686
- headers: {
687
- 'Content-Type': 'application/json'
688
- },
689
- body: JSON.stringify({
690
- Info: {
691
- storage: 'secure',
692
- appId: AppName,
693
- confirmations: Object.keys(requestData || {}),
694
- EncryptedUserPin: pin,
695
- // Use the actual PIN from user
696
- account: email.trim(),
697
- proofMode: false
698
- }
699
- })
700
- });
701
- if (!apiUrlResponse.ok) {
702
- throw new Error(`Failed to get API URL: ${apiUrlResponse.status}`);
703
- }
704
- const {
705
- apiUrl,
706
- token
707
- } = await apiUrlResponse.json();
708
- console.log('✅ Received API URL:', apiUrl);
709
- console.log('✅ Received token:', (token === null || token === void 0 ? void 0 : token.substring(0, 20)) + '...');
710
-
711
- // Now make the inference call with the provided data
712
- const inferenceResponse = await fetch(apiUrl, {
713
- method: 'POST',
714
- headers: {
715
- 'Content-Type': 'application/json',
716
- 'Authorization': `Bearer ${token}`
717
- },
718
- body: JSON.stringify({
719
- ...inferenceData,
720
- userEmail: email.trim(),
721
- appName: AppName,
722
- timestamp: new Date().toISOString()
723
- })
724
- });
725
- if (!inferenceResponse.ok) {
726
- throw new Error(`Inference API failed: ${inferenceResponse.status}`);
727
- }
728
- const inferenceResults = await inferenceResponse.json();
729
- console.log('✅ Auto mode inference results:', inferenceResults);
810
+ // Replace fake persona creation with real training setup
811
+ const startPersonaCreation = async () => {
812
+ setPersonaProgress(0);
813
+ setPersonaStatus('Initializing');
814
+ setIsPersonaComplete(false);
815
+ setHasError(false);
730
816
 
731
- // Close the modal first
732
- handleClose();
817
+ // Start the dots animation
818
+ startDotsAnimation();
819
+ try {
820
+ var _user$email4;
821
+ console.log('🚀 Starting persona creation...');
822
+
823
+ // Ensure we have a valid authentication token before starting
824
+ console.log('🔐 Step 1: Ensuring authentication token...');
825
+ const authToken = await ensureAuthToken();
826
+ if (!authToken) {
827
+ throw new Error('Failed to create or retrieve authentication token');
828
+ }
733
829
 
734
- // Complete onboarding with inference results
735
- setTimeout(() => {
736
- onComplete(apiUrl, token, {
737
- pin,
738
- connections,
739
- platformToggles,
740
- selectedTier,
741
- tierData: requestData === null || requestData === void 0 ? void 0 : requestData[selectedTier],
742
- sessionSaved: true,
743
- // Add inference data if auto mode is enabled
744
- ...(auto && inferenceData && {
745
- inferenceData
746
- }),
747
- // Add partner info for special partners
748
- ...(partner && {
749
- partner: partner === 'couplebible' ? 'CoupleBible' : partner
750
- }),
751
- autoMode: true,
752
- inferenceResults,
753
- apiUrl,
754
- token
755
- });
756
- }, 100);
757
- } else {
758
- console.log('📋 Standard mode: Returning API URL for manual use');
759
-
760
- // Prepare completion data
761
- const completionData = {
762
- pin,
763
- connections,
764
- platformToggles,
765
- selectedTier,
766
- tierData: requestData === null || requestData === void 0 ? void 0 : requestData[selectedTier],
767
- sessionSaved: true,
768
- // Add inference data if auto mode is enabled
769
- ...(auto && inferenceData && {
770
- inferenceData
771
- }),
772
- // Add partner info for special partners
773
- ...(partner && {
774
- partner: partner === 'couplebible' ? 'CoupleBible' : partner
775
- }),
776
- autoMode: false
830
+ // Set the token in state
831
+ setUserToken(authToken);
832
+ console.log('✅ Authentication token set in state:', `${authToken.substring(0, 20)}...`);
833
+ console.log('🔍 Token length:', authToken.length);
834
+
835
+ // Also verify it was stored properly
836
+ const storedToken = await _asyncStorage.default.getItem('onairos_jwt_token');
837
+ console.log('🔑 Token stored verification:', storedToken ? `${storedToken.substring(0, 20)}...` : 'Not stored');
838
+
839
+ // If userInfo is not set, try to reload it
840
+ if (!userInfo) {
841
+ var _user$email3;
842
+ console.log('🔄 UserInfo not available, attempting to reload...');
843
+ const storedUsername = await (0, _authService.getOnairosUsername)();
844
+ const fallbackUsername = storedUsername || (user === null || user === void 0 || (_user$email3 = user.email) === null || _user$email3 === void 0 ? void 0 : _user$email3.split('@')[0]) || (user === null || user === void 0 ? void 0 : user.name) || 'mobile_user';
845
+ const newUserInfo = {
846
+ username: fallbackUsername,
847
+ email: (user === null || user === void 0 ? void 0 : user.email) || null,
848
+ id: null
777
849
  };
778
- console.log('Completion data prepared:', completionData);
850
+ setUserInfo(newUserInfo);
851
+ setUsername(fallbackUsername);
852
+ console.log('🧑‍💻 Set user info:', newUserInfo);
779
853
 
780
- // Close the modal first
781
- handleClose();
782
-
783
- // Then call the completion callback
784
- setTimeout(() => {
785
- onComplete('https://api2.onairos.uk', 'dummy-token', completionData);
786
- }, 100);
854
+ // Give a moment for state to update
855
+ await new Promise(resolve => setTimeout(() => resolve(), 200));
787
856
  }
788
- } catch (error) {
789
- console.error('❌ Error in training complete:', error);
790
-
791
- // Fallback to standard mode
792
- const completionData = {
793
- pin,
794
- connections,
795
- platformToggles,
796
- selectedTier,
797
- tierData: requestData === null || requestData === void 0 ? void 0 : requestData[selectedTier],
798
- sessionSaved: true,
799
- // Add inference data if auto mode is enabled
800
- ...(auto && inferenceData && {
801
- inferenceData
802
- }),
803
- // Add partner info for special partners
804
- ...(partner && {
805
- partner: partner === 'couplebible' ? 'CoupleBible' : partner
806
- }),
807
- autoMode: false,
808
- error: error instanceof Error ? error.message : 'Unknown error'
809
- };
810
- console.log('Fallback completion data:', completionData);
811
-
812
- // Close the modal first
813
- handleClose();
814
857
 
815
- // Then call the completion callback
858
+ // Check again after potential reload
859
+ const currentUserInfo = userInfo || {
860
+ username: username || (user === null || user === void 0 || (_user$email4 = user.email) === null || _user$email4 === void 0 ? void 0 : _user$email4.split('@')[0]) || (user === null || user === void 0 ? void 0 : user.name) || 'mobile_user',
861
+ email: (user === null || user === void 0 ? void 0 : user.email) || null,
862
+ id: null
863
+ };
864
+ if (!authToken) {
865
+ console.error('❌ No authentication token available after ensureAuthToken');
866
+ throw new Error('No authentication token available');
867
+ }
868
+ console.log('🔧 Setting up socket connection for real training...');
869
+ console.log('🧑‍💻 User info available:', currentUserInfo);
870
+ console.log('🔑 Token available:', !!authToken);
871
+ console.log('🌐 Attempting to connect to: https://api2.onairos.uk');
872
+ console.log('📱 Device platform:', _reactNative.Platform.OS);
873
+ console.log('🔗 Network connectivity check starting...');
874
+ setPersonaStatus('Connecting');
875
+ setPersonaProgress(5);
876
+
877
+ // Initialize socket connection with enhanced configuration
878
+ socketRef.current = (0, _socket.io)('https://api2.onairos.uk', {
879
+ transports: ['websocket', 'polling'],
880
+ // Add polling as fallback
881
+ autoConnect: false,
882
+ timeout: 15000,
883
+ // Increase timeout to 15 seconds
884
+ reconnection: true,
885
+ // Enable reconnection with limits
886
+ reconnectionAttempts: 3,
887
+ reconnectionDelay: 1000,
888
+ forceNew: true // Force a new connection
889
+ });
890
+ console.log('🔌 Socket instance created:', {
891
+ connected: socketRef.current.connected,
892
+ id: socketRef.current.id,
893
+ disconnected: socketRef.current.disconnected
894
+ });
895
+
896
+ // Socket event listeners with enhanced error handling
897
+ socketRef.current.on('connect', () => {
898
+ var _socketRef$current, _socketRef$current2, _socketRef$current3, _socketRef$current4;
899
+ console.log('✅ Socket connected for training');
900
+ console.log('🔌 Socket connection details:', {
901
+ id: (_socketRef$current = socketRef.current) === null || _socketRef$current === void 0 ? void 0 : _socketRef$current.id,
902
+ connected: (_socketRef$current2 = socketRef.current) === null || _socketRef$current2 === void 0 ? void 0 : _socketRef$current2.connected,
903
+ transport: (_socketRef$current3 = socketRef.current) === null || _socketRef$current3 === void 0 || (_socketRef$current3 = _socketRef$current3.io) === null || _socketRef$current3 === void 0 || (_socketRef$current3 = _socketRef$current3.engine) === null || _socketRef$current3 === void 0 || (_socketRef$current3 = _socketRef$current3.transport) === null || _socketRef$current3 === void 0 ? void 0 : _socketRef$current3.name
904
+ });
905
+ setSocketConnected(true);
906
+ setPersonaStatus('Starting training');
907
+ setPersonaProgress(10);
908
+ const socketId = (_socketRef$current4 = socketRef.current) === null || _socketRef$current4 === void 0 ? void 0 : _socketRef$current4.id;
909
+ console.log('🔌 Socket ID for training:', socketId);
910
+ if (socketId) {
911
+ // Add a small delay to ensure socket is fully ready and registered on backend
912
+ console.log('🔄 Socket ready for persona display with token:', authToken ? `${authToken.substring(0, 20)}...` : 'None');
913
+ console.log('⏰ Socket registered but training will not start from persona screen...');
914
+ // ❌ DISABLED: Don't start training from persona screen
915
+ // Training should only start during connector→PIN transition
916
+ // setTimeout(() => {
917
+ // console.log('🚀 Now starting training with socket ID:', socketId);
918
+ // startEnochTraining(socketId, authToken);
919
+ // }, 2000);
920
+
921
+ // Just show the persona screen without starting training
922
+ setPersonaStatus('Waiting for training to start from connector→PIN transition');
923
+ } else {
924
+ console.error('❌ No socket ID available after connection');
925
+ setPersonaStatus('Connection error. Please try again.');
926
+ setHasError(true);
927
+ stopDotsAnimation();
928
+ }
929
+ });
930
+ socketRef.current.on('disconnect', reason => {
931
+ var _socketRef$current5;
932
+ console.log('❌ Socket disconnected, reason:', reason);
933
+ console.log('🔍 Disconnect details:', {
934
+ reason: reason,
935
+ wasConnected: socketConnected,
936
+ socketId: (_socketRef$current5 = socketRef.current) === null || _socketRef$current5 === void 0 ? void 0 : _socketRef$current5.id
937
+ });
938
+ setSocketConnected(false);
939
+ });
940
+ socketRef.current.on('reconnect', attemptNumber => {
941
+ console.log('🔄 Socket reconnected after', attemptNumber, 'attempts');
942
+ setSocketConnected(true);
943
+ });
944
+ socketRef.current.on('reconnect_attempt', attemptNumber => {
945
+ console.log('🔄 Socket reconnection attempt:', attemptNumber);
946
+ setPersonaStatus(`Reconnecting... (${attemptNumber}/3)`);
947
+ });
948
+ socketRef.current.on('reconnect_error', error => {
949
+ console.error('❌ Socket reconnection error:', error);
950
+ });
951
+ socketRef.current.on('reconnect_failed', () => {
952
+ console.error('❌ Socket reconnection failed after all attempts');
953
+ setPersonaStatus('Connection failed. Please try again.');
954
+ setHasError(true);
955
+ stopDotsAnimation();
956
+ });
957
+ socketRef.current.on('connect_error', error => {
958
+ console.error('❌ Socket connection error:', error);
959
+ console.error('❌ Socket error details:', {
960
+ message: error.message,
961
+ name: error.name,
962
+ stack: error.stack,
963
+ errorObject: error
964
+ });
965
+ setPersonaStatus('Connection error. Please try again.');
966
+ setHasError(true);
967
+ stopDotsAnimation();
968
+ });
969
+ socketRef.current.on('trainingCompleted', data => {
970
+ console.log('✅ Training Complete:', data);
971
+ setPersonaStatus('Running test inference');
972
+ setPersonaProgress(60);
973
+ });
974
+ socketRef.current.on('inferenceCompleted', data => {
975
+ console.log('🧠 Inference Complete:', data);
976
+ setPersonaStatus('Uploading to S3');
977
+ setPersonaProgress(80);
978
+ setUserTraits(data.traits);
979
+ setInferenceResults(data.inferenceResults);
980
+ });
981
+ socketRef.current.on('modelStandby', data => {
982
+ console.log('🎉 All Complete:', data);
983
+
984
+ // Log completion details based on new spec
985
+ if (data.completed) {
986
+ console.log('✅ Training completed:', data.message);
987
+ console.log('💾 Storage method:', data.storage);
988
+ console.log('🔐 Encryption enabled:', data.encryption);
989
+ console.log('🧠 Inference enabled:', data.inference);
990
+
991
+ // Log database info for Enoch mode
992
+ if (data.databases && Array.isArray(data.databases)) {
993
+ console.log('🗄️ Databases used:', data.databases.join(', '));
994
+ }
995
+
996
+ // Log testing mode
997
+ if (data.testing) {
998
+ console.log('🧪 Testing mode enabled');
999
+ }
1000
+ }
1001
+ setIsPersonaComplete(true);
1002
+ setPersonaStatus('Complete!');
1003
+ setPersonaProgress(100);
1004
+ stopDotsAnimation();
1005
+ });
1006
+ socketRef.current.on('trainingUpdate', data => {
1007
+ console.log('📊 Training update:', data);
1008
+
1009
+ // Handle YouTube token expiry
1010
+ if (data.error && data.error.includes('YouTube access token has expired')) {
1011
+ console.log('🔄 YouTube token expired, triggering reconnection...');
1012
+ setDataScenario(null);
1013
+ setShowDataWarning(false);
1014
+ setPersonaStatus('YouTube token expired - reconnecting...');
1015
+
1016
+ // Try to refresh tokens first before full reconnection
1017
+ setTimeout(async () => {
1018
+ try {
1019
+ // Import the refresh function
1020
+ const {
1021
+ refreshYouTubeTokens
1022
+ } = await Promise.resolve().then(() => _interopRequireWildcard(require('../services/platformAuthService')));
1023
+ console.log('🔄 Attempting to refresh YouTube tokens...');
1024
+ const refreshSuccess = await refreshYouTubeTokens();
1025
+ if (refreshSuccess) {
1026
+ console.log('✅ YouTube tokens refreshed, but training restart disabled');
1027
+ setPersonaStatus('YouTube tokens refreshed - but training only starts from connector→PIN');
1028
+
1029
+ // ❌ DISABLED: Don't restart training from persona screen
1030
+ // Training should only start during connector→PIN transition
1031
+ // if (socketRef.current?.id) {
1032
+ // startEnochTraining(socketRef.current.id, userToken ?? undefined);
1033
+ // }
1034
+
1035
+ setHasError(true); // Show error so user can restart flow properly
1036
+ } else {
1037
+ console.log('❌ Token refresh failed, attempting full reconnection...');
1038
+ setPersonaStatus('Token refresh failed - please restart from connector screen');
1039
+
1040
+ // ❌ DISABLED: Don't restart training from persona screen
1041
+ // Fall back to full reconnection
1042
+ try {
1043
+ await handleConnectPlatform('youtube');
1044
+ console.log('✅ YouTube reconnected, but training restart disabled');
1045
+ setPersonaStatus('YouTube reconnected - please restart from connector screen');
1046
+
1047
+ // ❌ DISABLED: Don't restart training from persona screen
1048
+ // Training should only start during connector→PIN transition
1049
+ // if (socketRef.current?.id) {
1050
+ // startEnochTraining(socketRef.current.id, userToken ?? undefined);
1051
+ // }
1052
+
1053
+ setHasError(true); // Show error so user can restart flow properly
1054
+ } catch (reconnectError) {
1055
+ console.error('❌ YouTube reconnection failed:', reconnectError);
1056
+ setPersonaStatus('YouTube reconnection failed. Please restart from connector screen.');
1057
+ setHasError(true);
1058
+ stopDotsAnimation();
1059
+ }
1060
+ }
1061
+ } catch (error) {
1062
+ console.error('❌ YouTube token refresh/reconnection error:', error);
1063
+ setPersonaStatus('YouTube connection failed. Please try again.');
1064
+ setHasError(true);
1065
+ stopDotsAnimation();
1066
+ }
1067
+ }, 1000);
1068
+ return;
1069
+ }
1070
+
1071
+ // Handle connections required scenario (pre-training validation)
1072
+ if (data.requiresConnections || data.code === 'CONNECTIONS_REQUIRED') {
1073
+ console.log('🔗 Connections required detected from socket');
1074
+ setDataScenario('CONNECTIONS_REQUIRED');
1075
+ setDataDetails(data);
1076
+ setShowDataWarning(true);
1077
+ setPersonaStatus('Connections required');
1078
+ setHasError(true);
1079
+ stopDotsAnimation();
1080
+ return;
1081
+ }
1082
+
1083
+ // Handle data scenario responses
1084
+ if (data.code === 'NO_DATA') {
1085
+ console.log('🚫 No data scenario detected');
1086
+ setDataScenario('NO_DATA');
1087
+ setDataDetails(data.details);
1088
+ setShowDataWarning(true);
1089
+ setPersonaStatus('No interaction data found');
1090
+ setHasError(true);
1091
+ stopDotsAnimation();
1092
+ return;
1093
+ }
1094
+ if (data.code === 'LIMITED_DATA') {
1095
+ console.log('ℹ️ Limited data scenario detected');
1096
+ setDataScenario('LIMITED_DATA');
1097
+ setDataDetails(data.details);
1098
+ setShowDataWarning(true);
1099
+ setPersonaStatus('Creating your persona with available data');
1100
+ // Don't set hasError - training continues
1101
+ return;
1102
+ }
1103
+
1104
+ // Handle regular training updates
1105
+ if (data.error) {
1106
+ console.error('❌ Training update error:', data.error);
1107
+ setPersonaStatus(`Error: ${data.error}`);
1108
+ setHasError(true);
1109
+ stopDotsAnimation();
1110
+ } else if (data.progress) {
1111
+ setPersonaProgress(data.progress);
1112
+ setPersonaStatus(data.status || 'Training in progress');
1113
+ // Clear data warning if training progresses normally
1114
+ if (showDataWarning && data.progress > 30) {
1115
+ setShowDataWarning(false);
1116
+ }
1117
+ }
1118
+ });
1119
+
1120
+ // Connect to socket with timeout
1121
+ console.log('🔌 Attempting to connect to socket...');
1122
+ console.log('🔌 Socket config:', {
1123
+ url: 'https://api2.onairos.uk',
1124
+ transports: ['websocket'],
1125
+ autoConnect: false,
1126
+ timeout: 10000,
1127
+ reconnection: false
1128
+ });
1129
+ socketRef.current.connect();
1130
+ console.log('🔌 Socket connect() called - waiting for connection...');
1131
+
1132
+ // Add immediate state check
816
1133
  setTimeout(() => {
817
- onComplete('https://api2.onairos.uk', 'dummy-token', completionData);
818
- }, 100);
1134
+ var _socketRef$current6, _socketRef$current7, _socketRef$current8, _socketRef$current9;
1135
+ console.log('🔍 Socket state after 1 second:', {
1136
+ connected: (_socketRef$current6 = socketRef.current) === null || _socketRef$current6 === void 0 ? void 0 : _socketRef$current6.connected,
1137
+ disconnected: (_socketRef$current7 = socketRef.current) === null || _socketRef$current7 === void 0 ? void 0 : _socketRef$current7.disconnected,
1138
+ id: (_socketRef$current8 = socketRef.current) === null || _socketRef$current8 === void 0 ? void 0 : _socketRef$current8.id,
1139
+ engineConnected: (_socketRef$current9 = socketRef.current) === null || _socketRef$current9 === void 0 || (_socketRef$current9 = _socketRef$current9.io) === null || _socketRef$current9 === void 0 || (_socketRef$current9 = _socketRef$current9.engine) === null || _socketRef$current9 === void 0 ? void 0 : _socketRef$current9.readyState
1140
+ });
1141
+ }, 1000);
1142
+ setTimeout(() => {
1143
+ var _socketRef$current0, _socketRef$current1, _socketRef$current10, _socketRef$current11;
1144
+ console.log('🔍 Socket state after 5 seconds:', {
1145
+ connected: (_socketRef$current0 = socketRef.current) === null || _socketRef$current0 === void 0 ? void 0 : _socketRef$current0.connected,
1146
+ disconnected: (_socketRef$current1 = socketRef.current) === null || _socketRef$current1 === void 0 ? void 0 : _socketRef$current1.disconnected,
1147
+ id: (_socketRef$current10 = socketRef.current) === null || _socketRef$current10 === void 0 ? void 0 : _socketRef$current10.id,
1148
+ engineConnected: (_socketRef$current11 = socketRef.current) === null || _socketRef$current11 === void 0 || (_socketRef$current11 = _socketRef$current11.io) === null || _socketRef$current11 === void 0 || (_socketRef$current11 = _socketRef$current11.engine) === null || _socketRef$current11 === void 0 ? void 0 : _socketRef$current11.readyState
1149
+ });
1150
+ }, 5000);
1151
+
1152
+ // Set a timeout for socket connection with enhanced fallback
1153
+ setTimeout(() => {
1154
+ if (!socketConnected && socketRef.current && !socketRef.current.connected) {
1155
+ console.error('❌ Socket connection timeout after 20 seconds');
1156
+ console.error('🔍 Socket state:', {
1157
+ connected: socketRef.current.connected,
1158
+ disconnected: socketRef.current.disconnected,
1159
+ id: socketRef.current.id
1160
+ });
1161
+ setPersonaStatus('Connection timeout. Please check your internet and try again.');
1162
+ setHasError(true);
1163
+ stopDotsAnimation();
1164
+
1165
+ // Cleanup socket
1166
+ if (socketRef.current) {
1167
+ socketRef.current.disconnect();
1168
+ socketRef.current = null;
1169
+ }
1170
+ }
1171
+ }, 20000); // Increased timeout to 20 seconds
1172
+ } catch (error) {
1173
+ console.error('❌ Error in startPersonaCreation:', error);
1174
+ setPersonaStatus('Failed to initialize training. Please try again.');
1175
+ setHasError(true);
1176
+ stopDotsAnimation();
1177
+ }
1178
+ };
1179
+
1180
+ // Get user-friendly status message based on progress (updated for real training)
1181
+ const getPersonaStatusMessage = progress => {
1182
+ if (hasError) return 'Something went wrong. Please try again.';
1183
+ if (isPersonaComplete) return 'Your persona is ready! 🎉';
1184
+ let baseMessage = '';
1185
+ if (progress < 20) {
1186
+ baseMessage = 'Keeping your data private';
1187
+ } else if (progress < 40) {
1188
+ baseMessage = 'Trying to understand your mind';
1189
+ } else if (progress < 60) {
1190
+ baseMessage = 'You\'re more interesting than I expected';
1191
+ } else if (progress < 80) {
1192
+ baseMessage = 'Finalizing your unique persona';
1193
+ } else if (progress < 95) {
1194
+ baseMessage = 'Almost done';
1195
+ } else {
1196
+ baseMessage = 'Just a few more seconds';
1197
+ }
1198
+ return baseMessage + animatedDots;
1199
+ };
1200
+
1201
+ // Handle persona completion - now continues the onboarding flow instead of going to separate training
1202
+ const handlePersonaComplete = async () => {
1203
+ console.log('🎉 Real persona creation completed successfully');
1204
+ // Cleanup socket connection
1205
+ if (socketRef.current) {
1206
+ console.log('🔌 Disconnecting training socket...');
1207
+ socketRef.current.disconnect();
1208
+ socketRef.current = null;
1209
+ }
1210
+ // Clear temporary PIN since training is complete
1211
+ (0, _pinStorageUtils.clearTemporaryPin)();
1212
+ // Set the completion flag BEFORE calling onComplete
1213
+ isCompletingRef.current = true;
1214
+
1215
+ // Get the real authentication token instead of using placeholder
1216
+ try {
1217
+ const realToken = (await _asyncStorage.default.getItem('onairos_jwt_token')) || (await _asyncStorage.default.getItem('enoch_token')) || (await _asyncStorage.default.getItem('auth_token'));
1218
+ if (realToken) {
1219
+ console.log('✅ Using real authentication token for onComplete:', `${realToken.substring(0, 30)}...`);
1220
+ // Call onComplete with the REAL token that was created during ensureAuthToken
1221
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', realToken, {
1222
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || '',
1223
+ ...userInfo
1224
+ });
1225
+ } else {
1226
+ console.error('❌ No real authentication token found after training completion');
1227
+ // Fallback to placeholder token if no real token exists
1228
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', 'training-complete-token', {
1229
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || '',
1230
+ ...userInfo
1231
+ });
1232
+ }
1233
+ } catch (error) {
1234
+ console.error('❌ Error retrieving real token for onComplete:', error);
1235
+ // Fallback to placeholder token on error
1236
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', 'training-complete-token', {
1237
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || '',
1238
+ ...userInfo
1239
+ });
819
1240
  }
820
- }, [pin, connections, platformToggles, selectedTier, requestData, auto, inferenceData, partner, handleClose, onComplete, AppName, email]);
821
- const handleDataRequestAccept = (0, _react.useCallback)(async () => {
822
- console.log('Data request accepted for existing user');
823
- console.log('🔍 Auto mode enabled:', auto);
824
- console.log('🔍 Inference data available:', !!inferenceData);
1241
+ };
1242
+
1243
+ // Ensure authentication token exists before training
1244
+ const ensureAuthToken = async () => {
825
1245
  try {
826
- if (auto && inferenceData) {
827
- console.log('🤖 Auto mode: Making API request to get URL and perform inference');
1246
+ var _user$name, _onairosResponseData$;
1247
+ // Check if we already have an authentication token (prioritize Enoch-specific tokens)
1248
+ let existingToken = (await _asyncStorage.default.getItem('onairos_jwt_token')) || (await _asyncStorage.default.getItem('enoch_token')) || (await _asyncStorage.default.getItem('auth_token'));
1249
+ if (existingToken && existingToken.trim().length > 20) {
1250
+ console.log('✅ Authentication token already exists:', `${existingToken.substring(0, 20)}...`);
1251
+ console.log('🔍 Token length:', existingToken.length);
1252
+ console.log('🔍 Token format check:', existingToken.includes('.') ? 'Looks like JWT' : 'Not JWT format');
1253
+ return existingToken;
1254
+ }
1255
+ console.log('🔐 Creating Enoch authentication token for universal onboarding...');
1256
+
1257
+ // Create user accounts and get proper Enoch token
1258
+ const fallbackEmail = (user === null || user === void 0 ? void 0 : user.email) || `${username || 'user'}@onairos.temp`;
1259
+ const fallbackUsername = username || (user === null || user === void 0 || (_user$name = user.name) === null || _user$name === void 0 ? void 0 : _user$name.split('@')[0]) || 'mobile_user';
1260
+ console.log('🔐 Using credentials:', {
1261
+ email: fallbackEmail,
1262
+ username: fallbackUsername
1263
+ });
828
1264
 
829
- // First, get the API URL from backend
830
- const apiUrlResponse = await fetch('https://api2.onairos.uk/', {
1265
+ // Step 1: Create Enoch user first
1266
+ console.log('🔐 Step 1: Creating Enoch user...');
1267
+ try {
1268
+ const enochRegisterResponse = await fetch('https://api2.onairos.uk/enoch/users/register', {
831
1269
  method: 'POST',
832
1270
  headers: {
833
1271
  'Content-Type': 'application/json'
834
1272
  },
835
1273
  body: JSON.stringify({
836
- Info: {
837
- storage: 'secure',
838
- // or whatever storage type
839
- appId: AppName,
840
- confirmations: Object.keys(requestData || {}),
841
- EncryptedUserPin: 'temp-pin',
842
- // This would come from user PIN in real flow
843
- account: email.trim(),
844
- proofMode: false
845
- }
846
- })
847
- });
848
- if (!apiUrlResponse.ok) {
849
- throw new Error(`Failed to get API URL: ${apiUrlResponse.status}`);
850
- }
851
- const {
852
- apiUrl,
853
- token
854
- } = await apiUrlResponse.json();
855
- console.log('✅ Received API URL:', apiUrl);
856
- console.log('✅ Received token:', (token === null || token === void 0 ? void 0 : token.substring(0, 20)) + '...');
857
-
858
- // Now make the inference call with the provided data
859
- const inferenceResponse = await fetch(apiUrl, {
860
- method: 'POST',
861
- headers: {
862
- 'Content-Type': 'application/json',
863
- 'Authorization': `Bearer ${token}`
864
- },
865
- body: JSON.stringify({
866
- ...inferenceData,
867
- userEmail: email.trim(),
868
- appName: AppName,
869
- timestamp: new Date().toISOString()
1274
+ email: fallbackEmail,
1275
+ name: fallbackUsername,
1276
+ photoUrl: ''
870
1277
  })
871
1278
  });
872
- if (!inferenceResponse.ok) {
873
- throw new Error(`Inference API failed: ${inferenceResponse.status}`);
874
- }
875
- const inferenceResults = await inferenceResponse.json();
876
- console.log(' Auto mode inference results:', inferenceResults);
877
-
878
- // Complete onboarding with inference results
879
- onComplete(apiUrl, token, {
880
- existingAccount: true,
881
- email: email.trim(),
882
- dataRequestAccepted: true,
883
- requestData,
884
- autoMode: true,
885
- inferenceResults,
886
- apiUrl,
887
- token
888
- });
1279
+ console.log('📡 Enoch register response status:', enochRegisterResponse.status);
1280
+ const enochResponseData = await enochRegisterResponse.json();
1281
+ console.log('🔗 Enoch user creation response:', enochResponseData);
1282
+ } catch (enochError) {
1283
+ console.warn('⚠️ Enoch user creation failed (continuing):', enochError);
1284
+ }
1285
+
1286
+ // Step 2: Create Onairos account to get JWT token (this is the critical step)
1287
+ console.log('🔐 Step 2: Creating Onairos account...');
1288
+ const onairosSignupResponse = await fetch('https://api2.onairos.uk/register/enoch', {
1289
+ method: 'POST',
1290
+ headers: {
1291
+ 'Content-Type': 'application/json'
1292
+ },
1293
+ body: JSON.stringify({
1294
+ email: fallbackEmail,
1295
+ username: fallbackUsername,
1296
+ name: fallbackUsername
1297
+ })
1298
+ });
1299
+ console.log('📡 Onairos register response status:', onairosSignupResponse.status);
1300
+ if (!onairosSignupResponse.ok) {
1301
+ const errorText = await onairosSignupResponse.text();
1302
+ console.error('❌ Onairos signup failed:', errorText);
1303
+ throw new Error(`Onairos signup failed: ${onairosSignupResponse.status} ${errorText}`);
1304
+ }
1305
+ const onairosResponseData = await onairosSignupResponse.json();
1306
+ console.log('🔗 Onairos account creation response:', onairosResponseData);
1307
+
1308
+ // Extract the token from the response
1309
+ let authToken = null;
1310
+ if (onairosResponseData.token) {
1311
+ authToken = onairosResponseData.token;
1312
+ } else if ((_onairosResponseData$ = onairosResponseData.data) !== null && _onairosResponseData$ !== void 0 && _onairosResponseData$.token) {
1313
+ authToken = onairosResponseData.data.token;
1314
+ } else if (onairosResponseData.jwt) {
1315
+ authToken = onairosResponseData.jwt;
1316
+ }
1317
+ if (!authToken) {
1318
+ console.error('❌ No token found in response:', onairosResponseData);
1319
+ throw new Error('No authentication token returned from server');
1320
+ }
1321
+
1322
+ // Validate the token format
1323
+ if (typeof authToken !== 'string' || authToken.length < 20) {
1324
+ console.error('❌ Invalid token format:', authToken);
1325
+ throw new Error('Invalid token format received');
1326
+ }
1327
+
1328
+ // Check if it looks like a JWT
1329
+ const jwtParts = authToken.split('.');
1330
+ if (jwtParts.length !== 3) {
1331
+ console.warn('⚠️ Token does not appear to be a valid JWT:', `${authToken.substring(0, 20)}...`);
889
1332
  } else {
890
- console.log('📋 Standard mode: Returning API URL for manual use');
891
-
892
- // Standard mode: just return the API URL
893
- onComplete('https://api2.onairos.uk', 'existing-session-token', {
894
- existingAccount: true,
895
- email: email.trim(),
896
- dataRequestAccepted: true,
897
- requestData,
898
- autoMode: false
899
- });
1333
+ console.log(' Token appears to be a valid JWT format');
900
1334
  }
1335
+
1336
+ // Store the token in multiple locations for maximum compatibility
1337
+ await _asyncStorage.default.setItem('onairos_jwt_token', authToken);
1338
+ await _asyncStorage.default.setItem('auth_token', authToken);
1339
+ await _asyncStorage.default.setItem('enoch_token', authToken);
1340
+ await _asyncStorage.default.setItem('onairos_username', onairosResponseData.username || fallbackUsername);
1341
+ console.log('✅ Successfully stored authentication tokens');
1342
+ console.log('🔑 Token preview:', `${authToken.substring(0, 20)}...`);
1343
+ console.log('🔑 Token length:', authToken.length);
1344
+ console.log('👤 Username stored:', onairosResponseData.username || fallbackUsername);
1345
+ return authToken;
901
1346
  } catch (error) {
902
- console.error('❌ Error in data request accept:', error);
903
-
904
- // Fallback to standard mode
905
- onComplete('https://api2.onairos.uk', 'existing-session-token', {
906
- existingAccount: true,
907
- email: email.trim(),
908
- dataRequestAccepted: true,
909
- requestData,
910
- autoMode: false,
911
- error: error instanceof Error ? error.message : 'Unknown error'
912
- });
1347
+ console.error('❌ Error ensuring authentication token:', error);
1348
+ throw error;
913
1349
  }
914
- }, [email, onComplete, requestData, auto, inferenceData, AppName]);
915
- const handleDataRequestDecline = (0, _react.useCallback)(() => {
916
- console.log('Data request declined');
917
- handleClose();
918
- }, [handleClose]);
919
- const canProceedToPin = (0, _react.useCallback)(() => {
920
- // Test mode: Always allow proceeding (simulates platform connections)
921
- if (isTestMode || testModeOptions.skipRealConnections) {
922
- console.log('🧪 Test mode: Allowing proceed without real platform connections');
923
- return true;
1350
+ };
1351
+ const canProceed = Object.values(platformToggles).some(value => value);
1352
+ const handleProceed = () => {
1353
+ if (canProceed) {
1354
+ // Trigger haptic feedback when continue button is pressed
1355
+ (0, _haptics.triggerHaptic)(_haptics.HapticType.BUTTON_PRESS);
1356
+
1357
+ // NEW: Start background training when transitioning from connectors to PIN screen
1358
+ console.log('🚀 [TRANSITION] Starting background training during connect pin transition');
1359
+ startBackgroundTraining().catch(error => {
1360
+ console.error('❌ [TRANSITION] Background training failed during transition:', error);
1361
+ // Continue to PIN screen even if training fails
1362
+ });
1363
+ setStep('pin');
924
1364
  }
1365
+ };
1366
+ const handleReviewerBypass = () => {
1367
+ console.log('Reviewer bypass activated');
925
1368
 
926
- // Production: Check if at least one platform is connected
927
- const hasPlatformConnected = Object.values(platformToggles).some(value => value === true);
1369
+ // Set the completion flag BEFORE calling onComplete
1370
+ isCompletingRef.current = true;
928
1371
 
929
- // Auto mode validation
930
- if (auto && partner !== 'couplebible' && !inferenceData) {
931
- console.warn('Auto mode enabled but no inference data provided (and partner is not couplebible)');
932
- return false;
933
- }
934
- return hasPlatformConnected;
935
- }, [platformToggles, auto, partner, inferenceData, isTestMode, testModeOptions]);
936
- const handleProceed = () => {
937
- console.log('Proceeding to next step');
938
- // Show success screen first
939
- setStep('success');
1372
+ // Call onComplete with a special reviewer token that the parent can recognize
1373
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', 'reviewer-bypass-token', {
1374
+ email: 'reviewer@apple.com'
1375
+ });
1376
+ };
1377
+
1378
+ // Removed navigation dependency for SDK compatibility
1379
+
1380
+ // Training is now handled by the TrainingModal component
1381
+
1382
+ // ✅ NEW: Background training function - starts when PIN screen appears
1383
+ const startBackgroundTraining = (0, _react.useCallback)(async () => {
1384
+ try {
1385
+ console.log('🚀 [BACKGROUND] Starting background training optimization...');
1386
+ setBackgroundTrainingProgress('Connecting...');
1387
+
1388
+ // Step 1: Ensure authentication token exists
1389
+ const authToken = await ensureAuthToken();
1390
+ if (!authToken) {
1391
+ throw new Error('Failed to create authentication token for background training');
1392
+ }
1393
+ console.log('✅ [BACKGROUND] Auth token ready:', `${authToken.substring(0, 20)}...`);
1394
+ setUserToken(authToken);
1395
+
1396
+ // Step 2: Set up user info if not available
1397
+ if (!userInfo) {
1398
+ var _user$email5;
1399
+ const storedUsername = await (0, _authService.getOnairosUsername)();
1400
+ const fallbackUsername = storedUsername || (user === null || user === void 0 || (_user$email5 = user.email) === null || _user$email5 === void 0 ? void 0 : _user$email5.split('@')[0]) || (user === null || user === void 0 ? void 0 : user.name) || 'mobile_user';
1401
+ const newUserInfo = {
1402
+ username: fallbackUsername,
1403
+ email: (user === null || user === void 0 ? void 0 : user.email) || null,
1404
+ id: null
1405
+ };
1406
+ setUserInfo(newUserInfo);
1407
+ setUsername(fallbackUsername);
1408
+ console.log('🧑‍💻 [BACKGROUND] User info set:', newUserInfo);
1409
+ }
1410
+
1411
+ // Step 3: Initialize socket connection for background training
1412
+ console.log('🔌 [BACKGROUND] Setting up socket for background training...');
1413
+ setBackgroundTrainingProgress('Initializing data collection...');
1414
+ const backgroundSocket = (0, _socket.io)('https://api2.onairos.uk', {
1415
+ transports: ['websocket', 'polling'],
1416
+ autoConnect: false,
1417
+ timeout: 15000,
1418
+ reconnection: true,
1419
+ reconnectionAttempts: 3,
1420
+ reconnectionDelay: 1000,
1421
+ forceNew: true
1422
+ });
1423
+
1424
+ // Set up socket event listeners for background training
1425
+ backgroundSocket.on('connect', async () => {
1426
+ console.log('✅ [BACKGROUND] Socket connected, starting background data collection...');
1427
+ const socketId = backgroundSocket.id;
1428
+ setBackgroundSocketId(socketId || null);
1429
+ setBackgroundTrainingProgress('Collecting your data...');
1430
+ if (socketId) {
1431
+ // Step 4: Start background training WITHOUT PIN (per backend instructions)
1432
+ await startBackgroundEnochTraining(socketId, authToken);
1433
+ }
1434
+ });
1435
+ backgroundSocket.on('trainingUpdate', data => {
1436
+ if (data.progress) {
1437
+ setBackgroundTrainingProgress(data.status || 'Processing...');
1438
+ console.log('📊 [BACKGROUND] Training progress:', data.progress, '%');
1439
+ }
1440
+ });
1441
+ backgroundSocket.on('disconnect', () => {
1442
+ console.log('❌ [BACKGROUND] Socket disconnected');
1443
+ });
1444
+
1445
+ // Store socket reference for later use
1446
+ socketRef.current = backgroundSocket;
940
1447
 
941
- // Clear any existing timeout
942
- if (successTimeoutRef.current) {
943
- clearTimeout(successTimeoutRef.current);
1448
+ // Connect the socket to start background training
1449
+ backgroundSocket.connect();
1450
+ console.log('✅ [BACKGROUND] Background training initiated successfully');
1451
+ } catch (error) {
1452
+ console.error('❌ [BACKGROUND] Background training failed:', error);
1453
+ setBackgroundTrainingProgress('');
1454
+ throw error;
944
1455
  }
1456
+ }, [userInfo, username, user]);
945
1457
 
946
- // After a delay, proceed to PIN
947
- successTimeoutRef.current = setTimeout(() => {
948
- // Only proceed if component is still mounted and visible
949
- if (isMountedRef.current && visible) {
950
- setStep('pin');
1458
+ // NEW: Background training API call - starts data collection without PIN
1459
+ const startBackgroundEnochTraining = async (socketId, authToken) => {
1460
+ try {
1461
+ console.log('🚀 [BACKGROUND] Starting background training with socketId:', socketId);
1462
+ console.log('🔑 Using auth token:', `${authToken.substring(0, 20)}...`);
1463
+
1464
+ // Prepare background training data
1465
+ const backgroundData = {
1466
+ socketId,
1467
+ username: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.username) || (userInfo === null || userInfo === void 0 ? void 0 : userInfo.name) || username || 'mobile_user',
1468
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || null,
1469
+ modelKey: null,
1470
+ connectedPlatforms: [],
1471
+ // No connected platforms for background training
1472
+ platformConnections: {} // No platform connections for background training
1473
+ // No encrypted PIN for background training
1474
+ };
1475
+ console.log('📤 Sending background training data to /mobile-training/enoch:', backgroundData);
1476
+
1477
+ // Use the new training function that includes YouTube migration check
1478
+ const backgroundResult = await (0, _mobileTrainingService.startEnochTrainingWithYouTubeCheck)(backgroundData);
1479
+ console.log('📡 Background training API response:', backgroundResult);
1480
+
1481
+ // Handle CONNECTIONS_REQUIRED scenario (pre-training validation)
1482
+ if (backgroundResult.requiresConnections || backgroundResult.code === 'CONNECTIONS_REQUIRED') {
1483
+ console.log('🔗 Connections required detected from background training');
1484
+ setDataScenario('CONNECTIONS_REQUIRED');
1485
+ setDataDetails(backgroundResult);
1486
+ setShowDataWarning(true);
1487
+ setPersonaStatus('Connections required');
1488
+ setHasError(true);
1489
+ stopDotsAnimation();
1490
+ return;
951
1491
  }
952
- successTimeoutRef.current = null;
953
- }, 3000);
1492
+ if (backgroundResult.success) {
1493
+ console.log('🚀 Background training started:', backgroundResult.message);
1494
+ console.log('🎯 Background training Features:', backgroundResult.features);
1495
+
1496
+ // ✅ CRITICAL: Set background training started flag
1497
+ setIsBackgroundTrainingStarted(true);
1498
+
1499
+ // Log the new features from the spec
1500
+ if (backgroundResult.features) {
1501
+ console.log('✅ Inference enabled:', backgroundResult.features.inference);
1502
+ console.log('💾 Storage method:', backgroundResult.features.storage);
1503
+ console.log('🔒 Compression enabled:', backgroundResult.features.compression);
1504
+ console.log('🔐 Encryption enabled:', backgroundResult.features.encryption);
1505
+ console.log('📊 Training type:', backgroundResult.features.type);
1506
+ console.log('🗄️ Databases:', backgroundResult.features.databases);
1507
+ console.log('📈 Query scores enabled:', backgroundResult.features.queryScores);
1508
+ }
1509
+ setPersonaStatus('Background training model...');
1510
+ setPersonaProgress(25);
1511
+ } else {
1512
+ console.error('❌ Background training start failed:', backgroundResult.error);
1513
+ setPersonaStatus(`Error: ${backgroundResult.error || 'Background training failed to start'}`);
1514
+ setHasError(true);
1515
+ stopDotsAnimation();
1516
+ }
1517
+ } catch (error) {
1518
+ console.error('❌ Background training start error:', error);
1519
+ setPersonaStatus(`Error: ${error instanceof Error ? error.message : 'Unknown error'}`);
1520
+ setHasError(true);
1521
+ stopDotsAnimation();
1522
+ }
954
1523
  };
955
1524
  return /*#__PURE__*/_react.default.createElement(_reactNative.Modal, {
956
- visible: visible,
957
1525
  transparent: true,
1526
+ visible: modalVisible,
958
1527
  animationType: "none",
959
- statusBarTranslucent: true,
960
1528
  onRequestClose: handleClose
961
- }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableWithoutFeedback, {
962
- onPress: handleClose
963
1529
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
964
1530
  style: styles.modalOverlay
965
- }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableWithoutFeedback, {
966
- onPress: e => e.stopPropagation()
967
1531
  }, /*#__PURE__*/_react.default.createElement(_reactNative.Animated.View, {
968
1532
  style: [styles.bottomSheet, {
969
1533
  transform: [{
@@ -974,214 +1538,313 @@ const UniversalOnboarding = ({
974
1538
  style: styles.container
975
1539
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
976
1540
  style: styles.handleContainer
1541
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1542
+ onPress: handleClose,
1543
+ style: styles.handleButton
977
1544
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
978
1545
  style: styles.handle
979
- })), step === 'email' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
980
- style: styles.emailInputContainer
1546
+ }))), step === 'connect' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1547
+ style: styles.connectContainer
981
1548
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
982
- style: styles.emailHeader
983
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
984
- style: styles.onairosIcon
985
- }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
986
- source: require('../assets/images/onairos_logo.png'),
987
- style: styles.onairosLogo,
988
- resizeMode: "contain"
989
- })), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
990
- style: styles.emailTitle
991
- }, "Welcome to Onairos"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
992
- style: styles.emailSubtitle
993
- }, "Enter your email to get started")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
994
- style: styles.emailInputSection
995
- }, /*#__PURE__*/_react.default.createElement(_reactNative.TextInput, {
996
- style: styles.emailInput,
997
- value: email,
998
- onChangeText: setEmail,
999
- placeholder: "Enter your email address",
1000
- keyboardType: "email-address",
1001
- autoCapitalize: "none",
1002
- autoCorrect: false,
1003
- autoFocus: true
1004
- }), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1005
- style: [styles.emailSubmitButton, !email.trim() && styles.emailSubmitButtonDisabled],
1006
- onPress: handleEmailSubmit,
1007
- disabled: !email.trim()
1008
- }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1009
- style: styles.emailSubmitButtonText
1010
- }, "Continue")))), step === 'verify' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1011
- style: styles.emailInputContainer
1012
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1013
- style: styles.emailHeader
1014
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1015
- style: styles.onairosIcon
1016
- }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1017
- source: require('../assets/images/onairos_logo.png'),
1018
- style: styles.onairosLogo,
1019
- resizeMode: "contain"
1020
- })), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1021
- style: styles.emailTitle
1022
- }, "Enter Verification Code"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1023
- style: styles.emailSubtitle
1024
- }, "We've sent a 6-digit code to ", email), isTestMode && /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1025
- style: styles.developmentNote
1026
- }, "\uD83D\uDD0D Test Mode: Any 6-digit code will work")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1027
- style: styles.emailInputSection
1028
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1029
- style: styles.codeInputContainer
1030
- }, [0, 1, 2, 3, 4, 5].map(index => /*#__PURE__*/_react.default.createElement(_reactNative.TextInput, {
1031
- key: index,
1032
- ref: ref => codeInputRefs.current[index] = ref,
1033
- style: [styles.codeDigit, verificationCode.length === index && styles.codeDigitActive],
1034
- value: verificationCode[index] || '',
1035
- onChangeText: text => {
1036
- if (text.length <= 1 && /^\d*$/.test(text)) {
1037
- const newCode = verificationCode.split('');
1038
- newCode[index] = text;
1039
- const updatedCode = newCode.join('').slice(0, 6);
1040
- setVerificationCode(updatedCode);
1041
-
1042
- // Auto-focus next input
1043
- if (text && index < 5) {
1044
- var _codeInputRefs$curren;
1045
- (_codeInputRefs$curren = codeInputRefs.current[index + 1]) === null || _codeInputRefs$curren === void 0 || _codeInputRefs$curren.focus();
1046
- }
1047
- }
1048
- },
1049
- onKeyPress: ({
1050
- nativeEvent
1051
- }) => {
1052
- // Handle backspace to move to previous input
1053
- if (nativeEvent.key === 'Backspace' && !verificationCode[index] && index > 0) {
1054
- var _codeInputRefs$curren2;
1055
- (_codeInputRefs$curren2 = codeInputRefs.current[index - 1]) === null || _codeInputRefs$curren2 === void 0 || _codeInputRefs$curren2.focus();
1056
- }
1057
- },
1058
- keyboardType: "number-pad",
1059
- maxLength: 1,
1060
- textAlign: "center",
1061
- autoFocus: index === 0
1062
- }))), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1063
- style: [styles.emailSubmitButton, (verificationCode.length !== 6 || isVerifyingCode) && styles.emailSubmitButtonDisabled],
1064
- onPress: handleVerificationSubmit,
1065
- disabled: verificationCode.length !== 6 || isVerifyingCode
1066
- }, isVerifyingCode ? /*#__PURE__*/_react.default.createElement(_reactNative.ActivityIndicator, {
1067
- size: "small",
1068
- color: "#fff"
1069
- }) : /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1070
- style: styles.emailSubmitButtonText
1071
- }, "Verify")), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1072
- style: styles.backButton,
1073
- onPress: () => setStep('email')
1074
- }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1075
- style: styles.backButtonText
1076
- }, "\u2190 Back to email")))), step === 'connect' && /*#__PURE__*/_react.default.createElement(_react.default.Fragment, null, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1077
1549
  style: styles.header
1078
1550
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1079
1551
  style: styles.headerContent
1080
1552
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1553
+ style: styles.appIcon
1554
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1555
+ style: styles.appIconText
1556
+ }, "O")), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1557
+ style: styles.arrow
1558
+ }, "\u2192"), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1081
1559
  style: styles.onairosIcon
1082
1560
  }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1083
- source: require('../assets/images/onairos_logo.png'),
1084
- style: styles.onairosLogo,
1561
+ source: require('../assets/images/Enochicon1.png'),
1562
+ style: styles.onairosIconImage,
1085
1563
  resizeMode: "contain"
1086
- })), /*#__PURE__*/_react.default.createElement(_MaterialIcons.default, {
1087
- name: "arrow-forward",
1088
- size: 24,
1089
- color: "#666",
1090
- style: styles.arrow
1091
- }), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1092
- style: styles.appIcon
1093
- }, appIcon ? /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1094
- source: appIcon,
1095
- style: styles.appIconImage,
1096
- resizeMode: "contain"
1097
- }) : /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1098
- style: styles.appIconText
1099
- }, AppName.charAt(0))))), /*#__PURE__*/_react.default.createElement(_reactNative.ScrollView, {
1100
- style: styles.content,
1101
- contentContainerStyle: styles.scrollContent,
1102
- showsVerticalScrollIndicator: true,
1103
- bounces: true,
1104
- scrollEnabled: true,
1105
- nestedScrollEnabled: true,
1106
- keyboardShouldPersistTaps: "handled"
1107
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1564
+ }))), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1108
1565
  style: styles.titleContainer
1109
1566
  }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1110
1567
  style: styles.mainTitle
1111
- }, "Let ", AppName, " learn about you from your data and apps"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1568
+ }, isExistingUser ? 'Add More Data to Enoch' : 'Connect your platforms to Enoch via Onairos'), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1112
1569
  style: styles.privacyMessage
1113
- }, "None of your app data is shared with ANYONE"), (debug || testMode) && /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1114
- style: styles.developmentNote
1115
- }, "\uD83E\uDDEA Test Mode: You can proceed without connecting any platforms")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1570
+ }, isExistingUser ? 'Connect additional accounts to enhance your digital personality. Your privacy is ensured.' : 'Connect one account to get started. Each additional connection improves your match quality. Your privacy is ensured.', ' ', /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1571
+ style: styles.privacyLink,
1572
+ onPress: () => setStep('privacy')
1573
+ }, "How it's used \u2192")), isExistingUser && existingUserInfo && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1574
+ style: styles.existingUserBanner
1575
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1576
+ style: styles.existingUserText
1577
+ }, "\u2705 You already have ", ((_existingUserInfo$exi = existingUserInfo.existingUserData) === null || _existingUserInfo$exi === void 0 || (_existingUserInfo$exi = _existingUserInfo$exi.summary) === null || _existingUserInfo$exi === void 0 ? void 0 : _existingUserInfo$exi.connectionsCount) || 0, " connections"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1578
+ style: styles.existingUserSubtext
1579
+ }, "Add more platforms to get even better insights")), connectionStatuses['linkedin'] === 'connected' && Object.values(connectionStatuses).filter(status => status === 'connected').length === 1 && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1580
+ style: styles.linkedinRequirementContainer
1581
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1582
+ style: styles.linkedinRequirementText
1583
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1584
+ style: styles.linkedinRequirementAsterisk
1585
+ }, "*"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1586
+ style: styles.linkedinRequirementMessage
1587
+ }, " LinkedIn requires pairing with an additional platform for optimal results"))))), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1588
+ style: {
1589
+ height: 1,
1590
+ backgroundColor: '#CCCCCC',
1591
+ width: '100%',
1592
+ marginVertical: 0
1593
+ }
1594
+ }), /*#__PURE__*/_react.default.createElement(_reactNative.ScrollView, {
1595
+ ref: scrollViewRef,
1596
+ style: styles.platformsScrollView,
1597
+ contentContainerStyle: styles.platformsScrollContent,
1598
+ showsVerticalScrollIndicator: true,
1599
+ bounces: true,
1600
+ alwaysBounceVertical: true,
1601
+ indicatorStyle: "black",
1602
+ scrollEventThrottle: 16,
1603
+ directionalLockEnabled: true,
1604
+ keyboardShouldPersistTaps: "handled",
1605
+ decelerationRate: "normal",
1606
+ contentOffset: {
1607
+ x: 0,
1608
+ y: 60
1609
+ }
1610
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1116
1611
  style: styles.platformsContainer
1117
- }, platformsToDisplay.map(platform => /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1118
- key: platform.id,
1119
- style: styles.platformItem,
1120
- onPress: () => togglePlatform(platform.id),
1121
- disabled: isConnectingPlatform
1612
+ }, primaryAuthOnly ?
1613
+ /*#__PURE__*/
1614
+ // Only show email option when primaryAuthOnly is true
1615
+ _react.default.createElement(_reactNative.View, {
1616
+ style: styles.platformItem
1122
1617
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1123
1618
  style: styles.platformInfo
1124
- }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1125
- source: platform.icon,
1126
- style: styles.platformIcon,
1127
- resizeMode: "contain"
1128
- }), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1129
- style: styles.platformName
1130
- }, platform.name)), isConnectingPlatform && currentPlatform === platform.id ? /*#__PURE__*/_react.default.createElement(_reactNative.ActivityIndicator, {
1131
- size: "small",
1132
- color: _constants.COLORS.primary
1133
- }) : /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1134
- style: [styles.platformToggle, platformToggles[platform.id] && styles.platformToggleActive]
1135
1619
  }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1136
- style: [styles.platformToggleThumb, platformToggles[platform.id] && styles.platformToggleThumbActive]
1137
- })))), additionalPlatforms.length > 0 && /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1138
- style: styles.expandButton,
1139
- onPress: () => setShowAllPlatforms(!showAllPlatforms)
1140
- }, /*#__PURE__*/_react.default.createElement(_MaterialIcons.default, {
1141
- name: showAllPlatforms ? "expand_less" : "add",
1142
- size: 24,
1143
- color: _constants.COLORS.primary
1144
- }), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1145
- style: styles.expandButtonText
1146
- }, showAllPlatforms ? "Show Less" : `${additionalPlatforms.length} More Connectors`))), showTestControls && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1147
- style: styles.testModeContainer
1620
+ style: [styles.platformIcon, {
1621
+ backgroundColor: '#4285F4'
1622
+ }]
1148
1623
  }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1149
- style: styles.testModeTitle
1150
- }, "\uD83E\uDDEA Test Mode - 2 Main Flows"), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1151
- style: styles.testExistingUserButton,
1624
+ style: styles.platformIconText
1625
+ }, "@")), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1626
+ style: styles.platformName
1627
+ }, "Email")), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1628
+ onPress: async () => {
1629
+ // Trigger haptic feedback when sign in button is pressed
1630
+ (0, _haptics.triggerHaptic)(_haptics.HapticType.BUTTON_PRESS);
1631
+
1632
+ // Mark email as connected for primaryAuth flow
1633
+ setConnections(prev => ({
1634
+ ...prev,
1635
+ email: {
1636
+ userName: email || 'user@example.com',
1637
+ connected: true
1638
+ }
1639
+ }));
1640
+ setConnectionStatuses(prev => ({
1641
+ ...prev,
1642
+ email: 'connected'
1643
+ }));
1644
+ setPlatformToggles(prev => ({
1645
+ ...prev,
1646
+ email: true
1647
+ }));
1648
+
1649
+ // Store the connected platform
1650
+ await storeConnectedPlatform('email');
1651
+ setStep('connections');
1652
+ },
1653
+ style: [styles.footerButtonConfirm, {
1654
+ paddingVertical: 8,
1655
+ paddingHorizontal: 16
1656
+ }]
1657
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1658
+ style: styles.footerButtonTextConfirm
1659
+ }, "Sign in"))) :
1660
+ /*#__PURE__*/
1661
+ // Show main platforms first
1662
+ _react.default.createElement(_react.default.Fragment, null, mainPlatforms.map(platform => {
1663
+ const isConnected = connectionStatuses[platform.id] === 'connected';
1664
+ const isPlatformConnecting = connectingPlatform === platform.id;
1665
+ return /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1666
+ key: platform.id,
1667
+ style: styles.platformItem
1668
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1669
+ style: styles.platformInfo
1670
+ }, platform.id === 'linkedin' ?
1671
+ /*#__PURE__*/
1672
+ // Use square container for LinkedIn
1673
+ _react.default.createElement(_reactNative.View, {
1674
+ style: [styles.linkedinPlatformIcon, {
1675
+ backgroundColor: platform.color
1676
+ }]
1677
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1678
+ source: getPlatformIcon(platform.id),
1679
+ style: styles.platformIconImage,
1680
+ resizeMode: "contain"
1681
+ })) : platform.id === 'pinterest' ?
1682
+ /*#__PURE__*/
1683
+ // Use smaller circular container for Pinterest
1684
+ _react.default.createElement(_reactNative.View, {
1685
+ style: [styles.pinterestPlatformIcon, {
1686
+ backgroundColor: platform.color
1687
+ }]
1688
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1689
+ source: getPlatformIcon(platform.id),
1690
+ style: styles.pinterestIconImage,
1691
+ resizeMode: "contain"
1692
+ })) : /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1693
+ style: [styles.platformIcon, {
1694
+ backgroundColor: platform.color
1695
+ }]
1696
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1697
+ source: getPlatformIcon(platform.id),
1698
+ style: platform.id === 'youtube' ? styles.youtubeIconImage : styles.platformIconImage,
1699
+ resizeMode: "contain"
1700
+ })), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1701
+ style: styles.platformName
1702
+ }, platform.name, platform.id === 'linkedin' && connectionStatuses['linkedin'] === 'connected' && Object.values(connectionStatuses).filter(status => status === 'connected').length === 1 && /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1703
+ style: styles.asterisk
1704
+ }, "*"))), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1705
+ onPress: () => {
1706
+ if (isConnected) {
1707
+ // Handle disconnect
1708
+ handleDisconnectPlatform(platform.id, platform.name);
1709
+ } else {
1710
+ // Handle connect
1711
+ handleConnectPlatform(platform.id);
1712
+ }
1713
+ },
1714
+ onLongPress: platform.id === 'youtube' ? () => {
1715
+ // Start a timer for haptic feedback at 2 seconds
1716
+ const hapticTimer = setTimeout(() => {
1717
+ // Provide haptic feedback
1718
+ _reactNative.Vibration.vibrate(100);
1719
+ }, 2000);
1720
+
1721
+ // Start a timer for 4 seconds for the bypass
1722
+ const bypassTimer = setTimeout(() => {
1723
+ handleReviewerBypass();
1724
+ }, 4000);
1725
+
1726
+ // Store the timer
1727
+ setLongPressTimer(bypassTimer);
1728
+ } : undefined,
1729
+ onPressOut: platform.id === 'youtube' ? () => {
1730
+ // Clear the timer if the press is released before 4 seconds
1731
+ if (longPressTimer) {
1732
+ clearTimeout(longPressTimer);
1733
+ setLongPressTimer(null);
1734
+ }
1735
+ } : undefined,
1736
+ style: [isConnected ? styles.footerButtonConnected : styles.footerButtonConfirm, {
1737
+ paddingVertical: 8,
1738
+ paddingHorizontal: 16
1739
+ }],
1740
+ disabled: isPlatformConnecting
1741
+ }, isPlatformConnecting ? /*#__PURE__*/_react.default.createElement(_reactNative.ActivityIndicator, {
1742
+ size: "small",
1743
+ color: "#fff"
1744
+ }) : /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1745
+ style: isConnected ? styles.footerButtonTextConnected : styles.footerButtonTextConfirm
1746
+ }, isConnected ? 'Connected' : 'Connect')));
1747
+ }), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1748
+ style: styles.additionalPlatformsToggle,
1152
1749
  onPress: () => {
1153
- // Flow 1: Existing User
1154
- setIsExistingUser(true);
1155
- setStep('dataRequest');
1750
+ (0, _haptics.triggerHaptic)(_haptics.HapticType.BUTTON_PRESS);
1751
+ const newShowState = !showAdditionalPlatforms;
1752
+ if (newShowState) {
1753
+ // Expanding - show platforms first, then animate in and scroll
1754
+ setShowAdditionalPlatforms(true);
1755
+ _reactNative.Animated.timing(additionalPlatformsOpacity, {
1756
+ toValue: 1,
1757
+ duration: 300,
1758
+ useNativeDriver: true
1759
+ }).start();
1760
+
1761
+ // Auto-scroll to reveal additional platforms when expanding
1762
+ setTimeout(() => {
1763
+ var _scrollViewRef$curren;
1764
+ (_scrollViewRef$curren = scrollViewRef.current) === null || _scrollViewRef$curren === void 0 || _scrollViewRef$curren.scrollTo({
1765
+ y: 220,
1766
+ // Scroll down to reveal additional platforms and hint at Gmail
1767
+ animated: true
1768
+ });
1769
+ }, 100);
1770
+ } else {
1771
+ // Collapsing - animate out first, then hide platforms and scroll back up
1772
+ _reactNative.Animated.timing(additionalPlatformsOpacity, {
1773
+ toValue: 0,
1774
+ duration: 300,
1775
+ useNativeDriver: true
1776
+ }).start(() => {
1777
+ setShowAdditionalPlatforms(false);
1778
+ });
1779
+
1780
+ // Scroll back up smoothly when collapsing
1781
+ setTimeout(() => {
1782
+ var _scrollViewRef$curren2;
1783
+ (_scrollViewRef$curren2 = scrollViewRef.current) === null || _scrollViewRef$curren2 === void 0 || _scrollViewRef$curren2.scrollTo({
1784
+ y: 0,
1785
+ // Scroll back to top
1786
+ animated: true
1787
+ });
1788
+ }, 100);
1789
+ }
1156
1790
  }
1157
- }, /*#__PURE__*/_react.default.createElement(_MaterialIcons.default, {
1158
- name: "person",
1159
- size: 20,
1160
- color: "#28a745"
1161
- }), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1162
- style: styles.testExistingUserButtonText
1163
- }, "Flow 1: Existing User (Email \u2192 Code \u2192 Data Request \u2192 Close)")), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1164
- style: styles.testSkipToTrainingButton,
1165
- onPress: () => {
1166
- // Flow 2: New User - Skip to connect step
1167
- setStep('connect');
1791
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1792
+ style: styles.additionalPlatformsText
1793
+ }, showAdditionalPlatforms ? '− Hide additional platforms' : '+ Add additional platforms')), showAdditionalPlatforms && /*#__PURE__*/_react.default.createElement(_reactNative.Animated.View, {
1794
+ style: {
1795
+ opacity: additionalPlatformsOpacity
1168
1796
  }
1169
- }, /*#__PURE__*/_react.default.createElement(_MaterialIcons.default, {
1170
- name: "person-add",
1171
- size: 20,
1172
- color: "#17a2b8"
1173
- }), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1174
- style: styles.testSkipToTrainingButtonText
1175
- }, "Flow 2: New User (Connect \u2192 PIN \u2192 Training)")), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1176
- style: styles.testDataRequestButton,
1177
- onPress: () => setStep('dataRequest')
1178
- }, /*#__PURE__*/_react.default.createElement(_MaterialIcons.default, {
1179
- name: "preview",
1180
- size: 20,
1181
- color: _constants.COLORS.primary
1182
- }), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1183
- style: styles.testDataRequestButtonText
1184
- }, "Preview Data Request Screen")))), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1797
+ }, additionalPlatforms.map(platform => {
1798
+ const isConnected = connectionStatuses[platform.id] === 'connected';
1799
+ const isPlatformConnecting = connectingPlatform === platform.id;
1800
+ return /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1801
+ key: platform.id,
1802
+ style: styles.platformItem
1803
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1804
+ style: styles.platformInfo
1805
+ }, platform.id === 'gmail' ?
1806
+ /*#__PURE__*/
1807
+ // Use the same wrapper for size/centering, but transparent background
1808
+ _react.default.createElement(_reactNative.View, {
1809
+ style: [styles.platformIcon, {
1810
+ backgroundColor: 'transparent'
1811
+ }]
1812
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1813
+ source: getPlatformIcon(platform.id),
1814
+ style: styles.gmailIconImage,
1815
+ resizeMode: "contain"
1816
+ })) : /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1817
+ style: [styles.platformIcon, {
1818
+ backgroundColor: platform.color
1819
+ }]
1820
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Image, {
1821
+ source: getPlatformIcon(platform.id),
1822
+ style: platform.id === 'reddit' ? styles.redditIconImage : styles.platformIconImage,
1823
+ resizeMode: "contain"
1824
+ })), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1825
+ style: styles.platformName
1826
+ }, platform.name)), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1827
+ onPress: () => {
1828
+ if (isConnected) {
1829
+ // Handle disconnect
1830
+ handleDisconnectPlatform(platform.id, platform.name);
1831
+ } else {
1832
+ // Handle connect
1833
+ handleConnectPlatform(platform.id);
1834
+ }
1835
+ },
1836
+ style: [isConnected ? styles.footerButtonConnected : styles.footerButtonConfirm, {
1837
+ paddingVertical: 8,
1838
+ paddingHorizontal: 16
1839
+ }],
1840
+ disabled: isPlatformConnecting
1841
+ }, isPlatformConnecting ? /*#__PURE__*/_react.default.createElement(_reactNative.ActivityIndicator, {
1842
+ size: "small",
1843
+ color: "#fff"
1844
+ }) : /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1845
+ style: isConnected ? styles.footerButtonTextConnected : styles.footerButtonTextConfirm
1846
+ }, isConnected ? 'Connected' : 'Connect')));
1847
+ }))))), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1185
1848
  style: styles.footer
1186
1849
  }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1187
1850
  style: styles.footerButtonCancel,
@@ -1189,58 +1852,155 @@ const UniversalOnboarding = ({
1189
1852
  }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1190
1853
  style: styles.footerButtonText
1191
1854
  }, "Cancel")), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1192
- style: [styles.footerButtonConfirm, !canProceedToPin() && styles.footerButtonDisabled],
1855
+ style: [styles.footerButtonConfirm, !canProceed && styles.footerButtonDisabled],
1193
1856
  onPress: handleProceed,
1194
- disabled: !canProceedToPin()
1857
+ disabled: !canProceed
1195
1858
  }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1196
1859
  style: styles.footerButtonTextConfirm
1197
- }, "Connect")))), step === 'success' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1198
- style: styles.successContainer
1199
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1200
- style: styles.successContent
1201
- }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1202
- style: styles.successIcon
1203
- }, /*#__PURE__*/_react.default.createElement(_MaterialIcons.default, {
1204
- name: "check",
1205
- size: 48,
1206
- color: "#fff"
1207
- })), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1208
- style: styles.successTitle
1209
- }, "Never Connect Again!"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1210
- style: styles.successSubtitle
1211
- }, "Your login session has been saved"), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1212
- style: styles.successMessage
1213
- }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1214
- style: styles.successMessageText
1215
- }, "Your Onairos account and platform connections are now saved in your browser cookies. Next time you use any app with Onairos, you'll be automatically signed in without needing to reconnect your accounts.")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1216
- style: styles.progressIndicator
1217
- }, /*#__PURE__*/_react.default.createElement(_reactNative.ActivityIndicator, {
1218
- size: "small",
1219
- color: "#4CAF50"
1220
- }), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1221
- style: styles.progressText
1222
- }, "Continuing...")))), step === 'pin' && /*#__PURE__*/_react.default.createElement(_PinInput.PinInput, {
1860
+ }, "Continue")))), step === 'pin' && /*#__PURE__*/_react.default.createElement(_PinInput.PinInput, {
1223
1861
  onSubmit: handlePinSubmit,
1224
1862
  minLength: 8,
1225
1863
  requireSpecialChar: true,
1226
1864
  requireNumber: true,
1227
- onBack: () => setStep('connect')
1228
- }), step === 'training' && /*#__PURE__*/_react.default.createElement(_TrainingModal.TrainingModal, {
1229
- visible: step === 'training',
1230
- progress: training.progress,
1231
- eta: training.eta,
1232
- onCancel: handleClose,
1233
- onComplete: handleTrainingComplete,
1234
- modelKey: "onairosTrainingModel",
1235
- username: username,
1236
- test: isTestMode
1237
- }), step === 'dataRequest' && /*#__PURE__*/_react.default.createElement(_DataRequestScreen.DataRequestScreen, {
1238
- onAccept: handleDataRequestAccept,
1239
- onDecline: handleDataRequestDecline,
1240
- requestData: requestData || {},
1241
- AppName: AppName,
1242
- appIcon: appIcon
1243
- }), step === 'oauth' && oauthUrl && /*#__PURE__*/_react.default.createElement(_OAuthWebView.OAuthWebView, {
1865
+ onBack: () => setStep('connect'),
1866
+ enableBiometricStorage: true
1867
+ // ✅ REMOVED: Background training now starts during transition, not on component mount
1868
+ // onBackgroundTrainingStart={startBackgroundTraining}
1869
+ ,
1870
+ showBackgroundProgress: true,
1871
+ backgroundProgressText: backgroundTrainingProgress || "Training is starting in the background..."
1872
+ }), step === 'persona' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1873
+ style: styles.personaContainer
1874
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1875
+ style: styles.personaHeaderWithBack
1876
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1877
+ style: [styles.personaBackButton,
1878
+ // Highlight the back button when there's insufficient data
1879
+ (dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED') && styles.highlightedBackButton],
1880
+ onPress: () => setStep('connect') // Changed from 'pin' to 'connect' to go back to platform connections
1881
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1882
+ style: [{
1883
+ fontSize: 24
1884
+ },
1885
+ // Make the arrow more prominent when insufficient data
1886
+ (dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED') && styles.highlightedBackArrow]
1887
+ }, "\u2190")), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1888
+ style: styles.personaTitle
1889
+ }, isPersonaComplete ? 'Your persona is ready! 🎉' : 'Creating your persona')), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1890
+ style: styles.personaSubtitle
1891
+ }, isPersonaComplete ? 'We\'ve created a personalized experience just for you.' : 'This will only take a moment. We\'re personalizing your experience.'), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1892
+ style: styles.personaProgressContainer
1893
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1894
+ style: styles.personaProgressBar
1895
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1896
+ style: [styles.personaProgressFill, {
1897
+ width: `${personaProgress}%`
1898
+ }, hasError && styles.progressError]
1899
+ })), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1900
+ style: styles.personaProgressText
1901
+ }, Math.round(personaProgress), "%"), !isPersonaComplete && /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1902
+ style: styles.personaStatusText
1903
+ }, getPersonaStatusMessage(personaProgress))), showDataWarning && dataScenario && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1904
+ style: [styles.dataWarningContainer, dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED' ? styles.dataConnectionsRequired : styles.dataInfoContainer]
1905
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1906
+ style: styles.dataWarningHeader
1907
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1908
+ style: styles.dataWarningIcon
1909
+ }, dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED' ? '‼️' : 'ℹ️'), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1910
+ style: [styles.dataWarningTitle, {
1911
+ color: dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED' ? '#000000' : '#0369A1'
1912
+ }]
1913
+ }, dataScenario === 'CONNECTIONS_REQUIRED' ? 'Not enough data to personalize your experience' : dataScenario === 'NO_DATA' ? 'Not enough data to personalize your experience' : 'Working with your available data')), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1914
+ style: [styles.dataWarningMessage, {
1915
+ color: dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED' ? '#374151' : '#0C4A6E'
1916
+ }]
1917
+ }, dataScenario === 'CONNECTIONS_REQUIRED' ? 'To provide the best experience possible, please go back and add an additional platform.' : dataScenario === 'NO_DATA' ? 'To provide the best experience possible, please go back and add an additional platform.' : 'We\'re building your persona with the information currently available.'), (dataScenario === 'NO_DATA' || dataScenario === 'CONNECTIONS_REQUIRED') && /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1918
+ style: styles.goBackButton,
1919
+ onPress: () => setStep('connect'),
1920
+ activeOpacity: 0.8
1921
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1922
+ style: styles.goBackButtonText
1923
+ }, "\u2190 Add another platform")), (dataDetails === null || dataDetails === void 0 ? void 0 : dataDetails.suggestions) && dataScenario !== 'NO_DATA' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1924
+ style: [styles.dataWarningSuggestions, {
1925
+ borderTopColor: 'rgba(3, 105, 161, 0.2)'
1926
+ }]
1927
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1928
+ style: [styles.dataWarningSuggestionsTitle, {
1929
+ color: '#0369A1'
1930
+ }]
1931
+ }, "For higher model quality:"), dataDetails.suggestions.slice(0, 2).map((suggestion, index) => {
1932
+ // Override specific suggestions with new text
1933
+ let displayText = suggestion;
1934
+ if (suggestion.toLowerCase().includes('better model quality') || suggestion.toLowerCase().includes('interact with more content')) {
1935
+ displayText = 'Connect additional platforms';
1936
+ } else if (suggestion.toLowerCase().includes('like/dislike more videos') || suggestion.toLowerCase().includes('posts, or content')) {
1937
+ displayText = 'Interact and generate more content (like/dislike more videos, etc.)';
1938
+ }
1939
+ return /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1940
+ key: index,
1941
+ style: [styles.dataWarningSuggestionItem, {
1942
+ color: '#0C4A6E'
1943
+ }]
1944
+ }, "\u2022 ", displayText);
1945
+ })), dataScenario === 'LIMITED_DATA' && /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1946
+ style: [styles.dataWarningContinueNote, {
1947
+ color: '#0369A1'
1948
+ }]
1949
+ })), personaStatus.includes('YouTube token expired') && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1950
+ style: [styles.dataWarningContainer, styles.dataInfoContainer]
1951
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1952
+ style: styles.dataWarningHeader
1953
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1954
+ style: styles.dataWarningIcon
1955
+ }, "\uD83D\uDD04"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1956
+ style: [styles.dataWarningTitle, {
1957
+ color: '#0369A1'
1958
+ }]
1959
+ }, "Refreshing YouTube connection")), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1960
+ style: [styles.dataWarningMessage, {
1961
+ color: '#0C4A6E'
1962
+ }]
1963
+ }, "Your YouTube access expired. We're automatically reconnecting...")), isPersonaComplete && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1964
+ style: styles.personaCompleteContainer
1965
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1966
+ style: styles.personaContinueButton,
1967
+ onPress: () => {
1968
+ console.log('🎯 Continue button pressed - completing onboarding');
1969
+ handlePersonaComplete();
1970
+ },
1971
+ activeOpacity: 0.8
1972
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1973
+ style: styles.personaContinueButtonText
1974
+ }, "Continue"))), hasError && !isPersonaComplete && !showDataWarning && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
1975
+ style: styles.personaCompleteContainer
1976
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1977
+ style: styles.personaCompleteTitle
1978
+ }, "Something went wrong"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1979
+ style: styles.personaCompleteSubtitle
1980
+ }, "Please try again or contact support if the issue persists."), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
1981
+ style: [styles.personaContinueButton, {
1982
+ backgroundColor: '#FF3B30'
1983
+ }],
1984
+ onPress: () => {
1985
+ console.log('🔄 Retry button pressed - redirecting to connector screen');
1986
+ setHasError(false);
1987
+ // ❌ DISABLED: Don't start new training on retry
1988
+ // Training should only start during connector→PIN transition
1989
+ // startPersonaCreation();
1990
+
1991
+ // Instead, go back to connector screen so user can restart proper flow
1992
+ setStep('connect');
1993
+ setPersonaStatus('Initializing');
1994
+ setPersonaProgress(0);
1995
+ },
1996
+ activeOpacity: 0.8
1997
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
1998
+ style: styles.personaContinueButtonText
1999
+ }, "Restart")))), step === 'oauth' && oauthUrl && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2000
+ style: {
2001
+ marginTop: -17
2002
+ }
2003
+ }, /*#__PURE__*/_react.default.createElement(_OAuthWebView.OAuthWebView, {
1244
2004
  url: oauthUrl,
1245
2005
  platform: currentPlatform,
1246
2006
  onClose: () => {
@@ -1249,33 +2009,147 @@ const UniversalOnboarding = ({
1249
2009
  },
1250
2010
  onSuccess: handleOAuthSuccess,
1251
2011
  onComplete: () => setStep('connect')
1252
- })))))));
2012
+ })), step === 'privacy' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2013
+ style: styles.modalContent
2014
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2015
+ style: styles.privacyHeader
2016
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
2017
+ style: styles.backButton,
2018
+ onPress: () => setStep('connect')
2019
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2020
+ style: styles.backButtonText
2021
+ }, "\u2190")), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2022
+ style: styles.headerTitle
2023
+ }, "How Enoch uses personal data"), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2024
+ style: styles.backButtonSpacer
2025
+ })), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2026
+ style: styles.privacyDetailsContainer
2027
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2028
+ style: styles.privacyDetailsTitle
2029
+ }), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2030
+ style: styles.privacyBulletPoint
2031
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2032
+ style: styles.bulletPoint
2033
+ }, "\u2022"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2034
+ style: styles.privacyBulletText
2035
+ }, "Enoch legally accesses your platform data with explicit permission for this event only - never stored post-session and auto-deleted.")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2036
+ style: styles.privacyBulletPoint
2037
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2038
+ style: styles.bulletPoint
2039
+ }, "\u2022"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2040
+ style: styles.privacyBulletText
2041
+ }, "Enoch NEVER sells your data. You are a user, not a commodity.")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2042
+ style: styles.privacyBulletPoint
2043
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2044
+ style: styles.bulletPoint
2045
+ }, "\u2022"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2046
+ style: styles.privacyBulletText
2047
+ }, "Data collected builds your Onairos persona, enabling personalized experiences across future products while prioritizing your data sovereignty."))), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
2048
+ style: styles.footerButtonConfirm,
2049
+ onPress: () => {
2050
+ (0, _haptics.triggerHaptic)(_haptics.HapticType.BUTTON_PRESS);
2051
+ setStep('connect');
2052
+ }
2053
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2054
+ style: styles.footerButtonTextConfirm
2055
+ }, "Got it"))), step === 'connections' && /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2056
+ style: styles.modalContent
2057
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2058
+ style: styles.privacyHeader
2059
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
2060
+ style: styles.backButton,
2061
+ onPress: () => setStep(primaryAuthOnly ? 'connections' : 'connect')
2062
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2063
+ style: styles.backButtonText
2064
+ }, "\u2190")), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2065
+ style: styles.headerTitle
2066
+ }, "Connections Found"), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2067
+ style: styles.backButtonSpacer
2068
+ })), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2069
+ style: styles.privacyDetailsContainer
2070
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2071
+ style: styles.connectionsCountText
2072
+ }, "We found ", connectionsCount, " potential connections for you!"), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2073
+ style: styles.privacyBulletPoint
2074
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2075
+ style: styles.bulletPoint
2076
+ }, "\u2022"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2077
+ style: styles.privacyBulletText
2078
+ }, "Continue to see your personalized matches")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2079
+ style: styles.privacyBulletPoint
2080
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2081
+ style: styles.bulletPoint
2082
+ }, "\u2022"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2083
+ style: styles.privacyBulletText
2084
+ }, "Your privacy is protected - we only show compatible profiles")), /*#__PURE__*/_react.default.createElement(_reactNative.View, {
2085
+ style: styles.privacyBulletPoint
2086
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2087
+ style: styles.bulletPoint
2088
+ }, "\u2022"), /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2089
+ style: styles.privacyBulletText
2090
+ }, "Ready to start building meaningful connections?"))), /*#__PURE__*/_react.default.createElement(_reactNative.TouchableOpacity, {
2091
+ style: styles.footerButtonConfirm,
2092
+ onPress: async () => {
2093
+ (0, _haptics.triggerHaptic)(_haptics.HapticType.BUTTON_PRESS);
2094
+ // Complete the onboarding flow
2095
+ isCompletingRef.current = true;
2096
+
2097
+ // Check if this is an existing user adding more data
2098
+ if (isExistingUser && existingUserToken) {
2099
+ console.log('🔑 EXISTING USER: UniversalOnboarding complete, returning existing user token:', `${existingUserToken.substring(0, 20)}...`);
2100
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', existingUserToken, {
2101
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || '',
2102
+ ...userInfo
2103
+ });
2104
+ } else {
2105
+ // For new users, retrieve the stored JWT token from TrainingModal
2106
+ const storedToken = (await _asyncStorage.default.getItem('onairos_jwt_token')) || (await _asyncStorage.default.getItem('auth_token')) || (await _asyncStorage.default.getItem('enoch_token'));
2107
+ const storedEmail = await _asyncStorage.default.getItem('user_email');
2108
+ if (storedToken) {
2109
+ console.log('🔑 NEW USER: UniversalOnboarding complete, returning stored JWT token:', `${storedToken.substring(0, 20)}...`);
2110
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', storedToken, {
2111
+ email: storedEmail || (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || '',
2112
+ ...userInfo
2113
+ });
2114
+ } else {
2115
+ console.warn('⚠️ NEW USER: No stored JWT token found, using fallback');
2116
+ onComplete === null || onComplete === void 0 || onComplete('https://api2.onairos.uk', 'connections-complete-token', {
2117
+ email: (userInfo === null || userInfo === void 0 ? void 0 : userInfo.email) || '',
2118
+ ...userInfo
2119
+ });
2120
+ }
2121
+ }
2122
+ }
2123
+ }, /*#__PURE__*/_react.default.createElement(_reactNative.Text, {
2124
+ style: styles.footerButtonTextConfirm
2125
+ }, "Continue to Setup")))))));
1253
2126
  };
1254
2127
  exports.UniversalOnboarding = UniversalOnboarding;
1255
2128
  const styles = _reactNative.StyleSheet.create({
1256
2129
  modalOverlay: {
1257
2130
  flex: 1,
1258
- backgroundColor: 'rgba(0, 0, 0, 0.5)',
1259
2131
  justifyContent: 'flex-end',
1260
- alignItems: 'center'
2132
+ backgroundColor: 'rgba(0, 0, 0, 0.5)'
1261
2133
  },
1262
2134
  bottomSheet: {
1263
- backgroundColor: '#fff',
1264
- width: width,
1265
- height: height * 0.8,
1266
- borderTopLeftRadius: 24,
1267
- borderTopRightRadius: 24,
1268
- overflow: 'hidden'
2135
+ backgroundColor: '#FFFFFF',
2136
+ borderTopLeftRadius: 20,
2137
+ borderTopRightRadius: 20,
2138
+ paddingTop: 8,
2139
+ paddingBottom: _reactNative.Platform.OS === 'ios' ? 20 : 0,
2140
+ minHeight: height * .86,
2141
+ width: '100%'
1269
2142
  },
1270
2143
  container: {
1271
- flex: 1,
1272
- backgroundColor: '#fff'
2144
+ flex: 1
1273
2145
  },
1274
2146
  handleContainer: {
1275
- width: '100%',
1276
2147
  alignItems: 'center',
1277
- paddingTop: 12,
1278
- paddingBottom: 8
2148
+ paddingVertical: 8
2149
+ },
2150
+ handleButton: {
2151
+ padding: 10,
2152
+ width: 60
1279
2153
  },
1280
2154
  handle: {
1281
2155
  width: 40,
@@ -1284,57 +2158,58 @@ const styles = _reactNative.StyleSheet.create({
1284
2158
  backgroundColor: '#E0E0E0'
1285
2159
  },
1286
2160
  header: {
1287
- padding: 24,
1288
- alignItems: 'center'
2161
+ alignItems: 'center',
2162
+ marginBottom: 20,
2163
+ paddingHorizontal: 24
1289
2164
  },
1290
2165
  headerContent: {
1291
2166
  flexDirection: 'row',
1292
2167
  alignItems: 'center',
1293
2168
  justifyContent: 'center',
1294
- marginBottom: 16
2169
+ marginBottom: 24
1295
2170
  },
1296
2171
  appIcon: {
1297
2172
  width: 48,
1298
2173
  height: 48,
1299
- borderRadius: 16,
2174
+ borderRadius: 24,
1300
2175
  backgroundColor: '#F5F5F5',
1301
2176
  alignItems: 'center',
1302
2177
  justifyContent: 'center'
1303
2178
  },
1304
2179
  appIconText: {
1305
2180
  fontSize: 24,
1306
- color: '#000'
1307
- },
1308
- appIconImage: {
1309
- width: 32,
1310
- height: 32
2181
+ fontWeight: 'bold',
2182
+ color: '#333'
1311
2183
  },
1312
2184
  arrow: {
1313
- marginHorizontal: 16
2185
+ marginHorizontal: 16,
2186
+ fontSize: 24,
2187
+ color: '#666'
1314
2188
  },
1315
2189
  onairosIcon: {
1316
- width: 48,
1317
- height: 48,
1318
- borderRadius: 16,
1319
- backgroundColor: '#F5F5F5',
2190
+ width: 54,
2191
+ height: 54,
2192
+ borderRadius: 32,
2193
+ backgroundColor: 'transparent',
1320
2194
  alignItems: 'center',
1321
2195
  justifyContent: 'center'
1322
2196
  },
1323
2197
  onairosIconText: {
1324
2198
  fontSize: 24,
1325
- color: '#000'
2199
+ fontWeight: 'bold',
2200
+ color: '#fff'
1326
2201
  },
1327
- onairosLogo: {
1328
- width: 32,
1329
- height: 32
2202
+ onairosIconImage: {
2203
+ width: 54,
2204
+ height: 54
1330
2205
  },
1331
2206
  titleContainer: {
1332
- marginBottom: 20
2207
+ alignItems: 'center'
1333
2208
  },
1334
2209
  mainTitle: {
1335
- fontSize: 20,
2210
+ fontSize: 24,
1336
2211
  fontWeight: '600',
1337
- color: '#000',
2212
+ color: '#333',
1338
2213
  textAlign: 'center',
1339
2214
  marginBottom: 12
1340
2215
  },
@@ -1342,44 +2217,102 @@ const styles = _reactNative.StyleSheet.create({
1342
2217
  fontSize: 14,
1343
2218
  color: '#666',
1344
2219
  textAlign: 'center',
1345
- marginBottom: 12
2220
+ marginBottom: 20
2221
+ },
2222
+ privacyLink: {
2223
+ color: '#000000',
2224
+ fontWeight: '600',
2225
+ textDecorationLine: 'underline'
2226
+ },
2227
+ boldText: {
2228
+ fontWeight: 'bold'
1346
2229
  },
1347
2230
  content: {
1348
2231
  flex: 1,
1349
2232
  paddingHorizontal: 24
1350
2233
  },
1351
- scrollContent: {
1352
- flexGrow: 1,
1353
- paddingBottom: 20
2234
+ platformsScrollView: {
2235
+ flex: 1,
2236
+ width: '100%'
2237
+ },
2238
+ platformsScrollContent: {
2239
+ paddingBottom: 0,
2240
+ paddingHorizontal: 24
1354
2241
  },
1355
2242
  platformsContainer: {
1356
2243
  marginTop: 16
1357
2244
  },
1358
- platformItem: {
1359
- flexDirection: 'row',
1360
- justifyContent: 'space-between',
2245
+ platformItem: {
2246
+ flexDirection: 'row',
2247
+ alignItems: 'center',
2248
+ justifyContent: 'space-between',
2249
+ paddingVertical: 16,
2250
+ paddingHorizontal: 8,
2251
+ borderBottomWidth: 1,
2252
+ borderBottomColor: '#E5E5E5'
2253
+ },
2254
+ platformInfo: {
2255
+ flexDirection: 'row',
2256
+ alignItems: 'center'
2257
+ },
2258
+ platformIcon: {
2259
+ width: 40,
2260
+ height: 40,
2261
+ borderRadius: 20,
2262
+ backgroundColor: '#F5F5F5',
2263
+ alignItems: 'center',
2264
+ justifyContent: 'center',
2265
+ marginRight: 16
2266
+ },
2267
+ platformIconText: {
2268
+ fontSize: 18,
2269
+ fontWeight: 'bold',
2270
+ color: '#333',
2271
+ textAlign: 'center',
2272
+ textAlignVertical: 'center'
2273
+ },
2274
+ platformIconImage: {
2275
+ width: 24,
2276
+ height: 24
2277
+ },
2278
+ youtubeIconImage: {
2279
+ width: 58,
2280
+ height: 58
2281
+ },
2282
+ redditIconImage: {
2283
+ width: 34,
2284
+ height: 34
2285
+ },
2286
+ pinterestIconImage: {
2287
+ width: 48,
2288
+ height: 48
2289
+ },
2290
+ gmailIconImage: {
2291
+ width: 32,
2292
+ height: 32
2293
+ },
2294
+ linkedinPlatformIcon: {
2295
+ width: 40,
2296
+ height: 40,
2297
+ borderRadius: 8,
2298
+ backgroundColor: '#F5F5F5',
1361
2299
  alignItems: 'center',
1362
- padding: 12,
1363
- backgroundColor: '#fff',
1364
- borderRadius: 12,
1365
- marginBottom: 8,
1366
- borderWidth: 1,
1367
- borderColor: '#eee'
2300
+ justifyContent: 'center',
2301
+ marginRight: 16
1368
2302
  },
1369
- platformInfo: {
1370
- flexDirection: 'row',
2303
+ pinterestPlatformIcon: {
2304
+ width: 34,
2305
+ height: 34,
2306
+ borderRadius: 17,
2307
+ backgroundColor: '#F5F5F5',
1371
2308
  alignItems: 'center',
1372
- flex: 1
1373
- },
1374
- platformIcon: {
1375
- width: 24,
1376
- height: 24,
1377
- marginRight: 12
2309
+ justifyContent: 'center',
2310
+ marginRight: 16
1378
2311
  },
1379
2312
  platformName: {
1380
2313
  fontSize: 16,
1381
- fontWeight: '500',
1382
- color: '#000'
2314
+ color: '#333',
2315
+ textAlignVertical: 'center'
1383
2316
  },
1384
2317
  footer: {
1385
2318
  flexDirection: 'row',
@@ -1387,301 +2320,389 @@ const styles = _reactNative.StyleSheet.create({
1387
2320
  justifyContent: 'space-between',
1388
2321
  padding: 24,
1389
2322
  borderTopWidth: 1,
1390
- borderTopColor: '#eee',
1391
- backgroundColor: '#fff'
2323
+ borderTopColor: '#E5E5E5'
1392
2324
  },
1393
2325
  footerButtonCancel: {
1394
- paddingVertical: 8,
2326
+ paddingVertical: 12,
1395
2327
  paddingHorizontal: 16
1396
2328
  },
1397
- footerButtonConfirm: {
1398
- paddingVertical: 16,
1399
- paddingHorizontal: 32,
1400
- borderRadius: 16,
1401
- backgroundColor: '#fff',
1402
- borderWidth: 1,
1403
- borderColor: '#000'
1404
- },
1405
- footerButtonDisabled: {
1406
- opacity: 0.5
1407
- },
1408
2329
  footerButtonText: {
1409
2330
  color: '#666',
1410
2331
  fontSize: 16
1411
2332
  },
2333
+ footerButtonConfirm: {
2334
+ paddingVertical: 12,
2335
+ paddingHorizontal: 24,
2336
+ backgroundColor: '#000000',
2337
+ borderRadius: 8,
2338
+ marginTop: 20
2339
+ },
2340
+ footerButtonConnected: {
2341
+ paddingVertical: 12,
2342
+ paddingHorizontal: 24,
2343
+ backgroundColor: '#E9C46A',
2344
+ borderRadius: 8
2345
+ },
2346
+ footerButtonDisabled: {
2347
+ backgroundColor: '#E5E5E5'
2348
+ },
1412
2349
  footerButtonTextConfirm: {
2350
+ color: '#fff',
2351
+ fontSize: 16,
2352
+ fontWeight: '600'
2353
+ },
2354
+ footerButtonTextConnected: {
1413
2355
  color: '#000',
1414
2356
  fontSize: 16,
1415
2357
  fontWeight: '600'
1416
2358
  },
1417
- successContainer: {
1418
- flex: 1,
1419
- justifyContent: 'center',
1420
- alignItems: 'center'
2359
+ connectContainer: {
2360
+ flex: 1
1421
2361
  },
1422
- successContent: {
1423
- backgroundColor: '#fff',
1424
- padding: 24,
1425
- borderRadius: 16,
1426
- alignItems: 'center'
2362
+ modalContent: {
2363
+ flex: 1,
2364
+ backgroundColor: '#FFFFFF',
2365
+ borderTopLeftRadius: 20,
2366
+ borderTopRightRadius: 20,
2367
+ padding: 24
1427
2368
  },
1428
- successIcon: {
1429
- backgroundColor: '#4CAF50',
1430
- borderRadius: 24,
1431
- padding: 12,
1432
- marginBottom: 16
2369
+ backButton: {
2370
+ padding: 8,
2371
+ width: 40
1433
2372
  },
1434
- successTitle: {
1435
- fontSize: 22,
1436
- fontWeight: '600',
1437
- color: '#000',
1438
- textAlign: 'center',
1439
- marginBottom: 16
2373
+ backButtonText: {
2374
+ fontSize: 24,
2375
+ color: '#000000'
1440
2376
  },
1441
- successSubtitle: {
1442
- fontSize: 14,
1443
- color: '#666',
1444
- textAlign: 'center',
1445
- marginBottom: 16
2377
+ backButtonSpacer: {
2378
+ width: 40
1446
2379
  },
1447
- successMessage: {
1448
- backgroundColor: '#f0f0f0',
1449
- padding: 16,
1450
- borderRadius: 8,
1451
- marginBottom: 16
2380
+ headerTitle: {
2381
+ fontSize: 18,
2382
+ fontWeight: '600',
2383
+ color: '#333',
2384
+ textAlign: 'center'
1452
2385
  },
1453
- successMessageText: {
1454
- fontSize: 14,
1455
- color: '#666'
2386
+ privacyHeader: {
2387
+ flexDirection: 'row',
2388
+ alignItems: 'center',
2389
+ justifyContent: 'space-between',
2390
+ paddingHorizontal: 16,
2391
+ paddingVertical: 20,
2392
+ backgroundColor: '#FFFFFF',
2393
+ borderBottomWidth: 1,
2394
+ borderBottomColor: '#F0F0F0'
1456
2395
  },
1457
- platformToggle: {
1458
- width: 50,
1459
- height: 28,
1460
- borderRadius: 14,
1461
- borderWidth: 1,
1462
- borderColor: '#ddd',
1463
- backgroundColor: '#f0f0f0',
1464
- justifyContent: 'center',
1465
- paddingHorizontal: 2
2396
+ privacyDetailsContainer: {
2397
+ paddingHorizontal: 24,
2398
+ paddingVertical: 8,
2399
+ flex: 1,
2400
+ marginTop: 20
1466
2401
  },
1467
- platformToggleActive: {
1468
- borderColor: '#4CAF50',
1469
- backgroundColor: '#4CAF50'
2402
+ privacyDetailsTitle: {
2403
+ fontSize: 20,
2404
+ fontWeight: '600',
2405
+ color: '#333',
2406
+ marginBottom: 0
1470
2407
  },
1471
- platformToggleThumb: {
1472
- width: 22,
1473
- height: 22,
1474
- borderRadius: 11,
1475
- backgroundColor: '#fff',
1476
- shadowColor: '#000',
1477
- shadowOffset: {
1478
- width: 0,
1479
- height: 1
1480
- },
1481
- shadowOpacity: 0.2,
1482
- shadowRadius: 2,
1483
- elevation: 2
2408
+ privacyBulletPoint: {
2409
+ flexDirection: 'row',
2410
+ marginBottom: 16,
2411
+ alignItems: 'flex-start'
1484
2412
  },
1485
- platformToggleThumbActive: {
1486
- alignSelf: 'flex-end'
2413
+ bulletPoint: {
2414
+ fontSize: 18,
2415
+ marginRight: 8,
2416
+ color: '#333'
1487
2417
  },
1488
- // Dark mode styles
1489
- darkPlatformItem: {
1490
- backgroundColor: '#333',
1491
- borderColor: '#555'
2418
+ privacyBulletText: {
2419
+ fontSize: 16,
2420
+ color: '#333',
2421
+ flex: 1,
2422
+ lineHeight: 24
1492
2423
  },
1493
- darkText: {
1494
- color: '#fff'
2424
+ connectionsCountText: {
2425
+ fontSize: 18,
2426
+ fontWeight: '600',
2427
+ color: '#333',
2428
+ marginBottom: 24
1495
2429
  },
1496
- darkSubText: {
1497
- color: '#ccc'
2430
+ personaContainer: {
2431
+ flex: 1,
2432
+ padding: 16,
2433
+ backgroundColor: '#fff',
2434
+ justifyContent: 'flex-start'
1498
2435
  },
1499
- progressIndicator: {
2436
+ personaHeaderWithBack: {
1500
2437
  flexDirection: 'row',
1501
2438
  alignItems: 'center',
1502
- marginTop: 16
1503
- },
1504
- progressText: {
1505
- fontSize: 16,
1506
- fontWeight: '500',
1507
- color: '#000',
1508
- marginLeft: 8
2439
+ justifyContent: 'space-between',
2440
+ marginBottom: 16,
2441
+ paddingVertical: 8
1509
2442
  },
1510
- // Email input styles
1511
- emailInputContainer: {
1512
- flex: 1,
1513
- justifyContent: 'flex-start',
1514
- alignItems: 'center',
1515
- padding: 24,
1516
- paddingTop: 60
2443
+ personaBackButton: {
2444
+ padding: 8
1517
2445
  },
1518
- emailHeader: {
2446
+ personaHeader: {
1519
2447
  alignItems: 'center',
1520
- marginBottom: 32
2448
+ marginBottom: 32,
2449
+ paddingHorizontal: 24
1521
2450
  },
1522
- emailTitle: {
1523
- fontSize: 24,
2451
+ personaTitle: {
2452
+ fontSize: 20,
1524
2453
  fontWeight: '600',
1525
- color: '#000',
2454
+ color: '#333',
1526
2455
  textAlign: 'center',
1527
- marginTop: 16,
2456
+ flex: 1,
1528
2457
  marginBottom: 8
1529
2458
  },
1530
- emailSubtitle: {
1531
- fontSize: 16,
2459
+ personaSubtitle: {
2460
+ fontSize: 14,
1532
2461
  color: '#666',
2462
+ marginBottom: 24,
1533
2463
  textAlign: 'center'
1534
2464
  },
1535
- emailInputSection: {
1536
- width: '100%',
1537
- maxWidth: 320
1538
- },
1539
- emailInput: {
1540
- borderWidth: 1,
1541
- borderColor: '#ddd',
1542
- borderRadius: 12,
1543
- padding: 16,
1544
- fontSize: 16,
1545
- marginBottom: 16,
1546
- backgroundColor: '#fff'
2465
+ personaProgressContainer: {
2466
+ marginBottom: 24,
2467
+ paddingHorizontal: 0
1547
2468
  },
1548
- emailSubmitButton: {
1549
- backgroundColor: '#4CAF50',
1550
- paddingVertical: 16,
1551
- paddingHorizontal: 32,
1552
- borderRadius: 12,
1553
- alignItems: 'center'
2469
+ personaProgressBar: {
2470
+ height: 8,
2471
+ backgroundColor: '#F5F5F5',
2472
+ borderRadius: 4,
2473
+ overflow: 'hidden',
2474
+ marginBottom: 12
1554
2475
  },
1555
- emailSubmitButtonDisabled: {
1556
- opacity: 0.5
2476
+ personaProgressFill: {
2477
+ height: '100%',
2478
+ backgroundColor: '#1BA9D4',
2479
+ borderRadius: 4
1557
2480
  },
1558
- emailSubmitButtonText: {
1559
- color: '#fff',
2481
+ personaProgressText: {
1560
2482
  fontSize: 16,
1561
- fontWeight: '600'
2483
+ fontWeight: '600',
2484
+ color: '#333',
2485
+ textAlign: 'center',
2486
+ marginBottom: 8
1562
2487
  },
1563
- // Verification code styles
1564
- developmentNote: {
2488
+ personaStatusText: {
1565
2489
  fontSize: 14,
1566
- color: '#FF9800',
1567
- textAlign: 'center',
1568
- marginTop: 8,
1569
- backgroundColor: '#FFF3E0',
1570
- padding: 8,
1571
- borderRadius: 4
2490
+ color: '#666',
2491
+ textAlign: 'center'
1572
2492
  },
1573
- codeInputContainer: {
1574
- flexDirection: 'row',
1575
- justifyContent: 'space-between',
1576
- marginBottom: 24,
1577
- paddingHorizontal: 20
2493
+ personaCompleteContainer: {
2494
+ alignItems: 'center',
2495
+ paddingHorizontal: 0
1578
2496
  },
1579
- codeDigit: {
1580
- width: 45,
1581
- height: 55,
1582
- borderWidth: 2,
1583
- borderColor: '#ddd',
1584
- borderRadius: 8,
1585
- fontSize: 24,
2497
+ personaCompleteTitle: {
2498
+ fontSize: 20,
1586
2499
  fontWeight: '600',
1587
- color: '#000',
1588
- backgroundColor: '#fff'
1589
- },
1590
- codeDigitActive: {
1591
- borderColor: '#4CAF50'
1592
- },
1593
- backButton: {
1594
- paddingVertical: 12,
1595
- alignItems: 'center'
2500
+ color: '#333',
2501
+ marginBottom: 8,
2502
+ textAlign: 'center'
1596
2503
  },
1597
- backButtonText: {
2504
+ personaCompleteSubtitle: {
2505
+ fontSize: 14,
1598
2506
  color: '#666',
1599
- fontSize: 16
2507
+ textAlign: 'center',
2508
+ marginBottom: 40
1600
2509
  },
1601
- // Expand button styles
1602
- expandButton: {
1603
- flexDirection: 'row',
2510
+ personaContinueButton: {
2511
+ backgroundColor: '#000000',
2512
+ paddingVertical: 16,
2513
+ paddingHorizontal: 48,
2514
+ borderRadius: 16,
1604
2515
  alignItems: 'center',
1605
- justifyContent: 'center',
1606
- padding: 12,
1607
- backgroundColor: '#f8f9fa',
1608
- borderRadius: 12,
1609
- borderWidth: 1,
1610
- borderColor: '#e9ecef',
1611
- marginTop: 8
2516
+ width: '100%',
2517
+ marginTop: 32,
2518
+ shadowColor: '#000',
2519
+ shadowOffset: {
2520
+ width: 0,
2521
+ height: 2
2522
+ },
2523
+ shadowOpacity: 0.1,
2524
+ shadowRadius: 4,
2525
+ elevation: 3
1612
2526
  },
1613
- expandButtonText: {
1614
- fontSize: 14,
1615
- fontWeight: '500',
1616
- color: _constants.COLORS.primary,
1617
- marginLeft: 8
2527
+ personaContinueButtonText: {
2528
+ color: '#fff',
2529
+ fontSize: 16,
2530
+ fontWeight: '600'
1618
2531
  },
1619
- // Test mode styles
1620
- testModeContainer: {
1621
- marginTop: 16,
1622
- paddingHorizontal: 16,
1623
- backgroundColor: '#f8f9fa',
1624
- borderRadius: 12,
2532
+ progressError: {
2533
+ backgroundColor: '#FF3B30'
2534
+ },
2535
+ dataWarningContainer: {
1625
2536
  padding: 16,
2537
+ borderRadius: 12,
2538
+ marginTop: 16,
1626
2539
  borderWidth: 1,
1627
- borderColor: '#e9ecef'
1628
- },
1629
- testModeTitle: {
1630
- fontSize: 16,
1631
- fontWeight: '600',
1632
- color: '#495057',
1633
- marginBottom: 12,
1634
- textAlign: 'center'
2540
+ shadowColor: '#000',
2541
+ shadowOffset: {
2542
+ width: 0,
2543
+ height: 2
2544
+ },
2545
+ shadowOpacity: 0.1,
2546
+ shadowRadius: 4,
2547
+ elevation: 3
1635
2548
  },
1636
- testDataRequestButton: {
2549
+ dataWarningHeader: {
1637
2550
  flexDirection: 'row',
1638
2551
  alignItems: 'center',
1639
- justifyContent: 'center',
1640
- padding: 12,
1641
- backgroundColor: '#fff3cd',
1642
- borderRadius: 12,
1643
- borderWidth: 1,
1644
- borderColor: '#ffeaa7',
1645
2552
  marginBottom: 8
1646
2553
  },
1647
- testDataRequestButtonText: {
2554
+ dataWarningIcon: {
2555
+ fontSize: 20,
2556
+ marginRight: 8
2557
+ },
2558
+ dataWarningTitle: {
2559
+ fontSize: 16,
2560
+ fontWeight: '600',
2561
+ flex: 1
2562
+ },
2563
+ dataWarningMessage: {
2564
+ fontSize: 14,
2565
+ marginBottom: 0,
2566
+ lineHeight: 20
2567
+ },
2568
+ dataWarningSuggestions: {
2569
+ marginTop: 12,
2570
+ paddingTop: 12,
2571
+ borderTopWidth: 1
2572
+ },
2573
+ dataWarningSuggestionsTitle: {
1648
2574
  fontSize: 14,
2575
+ fontWeight: '600',
2576
+ marginBottom: 6
2577
+ },
2578
+ dataWarningSuggestionItem: {
2579
+ fontSize: 13,
2580
+ marginBottom: 4,
2581
+ lineHeight: 18
2582
+ },
2583
+ dataWarningContinueNote: {
2584
+ fontSize: 13,
1649
2585
  fontWeight: '500',
1650
- color: '#856404',
1651
- marginLeft: 8
2586
+ marginTop: 12,
2587
+ fontStyle: 'italic'
1652
2588
  },
1653
- testExistingUserButton: {
1654
- flexDirection: 'row',
2589
+ dataWarningError: {
2590
+ backgroundColor: '#FFF5F5',
2591
+ borderColor: '#FEB2B2'
2592
+ },
2593
+ dataInfoContainer: {
2594
+ backgroundColor: '#F0F9FF',
2595
+ borderColor: '#BAE6FD'
2596
+ },
2597
+ dataConnectionsRequired: {
2598
+ backgroundColor: '#F5F5F5',
2599
+ borderColor: '#D1D5DB',
2600
+ shadowColor: '#6B7280',
2601
+ shadowOffset: {
2602
+ width: 0,
2603
+ height: 0
2604
+ },
2605
+ shadowOpacity: 0.15,
2606
+ shadowRadius: 8
2607
+ },
2608
+ highlightedBackButton: {
2609
+ backgroundColor: '#F5F5F5',
2610
+ borderRadius: 20,
2611
+ borderWidth: 2,
2612
+ borderColor: '#000000',
2613
+ shadowColor: '#000000',
2614
+ shadowOffset: {
2615
+ width: 0,
2616
+ height: 0
2617
+ },
2618
+ shadowOpacity: 0.3,
2619
+ shadowRadius: 8,
2620
+ elevation: 5
2621
+ },
2622
+ highlightedBackArrow: {
2623
+ color: '#000000',
2624
+ fontWeight: 'bold'
2625
+ },
2626
+ goBackButton: {
2627
+ backgroundColor: '#000000',
2628
+ paddingVertical: 12,
2629
+ paddingHorizontal: 16,
2630
+ borderRadius: 8,
2631
+ marginTop: 12,
1655
2632
  alignItems: 'center',
1656
- justifyContent: 'center',
1657
- padding: 12,
1658
- backgroundColor: '#d4edda',
1659
- borderRadius: 12,
1660
- borderWidth: 1,
1661
- borderColor: '#c3e6cb',
1662
- marginBottom: 8
2633
+ shadowColor: '#000000',
2634
+ shadowOffset: {
2635
+ width: 0,
2636
+ height: 0
2637
+ },
2638
+ shadowOpacity: 0.3,
2639
+ shadowRadius: 6,
2640
+ elevation: 3
1663
2641
  },
1664
- testExistingUserButtonText: {
2642
+ goBackButtonText: {
2643
+ color: '#FFFFFF',
1665
2644
  fontSize: 14,
1666
- fontWeight: '500',
1667
- color: '#155724',
1668
- marginLeft: 8
2645
+ fontWeight: '600'
1669
2646
  },
1670
- testSkipToTrainingButton: {
1671
- flexDirection: 'row',
2647
+ additionalPlatformsToggle: {
2648
+ paddingVertical: 16,
2649
+ paddingHorizontal: 8,
1672
2650
  alignItems: 'center',
1673
- justifyContent: 'center',
1674
- padding: 12,
1675
- backgroundColor: '#d1ecf1',
1676
- borderRadius: 12,
2651
+ borderBottomWidth: 1,
2652
+ borderBottomColor: '#E5E5E5'
2653
+ },
2654
+ additionalPlatformsText: {
2655
+ fontSize: 14,
2656
+ color: '#666',
2657
+ fontWeight: '500'
2658
+ },
2659
+ asterisk: {
2660
+ color: '#FF6B6B',
2661
+ fontSize: 16,
2662
+ fontWeight: 'bold',
2663
+ marginLeft: 2
2664
+ },
2665
+ linkedinRequirementContainer: {
2666
+ backgroundColor: '#F8F9FA',
2667
+ borderWidth: 1,
2668
+ borderColor: '#E5E7EB',
2669
+ borderRadius: 8,
2670
+ paddingHorizontal: 12,
2671
+ paddingVertical: 8,
2672
+ marginTop: 8,
2673
+ marginHorizontal: 4
2674
+ },
2675
+ linkedinRequirementText: {
2676
+ fontSize: 12,
2677
+ fontStyle: 'italic',
2678
+ textAlign: 'center'
2679
+ },
2680
+ linkedinRequirementAsterisk: {
2681
+ color: '#FF6B6B',
2682
+ fontWeight: 'bold'
2683
+ },
2684
+ linkedinRequirementMessage: {
2685
+ color: '#6B7280'
2686
+ },
2687
+ existingUserBanner: {
2688
+ backgroundColor: '#F0F9FF',
1677
2689
  borderWidth: 1,
1678
- borderColor: '#bee5eb'
2690
+ borderColor: '#0EA5E9',
2691
+ borderRadius: 12,
2692
+ paddingHorizontal: 16,
2693
+ paddingVertical: 12,
2694
+ marginTop: 12
1679
2695
  },
1680
- testSkipToTrainingButtonText: {
2696
+ existingUserText: {
1681
2697
  fontSize: 14,
1682
- fontWeight: '500',
1683
- color: '#0c5460',
1684
- marginLeft: 8
2698
+ fontWeight: '600',
2699
+ color: '#0369A1',
2700
+ marginBottom: 4
2701
+ },
2702
+ existingUserSubtext: {
2703
+ fontSize: 12,
2704
+ color: '#0C4A6E',
2705
+ lineHeight: 16
1685
2706
  }
1686
2707
  });
1687
2708
  //# sourceMappingURL=UniversalOnboarding.js.map