m
This commit is contained in:
+174
@@ -0,0 +1,174 @@
|
||||
"use strict";
|
||||
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
||||
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
||||
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
||||
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
||||
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
||||
};
|
||||
var __metadata = (this && this.__metadata) || function (k, v) {
|
||||
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
||||
};
|
||||
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
||||
return function (target, key) { decorator(target, key, paramIndex); }
|
||||
};
|
||||
var TaskUserVerifyService_1;
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.TaskUserVerifyService = void 0;
|
||||
const common_1 = require("@nestjs/common");
|
||||
const typeorm_1 = require("@nestjs/typeorm");
|
||||
const typeorm_2 = require("typeorm");
|
||||
const user_verify_model_1 = require("../../../model/user_verify.model");
|
||||
const getDelay = () => {
|
||||
const randomMinutes = Math.floor(Math.random() * 51) + 10;
|
||||
const delay = randomMinutes * 60 * 1000;
|
||||
return delay;
|
||||
};
|
||||
let TaskUserVerifyService = TaskUserVerifyService_1 = class TaskUserVerifyService {
|
||||
userVerifyModel;
|
||||
logger = new common_1.Logger(TaskUserVerifyService_1.name);
|
||||
constructor(userVerifyModel) {
|
||||
this.userVerifyModel = userVerifyModel;
|
||||
}
|
||||
onModuleInit() {
|
||||
this.logger.verbose('实名认证定时任务已加载');
|
||||
this.scheduleNextAudit();
|
||||
}
|
||||
scheduleNextAudit() {
|
||||
const delay = getDelay();
|
||||
this.logger.verbose(`下一次实名认证审核将在 ${delay / 60 / 1000} 分钟后执行`);
|
||||
setTimeout(() => {
|
||||
void this.executeAuditAndScheduleNext();
|
||||
}, delay);
|
||||
}
|
||||
async executeAuditAndScheduleNext() {
|
||||
await this.autoAuditVerify();
|
||||
this.scheduleNextAudit();
|
||||
}
|
||||
validateIdCard(idCardNo) {
|
||||
const idCard = idCardNo.trim();
|
||||
if (idCard.length === 18) {
|
||||
const first17 = idCard.substring(0, 17);
|
||||
if (!/^\d{17}$/.test(first17)) {
|
||||
return { valid: false, message: '前 17 位必须是数字' };
|
||||
}
|
||||
const lastChar = idCard.charAt(17).toUpperCase();
|
||||
if (!/^\d|X$/.test(lastChar)) {
|
||||
return { valid: false, message: '第 18 位必须是数字或 X' };
|
||||
}
|
||||
const provinceCode = parseInt(idCard.substring(0, 2));
|
||||
if (provinceCode < 11 || provinceCode > 82) {
|
||||
return { valid: false, message: '无效的地区码' };
|
||||
}
|
||||
const birthYear = parseInt(idCard.substring(6, 10));
|
||||
const birthMonth = parseInt(idCard.substring(10, 12));
|
||||
const birthDay = parseInt(idCard.substring(12, 14));
|
||||
const currentYear = new Date().getFullYear();
|
||||
if (birthYear < 1900 ||
|
||||
birthYear > currentYear ||
|
||||
birthMonth < 1 ||
|
||||
birthMonth > 12 ||
|
||||
birthDay < 1 ||
|
||||
birthDay > 31) {
|
||||
return { valid: false, message: '无效的出生日期' };
|
||||
}
|
||||
const weights = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2];
|
||||
const checkCodes = [
|
||||
'1',
|
||||
'0',
|
||||
'X',
|
||||
'9',
|
||||
'8',
|
||||
'7',
|
||||
'6',
|
||||
'5',
|
||||
'4',
|
||||
'3',
|
||||
'2',
|
||||
];
|
||||
let sum = 0;
|
||||
for (let i = 0; i < 17; i++) {
|
||||
sum += parseInt(first17.charAt(i)) * weights[i];
|
||||
}
|
||||
const mod = sum % 11;
|
||||
const expectedCheckCode = checkCodes[mod];
|
||||
if (lastChar !== expectedCheckCode) {
|
||||
return { valid: false, message: '身份证校验码错误' };
|
||||
}
|
||||
return { valid: true };
|
||||
}
|
||||
if (idCard.length === 15) {
|
||||
if (!/^\d{15}$/.test(idCard)) {
|
||||
return { valid: false, message: '15 位身份证必须全部是数字' };
|
||||
}
|
||||
const provinceCode = parseInt(idCard.substring(0, 2));
|
||||
if (provinceCode < 11 || provinceCode > 82) {
|
||||
return { valid: false, message: '无效的地区码' };
|
||||
}
|
||||
return { valid: true };
|
||||
}
|
||||
return { valid: false, message: '身份证号长度必须是 15 或 18 位' };
|
||||
}
|
||||
validateName(realName) {
|
||||
const name = realName.trim();
|
||||
if (!name) {
|
||||
return { valid: false, message: '姓名不能为空' };
|
||||
}
|
||||
if (name.length < 2 || name.length > 5) {
|
||||
return { valid: false, message: '姓名长度应为 2-5 个汉字' };
|
||||
}
|
||||
if (!/^[\u4e00-\u9fa5]+$/.test(name)) {
|
||||
return { valid: false, message: '姓名只能包含汉字' };
|
||||
}
|
||||
if (/(.)\1{2,}/.test(name)) {
|
||||
return { valid: false, message: '姓名包含过多重复字符' };
|
||||
}
|
||||
return { valid: true };
|
||||
}
|
||||
async autoAuditVerify() {
|
||||
this.logger.verbose('开始执行实名认证自动审核任务');
|
||||
try {
|
||||
const pendingRecords = await this.userVerifyModel.find({
|
||||
where: { status: user_verify_model_1.VerifyAuditStatus.Pending },
|
||||
});
|
||||
this.logger.verbose(`待审核记录数:${pendingRecords.length}`);
|
||||
let approvedCount = 0;
|
||||
let rejectedCount = 0;
|
||||
for (const record of pendingRecords) {
|
||||
const idCardValidation = this.validateIdCard(record.idCardNo);
|
||||
if (!idCardValidation.valid) {
|
||||
await this.userVerifyModel.update({ id: record.id }, {
|
||||
status: user_verify_model_1.VerifyAuditStatus.Rejected,
|
||||
rejectReason: `身份证验证失败:${idCardValidation.message}`,
|
||||
});
|
||||
rejectedCount++;
|
||||
this.logger.verbose(`实名认证审核拒绝 ID: ${record.id}, 原因:${idCardValidation.message}`);
|
||||
continue;
|
||||
}
|
||||
const nameValidation = this.validateName(record.realName);
|
||||
if (!nameValidation.valid) {
|
||||
await this.userVerifyModel.update({ id: record.id }, {
|
||||
status: user_verify_model_1.VerifyAuditStatus.Rejected,
|
||||
rejectReason: `姓名验证失败:${nameValidation.message}`,
|
||||
});
|
||||
rejectedCount++;
|
||||
this.logger.verbose(`实名认证审核拒绝 ID: ${record.id}, 原因:${nameValidation.message}`);
|
||||
continue;
|
||||
}
|
||||
await this.userVerifyModel.update({ id: record.id }, { status: user_verify_model_1.VerifyAuditStatus.Approved });
|
||||
approvedCount++;
|
||||
this.logger.verbose(`实名认证审核通过 ID: ${record.id}, 姓名:${record.realName}`);
|
||||
}
|
||||
this.logger.verbose(`实名认证自动审核任务执行完成,通过:${approvedCount} 人,拒绝:${rejectedCount} 人`);
|
||||
}
|
||||
catch (error) {
|
||||
this.logger.error(`实名认证自动审核任务执行失败`, error instanceof Error ? error.stack : error);
|
||||
}
|
||||
}
|
||||
};
|
||||
exports.TaskUserVerifyService = TaskUserVerifyService;
|
||||
exports.TaskUserVerifyService = TaskUserVerifyService = TaskUserVerifyService_1 = __decorate([
|
||||
(0, common_1.Injectable)(),
|
||||
__param(0, (0, typeorm_1.InjectRepository)(user_verify_model_1.UserVerifyModel)),
|
||||
__metadata("design:paramtypes", [typeorm_2.Repository])
|
||||
], TaskUserVerifyService);
|
||||
//# sourceMappingURL=task_user_verify.service.js.map
|
||||
Reference in New Issue
Block a user