Files

80 lines
2.7 KiB
JavaScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { z } from "zod";
import { req, text } from "./common.js";
export const ROLES = ["ADMIN", "EDITOR"];
export const ROLE_LABELS = {
ADMIN: "مدیر کل",
EDITOR: "ویرایشگر",
};
const password = z.string().min(8, "رمز عبور باید حداقل ۸ کاراکتر باشد").max(128);
const FA_DIGITS = "۰۱۲۳۴۵۶۷۸۹";
const AR_DIGITS = "٠١٢٣٤٥٦٧٨٩";
/** Normalize Iranian mobile to `09XXXXXXXXX` (Latin digits). */
export function normalizeIrMobile(raw) {
let s = raw.trim().replace(/[\s\-()]/g, "");
s = s.replace(/[۰-۹٠-٩]/g, (d) => {
const fa = FA_DIGITS.indexOf(d);
if (fa >= 0)
return String(fa);
const ar = AR_DIGITS.indexOf(d);
return ar >= 0 ? String(ar) : d;
});
if (s.startsWith("+98"))
s = `0${s.slice(3)}`;
else if (s.startsWith("0098"))
s = `0${s.slice(4)}`;
else if (s.startsWith("98") && s.length === 12)
s = `0${s.slice(2)}`;
return s;
}
export const irMobileSchema = z
.string()
.trim()
.min(1, "شماره موبایل را وارد کنید")
.transform(normalizeIrMobile)
.pipe(z.string().regex(/^09\d{9}$/, "شماره موبایل معتبر نیست (مثلاً ۰۹۱۲۱۲۳۴۵۶۷)"));
export const loginSchema = z.object({
phone: irMobileSchema,
password: z.string().min(1, "رمز عبور را وارد کنید").max(128),
});
export const changePasswordSchema = z.object({
currentPassword: z.string().min(1, "رمز فعلی را وارد کنید").max(128),
newPassword: password,
});
export const userCreateSchema = z.object({
phone: irMobileSchema,
name: req(80),
role: z.enum(ROLES),
password,
});
export const userUpdateSchema = z.object({
name: req(80),
role: z.enum(ROLES),
isActive: z.boolean(),
/** set only when resetting the password */
password: password.optional(),
});
/* ---------------- contact messages ---------------- */
export const MESSAGE_STATUSES = ["NEW", "READ", "ARCHIVED"];
export const MESSAGE_STATUS_LABELS = {
NEW: "جدید",
READ: "خوانده‌شده",
ARCHIVED: "بایگانی",
};
export const contactInputSchema = z.object({
name: req(80),
org: req(120),
phone: z
.string()
.trim()
.min(1, "این فیلد الزامی است")
.max(30)
.regex(/^[0-9۰-۹+\-\s()]{5,30}$/, "شماره تماس معتبر نیست"),
message: text(2000),
/** honeypot — real visitors never fill it */
website: z.string().max(200).optional(),
});
export const messageUpdateSchema = z.object({
status: z.enum(MESSAGE_STATUSES),
});
export const mediaUpdateSchema = z.object({ alt: text(200) });
//# sourceMappingURL=admin.js.map