86 lines
3.6 KiB
JavaScript
86 lines
3.6 KiB
JavaScript
const UserDocumentRepository = require('../repositories/UserDocumentRepository');
|
|
const { uploadBuffer } = require('../utils/exoscaleUploader');
|
|
const { logger } = require('../middleware/logger');
|
|
|
|
class PersonalDocumentService {
|
|
static async uploadPersonalId({ userId, idType, idNumber, expiryDate, files, unitOfWork }) {
|
|
logger.info('PersonalDocumentService.uploadPersonalId:start', { userId, idType, idNumber, expiryDate });
|
|
try {
|
|
// Validate required fields
|
|
if (!idType || !idNumber || !expiryDate || !files || !files.front) {
|
|
logger.warn('PersonalDocumentService.uploadPersonalId:missing_fields', { userId });
|
|
throw new Error('Missing required fields or front image');
|
|
}
|
|
|
|
// Validate file types (images only)
|
|
const allowedTypes = ['image/jpeg', 'image/png', 'image/webp'];
|
|
if (!allowedTypes.includes(files.front.mimetype)) {
|
|
logger.warn('PersonalDocumentService.uploadPersonalId:invalid_front_type', { userId, mimetype: files.front.mimetype });
|
|
throw new Error('Invalid file type for front image');
|
|
}
|
|
if (files.back && !allowedTypes.includes(files.back.mimetype)) {
|
|
logger.warn('PersonalDocumentService.uploadPersonalId:invalid_back_type', { userId, mimetype: files.back.mimetype });
|
|
throw new Error('Invalid file type for back image');
|
|
}
|
|
|
|
logger.info('PersonalDocumentService.uploadPersonalId:uploading_front', { userId });
|
|
// Upload front image
|
|
const frontUpload = await uploadBuffer(
|
|
files.front.buffer,
|
|
files.front.originalname,
|
|
files.front.mimetype,
|
|
`personal-id/${userId}`
|
|
);
|
|
|
|
// Upload back image if present
|
|
let backUpload = null;
|
|
if (files.back) {
|
|
logger.info('PersonalDocumentService.uploadPersonalId:uploading_back', { userId });
|
|
backUpload = await uploadBuffer(
|
|
files.back.buffer,
|
|
files.back.originalname,
|
|
files.back.mimetype,
|
|
`personal-id/${userId}`
|
|
);
|
|
}
|
|
|
|
// Insert a single row in user_id_documents for both images (back may be null)
|
|
const repo = new UserDocumentRepository(unitOfWork);
|
|
await repo.insertIdDocument({
|
|
userId,
|
|
documentType: 'personal_id',
|
|
frontObjectStorageId: frontUpload.objectKey,
|
|
backObjectStorageId: backUpload ? backUpload.objectKey : null,
|
|
idType,
|
|
idNumber,
|
|
expiryDate,
|
|
originalFilenameFront: files.front.originalname,
|
|
originalFilenameBack: files.back ? files.back.originalname : null
|
|
});
|
|
logger.info('PersonalDocumentService.uploadPersonalId:id_document_inserted', { userId });
|
|
|
|
// Set documents_uploaded in user_status
|
|
await unitOfWork.connection.query(
|
|
`UPDATE user_status SET documents_uploaded = 1, documents_uploaded_at = NOW() WHERE user_id = ?`,
|
|
[userId]
|
|
);
|
|
logger.info('PersonalDocumentService.uploadPersonalId:user_status_updated', { userId });
|
|
|
|
// Check if all steps are complete and set status to 'pending' if so
|
|
const UserStatusService = require('./UserStatusService');
|
|
await UserStatusService.checkAndSetPendingIfComplete(userId, unitOfWork);
|
|
logger.info('PersonalDocumentService.uploadPersonalId:pending_check_complete', { userId });
|
|
|
|
logger.info('PersonalDocumentService.uploadPersonalId:success', { userId });
|
|
return {
|
|
front: frontUpload,
|
|
back: backUpload
|
|
};
|
|
} catch (error) {
|
|
logger.error('PersonalDocumentService.uploadPersonalId:error', { userId, error: error.message });
|
|
throw error;
|
|
}
|
|
}
|
|
}
|
|
|
|
module.exports = PersonalDocumentService; |