@vgroup/dialbox 0.0.54 → 0.0.55

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.
@@ -1315,19 +1315,45 @@ class TwilioService {
1315
1315
  this.isAvailableNumber = new BehaviorSubject(false);
1316
1316
  this.callerIdList = new BehaviorSubject([]);
1317
1317
  this.triggerSMSReload = new BehaviorSubject(false);
1318
+ this.isInitialized = false;
1319
+ this.initializationInProgress = false;
1320
+ // Initialize when token is available
1318
1321
  this.initializeTwilioDevice();
1319
1322
  }
1320
- setupDeviceListeners() {
1321
- if (!this.device)
1323
+ initializeTwilioDevice() {
1324
+ if (this.initializationInProgress || !this.token)
1322
1325
  return;
1323
- // Remove any existing listeners first
1324
- this.device.off('incoming');
1325
- this.device.off('error');
1326
- this.device.off('registered');
1327
- this.device.off('unregistered');
1328
- // Set up new listeners
1326
+ this.initializationInProgress = true;
1327
+ this.extensionService.getIncomingCallToken().subscribe({
1328
+ next: (data) => {
1329
+ if (data?.token) {
1330
+ this.setupDevice(data.token);
1331
+ this.isInitialized = true;
1332
+ }
1333
+ },
1334
+ error: (error) => {
1335
+ console.error('Error initializing Twilio:', error);
1336
+ this.initializationInProgress = false;
1337
+ // Retry after delay
1338
+ setTimeout(() => this.initializeTwilioDevice(), 5000);
1339
+ }
1340
+ });
1341
+ }
1342
+ setupDevice(token) {
1343
+ // Clean up existing device if any
1344
+ if (this.device) {
1345
+ this.device.destroy();
1346
+ }
1347
+ this.incomingCallToken = token;
1348
+ localStorage.setItem('in-token', token);
1349
+ this.device = new Device(token, {
1350
+ allowIncomingWhileBusy: true,
1351
+ closeProtection: true
1352
+ });
1353
+ // Set up event listeners
1329
1354
  this.device.on('registered', () => {
1330
- console.log('Twilio Device registered');
1355
+ console.log('Twilio Device registered successfully');
1356
+ this.initializationInProgress = false;
1331
1357
  });
1332
1358
  this.device.on('incoming', (call) => {
1333
1359
  console.log('Incoming call received');
@@ -1337,40 +1363,19 @@ class TwilioService {
1337
1363
  });
1338
1364
  this.device.on('error', (error) => {
1339
1365
  console.error('Twilio Device Error:', error);
1366
+ this.isInitialized = false;
1367
+ this.initializationInProgress = false;
1368
+ // Attempt to reinitialize after error
1369
+ setTimeout(() => this.initializeTwilioDevice(), 5000);
1340
1370
  });
1371
+ this.device.on('unregistered', () => {
1372
+ console.log('Twilio Device unregistered');
1373
+ this.isInitialized = false;
1374
+ // Attempt to re-register
1375
+ this.initializeTwilioDevice();
1376
+ });
1377
+ this.device.register();
1341
1378
  }
1342
- initializeTwilioDevice() {
1343
- if (this.device) {
1344
- // If device already exists, just re-register
1345
- this.device.register();
1346
- return;
1347
- }
1348
- if (this.token) {
1349
- this.extensionService.getIncomingCallToken().subscribe({
1350
- next: (data) => {
1351
- this.incomingCallToken = data.token;
1352
- localStorage.setItem('in-token', data.token);
1353
- // Destroy existing device if any
1354
- if (this.device) {
1355
- this.device.destroy();
1356
- }
1357
- this.device = new Device(this.incomingCallToken, {
1358
- allowIncomingWhileBusy: true,
1359
- closeProtection: true
1360
- });
1361
- this.setupDeviceListeners();
1362
- this.device.register();
1363
- },
1364
- error: (error) => {
1365
- console.error('Error getting Twilio token:', error);
1366
- // Add retry logic here if needed
1367
- }
1368
- });
1369
- }
1370
- }
1371
- // onIncomingCall(){
1372
- // this.device.on('incoming', (call:any) => {
1373
- // console.log(call);
1374
1379
  // //call.accept();
1375
1380
  // });
1376
1381
  // }
@@ -2158,6 +2163,29 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.10", ngImpo
2158
2163
  }] } });
2159
2164
 
2160
2165
  class DialboxComponent {
2166
+ set isDialpadHidden(value) {
2167
+ this._isDialpadHidden = value;
2168
+ if (!value && !this.isInitialized) {
2169
+ this.initializeTwilio();
2170
+ }
2171
+ }
2172
+ get isDialpadHidden() {
2173
+ return this._isDialpadHidden;
2174
+ }
2175
+ initializeTwilio() {
2176
+ if (this.isInitialized || !this.token)
2177
+ return;
2178
+ this.twilioService.initializeTwilioDevice();
2179
+ this.isInitialized = true;
2180
+ // Subscribe to incoming calls
2181
+ const callSub = this.twilioService.currentCall.subscribe(call => {
2182
+ if (call) {
2183
+ this.isCallInProgress = true;
2184
+ this.isDialpadHidden = false; // Show dialpad on incoming call
2185
+ }
2186
+ });
2187
+ this.subscriptions.add(callSub);
2188
+ }
2161
2189
  constructor(twilioService, extService, dialog, ipService, extensionService, router) {
2162
2190
  this.twilioService = twilioService;
2163
2191
  this.extService = extService;
@@ -2165,7 +2193,7 @@ class DialboxComponent {
2165
2193
  this.ipService = ipService;
2166
2194
  this.extensionService = extensionService;
2167
2195
  this.router = router;
2168
- this.isDialpadHidden = true;
2196
+ this._isDialpadHidden = true;
2169
2197
  this.closeDialpadEvent = new EventEmitter();
2170
2198
  this.callInitiated = new EventEmitter();
2171
2199
  this.endCallEvent = new EventEmitter();
@@ -2211,14 +2239,8 @@ class DialboxComponent {
2211
2239
  this.subscriptions = new Subscription();
2212
2240
  this.shakeDedicatedBtn = false;
2213
2241
  this.isSmartDialCall = false;
2214
- this.isTwilioInitialized = false;
2242
+ this.isInitialized = false;
2215
2243
  this.isMinimised = false;
2216
- // Subscribe to incoming calls
2217
- this.subscriptions.add(this.twilioService.currentCall.subscribe(call => {
2218
- if (call) {
2219
- this.handleIncomingCall(call);
2220
- }
2221
- }));
2222
2244
  }
2223
2245
  ngOnInit() {
2224
2246
  try {
@@ -2228,10 +2250,10 @@ class DialboxComponent {
2228
2250
  this.getUserCallSetting();
2229
2251
  // Subscribe to dial number events
2230
2252
  const sub1 = this.twilioService.dialNumberFromOtherModule.subscribe((contact) => {
2231
- if (contact.number) {
2253
+ if (contact?.number) {
2232
2254
  this.isSmartDialCall = false;
2233
2255
  if (contact.isDialFromHistory) {
2234
- //handle dialing from history page
2256
+ // Handle dialing from history page
2235
2257
  if (contact.callerId == 'smartDialing') {
2236
2258
  this.selectedCallerId = { number: contact.from };
2237
2259
  this.isSmartDialCall = true;
@@ -2345,56 +2367,12 @@ class DialboxComponent {
2345
2367
  this.registerDragElement();
2346
2368
  }
2347
2369
  ngOnChanges(changes) {
2348
- if (changes['isDialpadHidden']) {
2349
- if (!changes['isDialpadHidden'].firstChange && !this.isDialpadHidden) {
2350
- // Re-initialize Twilio when dialpad becomes visible
2351
- this.initializeTwilio();
2352
- }
2353
- if (!this.isDialpadHidden) {
2354
- this.getContactList();
2355
- this.getUserCallSetting();
2356
- setTimeout(() => {
2357
- if (this.dialInputElement?.nativeElement) {
2358
- this.dialInputElement.nativeElement.focus();
2359
- }
2360
- }, 0);
2361
- }
2362
- }
2363
- }
2364
- initializeTwilio() {
2365
- if (this.isTwilioInitialized || !this.token)
2366
- return;
2367
- this.isTwilioInitialized = true;
2368
- // Clear any existing device first
2369
- if (this.twilioService.device) {
2370
- this.twilioService.device.destroy();
2371
- this.twilioService.device = null;
2372
- }
2373
- // Initialize new device
2374
- this.twilioService.initializeTwilioDevice();
2375
- // Reset the current call state
2376
- this.twilioService.currentCall.next(null);
2377
- this.twilioService.currentCallState.next('none');
2378
- }
2379
- handleIncomingCall(call) {
2380
- try {
2381
- if (!call)
2382
- return;
2383
- this.incomingCallInitiated.emit();
2384
- this.newIncomingCallData = call;
2385
- // Add to incoming calls list if not already present
2386
- const existingCall = this.incomingCallsList.find((c) => c.parameters.CallSid === call.parameters.CallSid);
2387
- if (!existingCall) {
2388
- this.incomingCallsList.unshift(call);
2389
- this.incomingCallsNewInfoEvent.emit(this.incomingCallsList);
2390
- }
2391
- // Show the dialpad if it's hidden
2392
- if (this.isDialpadHidden) {
2393
- this.isDialpadHidden = false;
2394
- }
2395
- }
2396
- catch (error) {
2397
- console.error('Error handling incoming call:', error);
2370
+ if (changes['isDialpadHidden'] && !this.isDialpadHidden) {
2371
+ this.getContactList();
2372
+ this.getUserCallSetting();
2373
+ setTimeout(() => {
2374
+ this.dialInputElement.nativeElement.focus();
2375
+ }, 0);
2398
2376
  }
2399
2377
  }
2400
2378
  registerDragElement() {
@@ -2604,232 +2582,6 @@ class DialboxComponent {
2604
2582
  this.endCallEvent.emit();
2605
2583
  }
2606
2584
  }
2607
- // async initiateCall() {
2608
- // try {
2609
- // console.log('Initiating call with number:', this.dialedNumber);
2610
- // if (!this.dialedNumber && this.lastDialed) {
2611
- // console.log('Using last dialed number:', this.lastDialed.number);
2612
- // this.sanitizedNum = this.lastDialed.number;
2613
- // }
2614
- // const isInvalid = await this.isInvalidNumber();
2615
- // if (isInvalid) {
2616
- // console.error('Invalid number format');
2617
- // return false;
2618
- // }
2619
- // this.saveLastDialed();
2620
- // this.isSavedContactDialled();
2621
- // // Check payment status
2622
- // this.isPaymentDue = localStorage.getItem('paymentDue') === 'true';
2623
- // if (this.isPaymentDue) {
2624
- // console.warn('Payment is due');
2625
- // swal('Warning', 'Please note that your payment is due. To continue using our services, kindly subscribe to avoid interruptions.');
2626
- // return false;
2627
- // }
2628
- // // Check if dialing own number
2629
- // if (this.sanitizedNum === localStorage.getItem('twilioNumber')) {
2630
- // console.error('Attempted to dial own number');
2631
- // swal('Error', 'You cannot dial your own number');
2632
- // return false;
2633
- // }
2634
- // // Check microphone permissions
2635
- // const hasPermission = await this.checkMicrophonePermission();
2636
- // if (!hasPermission) {
2637
- // console.warn('Microphone permission not granted');
2638
- // await this.askForMicrophonePermission();
2639
- // return false;
2640
- // }
2641
- // if (!this.selectedCallerId) {
2642
- // console.error('No caller ID selected');
2643
- // this.shakeDedicatedBtn = true;
2644
- // this.showDialAlert('Please select a C2C number to call from');
2645
- // setTimeout(() => {
2646
- // this.shakeDedicatedBtn = false;
2647
- // }, 3000);
2648
- // return false;
2649
- // }
2650
- // console.log('Getting number with country code...');
2651
- // this.callData.displayNum = '';
2652
- // try {
2653
- // await this.getToNumber(this.sanitizedNum);
2654
- // } catch (error) {
2655
- // console.error('Error getting number with country code:', error);
2656
- // this.showDialAlert('Error processing number. Please try again.');
2657
- // return false;
2658
- // }
2659
- // if (this.terminateCall) {
2660
- // console.log('Call terminated by user');
2661
- // this.terminateCall = false;
2662
- // return false;
2663
- // }
2664
- // // Prepare call data
2665
- // this.callData = {
2666
- // ...this.callData,
2667
- // phone: this.sanitizedNum,
2668
- // isIncomingCall: false,
2669
- // dial: true,
2670
- // from: this.isSmartDialCall ? this.callData.from : this.selectedCallerId.number,
2671
- // timestamp: new Date().toISOString()
2672
- // };
2673
- // console.log('Initiating call with data:', this.callData);
2674
- // this.isCallInProgress = true;
2675
- // this.callInitiated.emit({ ...this.callData });
2676
- // return true;
2677
- // } catch (error) {
2678
- // console.error('Error in initiateCall:', error);
2679
- // this.showDialAlert('Failed to initiate call. Please try again.');
2680
- // this.isCallInProgress = false;
2681
- // return false;
2682
- // }
2683
- // //this.clearAllDialed();
2684
- // // } else {
2685
- // // swal('Error', 'Trial period is over. Please setup payment method to continue services')
2686
- // // }
2687
- // }
2688
- // async initiateCall() {
2689
- // if (!this.dialedNumber && this.lastDialed) {
2690
- // this.sanitizedNum = this.lastDialed.number;
2691
- // }
2692
- // const isInvalid = await this.isInvalidNumber();
2693
- // if (isInvalid) {
2694
- // return false;
2695
- // }
2696
- // this.saveLastDialed();
2697
- // this.isSavedContactDialled();
2698
- // //let isCallerIdSet = await this.isCallerIdSet();
2699
- // this.isPaymentDue = localStorage.getItem('paymentDue') == 'false' ? false : true;
2700
- // if (this.isPaymentDue) {
2701
- // swal('Warning', 'Please note that your payment is due, To continue on your services kindly subscribe to use uninterrupted services.');
2702
- // return;
2703
- // }
2704
- // this.isTrialPeriodOver = localStorage.getItem('trialOver') == 'false' ? false : true;
2705
- // // if (!this.isTrialPeriodOver) {
2706
- // if (this.sanitizedNum == localStorage.getItem('twilioNumber')) {
2707
- // swal('Error', 'You can not dial this number');
2708
- // return;
2709
- // }
2710
- // const hasPermission = await this.checkMicrophonePermission();
2711
- // if (hasPermission) {
2712
- // if (this.selectedCallerId) {
2713
- // //clear displayNum if value is binded from previous call
2714
- // this.callData.displayNum = '';
2715
- // // get number to be dialled from backend
2716
- // await this.getToNumber(this.sanitizedNum);
2717
- // if (this.terminateCall) {
2718
- // this.terminateCall = false;
2719
- // return;
2720
- // }
2721
- // this.callData.phone = this.sanitizedNum;
2722
- // this.callData.isIncomingCall = false;
2723
- // this.callData.dial = true;
2724
- // if (!this.isSmartDialCall) {
2725
- // this.callData.from = this.selectedCallerId.number;
2726
- // }
2727
- // this.isCallInProgress = true;
2728
- // this.callData = {
2729
- // ...this.callData,
2730
- // phone: this.sanitizedNum,
2731
- // isIncomingCall: false,
2732
- // dial: true,
2733
- // from: this.isSmartDialCall ? this.callData.from : this.selectedCallerId.number,
2734
- // timestamp: new Date().toISOString()
2735
- // };
2736
- // console.log('Initiating call with data:', this.callData);
2737
- // this.isCallInProgress = true;
2738
- // this.callInitiated.emit({ ...this.callData });
2739
- // return true;
2740
- // } else {
2741
- // this.shakeDedicatedBtn = true;
2742
- // this.showDialAlert('Select a C2C number to call');
2743
- // setTimeout(() => {
2744
- // this.shakeDedicatedBtn = false;
2745
- // }, 3000);
2746
- // return false;
2747
- // }
2748
- // //this.callingOpenEvent.emit({ phone: this.dialedNumber });
2749
- // } else {
2750
- // await this.askForMicrophonePermission();
2751
- // }
2752
- // //this.clearAllDialed();
2753
- // // } else {
2754
- // // swal('Error', 'Trial period is over. Please setup payment method to continue services')
2755
- // // }
2756
- // }
2757
- // async initiateCall() {
2758
- // try{
2759
- // if (!this.dialedNumber && this.lastDialed) {
2760
- // this.sanitizedNum = this.lastDialed.number;
2761
- // }
2762
- // const isInvalid = await this.isInvalidNumber();
2763
- // if (isInvalid) {
2764
- // return false;
2765
- // }
2766
- // this.saveLastDialed();
2767
- // this.isSavedContactDialled();
2768
- // //let isCallerIdSet = await this.isCallerIdSet();
2769
- // this.isPaymentDue = localStorage.getItem('paymentDue') == 'false' ? false : true;
2770
- // if (this.isPaymentDue) {
2771
- // swal('Warning', 'Please note that your payment is due, To continue on your services kindly subscribe to use uninterrupted services.');
2772
- // return false;
2773
- // }
2774
- // this.isTrialPeriodOver = localStorage.getItem('trialOver') == 'false' ? false : true;
2775
- // // if (!this.isTrialPeriodOver) {
2776
- // if (this.sanitizedNum == localStorage.getItem('twilioNumber')) {
2777
- // swal('Error', 'You can not dial this number');
2778
- // return false;
2779
- // }
2780
- // const hasPermission = await this.checkMicrophonePermission();
2781
- // if (hasPermission) {
2782
- // if (this.selectedCallerId) {
2783
- // //clear displayNum if value is binded from previous call
2784
- // this.callData.displayNum = '';
2785
- // // get number to be dialled from backend
2786
- // await this.getToNumber(this.sanitizedNum);
2787
- // if (this.terminateCall) {
2788
- // this.terminateCall = false;
2789
- // return;
2790
- // }
2791
- // this.callData.phone = this.sanitizedNum;
2792
- // this.callData.isIncomingCall = false;
2793
- // this.callData.dial = true;
2794
- // if (!this.isSmartDialCall) {
2795
- // this.callData.from = this.selectedCallerId.number;
2796
- // }
2797
- // this.isCallInProgress = true;
2798
- // this.callData = {
2799
- // ...this.callData,
2800
- // phone: this.sanitizedNum,
2801
- // isIncomingCall: false,
2802
- // dial: true,
2803
- // from: this.isSmartDialCall ? this.callData.from : this.selectedCallerId.number,
2804
- // timestamp: new Date().toISOString()
2805
- // };
2806
- // console.log('Initiating call with data:', this.callData);
2807
- // this.isCallInProgress = true;
2808
- // this.callInitiated.emit({ ...this.callData });
2809
- // return true;
2810
- // } else {
2811
- // this.shakeDedicatedBtn = true;
2812
- // this.showDialAlert('Select a C2C number to call');
2813
- // setTimeout(() => {
2814
- // this.shakeDedicatedBtn = false;
2815
- // }, 3000);
2816
- // return false;
2817
- // }
2818
- // //this.callingOpenEvent.emit({ phone: this.dialedNumber });
2819
- // } else {
2820
- // await this.askForMicrophonePermission();
2821
- // }
2822
- // //this.clearAllDialed();
2823
- // // } else {
2824
- // // swal('Error', 'Trial period is over. Please setup payment method to continue services')
2825
- // // }
2826
- // }catch(e){
2827
- // console.error('Error in initiateCall:', e);
2828
- // this.showDialAlert('Failed to initiate call. Please try again.');
2829
- // this.isCallInProgress = false;
2830
- // return false;
2831
- // }
2832
- // }
2833
2585
  async initiateCall() {
2834
2586
  try {
2835
2587
  if (!this.dialedNumber && this.lastDialed) {
@@ -3122,22 +2874,19 @@ class DialboxComponent {
3122
2874
  }
3123
2875
  ngOnDestroy() {
3124
2876
  try {
2877
+ console.log('Cleaning up C2cDialpadComponent');
2878
+ // Unsubscribe from all subscriptions
2879
+ if (this.subscriptions) {
2880
+ this.subscriptions.unsubscribe();
2881
+ }
2882
+ // End any active call
2883
+ if (this.isCallInProgress) {
2884
+ this.endCall();
2885
+ }
3125
2886
  // Clear any timeouts or intervals if they exist
3126
2887
  if (this.toastTimeout) {
3127
2888
  clearTimeout(this.toastTimeout);
3128
2889
  }
3129
- // Unsubscribe from all subscriptions
3130
- this.subscriptions.unsubscribe();
3131
- // Clean up Twilio device if it exists
3132
- if (this.twilioService.device) {
3133
- try {
3134
- this.twilioService.device.destroy();
3135
- this.twilioService.device = null;
3136
- }
3137
- catch (error) {
3138
- console.error('Error cleaning up Twilio device:', error);
3139
- }
3140
- }
3141
2890
  console.log('C2cDialpadComponent cleanup complete');
3142
2891
  }
3143
2892
  catch (error) {