@sanctum-key/react-native-sdk 1.0.61 → 1.0.62

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 (149) hide show
  1. package/README.md +34 -0
  2. package/android/build/.transforms/ac63f648699cdd4b91e6ee06476f2a70/results.bin +1 -0
  3. package/android/build/.transforms/ac63f648699cdd4b91e6ee06476f2a70/transformed/classes/classes_dex/classes.dex +0 -0
  4. package/android/build/intermediates/aapt_friendly_merged_manifests/debug/processDebugManifest/aapt/AndroidManifest.xml +9 -0
  5. package/android/build/intermediates/compile_library_classes_jar/debug/bundleLibCompileToJarDebug/classes.jar +0 -0
  6. package/android/build/intermediates/incremental/debug/packageDebugResources/compile-file-map.properties +1 -1
  7. package/android/build/intermediates/manifest_merge_blame_file/debug/processDebugManifest/manifest-merger-blame-debug-report.txt +45 -25
  8. package/android/build/intermediates/merged_manifest/debug/processDebugManifest/AndroidManifest.xml +9 -0
  9. package/android/build/intermediates/runtime_library_classes_jar/debug/bundleLibRuntimeToJarDebug/classes.jar +0 -0
  10. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/inputs/source-to-output.tab +0 -0
  11. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/inputs/source-to-output.tab.values.at +0 -0
  12. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-attributes.tab +0 -0
  13. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-attributes.tab.keystream +0 -0
  14. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-attributes.tab.values.at +0 -0
  15. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-attributes.tab_i +0 -0
  16. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-fq-name-to-source.tab +0 -0
  17. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-fq-name-to-source.tab.keystream +0 -0
  18. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-fq-name-to-source.tab.values.at +0 -0
  19. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/class-fq-name-to-source.tab_i +0 -0
  20. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/internal-name-to-source.tab +0 -0
  21. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/internal-name-to-source.tab.keystream +0 -0
  22. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/internal-name-to-source.tab.keystream.len +0 -0
  23. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/internal-name-to-source.tab.len +0 -0
  24. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/internal-name-to-source.tab.values.at +0 -0
  25. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/internal-name-to-source.tab_i +0 -0
  26. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/proto.tab +0 -0
  27. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/proto.tab.keystream +0 -0
  28. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/proto.tab.values.at +0 -0
  29. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/proto.tab_i +0 -0
  30. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/source-to-classes.tab +0 -0
  31. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/source-to-classes.tab.values.at +0 -0
  32. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/subtypes.tab +0 -0
  33. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/subtypes.tab.values.at +0 -0
  34. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/supertypes.tab +0 -0
  35. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/jvm/kotlin/supertypes.tab.values.at +0 -0
  36. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/counters.tab +1 -1
  37. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/file-to-id.tab +0 -0
  38. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/file-to-id.tab.values.at +0 -0
  39. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/id-to-file.tab +0 -0
  40. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/id-to-file.tab.keystream +0 -0
  41. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/id-to-file.tab.keystream.len +0 -0
  42. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/id-to-file.tab.len +0 -0
  43. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/id-to-file.tab.values.at +0 -0
  44. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/id-to-file.tab_i +0 -0
  45. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/lookups.tab +0 -0
  46. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/lookups.tab.keystream +0 -0
  47. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/lookups.tab.keystream.len +0 -0
  48. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/lookups.tab.len +0 -0
  49. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/lookups.tab.values.at +0 -0
  50. package/android/build/kotlin/compileDebugKotlin/cacheable/caches-jvm/lookups/lookups.tab_i +0 -0
  51. package/android/build/kotlin/compileDebugKotlin/cacheable/last-build.bin +0 -0
  52. package/android/build/kotlin/compileDebugKotlin/classpath-snapshot/shrunk-classpath-snapshot.bin +0 -0
  53. package/android/build/kotlin/compileDebugKotlin/local-state/build-history.bin +0 -0
  54. package/android/build/outputs/logs/manifest-merger-debug-report.txt +34 -12
  55. package/android/build/tmp/compileDebugJavaWithJavac/previous-compilation-data.bin +0 -0
  56. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/SanctumKeySdkModule$BarcodeRegion.class +0 -0
  57. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/SanctumKeySdkModule$Companion.class +0 -0
  58. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$1$6$1.class → SanctumKeySdkModule$definition$1$7$1.class} +0 -0
  59. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$1$6$2.class → SanctumKeySdkModule$definition$1$7$2.class} +0 -0
  60. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunction$1.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$1.class} +0 -0
  61. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunction$5.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$2.class} +0 -0
  62. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunction$3.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$3.class} +0 -0
  63. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$4.class +0 -0
  64. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunction$2.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$5.class} +0 -0
  65. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$6.class +0 -0
  66. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunction$4.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$7.class} +0 -0
  67. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$8.class +0 -0
  68. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunction$6.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunction$9.class} +0 -0
  69. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$1.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$1.class} +0 -0
  70. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$2.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$2.class} +0 -0
  71. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$3.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$3.class} +0 -0
  72. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$4.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$4.class} +0 -0
  73. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$5.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$5.class} +0 -0
  74. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$6.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$6.class} +0 -0
  75. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$AsyncFunctionWithPromise$7.class → SanctumKeySdkModule$definition$lambda$24$$inlined$AsyncFunctionWithPromise$7.class} +0 -0
  76. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$$inlined$View$1.class → SanctumKeySdkModule$definition$lambda$24$$inlined$View$1.class} +0 -0
  77. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$lambda$15$$inlined$Prop$1.class → SanctumKeySdkModule$definition$lambda$24$lambda$23$$inlined$Prop$1.class} +0 -0
  78. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/{SanctumKeySdkModule$definition$lambda$16$lambda$15$$inlined$Prop$2.class → SanctumKeySdkModule$definition$lambda$24$lambda$23$$inlined$Prop$2.class} +0 -0
  79. package/android/build/tmp/kotlin-classes/debug/kyc/sanctumkey/com/SanctumKeySdkModule.class +0 -0
  80. package/android/src/main/AndroidManifest.xml +9 -0
  81. package/android/src/main/java/kyc/sanctumkey/com/SanctumKeySdkModule.kt +147 -0
  82. package/build/package.json +1 -1
  83. package/build/src/SanctumKeySdkModule.d.ts +2 -0
  84. package/build/src/SanctumKeySdkModule.d.ts.map +1 -1
  85. package/build/src/SanctumKeySdkModule.js.map +1 -1
  86. package/build/src/SanctumKeySdkModule.web.d.ts +2 -0
  87. package/build/src/SanctumKeySdkModule.web.d.ts.map +1 -1
  88. package/build/src/SanctumKeySdkModule.web.js +14 -0
  89. package/build/src/SanctumKeySdkModule.web.js.map +1 -1
  90. package/build/src/components/KYCElements/CountrySelection.d.ts.map +1 -1
  91. package/build/src/components/KYCElements/CountrySelection.js +1 -1
  92. package/build/src/components/KYCElements/CountrySelection.js.map +1 -1
  93. package/build/src/components/KYCElements/CountrySelectionTemplate.d.ts.map +1 -1
  94. package/build/src/components/KYCElements/CountrySelectionTemplate.js +27 -17
  95. package/build/src/components/KYCElements/CountrySelectionTemplate.js.map +1 -1
  96. package/build/src/components/KYCElements/IDCardCapture.d.ts.map +1 -1
  97. package/build/src/components/KYCElements/IDCardCapture.js +46 -28
  98. package/build/src/components/KYCElements/IDCardCapture.js.map +1 -1
  99. package/build/src/components/OverLay/IdCard.d.ts +1 -1
  100. package/build/src/components/OverLay/IdCard.d.ts.map +1 -1
  101. package/build/src/components/OverLay/IdCard.js +47 -14
  102. package/build/src/components/OverLay/IdCard.js.map +1 -1
  103. package/build/src/components/OverLay/type.d.ts +2 -0
  104. package/build/src/components/OverLay/type.d.ts.map +1 -1
  105. package/build/src/components/OverLay/type.js.map +1 -1
  106. package/build/src/components/Svgs/scanningLine.d.ts +4 -1
  107. package/build/src/components/Svgs/scanningLine.d.ts.map +1 -1
  108. package/build/src/components/Svgs/scanningLine.js +15 -11
  109. package/build/src/components/Svgs/scanningLine.js.map +1 -1
  110. package/build/src/components/TemplateKYCExample.d.ts +4 -1
  111. package/build/src/components/TemplateKYCExample.d.ts.map +1 -1
  112. package/build/src/components/TemplateKYCExample.js +2 -2
  113. package/build/src/components/TemplateKYCExample.js.map +1 -1
  114. package/build/src/components/TemplateKYCFlowRefactored.d.ts +4 -2
  115. package/build/src/components/TemplateKYCFlowRefactored.d.ts.map +1 -1
  116. package/build/src/components/TemplateKYCFlowRefactored.js +157 -8
  117. package/build/src/components/TemplateKYCFlowRefactored.js.map +1 -1
  118. package/build/src/config/region_mapping.d.ts.map +1 -1
  119. package/build/src/config/region_mapping.js +12 -0
  120. package/build/src/config/region_mapping.js.map +1 -1
  121. package/build/src/config/region_mapping.json +12 -0
  122. package/build/src/index.d.ts +2 -0
  123. package/build/src/index.d.ts.map +1 -1
  124. package/build/src/index.js +2 -0
  125. package/build/src/index.js.map +1 -1
  126. package/build/src/security/deviceSecurity.d.ts +30 -0
  127. package/build/src/security/deviceSecurity.d.ts.map +1 -0
  128. package/build/src/security/deviceSecurity.js +55 -0
  129. package/build/src/security/deviceSecurity.js.map +1 -0
  130. package/build/src/utils/logger.d.ts.map +1 -1
  131. package/build/src/utils/logger.js +5 -0
  132. package/build/src/utils/logger.js.map +1 -1
  133. package/ios/SanctumKeySdkModule.swift +93 -0
  134. package/package.json +1 -1
  135. package/src/SanctumKeySdkModule.ts +2 -0
  136. package/src/SanctumKeySdkModule.web.ts +16 -0
  137. package/src/components/KYCElements/CountrySelection.tsx +3 -1
  138. package/src/components/KYCElements/CountrySelectionTemplate.tsx +73 -24
  139. package/src/components/KYCElements/IDCardCapture.tsx +53 -30
  140. package/src/components/OverLay/IdCard.tsx +72 -15
  141. package/src/components/OverLay/type.ts +4 -2
  142. package/src/components/Svgs/scanningLine.tsx +19 -12
  143. package/src/components/TemplateKYCExample.tsx +8 -1
  144. package/src/components/TemplateKYCFlowRefactored.tsx +202 -16
  145. package/src/config/region_mapping.json +12 -0
  146. package/src/config/region_mapping.ts +12 -0
  147. package/src/index.ts +9 -1
  148. package/src/security/deviceSecurity.ts +106 -0
  149. package/src/utils/logger.ts +5 -0
@@ -594,6 +594,18 @@
594
594
  }
595
595
  },
596
596
  "Kenya": {
597
+ "drivers_licence": {
598
+ "root": [
599
+ {
600
+ "py_file": "dl_back.py",
601
+ "keys_found": null
602
+ },
603
+ {
604
+ "py_file": "dl_front.py",
605
+ "keys_found": null
606
+ }
607
+ ]
608
+ },
597
609
  "identity_card": {
598
610
  "root": [
599
611
  {
@@ -10,5 +10,7 @@ export { useTemplateLoader } from './hooks/useTemplateLoader';
10
10
  export { WelcomeTemplate } from './components/KYCElements/WelcomeTemplate';
11
11
  export { EnhancedCameraView } from './components/EnhancedCameraView';
12
12
  export { UnifiedCameraModule } from './modules/camera';
13
+ export { checkDeviceSecurity, getDeviceSecurityViolations } from './security/deviceSecurity';
14
+ export type { DeviceSecurityCheckResult, DeviceSecurityPolicy, DeviceSecurityViolation, } from './security/deviceSecurity';
13
15
  export { default as WebKYCEntry } from './web/WebKYCEntry';
14
16
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AACA,mBAAmB,uBAAuB,CAAC;AAG3C,mBAAmB,mBAAmB,CAAC;AAGvC,mBAAmB,mBAAmB,CAAC;AAGvC,OAAO,EAAE,kBAAkB,IAAI,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AAE5F,OAAO,EAAE,kBAAkB,IAAI,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAG3F,OAAO,EAAE,eAAe,EAAE,MAAM,wCAAwC,CAAC;AAGzE,OAAO,EAAE,OAAO,IAAI,eAAe,EAAE,MAAM,+BAA+B,CAAC;AAC3E,OAAO,EAAE,6BAA6B,EAAE,2BAA2B,EAAE,MAAM,8BAA8B,CAAC;AAC1G,OAAO,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AAG9D,OAAO,EAAE,eAAe,EAAE,MAAM,0CAA0C,CAAC;AAC3E,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AACrE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAGvD,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,mBAAmB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AACA,mBAAmB,uBAAuB,CAAC;AAG3C,mBAAmB,mBAAmB,CAAC;AAGvC,mBAAmB,mBAAmB,CAAC;AAGvC,OAAO,EAAE,kBAAkB,IAAI,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AAE5F,OAAO,EAAE,kBAAkB,IAAI,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAG3F,OAAO,EAAE,eAAe,EAAE,MAAM,wCAAwC,CAAC;AAGzE,OAAO,EAAE,OAAO,IAAI,eAAe,EAAE,MAAM,+BAA+B,CAAC;AAC3E,OAAO,EAAE,6BAA6B,EAAE,2BAA2B,EAAE,MAAM,8BAA8B,CAAC;AAC1G,OAAO,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AAG9D,OAAO,EAAE,eAAe,EAAE,MAAM,0CAA0C,CAAC;AAC3E,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AACrE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAGvD,OAAO,EAAE,mBAAmB,EAAE,2BAA2B,EAAE,MAAM,2BAA2B,CAAC;AAC7F,YAAY,EACV,yBAAyB,EACzB,oBAAoB,EACpB,uBAAuB,GACxB,MAAM,2BAA2B,CAAC;AAGnC,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,mBAAmB,CAAC"}
@@ -11,6 +11,8 @@ export { useTemplateLoader } from './hooks/useTemplateLoader';
11
11
  export { WelcomeTemplate } from './components/KYCElements/WelcomeTemplate';
12
12
  export { EnhancedCameraView } from './components/EnhancedCameraView';
13
13
  export { UnifiedCameraModule } from './modules/camera';
14
+ // Export native device-integrity checks and policy types.
15
+ export { checkDeviceSecurity, getDeviceSecurityViolations } from './security/deviceSecurity';
14
16
  // Export Web KYC Components
15
17
  export { default as WebKYCEntry } from './web/WebKYCEntry';
16
18
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAUA,OAAO,EAAE,kBAAkB,IAAI,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AAC5F,mEAAmE;AACnE,OAAO,EAAE,kBAAkB,IAAI,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAE3F,kCAAkC;AAClC,OAAO,EAAE,eAAe,EAAE,MAAM,wCAAwC,CAAC;AAEzE,wCAAwC;AACxC,OAAO,EAAE,OAAO,IAAI,eAAe,EAAE,MAAM,+BAA+B,CAAC;AAC3E,OAAO,EAAE,6BAA6B,EAAE,2BAA2B,EAAE,MAAM,8BAA8B,CAAC;AAC1G,OAAO,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AAE9D,6BAA6B;AAC7B,OAAO,EAAE,eAAe,EAAE,MAAM,0CAA0C,CAAC;AAC3E,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AACrE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAEvD,4BAA4B;AAC5B,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,mBAAmB,CAAC","sourcesContent":["// Explicitly mark these as type-only exports to prevent Web Bundler crashes\nexport type * from './SanctumKeySdk.types';\n\n// Export KYC types\nexport type * from './types/KYC.types';\n\n// Export Environment types\nexport type * from './types/env.types';\n\n\nexport { TemplateKYCExample as LaunchSanctumKeyKYC } from './components/TemplateKYCExample';\n// Backward compatibility for existing integrations using the typo.\nexport { TemplateKYCExample as LauchSanctumKeyKYC } from './components/TemplateKYCExample';\n\n// Export Template Flow Components\nexport { TemplateKYCFlow } from './components/TemplateKYCFlowRefactored';\n\n// Export Template Service and Utilities\nexport { default as templateService } from './modules/api/TemplateService';\nexport { transformBackendTemplateToSDK, validateTransformedTemplate } from './utils/template-transformer';\nexport { useTemplateLoader } from './hooks/useTemplateLoader';\n\n// Export Template Components\nexport { WelcomeTemplate } from './components/KYCElements/WelcomeTemplate';\nexport { EnhancedCameraView } from './components/EnhancedCameraView';\nexport { UnifiedCameraModule } from './modules/camera';\n\n// Export Web KYC Components\nexport { default as WebKYCEntry } from './web/WebKYCEntry';"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAUA,OAAO,EAAE,kBAAkB,IAAI,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AAC5F,mEAAmE;AACnE,OAAO,EAAE,kBAAkB,IAAI,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAE3F,kCAAkC;AAClC,OAAO,EAAE,eAAe,EAAE,MAAM,wCAAwC,CAAC;AAEzE,wCAAwC;AACxC,OAAO,EAAE,OAAO,IAAI,eAAe,EAAE,MAAM,+BAA+B,CAAC;AAC3E,OAAO,EAAE,6BAA6B,EAAE,2BAA2B,EAAE,MAAM,8BAA8B,CAAC;AAC1G,OAAO,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AAE9D,6BAA6B;AAC7B,OAAO,EAAE,eAAe,EAAE,MAAM,0CAA0C,CAAC;AAC3E,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AACrE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAEvD,0DAA0D;AAC1D,OAAO,EAAE,mBAAmB,EAAE,2BAA2B,EAAE,MAAM,2BAA2B,CAAC;AAO7F,4BAA4B;AAC5B,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,mBAAmB,CAAC","sourcesContent":["// Explicitly mark these as type-only exports to prevent Web Bundler crashes\nexport type * from './SanctumKeySdk.types';\n\n// Export KYC types\nexport type * from './types/KYC.types';\n\n// Export Environment types\nexport type * from './types/env.types';\n\n\nexport { TemplateKYCExample as LaunchSanctumKeyKYC } from './components/TemplateKYCExample';\n// Backward compatibility for existing integrations using the typo.\nexport { TemplateKYCExample as LauchSanctumKeyKYC } from './components/TemplateKYCExample';\n\n// Export Template Flow Components\nexport { TemplateKYCFlow } from './components/TemplateKYCFlowRefactored';\n\n// Export Template Service and Utilities\nexport { default as templateService } from './modules/api/TemplateService';\nexport { transformBackendTemplateToSDK, validateTransformedTemplate } from './utils/template-transformer';\nexport { useTemplateLoader } from './hooks/useTemplateLoader';\n\n// Export Template Components\nexport { WelcomeTemplate } from './components/KYCElements/WelcomeTemplate';\nexport { EnhancedCameraView } from './components/EnhancedCameraView';\nexport { UnifiedCameraModule } from './modules/camera';\n\n// Export native device-integrity checks and policy types.\nexport { checkDeviceSecurity, getDeviceSecurityViolations } from './security/deviceSecurity';\nexport type {\n DeviceSecurityCheckResult,\n DeviceSecurityPolicy,\n DeviceSecurityViolation,\n} from './security/deviceSecurity';\n\n// Export Web KYC Components\nexport { default as WebKYCEntry } from './web/WebKYCEntry';\n"]}
@@ -0,0 +1,30 @@
1
+ export type DeviceSecurityPlatform = 'android' | 'ios' | 'web' | 'unknown';
2
+ export interface DeviceSecurityCheckResult {
3
+ platform: DeviceSecurityPlatform;
4
+ supported: boolean;
5
+ isRooted: boolean;
6
+ isJailbroken: boolean;
7
+ isEmulator: boolean;
8
+ isDeveloperModeEnabled: boolean;
9
+ developerModeCheckSupported: boolean;
10
+ isDebuggerAttached: boolean;
11
+ isCompromised: boolean;
12
+ riskSignals: string[];
13
+ checkedAt: string;
14
+ }
15
+ export interface DeviceSecurityPolicy {
16
+ /** Run the check. Defaults to true on Android and iOS. */
17
+ enabled?: boolean;
18
+ /** Block rooted Android or jailbroken iOS devices. Defaults to true in production. */
19
+ blockCompromisedDevices?: boolean;
20
+ /** Block Android developer options or an attached iOS debugger. Defaults to true in production. */
21
+ blockDeveloperMode?: boolean;
22
+ /** Block Android emulators and the iOS Simulator. Defaults to true in production. */
23
+ blockEmulators?: boolean;
24
+ /** Block when the native check is unavailable or fails. Defaults to true in production. */
25
+ failClosed?: boolean;
26
+ }
27
+ export type DeviceSecurityViolation = 'compromised_device' | 'developer_mode' | 'emulator' | 'check_unavailable';
28
+ export declare function checkDeviceSecurity(): Promise<DeviceSecurityCheckResult>;
29
+ export declare function getDeviceSecurityViolations(result: DeviceSecurityCheckResult, policy: Required<Pick<DeviceSecurityPolicy, 'blockCompromisedDevices' | 'blockDeveloperMode' | 'blockEmulators' | 'failClosed'>>): DeviceSecurityViolation[];
30
+ //# sourceMappingURL=deviceSecurity.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"deviceSecurity.d.ts","sourceRoot":"","sources":["../../../src/security/deviceSecurity.ts"],"names":[],"mappings":"AAGA,MAAM,MAAM,sBAAsB,GAAG,SAAS,GAAG,KAAK,GAAG,KAAK,GAAG,SAAS,CAAC;AAE3E,MAAM,WAAW,yBAAyB;IACxC,QAAQ,EAAE,sBAAsB,CAAC;IACjC,SAAS,EAAE,OAAO,CAAC;IACnB,QAAQ,EAAE,OAAO,CAAC;IAClB,YAAY,EAAE,OAAO,CAAC;IACtB,UAAU,EAAE,OAAO,CAAC;IACpB,sBAAsB,EAAE,OAAO,CAAC;IAChC,2BAA2B,EAAE,OAAO,CAAC;IACrC,kBAAkB,EAAE,OAAO,CAAC;IAC5B,aAAa,EAAE,OAAO,CAAC;IACvB,WAAW,EAAE,MAAM,EAAE,CAAC;IACtB,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,oBAAoB;IACnC,0DAA0D;IAC1D,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,sFAAsF;IACtF,uBAAuB,CAAC,EAAE,OAAO,CAAC;IAClC,mGAAmG;IACnG,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,qFAAqF;IACrF,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,2FAA2F;IAC3F,UAAU,CAAC,EAAE,OAAO,CAAC;CACtB;AAED,MAAM,MAAM,uBAAuB,GAC/B,oBAAoB,GACpB,gBAAgB,GAChB,UAAU,GACV,mBAAmB,CAAC;AAUxB,wBAAsB,mBAAmB,IAAI,OAAO,CAAC,yBAAyB,CAAC,CA0C9E;AAED,wBAAgB,2BAA2B,CACzC,MAAM,EAAE,yBAAyB,EACjC,MAAM,EAAE,QAAQ,CAAC,IAAI,CACnB,oBAAoB,EACpB,yBAAyB,GAAG,oBAAoB,GAAG,gBAAgB,GAAG,YAAY,CACnF,CAAC,GACD,uBAAuB,EAAE,CAS3B"}
@@ -0,0 +1,55 @@
1
+ import { Platform } from 'react-native';
2
+ import SanctumKeySdkModule from '../SanctumKeySdkModule';
3
+ const booleanValue = (value) => value === true;
4
+ const stringArray = (value) => (Array.isArray(value) ? value.filter((item) => typeof item === 'string') : []);
5
+ export async function checkDeviceSecurity() {
6
+ if (Platform.OS === 'web') {
7
+ return {
8
+ platform: 'web',
9
+ supported: false,
10
+ isRooted: false,
11
+ isJailbroken: false,
12
+ isEmulator: false,
13
+ isDeveloperModeEnabled: false,
14
+ developerModeCheckSupported: false,
15
+ isDebuggerAttached: false,
16
+ isCompromised: false,
17
+ riskSignals: ['native_device_security_check_unavailable_on_web'],
18
+ checkedAt: new Date().toISOString(),
19
+ };
20
+ }
21
+ if (typeof SanctumKeySdkModule.checkDeviceSecurity !== 'function') {
22
+ throw new Error('The native device-security checker is unavailable. Rebuild the Android or iOS application with the latest SanctumKey SDK.');
23
+ }
24
+ const nativeResult = await SanctumKeySdkModule.checkDeviceSecurity();
25
+ const isRooted = booleanValue(nativeResult.isRooted);
26
+ const isJailbroken = booleanValue(nativeResult.isJailbroken);
27
+ return {
28
+ platform: nativeResult.platform === 'android' || nativeResult.platform === 'ios'
29
+ ? nativeResult.platform
30
+ : 'unknown',
31
+ supported: nativeResult.supported !== false,
32
+ isRooted,
33
+ isJailbroken,
34
+ isEmulator: booleanValue(nativeResult.isEmulator),
35
+ isDeveloperModeEnabled: booleanValue(nativeResult.isDeveloperModeEnabled),
36
+ developerModeCheckSupported: booleanValue(nativeResult.developerModeCheckSupported),
37
+ isDebuggerAttached: booleanValue(nativeResult.isDebuggerAttached),
38
+ isCompromised: booleanValue(nativeResult.isCompromised) || isRooted || isJailbroken,
39
+ riskSignals: stringArray(nativeResult.riskSignals),
40
+ checkedAt: new Date().toISOString(),
41
+ };
42
+ }
43
+ export function getDeviceSecurityViolations(result, policy) {
44
+ const violations = [];
45
+ if (!result.supported && policy.failClosed)
46
+ violations.push('check_unavailable');
47
+ if (result.isCompromised && policy.blockCompromisedDevices)
48
+ violations.push('compromised_device');
49
+ if (result.isDeveloperModeEnabled && policy.blockDeveloperMode)
50
+ violations.push('developer_mode');
51
+ if (result.isEmulator && policy.blockEmulators)
52
+ violations.push('emulator');
53
+ return violations;
54
+ }
55
+ //# sourceMappingURL=deviceSecurity.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"deviceSecurity.js","sourceRoot":"","sources":["../../../src/security/deviceSecurity.ts"],"names":[],"mappings":"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","sourcesContent":["import { Platform } from 'react-native';\nimport SanctumKeySdkModule from '../SanctumKeySdkModule';\n\nexport type DeviceSecurityPlatform = 'android' | 'ios' | 'web' | 'unknown';\n\nexport interface DeviceSecurityCheckResult {\n platform: DeviceSecurityPlatform;\n supported: boolean;\n isRooted: boolean;\n isJailbroken: boolean;\n isEmulator: boolean;\n isDeveloperModeEnabled: boolean;\n developerModeCheckSupported: boolean;\n isDebuggerAttached: boolean;\n isCompromised: boolean;\n riskSignals: string[];\n checkedAt: string;\n}\n\nexport interface DeviceSecurityPolicy {\n /** Run the check. Defaults to true on Android and iOS. */\n enabled?: boolean;\n /** Block rooted Android or jailbroken iOS devices. Defaults to true in production. */\n blockCompromisedDevices?: boolean;\n /** Block Android developer options or an attached iOS debugger. Defaults to true in production. */\n blockDeveloperMode?: boolean;\n /** Block Android emulators and the iOS Simulator. Defaults to true in production. */\n blockEmulators?: boolean;\n /** Block when the native check is unavailable or fails. Defaults to true in production. */\n failClosed?: boolean;\n}\n\nexport type DeviceSecurityViolation =\n | 'compromised_device'\n | 'developer_mode'\n | 'emulator'\n | 'check_unavailable';\n\ntype NativeDeviceSecurityResult = Partial<Omit<DeviceSecurityCheckResult, 'checkedAt'>>;\n\nconst booleanValue = (value: unknown): boolean => value === true;\n\nconst stringArray = (value: unknown): string[] => (\n Array.isArray(value) ? value.filter((item): item is string => typeof item === 'string') : []\n);\n\nexport async function checkDeviceSecurity(): Promise<DeviceSecurityCheckResult> {\n if (Platform.OS === 'web') {\n return {\n platform: 'web',\n supported: false,\n isRooted: false,\n isJailbroken: false,\n isEmulator: false,\n isDeveloperModeEnabled: false,\n developerModeCheckSupported: false,\n isDebuggerAttached: false,\n isCompromised: false,\n riskSignals: ['native_device_security_check_unavailable_on_web'],\n checkedAt: new Date().toISOString(),\n };\n }\n\n if (typeof SanctumKeySdkModule.checkDeviceSecurity !== 'function') {\n throw new Error(\n 'The native device-security checker is unavailable. Rebuild the Android or iOS application with the latest SanctumKey SDK.',\n );\n }\n\n const nativeResult = await SanctumKeySdkModule.checkDeviceSecurity() as NativeDeviceSecurityResult;\n const isRooted = booleanValue(nativeResult.isRooted);\n const isJailbroken = booleanValue(nativeResult.isJailbroken);\n\n return {\n platform: nativeResult.platform === 'android' || nativeResult.platform === 'ios'\n ? nativeResult.platform\n : 'unknown',\n supported: nativeResult.supported !== false,\n isRooted,\n isJailbroken,\n isEmulator: booleanValue(nativeResult.isEmulator),\n isDeveloperModeEnabled: booleanValue(nativeResult.isDeveloperModeEnabled),\n developerModeCheckSupported: booleanValue(nativeResult.developerModeCheckSupported),\n isDebuggerAttached: booleanValue(nativeResult.isDebuggerAttached),\n isCompromised: booleanValue(nativeResult.isCompromised) || isRooted || isJailbroken,\n riskSignals: stringArray(nativeResult.riskSignals),\n checkedAt: new Date().toISOString(),\n };\n}\n\nexport function getDeviceSecurityViolations(\n result: DeviceSecurityCheckResult,\n policy: Required<Pick<\n DeviceSecurityPolicy,\n 'blockCompromisedDevices' | 'blockDeveloperMode' | 'blockEmulators' | 'failClosed'\n >>,\n): DeviceSecurityViolation[] {\n const violations: DeviceSecurityViolation[] = [];\n\n if (!result.supported && policy.failClosed) violations.push('check_unavailable');\n if (result.isCompromised && policy.blockCompromisedDevices) violations.push('compromised_device');\n if (result.isDeveloperModeEnabled && policy.blockDeveloperMode) violations.push('developer_mode');\n if (result.isEmulator && policy.blockEmulators) violations.push('emulator');\n\n return violations;\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../../src/utils/logger.ts"],"names":[],"mappings":"AAsBA,eAAO,MAAM,MAAM;mBACF,GAAG,EAAE;qBACH,GAAG,EAAE;oBACN,GAAG,EAAE;oBACL,GAAG,EAAE;qBACJ,GAAG,EAAE;CACvB,CAAC;AA4GF,eAAO,MAAM,SAAS;uBACD,MAAM;;;;qBAIR,MAAM;uBAEJ,MAAM,eAAe,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC;mBAC5C,GAAG,EAAE;oBACJ,GAAG,EAAE;oBACL,GAAG,EAAE;qBACJ,GAAG,EAAE;qBACL,GAAG,EAAE;CACvB,CAAC"}
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../../src/utils/logger.ts"],"names":[],"mappings":"AA2BA,eAAO,MAAM,MAAM;mBACF,GAAG,EAAE;qBACH,GAAG,EAAE;oBACN,GAAG,EAAE;oBACL,GAAG,EAAE;qBACJ,GAAG,EAAE;CACvB,CAAC;AA4GF,eAAO,MAAM,SAAS;uBACD,MAAM;;;;qBAIR,MAAM;uBAEJ,MAAM,eAAe,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC;mBAC5C,GAAG,EAAE;oBACJ,GAAG,EAAE;oBACL,GAAG,EAAE;qBACJ,GAAG,EAAE;qBACL,GAAG,EAAE;CACvB,CAAC"}
@@ -1,11 +1,16 @@
1
1
  import { Platform, AppState } from 'react-native';
2
2
  import PostHog from 'posthog-react-native';
3
+ import AsyncStorage from '@react-native-async-storage/async-storage';
3
4
  const posthogClient = new PostHog('phc_qjCHjCgkdVniammXrrfLrmNPoPH5uAmkzoQMhrEhGaYR', {
4
5
  host: 'https://eu.i.posthog.com',
5
6
  disabled: false,
6
7
  captureAppLifecycleEvents: false,
7
8
  flushAt: 1,
8
9
  flushInterval: 1000, // Backup: flush automatically every 1 second
10
+ customStorage: {
11
+ getItem: async (key) => await AsyncStorage.getItem(key),
12
+ setItem: async (key, value) => await AsyncStorage.setItem(key, value),
13
+ }
9
14
  });
10
15
  const isProduction = () => {
11
16
  if (typeof __DEV__ !== 'undefined') {
@@ -1 +1 @@
1
- {"version":3,"file":"logger.js","sourceRoot":"","sources":["../../../src/utils/logger.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAkB,MAAM,cAAc,CAAC;AAClE,OAAO,OAAO,MAAM,sBAAsB,CAAC;AAE3C,MAAM,aAAa,GAAG,IAAI,OAAO,CAAC,kDAAkD,EAAE;IACpF,IAAI,EAAE,0BAA0B;IAChC,QAAQ,EAAE,KAAK;IACf,yBAAyB,EAAE,KAAK;IAChC,OAAO,EAAE,CAAC;IACV,aAAa,EAAE,IAAI,EAAG,6CAA6C;CACpE,CAAC,CAAC;AAEH,MAAM,YAAY,GAAG,GAAY,EAAE;IACjC,IAAI,OAAO,OAAO,KAAK,WAAW,EAAE,CAAC;QACnC,OAAO,CAAC,OAAO,CAAC;IAClB,CAAC;IACD,IAAI,OAAO,OAAO,KAAK,WAAW,IAAI,OAAO,CAAC,GAAG,EAAE,CAAC;QAClD,OAAO,OAAO,CAAC,GAAG,CAAC,QAAQ,KAAK,YAAY,CAAC;IAC/C,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC,CAAC;AACF,MAAM,OAAO,GAAG,YAAY,EAAE,CAAC;AAE/B,MAAM,CAAC,MAAM,MAAM,GAAG;IACpB,GAAG,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO;QAAE,OAAO,CAAC,GAAG,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IAChE,KAAK,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO;QAAE,OAAO,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IACpE,IAAI,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO;QAAE,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IAClE,IAAI,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO;QAAE,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IAClE,KAAK,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO;QAAE,OAAO,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;CACrE,CAAC;AAOF,MAAM,kBAAkB;IACd,SAAS,CAAqB;IAC9B,oBAAoB,CAAM;IAElC;QACE,sDAAsD;QACtD,IAAI,QAAQ,CAAC,EAAE,KAAK,KAAK,EAAE,CAAC;YAC1B,IAAI,CAAC,oBAAoB,GAAG,QAAQ,CAAC,gBAAgB,CAAC,QAAQ,EAAE,IAAI,CAAC,oBAAoB,CAAC,CAAC;QAC7F,CAAC;IACH,CAAC;IAEO,oBAAoB,GAAG,CAAC,YAA4B,EAAE,EAAE;QAC9D,IAAI,YAAY,KAAK,YAAY,IAAI,YAAY,KAAK,UAAU,EAAE,CAAC;YACjE,IAAI,CAAC,KAAK,EAAE,CAAC;QACf,CAAC;IACH,CAAC,CAAC;IAEK,YAAY,CAAC,EAAU;QAC5B,IAAI,CAAC,SAAS,GAAG,EAAE,CAAC;QACpB,aAAa,CAAC,QAAQ,CAAC,EAAE,EAAE;YACzB,cAAc,EAAE,EAAE;SACnB,CAAC,CAAC;IACL,CAAC;IAEM,cAAc;QACnB,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC3B,aAAa,CAAC,KAAK,EAAE,CAAC,CAAC,kBAAkB;IAC3C,CAAC;IAED,mEAAmE;IAC5D,SAAS,CAAC,IAAY;QAC3B,+BAA+B;IACjC,CAAC;IAEM,KAAK,CAAC,SAAiB,EAAE,UAAgC;QAC9D,aAAa,CAAC,OAAO,CAAC,gBAAgB,SAAS,EAAE,EAAE;YACjD,UAAU,EAAE,IAAI,CAAC,SAAS,IAAI,IAAI;YAClC,EAAE,EAAE,QAAQ,CAAC,EAAE;YACf,SAAS,EAAE,QAAQ,CAAC,OAAO;YAC3B,GAAG,UAAU;SACd,CAAC,CAAC;IACL,CAAC;IAEO,SAAS,CAAC,IAAW;QAC3B,IAAI,OAAO,GAAG,EAAE,CAAC;QACjB,IAAI,QAAQ,GAAQ,EAAE,CAAC;QACvB,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE;YACjB,IAAI,OAAO,GAAG,KAAK,QAAQ,EAAE,CAAC;gBAC5B,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,GAAG,CAAC;YACxC,CAAC;iBAAM,IAAI,GAAG,YAAY,KAAK,EAAE,CAAC;gBAChC,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,GAAG,CAAC,OAAO,CAAC;gBAC9C,QAAQ,CAAC,WAAW,GAAG,GAAG,CAAC,KAAK,CAAC;YACnC,CAAC;iBAAM,IAAI,OAAO,GAAG,KAAK,QAAQ,IAAI,GAAG,KAAK,IAAI,EAAE,CAAC;gBACnD,MAAM,CAAC,MAAM,CAAC,QAAQ,EAAE,GAAG,CAAC,CAAC;YAC/B,CAAC;iBAAM,CAAC;gBACN,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC;YAChD,CAAC;QACH,CAAC,CAAC,CAAC;QACH,OAAO,EAAE,OAAO,EAAE,OAAO,IAAI,qBAAqB,EAAE,QAAQ,EAAE,CAAC;IACjE,CAAC;IAEM,UAAU,CAAC,KAAe,EAAE,GAAG,IAAW;QAC/C,MAAM,EAAE,OAAO,EAAE,QAAQ,EAAE,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;QAEnD,IAAI,CAAC,OAAO,EAAE,CAAC;YACb,MAAM,SAAS,GAAG,kBAAkB,KAAK,CAAC,WAAW,EAAE,GAAG,CAAC;YAC3D,IAAI,KAAK,KAAK,OAAO;gBAAE,OAAO,CAAC,KAAK,CAAC,SAAS,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC;iBAC9D,IAAI,KAAK,KAAK,SAAS;gBAAE,OAAO,CAAC,IAAI,CAAC,SAAS,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC;;gBACpE,OAAO,CAAC,GAAG,CAAC,SAAS,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC;QACjD,CAAC;QAED,MAAM,eAAe,GAAG;YACtB,GAAG,QAAQ;YACX,EAAE,EAAE,QAAQ,CAAC,EAAE;YACf,SAAS,EAAE,QAAQ,CAAC,OAAO;SAC5B,CAAC;QAEF,MAAM,UAAU,GAAG,KAAK,CAAC,WAAW,EAAE,CAAC;QACvC,aAAa,CAAC,OAAO,CAAC,gBAAgB,OAAO,EAAE,EAAE;YAC/C,UAAU,EAAE,IAAI,CAAC,SAAS,IAAI,IAAI;YAClC,SAAS,EAAE,UAAU;YACrB,GAAG,eAAe;SACnB,CAAC,CAAC;QAEH,IAAI,KAAK,KAAK,OAAO,EAAE,CAAC;YACtB,IAAI,CAAC,KAAK,EAAE,CAAC;QACf,CAAC;IACH,CAAC;IAEM,KAAK,CAAC,KAAK;QAChB,MAAM,aAAa,CAAC,KAAK,EAAE,CAAC;IAC9B,CAAC;IAEM,OAAO;QACZ,IAAI,IAAI,CAAC,oBAAoB;YAAE,IAAI,CAAC,oBAAoB,CAAC,MAAM,EAAE,CAAC;QAClE,IAAI,CAAC,KAAK,EAAE,CAAC;IACf,CAAC;CACF;AAED,MAAM,iBAAiB,GAAG,IAAI,kBAAkB,EAAE,CAAC;AAEnD,MAAM,CAAC,MAAM,SAAS,GAAG;IACvB,YAAY,EAAE,CAAC,EAAU,EAAE,EAAE,CAAC,iBAAiB,CAAC,YAAY,CAAC,EAAE,CAAC;IAChE,cAAc,EAAE,GAAG,EAAE,CAAC,iBAAiB,CAAC,cAAc,EAAE;IACxD,KAAK,EAAE,GAAG,EAAE,CAAC,iBAAiB,CAAC,KAAK,EAAE;IACtC,OAAO,EAAE,GAAG,EAAE,CAAC,iBAAiB,CAAC,OAAO,EAAE;IAC1C,SAAS,EAAE,CAAC,GAAW,EAAE,EAAE,CAAC,iBAAiB,CAAC,SAAS,CAAC,GAAG,CAAC;IAE5D,KAAK,EAAE,CAAC,SAAiB,EAAE,UAAgC,EAAE,EAAE,CAAC,iBAAiB,CAAC,KAAK,CAAC,SAAS,EAAE,UAAU,CAAC;IAC9G,GAAG,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,CAAC,iBAAiB,CAAC,UAAU,CAAC,MAAM,EAAE,GAAG,IAAI,CAAC;IACtE,IAAI,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,CAAC,iBAAiB,CAAC,UAAU,CAAC,MAAM,EAAE,GAAG,IAAI,CAAC;IACvE,IAAI,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,CAAC,iBAAiB,CAAC,UAAU,CAAC,SAAS,EAAE,GAAG,IAAI,CAAC;IAC1E,KAAK,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,CAAC,iBAAiB,CAAC,UAAU,CAAC,OAAO,EAAE,GAAG,IAAI,CAAC;IACzE,KAAK,EAAE,CAAC,GAAG,IAAW,EAAE,EAAE,CAAC,iBAAiB,CAAC,UAAU,CAAC,OAAO,EAAE,GAAG,IAAI,CAAC;CAC1E,CAAC","sourcesContent":["import { Platform, AppState, AppStateStatus } from 'react-native';\nimport PostHog from 'posthog-react-native';\n\nconst posthogClient = new PostHog('phc_qjCHjCgkdVniammXrrfLrmNPoPH5uAmkzoQMhrEhGaYR', {\n host: 'https://eu.i.posthog.com',\n disabled: false,\n captureAppLifecycleEvents: false,\n flushAt: 1,\n flushInterval: 1000, // Backup: flush automatically every 1 second\n});\n\nconst isProduction = (): boolean => {\n if (typeof __DEV__ !== 'undefined') {\n return !__DEV__;\n }\n if (typeof process !== 'undefined' && process.env) {\n return process.env.NODE_ENV === 'production';\n }\n return false;\n};\nconst IS_PROD = isProduction();\n\nexport const logger = {\n log: (...args: any[]) => { if (!IS_PROD) console.log(...args); },\n error: (...args: any[]) => { if (!IS_PROD) console.error(...args); },\n warn: (...args: any[]) => { if (!IS_PROD) console.warn(...args); },\n info: (...args: any[]) => { if (!IS_PROD) console.info(...args); },\n debug: (...args: any[]) => { if (!IS_PROD) console.debug(...args); },\n};\n\n// ==========================================\n// 2. SDK TELEMETRY LOGGER (POSTHOG ONLY)\n// ==========================================\ntype LogLevel = 'info' | 'warning' | 'error' | 'debug';\n\nclass SDKTelemetryLogger {\n private sessionId: string | undefined;\n private appStateSubscription: any;\n\n constructor() {\n // Flush PostHog when the app goes into the background\n if (Platform.OS !== 'web') {\n this.appStateSubscription = AppState.addEventListener('change', this.handleAppStateChange);\n }\n }\n\n private handleAppStateChange = (nextAppState: AppStateStatus) => {\n if (nextAppState === 'background' || nextAppState === 'inactive') {\n this.flush();\n }\n };\n\n public setSessionId(id: string) {\n this.sessionId = id;\n posthogClient.identify(id, {\n kyc_session_id: id,\n });\n }\n\n public clearSessionId() {\n this.sessionId = undefined;\n posthogClient.reset(); // Clears identity\n }\n\n // Kept as a no-op just in case your SDK still calls this somewhere\n public setApiKey(_key: string) {\n // No longer needed for PostHog\n }\n\n public track(eventName: string, properties?: Record<string, any>) {\n posthogClient.capture(`[SanctumKey] ${eventName}`, {\n session_id: this.sessionId || null,\n os: Platform.OS,\n osVersion: Platform.Version,\n ...properties,\n });\n }\n\n private parseArgs(args: any[]): { message: string, metadata: any } {\n let message = '';\n let metadata: any = {};\n args.forEach(arg => {\n if (typeof arg === 'string') {\n message += (message ? ' ' : '') + arg;\n } else if (arg instanceof Error) {\n message += (message ? ' ' : '') + arg.message;\n metadata.error_stack = arg.stack;\n } else if (typeof arg === 'object' && arg !== null) {\n Object.assign(metadata, arg);\n } else {\n message += (message ? ' ' : '') + String(arg);\n }\n });\n return { message: message || 'No message provided', metadata };\n }\n\n public processLog(level: LogLevel, ...args: any[]) {\n const { message, metadata } = this.parseArgs(args);\n\n if (!IS_PROD) {\n const devPrefix = `[SDK_TELEMETRY_${level.toUpperCase()}]`;\n if (level === 'error') console.error(devPrefix, message, metadata);\n else if (level === 'warning') console.warn(devPrefix, message, metadata);\n else console.log(devPrefix, message, metadata);\n }\n\n const payloadMetadata = {\n ...metadata,\n os: Platform.OS,\n osVersion: Platform.Version,\n };\n\n const levelLabel = level.toUpperCase();\n posthogClient.capture(`[SanctumKey] ${message}`, {\n session_id: this.sessionId || null,\n log_level: levelLabel,\n ...payloadMetadata,\n });\n\n if (level === 'error') {\n this.flush();\n }\n }\n\n public async flush() {\n await posthogClient.flush();\n }\n\n public destroy() {\n if (this.appStateSubscription) this.appStateSubscription.remove();\n this.flush();\n }\n}\n\nconst telemetryInstance = new SDKTelemetryLogger();\n\nexport const sdkLogger = {\n setSessionId: (id: string) => telemetryInstance.setSessionId(id),\n clearSessionId: () => telemetryInstance.clearSessionId(),\n flush: () => telemetryInstance.flush(),\n destroy: () => telemetryInstance.destroy(),\n setApiKey: (key: string) => telemetryInstance.setApiKey(key),\n \n track: (eventName: string, properties?: Record<string, any>) => telemetryInstance.track(eventName, properties),\n log: (...args: any[]) => telemetryInstance.processLog('info', ...args),\n info: (...args: any[]) => telemetryInstance.processLog('info', ...args),\n warn: (...args: any[]) => telemetryInstance.processLog('warning', ...args),\n error: (...args: any[]) => telemetryInstance.processLog('error', ...args),\n debug: (...args: any[]) => telemetryInstance.processLog('debug', ...args),\n};"]}
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../../../src/utils/logger.ts"],"names":[],"mappings":"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","sourcesContent":["import { Platform, AppState, AppStateStatus } from 'react-native';\nimport PostHog from 'posthog-react-native';\nimport AsyncStorage from '@react-native-async-storage/async-storage';\n\nconst posthogClient = new PostHog('phc_qjCHjCgkdVniammXrrfLrmNPoPH5uAmkzoQMhrEhGaYR', {\n host: 'https://eu.i.posthog.com',\n disabled: false,\n captureAppLifecycleEvents: false,\n flushAt: 1,\n flushInterval: 1000, // Backup: flush automatically every 1 second\n customStorage: {\n getItem: async (key) => await AsyncStorage.getItem(key),\n setItem: async (key, value) => await AsyncStorage.setItem(key, value),\n }\n});\n\nconst isProduction = (): boolean => {\n if (typeof __DEV__ !== 'undefined') {\n return !__DEV__;\n }\n if (typeof process !== 'undefined' && process.env) {\n return process.env.NODE_ENV === 'production';\n }\n return false;\n};\nconst IS_PROD = isProduction();\n\nexport const logger = {\n log: (...args: any[]) => { if (!IS_PROD) console.log(...args); },\n error: (...args: any[]) => { if (!IS_PROD) console.error(...args); },\n warn: (...args: any[]) => { if (!IS_PROD) console.warn(...args); },\n info: (...args: any[]) => { if (!IS_PROD) console.info(...args); },\n debug: (...args: any[]) => { if (!IS_PROD) console.debug(...args); },\n};\n\n// ==========================================\n// 2. SDK TELEMETRY LOGGER (POSTHOG ONLY)\n// ==========================================\ntype LogLevel = 'info' | 'warning' | 'error' | 'debug';\n\nclass SDKTelemetryLogger {\n private sessionId: string | undefined;\n private appStateSubscription: any;\n\n constructor() {\n // Flush PostHog when the app goes into the background\n if (Platform.OS !== 'web') {\n this.appStateSubscription = AppState.addEventListener('change', this.handleAppStateChange);\n }\n }\n\n private handleAppStateChange = (nextAppState: AppStateStatus) => {\n if (nextAppState === 'background' || nextAppState === 'inactive') {\n this.flush();\n }\n };\n\n public setSessionId(id: string) {\n this.sessionId = id;\n posthogClient.identify(id, {\n kyc_session_id: id,\n });\n }\n\n public clearSessionId() {\n this.sessionId = undefined;\n posthogClient.reset(); // Clears identity\n }\n\n // Kept as a no-op just in case your SDK still calls this somewhere\n public setApiKey(_key: string) {\n // No longer needed for PostHog\n }\n\n public track(eventName: string, properties?: Record<string, any>) {\n posthogClient.capture(`[SanctumKey] ${eventName}`, {\n session_id: this.sessionId || null,\n os: Platform.OS,\n osVersion: Platform.Version,\n ...properties,\n });\n }\n\n private parseArgs(args: any[]): { message: string, metadata: any } {\n let message = '';\n let metadata: any = {};\n args.forEach(arg => {\n if (typeof arg === 'string') {\n message += (message ? ' ' : '') + arg;\n } else if (arg instanceof Error) {\n message += (message ? ' ' : '') + arg.message;\n metadata.error_stack = arg.stack;\n } else if (typeof arg === 'object' && arg !== null) {\n Object.assign(metadata, arg);\n } else {\n message += (message ? ' ' : '') + String(arg);\n }\n });\n return { message: message || 'No message provided', metadata };\n }\n\n public processLog(level: LogLevel, ...args: any[]) {\n const { message, metadata } = this.parseArgs(args);\n\n if (!IS_PROD) {\n const devPrefix = `[SDK_TELEMETRY_${level.toUpperCase()}]`;\n if (level === 'error') console.error(devPrefix, message, metadata);\n else if (level === 'warning') console.warn(devPrefix, message, metadata);\n else console.log(devPrefix, message, metadata);\n }\n\n const payloadMetadata = {\n ...metadata,\n os: Platform.OS,\n osVersion: Platform.Version,\n };\n\n const levelLabel = level.toUpperCase();\n posthogClient.capture(`[SanctumKey] ${message}`, {\n session_id: this.sessionId || null,\n log_level: levelLabel,\n ...payloadMetadata,\n });\n\n if (level === 'error') {\n this.flush();\n }\n }\n\n public async flush() {\n await posthogClient.flush();\n }\n\n public destroy() {\n if (this.appStateSubscription) this.appStateSubscription.remove();\n this.flush();\n }\n}\n\nconst telemetryInstance = new SDKTelemetryLogger();\n\nexport const sdkLogger = {\n setSessionId: (id: string) => telemetryInstance.setSessionId(id),\n clearSessionId: () => telemetryInstance.clearSessionId(),\n flush: () => telemetryInstance.flush(),\n destroy: () => telemetryInstance.destroy(),\n setApiKey: (key: string) => telemetryInstance.setApiKey(key),\n \n track: (eventName: string, properties?: Record<string, any>) => telemetryInstance.track(eventName, properties),\n log: (...args: any[]) => telemetryInstance.processLog('info', ...args),\n info: (...args: any[]) => telemetryInstance.processLog('info', ...args),\n warn: (...args: any[]) => telemetryInstance.processLog('warning', ...args),\n error: (...args: any[]) => telemetryInstance.processLog('error', ...args),\n debug: (...args: any[]) => telemetryInstance.processLog('debug', ...args),\n};"]}
@@ -2,6 +2,7 @@ import ExpoModulesCore
2
2
  import AVFoundation
3
3
  import UIKit
4
4
  import Photos
5
+ import Darwin
5
6
 
6
7
  // Vue caméra native avec logs et interface améliorée
7
8
  public final class SanctumKeySdkView: ExpoView {
@@ -267,6 +268,94 @@ public class SanctumKeySdkModule: Module {
267
268
  var currentPhotoPath: String?
268
269
  private var cameraDelegate: CameraDelegate?
269
270
  private var filePickerDelegate: FilePickerDelegate?
271
+
272
+ private func isSimulator() -> Bool {
273
+ #if targetEnvironment(simulator)
274
+ return true
275
+ #else
276
+ return false
277
+ #endif
278
+ }
279
+
280
+ private func isDebuggerAttached() -> Bool {
281
+ var processInfo = kinfo_proc()
282
+ var mib: [Int32] = [CTL_KERN, KERN_PROC, KERN_PROC_PID, getpid()]
283
+ var size = MemoryLayout<kinfo_proc>.stride
284
+
285
+ let result = mib.withUnsafeMutableBufferPointer { buffer in
286
+ sysctl(buffer.baseAddress, u_int(buffer.count), &processInfo, &size, nil, 0)
287
+ }
288
+
289
+ return result == 0 && (processInfo.kp_proc.p_flag & P_TRACED) != 0
290
+ }
291
+
292
+ private func jailbreakSignals() -> [String] {
293
+ if isSimulator() { return [] }
294
+
295
+ var signals: [String] = []
296
+ let suspiciousPaths = [
297
+ "/Applications/Cydia.app",
298
+ "/Applications/Sileo.app",
299
+ "/Applications/Zebra.app",
300
+ "/Library/MobileSubstrate/MobileSubstrate.dylib",
301
+ "/usr/sbin/sshd",
302
+ "/usr/bin/ssh",
303
+ "/bin/bash",
304
+ "/etc/apt",
305
+ "/private/var/lib/apt",
306
+ "/var/jb"
307
+ ]
308
+
309
+ if let path = suspiciousPaths.first(where: { FileManager.default.fileExists(atPath: $0) }) {
310
+ signals.append("jailbreak_artifact:\(path)")
311
+ }
312
+
313
+ let writeProbe = URL(fileURLWithPath: "/private/sanctumkey-\(UUID().uuidString)")
314
+ do {
315
+ try Data("device-security-check".utf8).write(to: writeProbe)
316
+ try? FileManager.default.removeItem(at: writeProbe)
317
+ signals.append("writable_outside_app_sandbox")
318
+ } catch {
319
+ // A normal iOS application cannot write outside its sandbox.
320
+ }
321
+
322
+ if let injectedLibraries = getenv("DYLD_INSERT_LIBRARIES"),
323
+ !String(cString: injectedLibraries).isEmpty {
324
+ signals.append("dyld_injected_libraries")
325
+ }
326
+
327
+ return signals
328
+ }
329
+
330
+ private func deviceSecurityStatus() -> [String: Any] {
331
+ let simulator = isSimulator()
332
+ let debuggerAttached = isDebuggerAttached()
333
+ var signals = jailbreakSignals()
334
+
335
+ if simulator { signals.append("ios_simulator") }
336
+ if debuggerAttached { signals.append("ios_debugger_attached") }
337
+
338
+ let jailbroken = !signals.filter {
339
+ $0.hasPrefix("jailbreak_") ||
340
+ $0 == "writable_outside_app_sandbox" ||
341
+ $0 == "dyld_injected_libraries"
342
+ }.isEmpty
343
+
344
+ return [
345
+ "platform": "ios",
346
+ "supported": true,
347
+ "isRooted": false,
348
+ "isJailbroken": jailbroken,
349
+ "isEmulator": simulator,
350
+ // iOS has no public API for reading the Developer Mode setting. An
351
+ // attached debugger is the reliable runtime signal available to apps.
352
+ "isDeveloperModeEnabled": debuggerAttached,
353
+ "developerModeCheckSupported": false,
354
+ "isDebuggerAttached": debuggerAttached,
355
+ "isCompromised": jailbroken,
356
+ "riskSignals": signals
357
+ ]
358
+ }
270
359
 
271
360
  public func definition() -> ModuleDefinition {
272
361
  Name("SanctumKeySdk")
@@ -280,6 +369,10 @@ public class SanctumKeySdkModule: Module {
280
369
  Events("onCameraCapture", "onFileSelected", "onError")
281
370
  // Removed print statement to conform to expected type 'AnyDefinition'
282
371
 
372
+ AsyncFunction("checkDeviceSecurity") { (promise: Promise) in
373
+ promise.resolve(self.deviceSecurityStatus())
374
+ }
375
+
283
376
  // Fonction pour demander les permissions de caméra
284
377
  AsyncFunction("requestCameraPermission") { (promise: Promise) in
285
378
  switch AVCaptureDevice.authorizationStatus(for: .video) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sanctum-key/react-native-sdk",
3
- "version": "1.0.61",
3
+ "version": "1.0.62",
4
4
  "description": "Sanctum Key React Native SDK",
5
5
  "main": "build/src/index.js",
6
6
  "types": "build/src/index.d.ts",
@@ -3,10 +3,12 @@ import { requireNativeModule } from 'expo-modules-core';
3
3
  import { NativeModule } from 'expo';
4
4
 
5
5
  import { SanctumKeySdkModuleEvents } from './SanctumKeySdk.types';
6
+ import type { DeviceSecurityCheckResult } from './security/deviceSecurity';
6
7
 
7
8
  declare class SanctumKeySdkModule extends NativeModule<SanctumKeySdkModuleEvents> {
8
9
  PI: number;
9
10
  testModule(): Promise<string>;
11
+ checkDeviceSecurity(): Promise<Omit<DeviceSecurityCheckResult, 'checkedAt'>>;
10
12
  requestCameraPermission(): Promise<boolean>;
11
13
  decodeBarcodeFromImage?(imagePath: string, formats: string[]): Promise<string | null>;
12
14
  openCameraWithInstructions(instructions: string): Promise<{ success: boolean; path?: string; error?: string }>;
@@ -2,9 +2,25 @@ import { registerWebModule } from 'expo-modules-core';
2
2
  import { NativeModule } from 'expo';
3
3
 
4
4
  import { SanctumKeySdkModuleEvents } from './SanctumKeySdk.types';
5
+ import type { DeviceSecurityCheckResult } from './security/deviceSecurity';
5
6
 
6
7
  class SanctumKeySdkModule extends NativeModule<SanctumKeySdkModuleEvents> {
7
8
  PI = Math.PI;
9
+
10
+ async checkDeviceSecurity(): Promise<Omit<DeviceSecurityCheckResult, 'checkedAt'>> {
11
+ return {
12
+ platform: 'web',
13
+ supported: false,
14
+ isRooted: false,
15
+ isJailbroken: false,
16
+ isEmulator: false,
17
+ isDeveloperModeEnabled: false,
18
+ developerModeCheckSupported: false,
19
+ isDebuggerAttached: false,
20
+ isCompromised: false,
21
+ riskSignals: ['native_device_security_check_unavailable_on_web'],
22
+ };
23
+ }
8
24
 
9
25
  async requestCameraPermission(): Promise<boolean> {
10
26
  console.warn('Camera permission not available on web');
@@ -111,6 +111,8 @@ export const CountrySelection: React.FC<CountrySelectionProps> = ({
111
111
  contentContainerStyle={styles.listContent}
112
112
  keyboardShouldPersistTaps="handled"
113
113
  keyboardDismissMode="on-drag" // 🚨 UX FIX: Hides keyboard naturally when user starts scrolling
114
+ nestedScrollEnabled
115
+ persistentScrollbar
114
116
  initialNumToRender={15}
115
117
  maxToRenderPerBatch={20}
116
118
  windowSize={5}
@@ -147,4 +149,4 @@ const styles = StyleSheet.create({
147
149
  checkmark: { width: 24, height: 24, borderRadius: 12, backgroundColor: '#4CAF50', justifyContent: 'center', alignItems: 'center', },
148
150
  checkmarkText: { color: 'white', fontSize: 16, fontWeight: 'bold', },
149
151
  errorText: { color: '#dc2626', fontSize: 14, margin: 16, textAlign: 'center', },
150
- });
152
+ });
@@ -1,5 +1,5 @@
1
1
  import React, { useState, useMemo, useEffect } from 'react';
2
- import { View, Text, TouchableOpacity, StyleSheet, ScrollView, TextInput } from 'react-native';
2
+ import { FlatList, Platform, ScrollView, StyleSheet, Text, TextInput, TouchableOpacity, View } from 'react-native';
3
3
  import { TemplateComponent, CountrySelectionConfig, LocalizedText, Country, IDCardConfig } from '../../types/KYC.types';
4
4
  import { countryMapping } from '../../config/region_mapping';
5
5
  import { useTemplateKYCFlowContext } from '../../hooks/useTemplateKYCFlow';
@@ -208,24 +208,71 @@ export const CountrySelectionTemplate: React.FC<CountrySelectionTemplateProps> =
208
208
  const renderCountrySelection = () => {
209
209
  return (
210
210
  <>
211
- <TextInput style={styles.searchBar} placeholder={state.currentLanguage === "en" ? "🔍 Search country..." : "🔍 Rechercher un pays..."} placeholderTextColor="#94A3B8" value={searchQuery} onChangeText={setSearchQuery} autoCorrect={false} />
212
- <ScrollView style={styles.listContainer} showsVerticalScrollIndicator={false}>
213
- {filteredCountries.map((country: Country & { code?: string }) => (
214
- <TouchableOpacity key={country.code} style={[styles.option, selectedCountryCode === country.code && styles.selectedOption]} onPress={() => handleCountrySelect(country.code!)}>
215
- <Text style={styles.flag}>{country.flag}</Text>
216
- <View style={styles.optionContent}>
217
- <Text style={[styles.optionName, selectedCountryCode === country.code && styles.selectedOptionName]}>{state.currentLanguage === "en" ? country.name_en : country.name}</Text>
218
- <Text style={styles.optionCode}>{country.code}</Text>
219
- </View>
220
- {selectedCountryCode === country.code && (
221
- <View style={[styles.checkmark, { backgroundColor: component.ui.themeColor as string || '#2DBD60' }]}><Text style={styles.checkmarkText}>✓</Text></View>
222
- )}
223
- </TouchableOpacity>
224
- ))}
225
- {filteredCountries.length === 0 && (
226
- <Text style={styles.emptyText}>{state.currentLanguage === "en" ? "No matching countries found." : "Aucun pays trouvé."}</Text>
227
- )}
228
- </ScrollView>
211
+ <TextInput
212
+ style={styles.searchBar}
213
+ placeholder={state.currentLanguage === "en" ? "Search countries" : "Rechercher un pays"}
214
+ placeholderTextColor="#64748B"
215
+ value={searchQuery}
216
+ onChangeText={setSearchQuery}
217
+ autoCorrect={false}
218
+ autoCapitalize="none"
219
+ clearButtonMode="while-editing"
220
+ returnKeyType="search"
221
+ accessibilityRole="search"
222
+ accessibilityLabel={state.currentLanguage === "en" ? "Search countries" : "Rechercher un pays"}
223
+ accessibilityHint={state.currentLanguage === "en" ? "Filters the country list as you type" : "Filtre la liste des pays pendant la saisie"}
224
+ />
225
+ <FlatList
226
+ style={styles.listContainer}
227
+ contentContainerStyle={[
228
+ styles.listContent,
229
+ filteredCountries.length === 0 && styles.emptyListContent,
230
+ ]}
231
+ data={filteredCountries}
232
+ keyExtractor={(country) => country.code!}
233
+ renderItem={({ item: country }) => {
234
+ const isSelected = selectedCountryCode === country.code;
235
+ const countryName = state.currentLanguage === "en" ? country.name_en : country.name;
236
+
237
+ return (
238
+ <TouchableOpacity
239
+ style={[styles.option, isSelected && styles.selectedOption]}
240
+ onPress={() => handleCountrySelect(country.code!)}
241
+ activeOpacity={0.7}
242
+ accessible
243
+ accessibilityRole="radio"
244
+ accessibilityState={{ selected: isSelected }}
245
+ accessibilityLabel={`${countryName}, ${country.code}`}
246
+ accessibilityHint={state.currentLanguage === "en" ? "Select this issuing country" : "Sélectionner ce pays émetteur"}
247
+ >
248
+ <Text style={styles.flag} accessible={false}>{country.flag}</Text>
249
+ <View style={styles.optionContent}>
250
+ <Text style={[styles.optionName, isSelected && styles.selectedOptionName]}>{countryName}</Text>
251
+ <Text style={styles.optionCode}>{country.code}</Text>
252
+ </View>
253
+ {isSelected && (
254
+ <View style={[styles.checkmark, { backgroundColor: component.ui.themeColor as string || '#2DBD60' }]} accessible={false}>
255
+ <Text style={styles.checkmarkText}>✓</Text>
256
+ </View>
257
+ )}
258
+ </TouchableOpacity>
259
+ );
260
+ }}
261
+ ListEmptyComponent={
262
+ <Text style={styles.emptyText} accessibilityRole="text">
263
+ {state.currentLanguage === "en" ? "No matching countries found." : "Aucun pays trouvé."}
264
+ </Text>
265
+ }
266
+ showsVerticalScrollIndicator
267
+ persistentScrollbar={Platform.OS === 'android'}
268
+ keyboardShouldPersistTaps="handled"
269
+ keyboardDismissMode={Platform.OS === 'ios' ? 'interactive' : 'on-drag'}
270
+ nestedScrollEnabled
271
+ initialNumToRender={12}
272
+ maxToRenderPerBatch={12}
273
+ windowSize={7}
274
+ accessibilityRole="list"
275
+ />
229
276
  </>
230
277
  );
231
278
  };
@@ -341,14 +388,16 @@ export const CountrySelectionTemplate: React.FC<CountrySelectionTemplateProps> =
341
388
  };
342
389
 
343
390
  const styles = StyleSheet.create({
344
- root: { flex: 1, maxWidth: 760, width: '100%' },
345
- container: { backgroundColor: 'white', margin: 10, borderRadius: 10, paddingVertical: 16, paddingHorizontal: 16, shadowColor: '#000', shadowOffset: { width: 0, height: 2 }, shadowOpacity: 0.35, shadowRadius: 4.84, elevation: 10 },
391
+ root: { flex: 1, minHeight: 0, maxWidth: 760, width: '100%' },
392
+ container: { flex: 1, minHeight: 0, backgroundColor: 'white', margin: 10, borderRadius: 10, paddingVertical: 16, paddingHorizontal: 16, shadowColor: '#000', shadowOffset: { width: 0, height: 2 }, shadowOpacity: 0.35, shadowRadius: 4.84, elevation: 10 },
346
393
  progressContainer: { marginBottom: 16, alignItems: 'center' },
347
394
  progressText: { fontSize: 14, color: '#666', fontWeight: '500' },
348
395
  title: { fontSize: 24, fontWeight: 'bold', color: '#333', marginBottom: 8, textAlign: 'center' },
349
396
  description: { fontSize: 16, color: '#666', textAlign: 'center', marginBottom: 24, lineHeight: 22 },
350
397
  searchBar: { height: 52, backgroundColor: '#F1F5F9', borderRadius: 12, paddingHorizontal: 16, fontSize: 16, color: '#1E293B', marginBottom: 16, borderWidth: 1, borderColor: '#CBD5E1', fontWeight: '500' },
351
- listContainer: { maxHeight: 360, marginBottom: 24 },
398
+ listContainer: { flex: 1, minHeight: 120, marginBottom: 12 },
399
+ listContent: { paddingBottom: 8 },
400
+ emptyListContent: { flexGrow: 1, justifyContent: 'center' },
352
401
  option: { flexDirection: 'row', alignItems: 'center', padding: 16, backgroundColor: '#F8F9FA', borderRadius: 12, marginBottom: 12, borderWidth: 2, borderColor: '#E9ECEF', minHeight: 64 },
353
402
  selectedOption: { borderColor: '#2DBD60', backgroundColor: '#F0F9F0' },
354
403
  flag: { fontSize: 32, marginRight: 16 },
@@ -360,7 +409,7 @@ const styles = StyleSheet.create({
360
409
  checkmarkText: { color: 'white', fontSize: 16, fontWeight: 'bold' },
361
410
  infoBox: { backgroundColor: '#F9FAFB', padding: 12, borderRadius: 12, marginBottom: 16 },
362
411
  infoText: { fontSize: 14, color: '#666', lineHeight: 20 },
363
- buttonContainer: { flexDirection: 'row', marginTop: 24, gap: 12 },
412
+ buttonContainer: { flexDirection: 'row', marginTop: 12, gap: 12 },
364
413
  errorText: { color: '#dc2626', fontSize: 14, marginTop: 8, textAlign: 'center' },
365
414
  emptyText: { textAlign: 'center', color: '#64748B', fontSize: 16, marginTop: 24, fontWeight: '500' }
366
- });
415
+ });