Initial commit: teaching institution management API.
Express/MongoDB backend with JWT auth, RBAC, S3 uploads, notifications, and scheduled jobs.
This commit is contained in:
@@ -0,0 +1,91 @@
|
||||
// /components/contactInquiries/contactInquiryValidator.js
|
||||
|
||||
const AppError = require('../../utils/AppError');
|
||||
const ContactInquiry = require('./contactInquiryModel');
|
||||
|
||||
const IRAN_MOBILE = /^(0?9\d{9}|\+989\d{9}|00989\d{9})$/;
|
||||
const EMAIL_RE = /^\w+([.-]?\w+)*@\w+([.-]?\w+)*(\.\w{2,3})+$/;
|
||||
|
||||
const isValidNationalId = (code) => {
|
||||
if (!/^\d{10}$/.test(code)) return false;
|
||||
if (/^(\d)\1{9}$/.test(code)) return false;
|
||||
const check = Number(code[9]);
|
||||
const sum = code
|
||||
.split('')
|
||||
.slice(0, 9)
|
||||
.reduce((acc, digit, index) => acc + Number(digit) * (10 - index), 0);
|
||||
const remainder = sum % 11;
|
||||
return (remainder < 2 && check === remainder) || (remainder >= 2 && check === 11 - remainder);
|
||||
};
|
||||
|
||||
const validateCreateInquiry = (req, res, next) => {
|
||||
const body = req.body || {};
|
||||
const details = {};
|
||||
|
||||
const name = (body.name || body.firstName || '').trim();
|
||||
const surname = (body.surname || body.lastName || '').trim();
|
||||
const nationalIdCode = (body.nationalIdCode || body.nationalId || '').trim();
|
||||
const phoneNumber = String(body.phoneNumber || body.phone || '').replace(/[\s\-()]/g, '').trim();
|
||||
const email = (body.email || '').trim();
|
||||
const message = (body.message || '').trim();
|
||||
const preferredContactMethods = Array.isArray(body.preferredContactMethods)
|
||||
? body.preferredContactMethods
|
||||
: [];
|
||||
const courses = Array.isArray(body.courses) ? body.courses : [];
|
||||
|
||||
if (!name) details.name = 'نام الزامی است';
|
||||
if (!surname) details.surname = 'نام خانوادگی الزامی است';
|
||||
|
||||
if (nationalIdCode && !isValidNationalId(nationalIdCode)) {
|
||||
details.nationalIdCode = 'کد ملی معتبر نیست';
|
||||
}
|
||||
|
||||
if (phoneNumber && !IRAN_MOBILE.test(phoneNumber)) {
|
||||
details.phoneNumber = 'شماره موبایل معتبر نیست';
|
||||
}
|
||||
|
||||
if (email && !EMAIL_RE.test(email)) {
|
||||
details.email = 'ایمیل معتبر نیست';
|
||||
}
|
||||
|
||||
if (!phoneNumber && !email) {
|
||||
details.contact = 'شماره تلفن یا ایمیل الزامی است';
|
||||
}
|
||||
|
||||
if (message.length > 2000) {
|
||||
details.message = 'پیام نباید بیش از ۲۰۰۰ کاراکتر باشد';
|
||||
}
|
||||
|
||||
const allowed = ContactInquiry.CONTACT_METHODS;
|
||||
const invalidMethods = preferredContactMethods.filter((m) => !allowed.includes(m));
|
||||
if (!preferredContactMethods.length) {
|
||||
details.preferredContactMethods = 'حداقل یک روش تماس را انتخاب کنید';
|
||||
} else if (invalidMethods.length) {
|
||||
details.preferredContactMethods = 'روش تماس نامعتبر است';
|
||||
}
|
||||
|
||||
if (courses.some((id) => typeof id !== 'string' && typeof id !== 'number')) {
|
||||
details.courses = 'شناسه دوره نامعتبر است';
|
||||
}
|
||||
|
||||
if (Object.keys(details).length) {
|
||||
return next(new AppError('VALIDATION_FAILED', details));
|
||||
}
|
||||
|
||||
req.body = {
|
||||
name,
|
||||
surname,
|
||||
nationalIdCode: nationalIdCode || undefined,
|
||||
phoneNumber: phoneNumber || undefined,
|
||||
email: email || undefined,
|
||||
message: message || undefined,
|
||||
preferredContactMethods,
|
||||
courses
|
||||
};
|
||||
|
||||
return next();
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
validateCreateInquiry
|
||||
};
|
||||
Reference in New Issue
Block a user