const UUID_RE = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i; export const HUB_STATUS: Record = { active: "فعال", archived: "بایگانی‌شده", }; export const TEAM_STATUS: Record = { active: "فعال", archived: "بایگانی‌شده", }; export const TEAM_ROLE: Record = { owner: "مالک", manager: "مدیر", member: "عضو", viewer: "ناظر", }; export const PROJECT_STATUS: Record = { planning: "برنامه‌ریزی", active: "فعال", on_hold: "متوقف", completed: "تکمیل‌شده", archived: "بایگانی‌شده", }; export const PRIORITY: Record = { low: "کم", medium: "متوسط", high: "بالا", urgent: "فوری", }; export const TASK_STATUS: Record = { backlog: "بک‌لاگ", todo: "انجام شود", in_progress: "در حال انجام", review: "بررسی", done: "انجام‌شده", archived: "بایگانی‌شده", }; export const KANBAN_COLUMNS = [ { id: "backlog", label: "بک‌لاگ" }, { id: "todo", label: "انجام شود" }, { id: "in_progress", label: "در حال انجام" }, { id: "review", label: "بررسی" }, { id: "done", label: "انجام‌شده" }, ] as const; export const CONTENT_STATUS: Record = { draft: "پیش‌نویس", brief: "بریف", in_production: "در حال تولید", internal_review: "بررسی داخلی", client_review: "بررسی مشتری", approved: "تأیید شده", scheduled: "زمان‌بندی شده", published: "منتشر شده", archived: "بایگانی‌شده", }; export const CONTENT_BOARD_COLUMNS = [ { id: "draft", label: "ایده‌ها", statuses: ["draft"] }, { id: "brief", label: "بریف", statuses: ["brief"] }, { id: "in_production", label: "تولید", statuses: ["in_production"] }, { id: "review", label: "در انتظار بررسی", statuses: ["internal_review", "client_review"] }, { id: "approved", label: "تأیید شده", statuses: ["approved"] }, { id: "scheduled", label: "زمان‌بندی شده", statuses: ["scheduled"] }, { id: "published", label: "منتشر شده", statuses: ["published"] }, ] as const; export const CONTENT_TYPE: Record = { instagram_post: "پست اینستاگرام", instagram_reel: "ریل اینستاگرام", instagram_story: "استوری اینستاگرام", blog_article: "مقاله وبلاگ", website_page: "محتوای صفحه وب", video: "ویدیو", podcast: "پادکست", advertisement: "تبلیغات", email: "ایمیل", sms_brief: "بریف پیامک", creative_brief: "بریف خلاق", other: "سایر", }; export const CHANNEL: Record = { instagram: "اینستاگرام", blog: "وبلاگ", website: "وب‌سایت", video: "ویدیو", audio: "صوتی", ads: "تبلیغات", email: "ایمیل", sms: "پیامک", creative: "خلاق", other: "سایر", }; export const APPROVAL_TYPE: Record = { internal: "تأیید داخلی", client: "تأیید مشتری", final: "تأیید نهایی", }; export const APPROVAL_STATUS: Record = { pending: "در انتظار", approved: "تأیید شده", rejected: "رد شده", changes_requested: "نیاز به اصلاح", }; export const BRIEF_FIELDS: { key: string; label: string; multiline?: boolean }[] = [ { key: "objective", label: "هدف", multiline: true }, { key: "audience", label: "مخاطب" }, { key: "key_message", label: "پیام کلیدی", multiline: true }, { key: "hook", label: "هوک" }, { key: "cta", label: "فراخوان عمل" }, { key: "tone", label: "لحن" }, { key: "platform", label: "پلتفرم / کانال" }, { key: "references", label: "مراجع", multiline: true }, { key: "deliverables", label: "تحویل‌دادنی‌ها", multiline: true }, { key: "deadline", label: "مهلت" }, { key: "notes", label: "یادداشت", multiline: true }, ]; export const ACTIVITY_ACTION: Record = { created: "ایجاد شد", updated: "به‌روزرسانی شد", status_changed: "وضعیت تغییر کرد", member_added: "عضو اضافه شد", member_updated: "نقش عضو تغییر کرد", approval_requested: "تأیید درخواست شد", approval_responded: "پاسخ تأیید ثبت شد", asset_referenced: "ارجاع فایل ثبت شد", commented: "نظر ثبت شد", }; export function labelOf(map: Record, value?: string | null, fallback = "نامشخص") { if (!value) return fallback; return map[value] ?? fallback; } export function displayPerson(value?: string | null) { if (!value || value === "unassigned") return "تعیین نشده"; if (UUID_RE.test(value)) return "عضو تیم"; return value; } export function isTechnicalId(value?: string | null) { return !!value && UUID_RE.test(value); } export function formatWhen(value?: string | null) { if (!value) return "—"; const date = new Date(value); if (Number.isNaN(date.getTime())) return value.slice(0, 10); return new Intl.DateTimeFormat("fa-IR", { dateStyle: "medium", timeStyle: "short" }).format(date); } export function formatDay(value?: string | null) { if (!value) return "—"; const date = new Date(value); if (Number.isNaN(date.getTime())) return value.slice(0, 10); return new Intl.DateTimeFormat("fa-IR", { dateStyle: "medium" }).format(date); } export function contentActionLabel(current: string, next: string) { if (current === "draft" && next === "in_production") return "شروع تولید"; if (current === "brief" && next === "in_production") return "شروع تولید"; if (current === "draft" && next === "brief") return "تکمیل بریف"; if (current === "in_production" && next === "internal_review") return "ارسال برای بررسی"; if (current === "internal_review" && next === "client_review") return "ارسال به بررسی مشتری"; if (next === "scheduled") return "زمان‌بندی انتشار"; if (current === "scheduled" && next === "approved") return "ویرایش زمان‌بندی"; if (next === "published") return "انتشار"; if (next === "archived") return "بایگانی"; if (next === "in_production") return "بازگشت به تولید"; return labelOf(CONTENT_STATUS, next); } export function personLabel(value?: string | null, directory?: Record) { if (!value) return "تعیین نشده"; if (directory?.[value]) return directory[value]; return displayPerson(value); }