@finos_sdk/sdk-ekyc 1.2.1 → 1.2.8

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 (98) hide show
  1. package/LICENSE +13 -10
  2. package/README.md +41 -42
  3. package/android/build.gradle +53 -20
  4. package/android/gradle.properties +7 -1
  5. package/android/settings.gradle +53 -0
  6. package/android/src/main/java/finos/sdk/ekyc/EKYCModule.kt +790 -82
  7. package/dist/EKYCModule.d.ts +72 -0
  8. package/dist/EKYCModule.js +650 -71
  9. package/dist/finos_sdk-sdk-ekyc-1.2.8.tgz +0 -0
  10. package/dist/index.d.ts +6 -1
  11. package/dist/index.js +5 -1
  12. package/dist/package.json +31 -21
  13. package/dist/src/modules/FinosEKYCModule.d.ts +147 -2
  14. package/dist/src/modules/FinosEKYCModule.js +476 -4
  15. package/dist/src/modules/FinosESignModule.d.ts +270 -0
  16. package/dist/src/modules/FinosESignModule.js +752 -0
  17. package/dist/src/types/ekycESignType.d.ts +67 -0
  18. package/dist/src/types/ekycESignType.js +2 -0
  19. package/dist/src/types/ekycLivenessType.d.ts +1 -0
  20. package/dist/src/types/ekycSmsOtpType.d.ts +52 -0
  21. package/dist/src/types/ekycSmsOtpType.js +2 -0
  22. package/package.json +31 -21
  23. package/src/modules/FinosEKYCModule.ts +563 -4
  24. package/src/modules/FinosESignModule.ts +919 -0
  25. package/src/modules/README.md +3 -3
  26. package/src/types/ekycESignType.ts +76 -0
  27. package/src/types/ekycLivenessType.ts +1 -0
  28. package/src/types/ekycSmsOtpType.ts +59 -0
  29. package/android/SDKeKYC/finos/sdk/ekyc/c06/1.2.0/c06-1.2.0-javadoc.jar +0 -0
  30. package/android/SDKeKYC/finos/sdk/ekyc/c06/1.2.0/c06-1.2.0-sources.jar +0 -0
  31. package/android/SDKeKYC/finos/sdk/ekyc/c06/1.2.0/c06-1.2.0.aar +0 -0
  32. package/android/SDKeKYC/finos/sdk/ekyc/c06/1.2.0/c06-1.2.0.module +0 -130
  33. package/android/SDKeKYC/finos/sdk/ekyc/c06/1.2.0/c06-1.2.0.pom +0 -37
  34. package/android/SDKeKYC/finos/sdk/ekyc/c06/maven-metadata-local.xml +0 -13
  35. package/android/SDKeKYC/finos/sdk/ekyc/ekyc/1.2.0/ekyc-1.2.0-javadoc.jar +0 -0
  36. package/android/SDKeKYC/finos/sdk/ekyc/ekyc/1.2.0/ekyc-1.2.0-sources.jar +0 -0
  37. package/android/SDKeKYC/finos/sdk/ekyc/ekyc/1.2.0/ekyc-1.2.0.aar +0 -0
  38. package/android/SDKeKYC/finos/sdk/ekyc/ekyc/1.2.0/ekyc-1.2.0.module +0 -221
  39. package/android/SDKeKYC/finos/sdk/ekyc/ekyc/1.2.0/ekyc-1.2.0.pom +0 -73
  40. package/android/SDKeKYC/finos/sdk/ekyc/ekyc/maven-metadata-local.xml +0 -13
  41. package/android/SDKeKYC/finos/sdk/ekyc/ekycui/1.2.0/ekycui-1.2.0-javadoc.jar +0 -0
  42. package/android/SDKeKYC/finos/sdk/ekyc/ekycui/1.2.0/ekycui-1.2.0-sources.jar +0 -0
  43. package/android/SDKeKYC/finos/sdk/ekyc/ekycui/1.2.0/ekycui-1.2.0.aar +0 -0
  44. package/android/SDKeKYC/finos/sdk/ekyc/ekycui/1.2.0/ekycui-1.2.0.module +0 -151
  45. package/android/SDKeKYC/finos/sdk/ekyc/ekycui/1.2.0/ekycui-1.2.0.pom +0 -43
  46. package/android/SDKeKYC/finos/sdk/ekyc/ekycui/maven-metadata-local.xml +0 -13
  47. package/android/SDKeKYC/finos/sdk/ekyc/faceservice/1.2.0/faceservice-1.2.0-javadoc.jar +0 -0
  48. package/android/SDKeKYC/finos/sdk/ekyc/faceservice/1.2.0/faceservice-1.2.0-sources.jar +0 -0
  49. package/android/SDKeKYC/finos/sdk/ekyc/faceservice/1.2.0/faceservice-1.2.0.aar +0 -0
  50. package/android/SDKeKYC/finos/sdk/ekyc/faceservice/1.2.0/faceservice-1.2.0.module +0 -130
  51. package/android/SDKeKYC/finos/sdk/ekyc/faceservice/1.2.0/faceservice-1.2.0.pom +0 -37
  52. package/android/SDKeKYC/finos/sdk/ekyc/faceservice/maven-metadata-local.xml +0 -13
  53. package/android/SDKeKYC/finos/sdk/ekyc/liveness/1.2.0/liveness-1.2.0-javadoc.jar +0 -0
  54. package/android/SDKeKYC/finos/sdk/ekyc/liveness/1.2.0/liveness-1.2.0-sources.jar +0 -0
  55. package/android/SDKeKYC/finos/sdk/ekyc/liveness/1.2.0/liveness-1.2.0.aar +0 -0
  56. package/android/SDKeKYC/finos/sdk/ekyc/liveness/1.2.0/liveness-1.2.0.module +0 -158
  57. package/android/SDKeKYC/finos/sdk/ekyc/liveness/1.2.0/liveness-1.2.0.pom +0 -55
  58. package/android/SDKeKYC/finos/sdk/ekyc/liveness/maven-metadata-local.xml +0 -13
  59. package/android/SDKeKYC/finos/sdk/ekyc/nfc/1.2.0/nfc-1.2.0-javadoc.jar +0 -0
  60. package/android/SDKeKYC/finos/sdk/ekyc/nfc/1.2.0/nfc-1.2.0-sources.jar +0 -0
  61. package/android/SDKeKYC/finos/sdk/ekyc/nfc/1.2.0/nfc-1.2.0.aar +0 -0
  62. package/android/SDKeKYC/finos/sdk/ekyc/nfc/1.2.0/nfc-1.2.0.module +0 -151
  63. package/android/SDKeKYC/finos/sdk/ekyc/nfc/1.2.0/nfc-1.2.0.pom +0 -55
  64. package/android/SDKeKYC/finos/sdk/ekyc/nfc/maven-metadata-local.xml +0 -13
  65. package/android/SDKeKYC/finos/sdk/ekyc/ocr/1.2.0/ocr-1.2.0-javadoc.jar +0 -0
  66. package/android/SDKeKYC/finos/sdk/ekyc/ocr/1.2.0/ocr-1.2.0-sources.jar +0 -0
  67. package/android/SDKeKYC/finos/sdk/ekyc/ocr/1.2.0/ocr-1.2.0.aar +0 -0
  68. package/android/SDKeKYC/finos/sdk/ekyc/ocr/1.2.0/ocr-1.2.0.module +0 -144
  69. package/android/SDKeKYC/finos/sdk/ekyc/ocr/1.2.0/ocr-1.2.0.pom +0 -43
  70. package/android/SDKeKYC/finos/sdk/ekyc/ocr/maven-metadata-local.xml +0 -13
  71. package/android/SDKeKYC/finos/sdk/ekyc/qrcode/1.2.0/qrcode-1.2.0-javadoc.jar +0 -0
  72. package/android/SDKeKYC/finos/sdk/ekyc/qrcode/1.2.0/qrcode-1.2.0-sources.jar +0 -0
  73. package/android/SDKeKYC/finos/sdk/ekyc/qrcode/1.2.0/qrcode-1.2.0.aar +0 -0
  74. package/android/SDKeKYC/finos/sdk/ekyc/qrcode/1.2.0/qrcode-1.2.0.module +0 -158
  75. package/android/SDKeKYC/finos/sdk/ekyc/qrcode/1.2.0/qrcode-1.2.0.pom +0 -55
  76. package/android/SDKeKYC/finos/sdk/ekyc/qrcode/maven-metadata-local.xml +0 -13
  77. package/android/SDKeKYC/finos/sdk/ekyc/sdkcore/1.2.0/sdkcore-1.2.0-javadoc.jar +0 -0
  78. package/android/SDKeKYC/finos/sdk/ekyc/sdkcore/1.2.0/sdkcore-1.2.0-sources.jar +0 -0
  79. package/android/SDKeKYC/finos/sdk/ekyc/sdkcore/1.2.0/sdkcore-1.2.0.aar +0 -0
  80. package/android/SDKeKYC/finos/sdk/ekyc/sdkcore/1.2.0/sdkcore-1.2.0.module +0 -361
  81. package/android/SDKeKYC/finos/sdk/ekyc/sdkcore/1.2.0/sdkcore-1.2.0.pom +0 -139
  82. package/android/SDKeKYC/finos/sdk/ekyc/sdkcore/maven-metadata-local.xml +0 -13
  83. package/android/SDKeKYC/finos/sdk/ekyc/sdkcorecamera/1.2.0/sdkcorecamera-1.2.0-javadoc.jar +0 -0
  84. package/android/SDKeKYC/finos/sdk/ekyc/sdkcorecamera/1.2.0/sdkcorecamera-1.2.0-sources.jar +0 -0
  85. package/android/SDKeKYC/finos/sdk/ekyc/sdkcorecamera/1.2.0/sdkcorecamera-1.2.0.aar +0 -0
  86. package/android/SDKeKYC/finos/sdk/ekyc/sdkcorecamera/1.2.0/sdkcorecamera-1.2.0.module +0 -221
  87. package/android/SDKeKYC/finos/sdk/ekyc/sdkcorecamera/1.2.0/sdkcorecamera-1.2.0.pom +0 -85
  88. package/android/SDKeKYC/finos/sdk/ekyc/sdkcorecamera/maven-metadata-local.xml +0 -13
  89. package/android/SDKeKYC/finos/sdk/ekyc/sdkui/1.2.0/sdkui-1.2.0-javadoc.jar +0 -0
  90. package/android/SDKeKYC/finos/sdk/ekyc/sdkui/1.2.0/sdkui-1.2.0-sources.jar +0 -0
  91. package/android/SDKeKYC/finos/sdk/ekyc/sdkui/1.2.0/sdkui-1.2.0.aar +0 -0
  92. package/android/SDKeKYC/finos/sdk/ekyc/sdkui/1.2.0/sdkui-1.2.0.module +0 -228
  93. package/android/SDKeKYC/finos/sdk/ekyc/sdkui/1.2.0/sdkui-1.2.0.pom +0 -103
  94. package/android/SDKeKYC/finos/sdk/ekyc/sdkui/maven-metadata-local.xml +0 -13
  95. package/android/src/main/AndroidManifest.xml +0 -22
  96. package/android/src/main/build.gradle +0 -31
  97. package/dist/App.d.ts +0 -3
  98. package/dist/App.js +0 -497
@@ -6,6 +6,8 @@ import { C06Config } from '../types/ekycC06Type';
6
6
  import { OcrConfig } from '../types/ekycOCRType';
7
7
  import { LivenessConfig } from '../types/ekycLivenessType';
8
8
  import { FaceServiceConfig } from '../types/ekycFaceType';
9
+ import { SmsOtpConfig, SmsOtpResult, SmsOtpError } from '../types/ekycSmsOtpType';
10
+ import { UserEsignModel, ESignInitResult, ESignOpenSessionResult, ESignCertificate, ESignSignRequest, ESignError, ESignAuthenticateResult } from '../types/ekycESignType';
9
11
 
10
12
  /**
11
13
  * Finos eKYC SDK Module
@@ -165,13 +167,16 @@ export class FinosEKYCModule {
165
167
 
166
168
  /**
167
169
  * Start liveness detection
168
- * @param config Liveness configuration
170
+ * @param config Liveness configuration (includes switchFrontCamera for camera control)
169
171
  */
170
172
  public async startLiveness(config: LivenessConfig): Promise<SDKEkycResultStringWithEvent> {
171
173
  this.validateSDKReady();
172
174
 
173
175
  try {
174
176
  console.log('👁️ Starting liveness detection...');
177
+ if (config.switchFrontCamera !== undefined) {
178
+ console.log('📷 Front camera setting:', config.switchFrontCamera ? 'ON' : 'OFF');
179
+ }
175
180
  const result = await this.sdk.startLiveness(config);
176
181
  console.log('✅ Liveness detection completed:', result.event);
177
182
  return result;
@@ -327,14 +332,408 @@ export class FinosEKYCModule {
327
332
  console.log('🧹 All event listeners removed');
328
333
  }
329
334
 
335
+ // ==================== SMS OTP Methods ====================
336
+
337
+ /**
338
+ * Send SMS OTP
339
+ * @param config SMS OTP configuration
340
+ */
341
+ public async sendOtp(config: SmsOtpConfig): Promise<SmsOtpResult> {
342
+ this.validateSDKReady();
343
+
344
+ try {
345
+ console.log('📱 Sending SMS OTP...');
346
+ const result = await this.sdk.sendOtp(config);
347
+ console.log('✅ SMS OTP sent successfully');
348
+ return result;
349
+ } catch (error) {
350
+ console.error('❌ SMS OTP send failed:', error);
351
+ throw error;
352
+ }
353
+ }
354
+
355
+ /**
356
+ * Verify SMS OTP
357
+ * @param config SMS OTP configuration (must include requestId)
358
+ * @param otpCode OTP code from SMS
359
+ */
360
+ public async verifyOtp(config: SmsOtpConfig, otpCode: string): Promise<SmsOtpResult> {
361
+ this.validateSDKReady();
362
+
363
+ try {
364
+ console.log('🔐 Verifying SMS OTP...');
365
+ const result = await this.sdk.verifyOtp(config, otpCode);
366
+ console.log('✅ SMS OTP verified successfully');
367
+ return result;
368
+ } catch (error) {
369
+ console.error('❌ SMS OTP verification failed:', error);
370
+ throw error;
371
+ }
372
+ }
373
+
374
+ /**
375
+ * Resend SMS OTP
376
+ * @param config SMS OTP configuration (must include requestId)
377
+ */
378
+ public async resendOtp(config: SmsOtpConfig): Promise<SmsOtpResult> {
379
+ this.validateSDKReady();
380
+
381
+ try {
382
+ console.log('📱 Resending SMS OTP...');
383
+ const result = await this.sdk.resendOtp(config);
384
+ console.log('✅ SMS OTP resent successfully');
385
+ return result;
386
+ } catch (error) {
387
+ console.error('❌ SMS OTP resend failed:', error);
388
+ throw error;
389
+ }
390
+ }
391
+
392
+ // SMS OTP Event Listeners
393
+ public onSmsOtpSendSuccess(callback: (data: SmsOtpResult) => void) {
394
+ const listener = this.sdk.onSmsOtpSendSuccess(callback);
395
+ if (!listener) {
396
+ console.warn('⚠️ onSmsOtpSendSuccess: Event emitter not ready. Make sure SDK is initialized.');
397
+ }
398
+ return listener;
399
+ }
400
+
401
+ public onSmsOtpVerifySuccess(callback: (data: SmsOtpResult) => void) {
402
+ const listener = this.sdk.onSmsOtpVerifySuccess(callback);
403
+ if (!listener) {
404
+ console.warn('⚠️ onSmsOtpVerifySuccess: Event emitter not ready.');
405
+ }
406
+ return listener;
407
+ }
408
+
409
+ public onSmsOtpResendSuccess(callback: (data: SmsOtpResult) => void) {
410
+ const listener = this.sdk.onSmsOtpResendSuccess(callback);
411
+ if (!listener) {
412
+ console.warn('⚠️ onSmsOtpResendSuccess: Event emitter not ready.');
413
+ }
414
+ return listener;
415
+ }
416
+
417
+ public onSmsOtpError(callback: (error: SmsOtpError) => void) {
418
+ const listener = this.sdk.onSmsOtpError(callback);
419
+ if (!listener) {
420
+ console.warn('⚠️ onSmsOtpError: Event emitter not ready.');
421
+ }
422
+ return listener;
423
+ }
424
+
425
+ // ==================== eSign Methods ====================
426
+
427
+ /**
428
+ * Initialize eSign SDK
429
+ */
430
+ public async initializeESign(): Promise<ESignInitResult> {
431
+ this.validateSDKReady();
432
+
433
+ try {
434
+ console.log('🔐 Initializing eSign SDK...');
435
+ const result = await this.sdk.initializeESign();
436
+ console.log('✅ eSign SDK initialized successfully');
437
+ return result;
438
+ } catch (error) {
439
+ console.error('❌ eSign initialization failed:', error);
440
+ throw error;
441
+ }
442
+ }
443
+
444
+ /**
445
+ * Open eSign session
446
+ * @param accessToken JWT access token (optional if using userEsignModel)
447
+ * @param username Optional username
448
+ * @param rememberMe Remember session
449
+ * @param userEsignModel User info for auto token creation (optional if using accessToken)
450
+ * @param privateKeyFilePath Path to private key file in assets (required if using userEsignModel)
451
+ */
452
+ public async openSessionId(
453
+ accessToken?: string,
454
+ username?: string,
455
+ rememberMe?: boolean,
456
+ userEsignModel?: UserEsignModel,
457
+ privateKeyFilePath?: string
458
+ ): Promise<ESignOpenSessionResult> {
459
+ this.validateSDKReady();
460
+
461
+ try {
462
+ console.log('🔓 Opening eSign session...');
463
+ const result = await this.sdk.openSessionId(
464
+ accessToken,
465
+ username,
466
+ rememberMe,
467
+ userEsignModel,
468
+ privateKeyFilePath
469
+ );
470
+ console.log('✅ eSign session opened successfully');
471
+ return result;
472
+ } catch (error) {
473
+ console.error('❌ eSign session open failed:', error);
474
+ throw error;
475
+ }
476
+ }
477
+
478
+ /**
479
+ * Register device for eSign
480
+ * @param recoverCode 8-digit recovery code
481
+ * @param pinCode 6-digit PIN code
482
+ * @param fcmToken Optional FCM token
483
+ */
484
+ public async registerDevice(
485
+ recoverCode: string,
486
+ pinCode: string,
487
+ fcmToken?: string
488
+ ): Promise<{ code: string; message: string }> {
489
+ this.validateSDKReady();
490
+
491
+ try {
492
+ console.log('📱 Registering eSign device...');
493
+ const result = await this.sdk.registerDevice(recoverCode, pinCode, fcmToken);
494
+ console.log('✅ eSign device registered successfully');
495
+ return result;
496
+ } catch (error) {
497
+ console.error('❌ eSign device registration failed:', error);
498
+ throw error;
499
+ }
500
+ }
501
+
502
+ /**
503
+ * List eSign certificates
504
+ * @param pageNumber Page number (default: 1)
505
+ * @param pageSize Page size (default: 10)
506
+ */
507
+ public async listCerts(
508
+ pageNumber: number = 1,
509
+ pageSize: number = 10
510
+ ): Promise<{ certs: ESignCertificate[] }> {
511
+ this.validateSDKReady();
512
+
513
+ try {
514
+ console.log('📋 Listing eSign certificates...');
515
+ const result = await this.sdk.listCerts(pageNumber, pageSize);
516
+ console.log(`✅ Found ${result.certs.length} certificates`);
517
+ return result;
518
+ } catch (error) {
519
+ console.error('❌ eSign list certificates failed:', error);
520
+ throw error;
521
+ }
522
+ }
523
+
524
+ /**
525
+ * Verify eSign certificate
526
+ * @param serial Certificate serial number
527
+ */
528
+ public async verifyCert(serial: string): Promise<{ code: string; message: string }> {
529
+ this.validateSDKReady();
530
+
531
+ try {
532
+ console.log('✅ Verifying eSign certificate...');
533
+ const result = await this.sdk.verifyCert(serial);
534
+ console.log('✅ eSign certificate verified successfully');
535
+ return result;
536
+ } catch (error) {
537
+ console.error('❌ eSign certificate verification failed:', error);
538
+ throw error;
539
+ }
540
+ }
541
+
542
+ /**
543
+ * List eSign sign requests
544
+ * @param pageNumber Page number (default: 1)
545
+ * @param pageSize Page size (default: 10)
546
+ */
547
+ public async listSignRequest(
548
+ pageNumber: number = 1,
549
+ pageSize: number = 10
550
+ ): Promise<{ requests: ESignSignRequest[] }> {
551
+ this.validateSDKReady();
552
+
553
+ try {
554
+ console.log('📋 Listing eSign sign requests...');
555
+ const result = await this.sdk.listSignRequest(pageNumber, pageSize);
556
+ console.log(`✅ Found ${result.requests.length} sign requests`);
557
+ return result;
558
+ } catch (error) {
559
+ console.error('❌ eSign list sign requests failed:', error);
560
+ throw error;
561
+ }
562
+ }
563
+
564
+ /**
565
+ * Confirm eSign signature
566
+ * @param signRequestId Sign request ID
567
+ * @param pinCode 6-digit PIN code
568
+ * @param authId Optional auth ID
569
+ * @param authData Optional auth data
570
+ * @param confirm Confirm the signature (default: true)
571
+ */
572
+ public async confirmSign(
573
+ signRequestId: string,
574
+ pinCode: string,
575
+ authId?: string,
576
+ authData?: string,
577
+ confirm: boolean = true
578
+ ): Promise<{ code: string; message: string }> {
579
+ this.validateSDKReady();
580
+
581
+ try {
582
+ console.log('✍️ Confirming eSign signature...');
583
+ const result = await this.sdk.confirmSign(signRequestId, pinCode, authId, authData, confirm);
584
+ console.log('✅ eSign signature confirmed successfully');
585
+ return result;
586
+ } catch (error) {
587
+ console.error('❌ eSign signature confirmation failed:', error);
588
+ throw error;
589
+ }
590
+ }
591
+
592
+ /**
593
+ * Authenticate with eSign
594
+ * @param username eSign username
595
+ * @param password eSign password
596
+ */
597
+ public async authenticate(
598
+ username: string,
599
+ password: string
600
+ ): Promise<ESignAuthenticateResult> {
601
+ this.validateSDKReady();
602
+
603
+ try {
604
+ console.log('🔐 Authenticating with eSign...');
605
+ const result = await this.sdk.authenticate(username, password);
606
+ console.log('✅ eSign authentication successful');
607
+ return result;
608
+ } catch (error) {
609
+ console.error('❌ eSign authentication failed:', error);
610
+ throw error;
611
+ }
612
+ }
613
+
614
+ /**
615
+ * Register remote signing certificate
616
+ * @param accessToken JWT access token
617
+ * @param requestJson JSON request body
618
+ */
619
+ public async registerRemoteSigning(
620
+ accessToken: string,
621
+ requestJson: string
622
+ ): Promise<{ response: string }> {
623
+ this.validateSDKReady();
624
+
625
+ try {
626
+ console.log('📝 Registering remote signing certificate...');
627
+ const result = await this.sdk.registerRemoteSigning(accessToken, requestJson);
628
+ console.log('✅ Remote signing certificate registered successfully');
629
+ return result;
630
+ } catch (error) {
631
+ console.error('❌ Remote signing certificate registration failed:', error);
632
+ throw error;
633
+ }
634
+ }
635
+
636
+ /**
637
+ * Sign PDF document
638
+ * @param accessToken JWT access token
639
+ * @param requestJson JSON request body
640
+ */
641
+ public async signPdf(
642
+ accessToken: string,
643
+ requestJson: string
644
+ ): Promise<{ response: string }> {
645
+ this.validateSDKReady();
646
+
647
+ try {
648
+ console.log('📄 Signing PDF document...');
649
+ const result = await this.sdk.signPdf(accessToken, requestJson);
650
+ console.log('✅ PDF document signed successfully');
651
+ return result;
652
+ } catch (error) {
653
+ console.error('❌ PDF document signing failed:', error);
654
+ throw error;
655
+ }
656
+ }
657
+
658
+ /**
659
+ * Send confirmation document
660
+ * @param accessToken JWT access token
661
+ * @param requestJson JSON string containing request data
662
+ */
663
+ public async sendConfirmationDocument(
664
+ accessToken: string,
665
+ requestJson: string
666
+ ): Promise<{ response: string }> {
667
+ this.validateSDKReady();
668
+
669
+ try {
670
+ console.log('📧 Sending confirmation document...');
671
+ const result = await this.sdk.sendConfirmationDocument(accessToken, requestJson);
672
+ console.log('✅ Confirmation document sent successfully');
673
+ return result;
674
+ } catch (error) {
675
+ console.error('❌ Confirmation document sending failed:', error);
676
+ throw error;
677
+ }
678
+ }
679
+
680
+ // eSign Event Listeners
681
+ public onESignInitSuccess(callback: (data: ESignInitResult) => void) {
682
+ return this.sdk.onESignInitSuccess(callback);
683
+ }
684
+
685
+ public onESignOpenSessionSuccess(callback: (data: ESignOpenSessionResult) => void) {
686
+ return this.sdk.onESignOpenSessionSuccess(callback);
687
+ }
688
+
689
+ public onESignRegisterDeviceSuccess(callback: (data: { code: string; message: string }) => void) {
690
+ return this.sdk.onESignRegisterDeviceSuccess(callback);
691
+ }
692
+
693
+ public onESignListCertsSuccess(callback: (data: { certs: ESignCertificate[] }) => void) {
694
+ return this.sdk.onESignListCertsSuccess(callback);
695
+ }
696
+
697
+ public onESignVerifyCertSuccess(callback: (data: { code: string; message: string }) => void) {
698
+ return this.sdk.onESignVerifyCertSuccess(callback);
699
+ }
700
+
701
+ public onESignListSignRequestSuccess(callback: (data: { requests: ESignSignRequest[] }) => void) {
702
+ return this.sdk.onESignListSignRequestSuccess(callback);
703
+ }
704
+
705
+ public onESignConfirmSignSuccess(callback: (data: { code: string; message: string }) => void) {
706
+ return this.sdk.onESignConfirmSignSuccess(callback);
707
+ }
708
+
709
+ public onESignAuthenticateSuccess(callback: (data: ESignAuthenticateResult) => void) {
710
+ return this.sdk.onESignAuthenticateSuccess(callback);
711
+ }
712
+
713
+ public onESignRegisterRemoteSigningSuccess(callback: (data: { response: string }) => void) {
714
+ return this.sdk.onESignRegisterRemoteSigningSuccess(callback);
715
+ }
716
+
717
+ public onESignSignPdfSuccess(callback: (data: { response: string }) => void) {
718
+ return this.sdk.onESignSignPdfSuccess(callback);
719
+ }
720
+
721
+ public onESignSendConfirmationDocumentSuccess(callback: (data: { response: string }) => void) {
722
+ return this.sdk.onESignSendConfirmationDocumentSuccess(callback);
723
+ }
724
+
725
+ public onESignError(callback: (error: ESignError) => void) {
726
+ return this.sdk.onESignError(callback);
727
+ }
728
+
330
729
  /**
331
730
  * Start eKYC UI with flow (like MainActivity.kt)
332
731
  * @param appKey Main app key
333
732
  * @param flowSDK Array of SDK types
334
733
  * @param language Language code (vi/en)
335
734
  * @param transactionId Transaction ID
336
- * @param optionConfig Optional configuration settings
337
735
  * @param appKeyConfig Optional app key configuration
736
+ * @param optionConfig Optional configuration settings (includes switchFrontCamera for camera control)
338
737
  * @param styleConfig Optional style configuration
339
738
  */
340
739
  public async startEkycUI(
@@ -354,6 +753,7 @@ export class FinosEKYCModule {
354
753
  baseUrl?: string;
355
754
  countMaxRetry?: number;
356
755
  language?: string;
756
+ switchFrontCamera?: boolean;
357
757
  },
358
758
  styleConfig?: {
359
759
  textSize?: number;
@@ -398,6 +798,9 @@ export class FinosEKYCModule {
398
798
  try {
399
799
  console.log('🚀 Starting eKYC UI with flow:', flowSDK);
400
800
  console.log('🔧 OptionConfig:', optionConfig);
801
+ if (optionConfig?.switchFrontCamera !== undefined) {
802
+ console.log('📷 Front camera setting:', optionConfig.switchFrontCamera ? 'ON' : 'OFF');
803
+ }
401
804
  console.log('🔑 AppKeyConfig:', appKeyConfig);
402
805
  console.log('🎨 StyleConfig:', styleConfig);
403
806
 
@@ -432,8 +835,162 @@ export class FinosEKYCModule {
432
835
  }
433
836
  }
434
837
 
435
- // Export singleton instance
436
- export const FinosEKYC = FinosEKYCModule.getInstance();
838
+ // Export singleton instance - ensure it's always initialized
839
+ let _finosEKYCInstance: FinosEKYCModule | null = null;
840
+
841
+ const getFinosEKYCInstance = (): FinosEKYCModule => {
842
+ if (!_finosEKYCInstance) {
843
+ try {
844
+ _finosEKYCInstance = FinosEKYCModule.getInstance();
845
+ } catch (error) {
846
+ console.error('Failed to initialize FinosEKYCModule:', error);
847
+ throw new Error('FinosEKYCModule initialization failed. Please check native module setup.');
848
+ }
849
+ }
850
+ return _finosEKYCInstance;
851
+ };
852
+
853
+ // Initialize immediately
854
+ try {
855
+ _finosEKYCInstance = FinosEKYCModule.getInstance();
856
+ } catch (error) {
857
+ // Silent initialization - will be created on first access
858
+ }
859
+
860
+ // Helper to check if a property is a method on FinosEKYCModule
861
+ const isMethod = (prop: string | symbol): boolean => {
862
+ if (typeof prop !== 'string') return false;
863
+ // Check if it's a known method from the class
864
+ const prototype = FinosEKYCModule.prototype as any;
865
+ return typeof prototype[prop] === 'function' ||
866
+ prop.startsWith('on') ||
867
+ prop === 'initialize' ||
868
+ prop === 'startEkycUI' ||
869
+ prop === 'startNfcScan' ||
870
+ prop === 'checkC06' ||
871
+ prop === 'startOcr' ||
872
+ prop === 'startLiveness' ||
873
+ prop === 'startFaceCompare';
874
+ };
875
+
876
+ // Create a comprehensive stub object with all methods to prevent undefined errors
877
+ const createFinosEKYCStub = (): FinosEKYCModule => {
878
+ const stub = {} as any;
879
+
880
+ // Add all event listener methods (on* methods)
881
+ const eventListenerMethods = [
882
+ 'onNfcScanStart', 'onNfcScanSuccess', 'onNfcError',
883
+ 'onC06Success', 'onC06Error',
884
+ 'onOCRSuccess', 'onOCRError',
885
+ 'onLivenessSuccess', 'onLivenessError',
886
+ 'onFaceCompareSuccess', 'onFaceCompareError',
887
+ 'onSmsOtpSendSuccess', 'onSmsOtpVerifySuccess', 'onSmsOtpResendSuccess', 'onSmsOtpError',
888
+ 'onESignInitSuccess', 'onESignOpenSessionSuccess', 'onESignRegisterDeviceSuccess',
889
+ 'onESignListCertsSuccess', 'onESignVerifyCertSuccess', 'onESignListSignRequestSuccess',
890
+ 'onESignConfirmSignSuccess', 'onESignAuthenticateSuccess', 'onESignRegisterRemoteSigningSuccess',
891
+ 'onESignSignPdfSuccess', 'onESignSendConfirmationDocumentSuccess', 'onESignError'
892
+ ];
893
+
894
+ eventListenerMethods.forEach(method => {
895
+ stub[method] = (callback?: any) => {
896
+ console.warn(`⚠️ FinosEKYC.${method} called but module is not initialized`);
897
+ return null;
898
+ };
899
+ });
900
+
901
+ // Add all other methods
902
+ const otherMethods = [
903
+ 'initialize', 'startNfcScan', 'checkC06', 'startOCR', 'startLiveness', 'startFaceCompare',
904
+ 'startEkycUI', 'sendOtp', 'verifyOtp', 'resendOtp', 'initializeESign', 'openSessionId',
905
+ 'registerDevice', 'listCerts', 'verifyCert', 'listSignRequest', 'confirmSign',
906
+ 'authenticate', 'registerRemoteSigning', 'signPdf', 'sendConfirmationDocument',
907
+ 'onResume', 'onPause', 'isSDKReady', 'getSDKInfo'
908
+ ];
909
+
910
+ otherMethods.forEach(method => {
911
+ stub[method] = async (...args: any[]) => {
912
+ console.warn(`⚠️ FinosEKYC.${method} called but module is not initialized`);
913
+ throw new Error(`FinosEKYC.${method} is not available. Module may not be initialized.`);
914
+ };
915
+ });
916
+
917
+ return stub as FinosEKYCModule;
918
+ };
919
+
920
+ // Create a safe wrapper using Proxy - ensure it's always an object
921
+ const createFinosEKYCProxy = (): FinosEKYCModule => {
922
+ try {
923
+ return new Proxy({} as FinosEKYCModule, {
924
+ get(_target, prop) {
925
+ try {
926
+ const instance = getFinosEKYCInstance();
927
+ const value = (instance as any)[prop];
928
+ if (typeof value === 'function') {
929
+ return value.bind(instance);
930
+ }
931
+ return value;
932
+ } catch (error) {
933
+ console.warn(`⚠️ FinosEKYC.${String(prop)} is not available:`, error);
934
+ // Always return a function for methods to prevent "undefined" errors
935
+ if (isMethod(prop)) {
936
+ // For event listeners (on* methods), return a function that returns null
937
+ if (typeof prop === 'string' && prop.startsWith('on')) {
938
+ return (callback?: any) => {
939
+ console.warn(`⚠️ FinosEKYC.${prop} called but module is not initialized`);
940
+ return null;
941
+ };
942
+ }
943
+ // For other methods, return a no-op async function
944
+ return async (...args: any[]) => {
945
+ console.warn(`⚠️ FinosEKYC.${String(prop)} called but module is not initialized`);
946
+ throw new Error(`FinosEKYC.${String(prop)} is not available. Module may not be initialized.`);
947
+ };
948
+ }
949
+ return undefined;
950
+ }
951
+ }
952
+ });
953
+ } catch (error) {
954
+ console.error('❌ Failed to create FinosEKYC proxy:', error);
955
+ // Return a comprehensive stub object
956
+ return createFinosEKYCStub();
957
+ }
958
+ };
959
+
960
+ // Create a wrapper that always returns a valid object
961
+ // This ensures FinosEKYC is NEVER undefined and always has all methods
962
+ const createFinosEKYCWrapper = (): FinosEKYCModule => {
963
+ // Always start with stub to ensure all methods exist
964
+ const stub = createFinosEKYCStub();
965
+ const wrapper = { ...stub } as any;
966
+
967
+ // Try to get real instance and override methods
968
+ try {
969
+ const realInstance = getFinosEKYCInstance();
970
+
971
+ // Override with real instance methods
972
+ Object.getOwnPropertyNames(Object.getPrototypeOf(realInstance)).forEach(key => {
973
+ if (key !== 'constructor' && typeof (realInstance as any)[key] === 'function') {
974
+ wrapper[key] = ((realInstance as any)[key]).bind(realInstance);
975
+ }
976
+ });
977
+
978
+ // Also copy any own properties from real instance
979
+ Object.keys(realInstance).forEach(key => {
980
+ if ((realInstance as any)[key] !== undefined) {
981
+ wrapper[key] = (realInstance as any)[key];
982
+ }
983
+ });
984
+ } catch (error) {
985
+ // If we can't get instance, wrapper already has all stub methods
986
+ // No need to do anything
987
+ }
988
+
989
+ return wrapper as FinosEKYCModule;
990
+ };
991
+
992
+ // Export - this ensures FinosEKYC is never undefined
993
+ export const FinosEKYC = createFinosEKYCWrapper();
437
994
 
438
995
  // Export types
439
996
  export type { NfcConfig, NfcError } from '../types/ekycNFCType';
@@ -442,6 +999,8 @@ export type { OcrConfig } from '../types/ekycOCRType';
442
999
  export type { LivenessConfig } from '../types/ekycLivenessType';
443
1000
  export type { FaceServiceConfig } from '../types/ekycFaceType';
444
1001
  export type { SDKEkycResultWithEvent, SDKEkycResultStringWithEvent } from '../types/ekycType';
1002
+ export type { SmsOtpConfig, SmsOtpResult, SmsOtpError } from '../types/ekycSmsOtpType';
1003
+ export type { UserEsignModel, ESignInitResult, ESignOpenSessionResult, ESignCertificate, ESignSignRequest, ESignError, ESignAuthenticateResult } from '../types/ekycESignType';
445
1004
 
446
1005
  // Export constants
447
1006
  export { SDK_VERSION, SDK_NAME };