ngx-image-id-detector
Version:
A package that detects if an image is a Vietnamese citizen ID using Tesseract.js
87 lines • 11.9 kB
JavaScript
import { Injectable } from '@angular/core';
import { createWorker, PSM } from 'tesseract.js';
import { from } from 'rxjs';
import { map, catchError } from 'rxjs/operators';
import * as i0 from "@angular/core";
export class DetectIdService {
constructor() {
this.SIDE_PATTERNS = new Map([
['front', [
'CANCUCCONGDAN',
'CONGHAXHICHNGHAVITNAM',
'CNGHAXHICHNGHAVIETNAM',
'CONGHOAXAHOICHUNGHIAVIETNAM',
'ĐOCLAPTUDOHANHPHUC',
'HOVATENEULLNAME',
'DENTITYCARD'
]],
['back', [
'ĐACĐIEMNHANDANGPERSONALIDENTIICATION',
'CUCTRUONGCUCCANHSAT',
'DANGPERSONALIDENTILICATION',
'CUCCANHSAT',
'NGONTROTRAI',
'NGONTROPHAI',
'CCTRUNGCCCNH',
'QUNLHNHCHNHVETRATTUXAHĐHU',
'THEPOLICEDEPARTMENT',
'NHANDANGPERSONALIDENTILICATI',
'BOGONGANIUISRYOEPUBLICSECURITY',
'SINHPACEOBIRIH'
]]
]);
}
detectIdCard(file, options) {
return from(this.processImage(file, options)).pipe(map(result => result), catchError(error => {
console.error('OCR Processing Error:', error);
throw new Error('Không thể xử lý hình ảnh CCCD. Vui lòng thử lại.');
}));
}
async processImage(file, options) {
const { language = 'vie', whitelist = 'AĂÂBCDĐEÊGHIKLMNOÔƠPQRSTUƯVXYZaăâbcdđeêghiklmnoôơpqrstuưvxyz' +
'ÀÁẢÃẠÂẤẦẨẪẬĂẮẰẲẴẶĐÈÉẺẼẸÊẾỀỂỄỆÌÍỈĨỊÒÓỎÕỌÔỐỒỔỖỘƠỚỜỞỠỢÙÚỦŨỤƯỨỪỬỮỰ' +
'àáảãạâấầẩẫậăắằẳẵặđèéẻẽẹêếềểễệìíỉĩịòóỏõọôốồổỗộơớờởỡợùúủũụưứừửữự' +
'ÝỲỶỸỴýỳỷỹỵ', logger } = options || {};
let worker = null;
try {
worker = await createWorker(language, 1, { logger });
await worker.setParameters({
tessedit_char_whitelist: whitelist,
tessedit_pageseg_mode: PSM.AUTO_OSD,
});
const { data: { text } } = await worker.recognize(file, { rotateAuto: true });
const normalizedText = this.normalizeText(text);
for (const [side, patterns] of this.SIDE_PATTERNS.entries()) {
if (patterns.some(p => normalizedText.includes(this.normalizeText(p)))) {
return { side, text: normalizedText };
}
}
return { side: 'unknown', text: normalizedText };
}
catch (error) {
throw new Error('Không thể xử lý hình ảnh. Vui lòng kiểm tra lại ảnh CCCD.');
}
finally {
if (worker) {
await worker.terminate();
}
}
}
normalizeText(text) {
return text
.toUpperCase()
.normalize('NFD')
.replace(/[\u0300-\u036f]/g, '') // Remove diacritics
.replace(/\s+/g, ' ') // Normalize spaces
.trim();
}
}
DetectIdService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.2.7", ngImport: i0, type: DetectIdService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
DetectIdService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "13.2.7", ngImport: i0, type: DetectIdService, providedIn: 'root' });
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.2.7", ngImport: i0, type: DetectIdService, decorators: [{
type: Injectable,
args: [{
providedIn: 'root'
}]
}] });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmd4LWltYWdlLWlkLWRldGVjdG9yLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtaW1hZ2UtaWQtZGV0ZWN0b3Ivc3JjL2xpYi9uZ3gtaW1hZ2UtaWQtZGV0ZWN0b3Iuc2VydmljZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQzNDLE9BQU8sRUFBRSxZQUFZLEVBQUUsR0FBRyxFQUFVLE1BQU0sY0FBYyxDQUFDO0FBQ3pELE9BQU8sRUFBRSxJQUFJLEVBQWMsTUFBTSxNQUFNLENBQUM7QUFDeEMsT0FBTyxFQUFFLEdBQUcsRUFBRSxVQUFVLEVBQUUsTUFBTSxnQkFBZ0IsQ0FBQzs7QUFpQmpELE1BQU0sT0FBTyxlQUFlO0lBSDVCO1FBSW1CLGtCQUFhLEdBQUcsSUFBSSxHQUFHLENBQXVCO1lBQzdELENBQUMsT0FBTyxFQUFFO29CQUNSLGVBQWU7b0JBQ2YsdUJBQXVCO29CQUN2Qix1QkFBdUI7b0JBQ3ZCLDZCQUE2QjtvQkFDN0Isb0JBQW9CO29CQUNwQixpQkFBaUI7b0JBQ2pCLGFBQWE7aUJBQ2QsQ0FBQztZQUNGLENBQUMsTUFBTSxFQUFFO29CQUNQLHNDQUFzQztvQkFDdEMscUJBQXFCO29CQUNyQiw0QkFBNEI7b0JBQzVCLFlBQVk7b0JBQ1osYUFBYTtvQkFDYixhQUFhO29CQUNiLGNBQWM7b0JBQ2QsMkJBQTJCO29CQUMzQixxQkFBcUI7b0JBQ3JCLDhCQUE4QjtvQkFDOUIsZ0NBQWdDO29CQUNoQyxnQkFBZ0I7aUJBQ2pCLENBQUM7U0FDSCxDQUFDLENBQUM7S0EwREo7SUF4REMsWUFBWSxDQUFDLElBQVUsRUFBRSxPQUF5QjtRQUNoRCxPQUFPLElBQUksQ0FBQyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksRUFBRSxPQUFPLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FDaEQsR0FBRyxDQUFDLE1BQU0sQ0FBQyxFQUFFLENBQUMsTUFBTSxDQUFDLEVBQ3JCLFVBQVUsQ0FBQyxLQUFLLENBQUMsRUFBRTtZQUNqQixPQUFPLENBQUMsS0FBSyxDQUFDLHVCQUF1QixFQUFFLEtBQUssQ0FBQyxDQUFDO1lBQzlDLE1BQU0sSUFBSSxLQUFLLENBQUMsa0RBQWtELENBQUMsQ0FBQztRQUN0RSxDQUFDLENBQUMsQ0FDSCxDQUFDO0lBQ0osQ0FBQztJQUVPLEtBQUssQ0FBQyxZQUFZLENBQUMsSUFBVSxFQUFFLE9BQXlCO1FBQzlELE1BQU0sRUFDSixRQUFRLEdBQUcsS0FBSyxFQUNoQixTQUFTLEdBQUcsOERBQThEO1lBQzFFLGdFQUFnRTtZQUNoRSxnRUFBZ0U7WUFDaEUsWUFBWSxFQUNaLE1BQU0sRUFDUCxHQUFHLE9BQU8sSUFBSSxFQUFFLENBQUM7UUFFbEIsSUFBSSxNQUFNLEdBQWtCLElBQUksQ0FBQztRQUNqQyxJQUFJO1lBQ0YsTUFBTSxHQUFHLE1BQU0sWUFBWSxDQUFDLFFBQVEsRUFBRSxDQUFDLEVBQUUsRUFBRSxNQUFNLEVBQUUsQ0FBQyxDQUFDO1lBRXJELE1BQU0sTUFBTSxDQUFDLGFBQWEsQ0FBQztnQkFDekIsdUJBQXVCLEVBQUUsU0FBUztnQkFDbEMscUJBQXFCLEVBQUUsR0FBRyxDQUFDLFFBQVE7YUFDcEMsQ0FBQyxDQUFDO1lBRUgsTUFBTSxFQUFFLElBQUksRUFBRSxFQUFFLElBQUksRUFBRSxFQUFFLEdBQUcsTUFBTSxNQUFNLENBQUMsU0FBUyxDQUFDLElBQUksRUFBRSxFQUFFLFVBQVUsRUFBRSxJQUFJLEVBQUUsQ0FBQyxDQUFDO1lBQzlFLE1BQU0sY0FBYyxHQUFHLElBQUksQ0FBQyxhQUFhLENBQUMsSUFBSSxDQUFDLENBQUM7WUFFaEQsS0FBSyxNQUFNLENBQUMsSUFBSSxFQUFFLFFBQVEsQ0FBQyxJQUFJLElBQUksQ0FBQyxhQUFhLENBQUMsT0FBTyxFQUFFLEVBQUU7Z0JBQzNELElBQUksUUFBUSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLGNBQWMsQ0FBQyxRQUFRLENBQUMsSUFBSSxDQUFDLGFBQWEsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUU7b0JBQ3RFLE9BQU8sRUFBRSxJQUFJLEVBQUUsSUFBSSxFQUFFLGNBQWMsRUFBRSxDQUFDO2lCQUN2QzthQUNGO1lBRUQsT0FBTyxFQUFFLElBQUksRUFBRSxTQUFTLEVBQUUsSUFBSSxFQUFFLGNBQWMsRUFBRSxDQUFDO1NBQ2xEO1FBQUMsT0FBTyxLQUFLLEVBQUU7WUFDZCxNQUFNLElBQUksS0FBSyxDQUFDLDJEQUEyRCxDQUFDLENBQUM7U0FDOUU7Z0JBQVM7WUFDUixJQUFJLE1BQU0sRUFBRTtnQkFDVixNQUFNLE1BQU0sQ0FBQyxTQUFTLEVBQUUsQ0FBQzthQUMxQjtTQUNGO0lBQ0gsQ0FBQztJQUVPLGFBQWEsQ0FBQyxJQUFZO1FBQ2hDLE9BQU8sSUFBSTthQUNSLFdBQVcsRUFBRTthQUNiLFNBQVMsQ0FBQyxLQUFLLENBQUM7YUFDaEIsT0FBTyxDQUFDLGtCQUFrQixFQUFFLEVBQUUsQ0FBQyxDQUFDLG9CQUFvQjthQUNwRCxPQUFPLENBQUMsTUFBTSxFQUFFLEdBQUcsQ0FBQyxDQUFDLG1CQUFtQjthQUN4QyxJQUFJLEVBQUUsQ0FBQztJQUNaLENBQUM7OzRHQWxGVSxlQUFlO2dIQUFmLGVBQWUsY0FGZCxNQUFNOzJGQUVQLGVBQWU7a0JBSDNCLFVBQVU7bUJBQUM7b0JBQ1YsVUFBVSxFQUFFLE1BQU07aUJBQ25CIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgY3JlYXRlV29ya2VyLCBQU00sIFdvcmtlciB9IGZyb20gJ3Rlc3NlcmFjdC5qcyc7XG5pbXBvcnQgeyBmcm9tLCBPYnNlcnZhYmxlIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBtYXAsIGNhdGNoRXJyb3IgfSBmcm9tICdyeGpzL29wZXJhdG9ycyc7XG5cbmV4cG9ydCB0eXBlIElkQ2FyZFNpZGUgPSAnZnJvbnQnIHwgJ2JhY2snIHwgJ3Vua25vd24nO1xuXG5leHBvcnQgaW50ZXJmYWNlIERldGVjdElkUmVzdWx0IHtcbiAgc2lkZTogSWRDYXJkU2lkZTtcbiAgdGV4dDogc3RyaW5nO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIERldGVjdElkT3B0aW9ucyB7XG4gIGxhbmd1YWdlPzogc3RyaW5nO1xuICB3aGl0ZWxpc3Q/OiBzdHJpbmc7XG4gIGxvZ2dlcj86IChtc2c6IGFueSkgPT4gdm9pZDtcbn1cbkBJbmplY3RhYmxlKHtcbiAgcHJvdmlkZWRJbjogJ3Jvb3QnXG59KVxuZXhwb3J0IGNsYXNzIERldGVjdElkU2VydmljZSB7XG4gIHByaXZhdGUgcmVhZG9ubHkgU0lERV9QQVRURVJOUyA9IG5ldyBNYXA8SWRDYXJkU2lkZSwgc3RyaW5nW10+KFtcbiAgICBbJ2Zyb250JywgW1xuICAgICAgJ0NBTkNVQ0NPTkdEQU4nLFxuICAgICAgJ0NPTkdIQVhISUNITkdIQVZJVE5BTScsXG4gICAgICAnQ05HSEFYSElDSE5HSEFWSUVUTkFNJyxcbiAgICAgICdDT05HSE9BWEFIT0lDSFVOR0hJQVZJRVROQU0nLFxuICAgICAgJ8SQT0NMQVBUVURPSEFOSFBIVUMnLFxuICAgICAgJ0hPVkFURU5FVUxMTkFNRScsXG4gICAgICAnREVOVElUWUNBUkQnXG4gICAgXV0sXG4gICAgWydiYWNrJywgW1xuICAgICAgJ8SQQUPEkElFTU5IQU5EQU5HUEVSU09OQUxJREVOVElJQ0FUSU9OJyxcbiAgICAgICdDVUNUUlVPTkdDVUNDQU5IU0FUJyxcbiAgICAgICdEQU5HUEVSU09OQUxJREVOVElMSUNBVElPTicsXG4gICAgICAnQ1VDQ0FOSFNBVCcsXG4gICAgICAnTkdPTlRST1RSQUknLFxuICAgICAgJ05HT05UUk9QSEFJJyxcbiAgICAgICdDQ1RSVU5HQ0NDTkgnLFxuICAgICAgJ1FVTkxITkhDSE5IVkVUUkFUVFVYQUjEkEhVJyxcbiAgICAgICdUSEVQT0xJQ0VERVBBUlRNRU5UJyxcbiAgICAgICdOSEFOREFOR1BFUlNPTkFMSURFTlRJTElDQVRJJyxcbiAgICAgICdCT0dPTkdBTklVSVNSWU9FUFVCTElDU0VDVVJJVFknLFxuICAgICAgJ1NJTkhQQUNFT0JJUklIJ1xuICAgIF1dXG4gIF0pO1xuXG4gIGRldGVjdElkQ2FyZChmaWxlOiBGaWxlLCBvcHRpb25zPzogRGV0ZWN0SWRPcHRpb25zKTogT2JzZXJ2YWJsZTxEZXRlY3RJZFJlc3VsdD4ge1xuICAgIHJldHVybiBmcm9tKHRoaXMucHJvY2Vzc0ltYWdlKGZpbGUsIG9wdGlvbnMpKS5waXBlKFxuICAgICAgbWFwKHJlc3VsdCA9PiByZXN1bHQpLFxuICAgICAgY2F0Y2hFcnJvcihlcnJvciA9PiB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoJ09DUiBQcm9jZXNzaW5nIEVycm9yOicsIGVycm9yKTtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdLaMO0bmcgdGjhu4MgeOG7rSBsw70gaMOsbmgg4bqjbmggQ0NDRC4gVnVpIGzDsm5nIHRo4butIGzhuqFpLicpO1xuICAgICAgfSlcbiAgICApO1xuICB9XG5cbiAgcHJpdmF0ZSBhc3luYyBwcm9jZXNzSW1hZ2UoZmlsZTogRmlsZSwgb3B0aW9ucz86IERldGVjdElkT3B0aW9ucyk6IFByb21pc2U8RGV0ZWN0SWRSZXN1bHQ+IHtcbiAgICBjb25zdCB7XG4gICAgICBsYW5ndWFnZSA9ICd2aWUnLFxuICAgICAgd2hpdGVsaXN0ID0gJ0HEgsOCQkNExJBFw4pHSElLTE1OT8OUxqBQUVJTVFXGr1ZYWVphxIPDomJjZMSRZcOqZ2hpa2xtbm/DtMahcHFyc3R1xrB2eHl6JyArXG4gICAgICAnw4DDgeG6osOD4bqgw4LhuqThuqbhuqjhuqrhuqzEguG6ruG6sOG6suG6tOG6tsSQw4jDieG6uuG6vOG6uMOK4bq+4buA4buC4buE4buGw4zDjeG7iMSo4buKw5LDk+G7jsOV4buMw5Thu5Dhu5Lhu5Thu5bhu5jGoOG7muG7nOG7nuG7oOG7osOZw5rhu6bFqOG7pMav4buo4buq4bus4buu4buwJyArXG4gICAgICAnw6DDoeG6o8Oj4bqhw6LhuqXhuqfhuqnhuqvhuq3Eg+G6r+G6seG6s+G6teG6t8SRw6jDqeG6u+G6veG6ucOq4bq/4buB4buD4buF4buHw6zDreG7icSp4buLw7LDs+G7j8O14buNw7Thu5Hhu5Phu5Xhu5fhu5nGoeG7m+G7neG7n+G7oeG7o8O5w7rhu6fFqeG7pcaw4bup4bur4but4buv4buxJyArXG4gICAgICAnw53hu7Lhu7bhu7jhu7TDveG7s+G7t+G7ueG7tScsXG4gICAgICBsb2dnZXJcbiAgICB9ID0gb3B0aW9ucyB8fCB7fTtcblxuICAgIGxldCB3b3JrZXI6IFdvcmtlciB8IG51bGwgPSBudWxsO1xuICAgIHRyeSB7XG4gICAgICB3b3JrZXIgPSBhd2FpdCBjcmVhdGVXb3JrZXIobGFuZ3VhZ2UsIDEsIHsgbG9nZ2VyIH0pO1xuXG4gICAgICBhd2FpdCB3b3JrZXIuc2V0UGFyYW1ldGVycyh7XG4gICAgICAgIHRlc3NlZGl0X2NoYXJfd2hpdGVsaXN0OiB3aGl0ZWxpc3QsXG4gICAgICAgIHRlc3NlZGl0X3BhZ2VzZWdfbW9kZTogUFNNLkFVVE9fT1NELFxuICAgICAgfSk7XG5cbiAgICAgIGNvbnN0IHsgZGF0YTogeyB0ZXh0IH0gfSA9IGF3YWl0IHdvcmtlci5yZWNvZ25pemUoZmlsZSwgeyByb3RhdGVBdXRvOiB0cnVlIH0pO1xuICAgICAgY29uc3Qgbm9ybWFsaXplZFRleHQgPSB0aGlzLm5vcm1hbGl6ZVRleHQodGV4dCk7XG5cbiAgICAgIGZvciAoY29uc3QgW3NpZGUsIHBhdHRlcm5zXSBvZiB0aGlzLlNJREVfUEFUVEVSTlMuZW50cmllcygpKSB7XG4gICAgICAgIGlmIChwYXR0ZXJucy5zb21lKHAgPT4gbm9ybWFsaXplZFRleHQuaW5jbHVkZXModGhpcy5ub3JtYWxpemVUZXh0KHApKSkpIHtcbiAgICAgICAgICByZXR1cm4geyBzaWRlLCB0ZXh0OiBub3JtYWxpemVkVGV4dCB9O1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIHJldHVybiB7IHNpZGU6ICd1bmtub3duJywgdGV4dDogbm9ybWFsaXplZFRleHQgfTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdLaMO0bmcgdGjhu4MgeOG7rSBsw70gaMOsbmgg4bqjbmguIFZ1aSBsw7JuZyBraeG7g20gdHJhIGzhuqFpIOG6o25oIENDQ0QuJyk7XG4gICAgfSBmaW5hbGx5IHtcbiAgICAgIGlmICh3b3JrZXIpIHtcbiAgICAgICAgYXdhaXQgd29ya2VyLnRlcm1pbmF0ZSgpO1xuICAgICAgfVxuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgbm9ybWFsaXplVGV4dCh0ZXh0OiBzdHJpbmcpOiBzdHJpbmcge1xuICAgIHJldHVybiB0ZXh0XG4gICAgICAudG9VcHBlckNhc2UoKVxuICAgICAgLm5vcm1hbGl6ZSgnTkZEJylcbiAgICAgIC5yZXBsYWNlKC9bXFx1MDMwMC1cXHUwMzZmXS9nLCAnJykgLy8gUmVtb3ZlIGRpYWNyaXRpY3NcbiAgICAgIC5yZXBsYWNlKC9cXHMrL2csICcgJykgLy8gTm9ybWFsaXplIHNwYWNlc1xuICAgICAgLnRyaW0oKTtcbiAgfVxufVxuIl19