src/services/sunbirdqrscanner.service.ts
Properties |
|
Methods |
|
constructor(translate: TranslateService, platform: Platform, qrScannerResultHandler: QRScannerResultHandler, telemetryGeneratorService: TelemetryGeneratorService, appGlobalService: AppGlobalService, container: ContainerService, permission: AndroidPermissionsService, commonUtilService: CommonUtilService, appVersion: AppVersion, toastController: ToastController, router: Router, modalCtrl: ModalController, projectCert: ManageLearnCertificateService)
|
||||||||||||||||||||||||||||||||||||||||||
Defined in src/services/sunbirdqrscanner.service.ts:44
|
||||||||||||||||||||||||||||||||||||||||||
Parameters :
|
Private generateEndEvent |
generateEndEvent(pageId: string, qrData: string)
|
Defined in src/services/sunbirdqrscanner.service.ts:316
|
Returns :
void
|
Private generateImpressionTelemetry | ||||||
generateImpressionTelemetry(source, dialCode?)
|
||||||
Defined in src/services/sunbirdqrscanner.service.ts:286
|
||||||
Parameters :
Returns :
void
|
Private generateStartEvent | ||||||
generateStartEvent(pageId: string)
|
||||||
Defined in src/services/sunbirdqrscanner.service.ts:309
|
||||||
Parameters :
Returns :
void
|
Private getProfileSettingConfig |
getProfileSettingConfig()
|
Defined in src/services/sunbirdqrscanner.service.ts:179
|
Returns :
void
|
Private Async showInvalidCodeAlert | ||||
showInvalidCodeAlert(scannedData)
|
||||
Defined in src/services/sunbirdqrscanner.service.ts:330
|
||||
Parameters :
Returns :
any
|
Private Async showPopover | ||||||
showPopover(pageId: string)
|
||||||
Defined in src/services/sunbirdqrscanner.service.ts:110
|
||||||
Parameters :
Returns :
Promise<string | undefined>
|
Private Async startQRScanner | |||||||||||||||||||||
startQRScanner(screenTitle: string, displayText: string, displayTextColor: string, buttonText: string, showButton: boolean, source: string)
|
|||||||||||||||||||||
Defined in src/services/sunbirdqrscanner.service.ts:191
|
|||||||||||||||||||||
Parameters :
Returns :
Promise<string | undefined>
|
Public Async startScanner | ||||||||||||||||||||||||||||
startScanner(source: string, showButton: boolean, screenTitle, displayText, displayTextColor: string, buttonText)
|
||||||||||||||||||||||||||||
Defined in src/services/sunbirdqrscanner.service.ts:72
|
||||||||||||||||||||||||||||
Parameters :
Returns :
Promise<string | undefined>
|
Public stopScanner |
stopScanner()
|
Defined in src/services/sunbirdqrscanner.service.ts:167
|
Returns :
void
|
appName |
Type : string
|
Default value : ''
|
Defined in src/services/sunbirdqrscanner.service.ts:42
|
backButtonFunc |
Default value : undefined
|
Defined in src/services/sunbirdqrscanner.service.ts:39
|
Private isScannerActive |
Default value : false
|
Defined in src/services/sunbirdqrscanner.service.ts:43
|
Private mQRScannerText |
Defined in src/services/sunbirdqrscanner.service.ts:38
|
profile |
Type : Profile
|
Defined in src/services/sunbirdqrscanner.service.ts:29
|
Private Readonly QR_SCANNER_TEXT |
Type : []
|
Default value : [
'SCAN_QR_CODE',
'SCAN_QR_INSTRUCTION',
'UNKNOWN_QR',
'NO_QR_CODE',
'CANCEL',
'TRY_AGAIN',
]
|
Defined in src/services/sunbirdqrscanner.service.ts:30
|
Private qrModal |
Type : HTMLIonModalElement
|
Defined in src/services/sunbirdqrscanner.service.ts:44
|
showButton |
Default value : false
|
Defined in src/services/sunbirdqrscanner.service.ts:41
|
source |
Type : string
|
Defined in src/services/sunbirdqrscanner.service.ts:40
|
import { Injectable } from '@angular/core';
import { NavigationExtras, Router } from '@angular/router';
import { QrScannerIOSComponent } from '@app/app/components/qr-scanner-ios/qr-scanner-ios.component';
import { GUEST_STUDENT_TABS, GUEST_TEACHER_TABS, initTabs } from '@app/app/module.service';
import { AppGlobalService, CommonUtilService, QRScannerResultHandler, TelemetryGeneratorService } from '@app/services/';
import { AndroidPermissionsService } from '@app/services/android-permissions/android-permissions.service';
import { ContainerService } from '@app/services/container.services';
import { AppVersion } from '@ionic-native/app-version/ngx';
import { ModalController, Platform, ToastController } from '@ionic/angular';
import { TranslateService } from '@ngx-translate/core';
import { take } from 'rxjs/operators';
import { CorrelationData, Profile, ProfileType, TelemetryObject } from 'sunbird-sdk';
import { AndroidPermission, AndroidPermissionsStatus, PermissionAskedEnum } from './android-permissions/android-permission';
import {
CorReleationDataType, Environment,
ImpressionSubtype,
ImpressionType,
InteractSubtype,
InteractType,
Mode,
PageId
} from './telemetry-constants';
import { ManageLearnCertificateService } from '@app/app/manage-learn/core/services/manage-learn-certificate.service';
declare const cordova;
@Injectable()
export class SunbirdQRScanner {
profile: Profile;
private readonly QR_SCANNER_TEXT = [
'SCAN_QR_CODE',
'SCAN_QR_INSTRUCTION',
'UNKNOWN_QR',
'NO_QR_CODE',
'CANCEL',
'TRY_AGAIN',
];
private mQRScannerText;
backButtonFunc = undefined;
source: string;
showButton = false;
appName = '';
private isScannerActive = false;
private qrModal: HTMLIonModalElement
constructor(
private translate: TranslateService,
private platform: Platform,
private qrScannerResultHandler: QRScannerResultHandler,
private telemetryGeneratorService: TelemetryGeneratorService,
private appGlobalService: AppGlobalService,
private container: ContainerService,
private permission: AndroidPermissionsService,
private commonUtilService: CommonUtilService,
private appVersion: AppVersion,
private toastController: ToastController,
private router: Router,
private modalCtrl: ModalController,
private projectCert : ManageLearnCertificateService
) {
const that = this;
this.translate.get(this.QR_SCANNER_TEXT).subscribe((data) => {
that.mQRScannerText = data;
});
this.translate.onLangChange.subscribe(() => {
that.mQRScannerText = that.translate.instant(that.QR_SCANNER_TEXT);
});
this.appVersion.getAppName().then((appName: any) => this.appName = appName);
}
public async startScanner(
source: string,
showButton: boolean = false,
screenTitle = this.mQRScannerText['SCAN_QR_CODE'],
displayText = this.mQRScannerText['SCAN_QR_INSTRUCTION'],
displayTextColor = '#0b0b0b',
buttonText = this.mQRScannerText['NO_QR_CODE']
): Promise<string | undefined> {
return new Promise<string | undefined>(async (resolve, reject) => {
this.source = source;
this.showButton = showButton;
this.platform.pause.pipe(
take(1)
).subscribe(() => this.stopScanner());
this.generateImpressionTelemetry(source);
this.generateStartEvent(source);
if (this.platform.is("ios")) {
resolve(this.startQRScanner(screenTitle, displayText, displayTextColor, buttonText, showButton, source));
} else {
const permissionStatus = await this.commonUtilService.getGivenPermissionStatus(AndroidPermission.CAMERA);
if (permissionStatus.hasPermission) {
resolve(this.startQRScanner(screenTitle, displayText, displayTextColor, buttonText, showButton, source));
} else if (permissionStatus.isPermissionAlwaysDenied) {
await this.commonUtilService.showSettingsPageToast('CAMERA_PERMISSION_DESCRIPTION', this.appName, PageId.QRCodeScanner, false);
} else {
this.showPopover(source).then((result) => {
if (result) {
resolve(result);
} else {
resolve(undefined);
}
});
}
}
});
}
private async showPopover(pageId: string): Promise<string | undefined> {
return new Promise<string | undefined>(async (resolve, reject) => {
const confirm = await this.commonUtilService.buildPermissionPopover(
async (whichBtnClicked: string) => {
if (whichBtnClicked === this.commonUtilService.translateMessage('NOT_NOW')) {
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.TOUCH,
InteractSubtype.NOT_NOW_CLICKED,
pageId === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
PageId.PERMISSION_POPUP);
await this.commonUtilService.showSettingsPageToast
('CAMERA_PERMISSION_DESCRIPTION', this.appName, PageId.QRCodeScanner, this.appGlobalService.isOnBoardingCompleted);
} else {
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.TOUCH,
InteractSubtype.ALLOW_CLICKED,
pageId === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
PageId.PERMISSION_POPUP);
this.appGlobalService.setIsPermissionAsked(PermissionAskedEnum.isCameraAsked, true);
this.appGlobalService.isNativePopupVisible = true;
this.permission.requestPermissions([AndroidPermission.CAMERA]).subscribe((status: AndroidPermissionsStatus) => {
if (status && status.hasPermission) {
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.TOUCH,
InteractSubtype.ALLOW_CLICKED,
pageId === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
PageId.APP_PERMISSION_POPUP
);
this.startScanner(this.source, this.showButton).then((result) => {
if (result) {
resolve(result);
} else {
resolve(undefined);
}
this.appGlobalService.isNativePopupVisible = false;
});
} else {
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.TOUCH,
InteractSubtype.DENY_CLICKED,
pageId === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
PageId.APP_PERMISSION_POPUP
);
this.commonUtilService.showSettingsPageToast
('CAMERA_PERMISSION_DESCRIPTION', this.appName, PageId.QRCodeScanner, this.appGlobalService.isOnBoardingCompleted);
this.appGlobalService.setNativePopupVisible(false, 1000);
}
}, (e) => { reject(e); });
}
}, this.appName, this.commonUtilService.translateMessage('CAMERA'), 'CAMERA_PERMISSION_DESCRIPTION', PageId.QRCodeScanner,
this.appGlobalService.isOnBoardingCompleted
);
await confirm.present();
});
}
public stopScanner() {
if (!this.isScannerActive) {
return;
}
if (this.platform.is("ios") && this.qrModal) this.qrModal.dismiss();
// to prevent back event propagating up to parent
setTimeout(() => {
(window as any).qrScanner.stopScanner();
this.isScannerActive = false;
}, 100);
}
private getProfileSettingConfig() {
this.profile = this.appGlobalService.getCurrentUser();
if (this.commonUtilService.isAccessibleForNonStudentRole(this.profile.profileType)) {
initTabs(this.container, GUEST_TEACHER_TABS);
} else if (this.profile.profileType === ProfileType.STUDENT) {
initTabs(this.container, GUEST_STUDENT_TABS);
}
this.stopScanner();
const navigationExtras: NavigationExtras = { state: { loginMode: 'guest' } };
this.router.navigate(['/tabs'], navigationExtras);
}
private async startQRScanner(
screenTitle: string, displayText: string, displayTextColor: string,
buttonText: string, showButton: boolean, source: string): Promise<string | undefined> {
if (this.isScannerActive) {
return;
}
this.isScannerActive = true;
if (this.platform.is("ios")) {
this.qrModal = await this.modalCtrl.create({
component: QrScannerIOSComponent,
cssClass: 'qr-scanner-modal',
showBackdrop: false,
backdropDismiss: true,
mode: 'ios',
swipeToClose: false
})
await this.qrModal.present();
this.qrModal.onWillDismiss().finally(() => {
this.stopScanner();
});
}
return new Promise<string | undefined>((resolve, reject) => {
(window as any).qrScanner.startScanner(screenTitle, displayText,
displayTextColor, buttonText, showButton, this.platform.isRTL, async (scannedData) => {
if (scannedData === 'skip') {
this.stopScanner();
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.TOUCH,
InteractSubtype.NO_QR_CODE_CLICKED,
Environment.ONBOARDING,
PageId.QRCodeScanner);
this.generateEndEvent(source, '');
} else {
const dialCode = await this.qrScannerResultHandler.parseDialCode(scannedData);
if (scannedData === 'cancel' ||
scannedData === 'cancel_hw_back' ||
scannedData === 'cancel_nav_back') {
this.telemetryGeneratorService.generateBackClickedTelemetry(PageId.SCAN,
source === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
scannedData === 'cancel_nav_back');
this.telemetryGeneratorService.generateBackClickedNewTelemetry(
scannedData === 'cancel_hw_back',
this.appGlobalService.isOnBoardingCompleted ? Environment.HOME : Environment.ONBOARDING,
PageId.SCAN
);
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.OTHER,
InteractSubtype.QRCodeScanCancelled,
Environment.HOME,
PageId.QRCodeScanner);
this.generateEndEvent(source, '');
} else if (dialCode) {
const corRelationList: Array<CorrelationData> = [];
corRelationList.push({id: dialCode, type: CorReleationDataType.QR});
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.QR_CAPTURED,
'',
source === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
PageId.SCAN,
undefined,
undefined,
undefined,
corRelationList);
this.generateImpressionTelemetry(source, dialCode);
this.qrScannerResultHandler.handleDialCode(source, scannedData, dialCode);
} else if (this.qrScannerResultHandler.isContentId(scannedData)) {
this.qrScannerResultHandler.handleContentId(source, scannedData);
} else if(scannedData.includes('ProjectCertificate')) {
this.projectCert.getProjectCertificate(scannedData);
} else if(scannedData.includes('data=') || scannedData.includes('t=URL')) {
this.qrScannerResultHandler.handleRcCertsQR(scannedData);
} else if (scannedData.includes('/certs/')) {
this.qrScannerResultHandler.handleCertsQR(source, scannedData);
} else if(scannedData.includes('/manage-learn/')) {
this.qrScannerResultHandler.manageLearScan(scannedData);
} else {
this.qrScannerResultHandler.handleInvalidQRCode(source, scannedData);
this.showInvalidCodeAlert(scannedData);
}
this.stopScanner();
}
resolve(scannedData);
}, (e) => {
reject(e);
if (this.platform.is("ios") && ["camera_access_denied", "camera_access_restricted"].includes(e)) {
this.commonUtilService.showSettingsPageToast('CAMERA_PERMISSION_DESCRIPTION', this.appName, PageId.QRCodeScanner, false)
}
this.stopScanner();
});
});
}
private generateImpressionTelemetry(source, dialCode?) {
if (dialCode) {
const corRelationList: Array<CorrelationData> = [];
corRelationList.push({id: dialCode, type: CorReleationDataType.QR});
this.telemetryGeneratorService.generateImpressionTelemetry(
ImpressionType.QR_REQUEST, '',
PageId.SCAN,
source ? Environment.ONBOARDING : Environment.HOME, '', '', '',
undefined,
corRelationList);
} else {
this.telemetryGeneratorService.generatePageLoadedTelemetry(
PageId.SCAN,
source === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME
);
this.telemetryGeneratorService.generateImpressionTelemetry(
ImpressionType.VIEW,
ImpressionSubtype.QRCodeScanInitiate,
source,
source === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME);
}
}
private generateStartEvent(pageId: string) {
const telemetryObject = new TelemetryObject('', 'qr', undefined);
this.telemetryGeneratorService.generateStartTelemetry(
PageId.QRCodeScanner,
telemetryObject);
}
private generateEndEvent(pageId: string, qrData: string) {
if (pageId) {
const telemetryObject: TelemetryObject = new TelemetryObject(qrData, 'qr', undefined);
this.telemetryGeneratorService.generateEndTelemetry(
'qr',
Mode.PLAY,
PageId.QRCodeScanner,
Environment.HOME,
telemetryObject
);
}
}
private async showInvalidCodeAlert(scannedData) {
this.telemetryGeneratorService.generateInteractTelemetry(
InteractType.OTHER,
InteractSubtype.QR_CODE_INVALID,
this.source === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
this.source
);
if (this.source !== 'permission') {
const corRelationList: CorrelationData[] = [{
id: PageId.SCAN,
type: CorReleationDataType.CHILD_UI
}];
this.telemetryGeneratorService.generateImpressionTelemetry(
InteractSubtype.QR_CODE_INVALID, '',
this.source === PageId.ONBOARDING_PROFILE_PREFERENCES ? PageId.SCAN_OR_MANUAL : this.source,
this.source === PageId.ONBOARDING_PROFILE_PREFERENCES ? Environment.ONBOARDING : Environment.HOME,
undefined,
undefined,
undefined,
undefined,
corRelationList
);
this.commonUtilService.afterOnBoardQRErrorAlert('INVALID_QR', 'UNKNOWN_QR', this.source, scannedData);
return;
}
}
}
export interface QRResultCallback {
dialcode(scanResult: string, code: string);
content(scanResult: string, contentId: string);
}