build: include production build artifacts in repo

This commit is contained in:
S. Esmaeili
2026-10-24 10:11:05 +03:30
parent dfd8a82809
commit 7399812d0e
213 changed files with 65702 additions and 2 deletions
+45
View File
@@ -0,0 +1,45 @@
import { normalizeIrMobile } from "@imen/shared";
import { hashPassword } from "../auth/auth.service.js";
import { createPrismaClient } from "../prisma/prisma.service.js";
const prisma = createPrismaClient();
async function main() {
const phone = normalizeIrMobile("09128081392");
const password = "09128081392";
const name = "مدیر سایت";
const role = "ADMIN";
const passwordHash = await hashPassword(password);
const existing = await prisma.adminUser.findUnique({ where: { phone } });
if (existing) {
const updated = await prisma.adminUser.update({
where: { id: existing.id },
data: {
passwordHash,
name,
role,
},
});
console.log(`User already existed, password updated for: ${updated.phone} (ID: ${updated.id})`);
}
else {
const user = await prisma.adminUser.create({
data: {
phone,
passwordHash,
name,
role,
},
});
console.log(`User successfully created: ${user.phone} (ID: ${user.id}, Role: ${user.role})`);
}
}
try {
await main();
}
catch (e) {
console.error("Error creating user:", e);
process.exitCode = 1;
}
finally {
await prisma.$disconnect();
}
//# sourceMappingURL=create-admin.js.map
+1
View File
@@ -0,0 +1 @@
{"version":3,"file":"create-admin.js","sourceRoot":"","sources":["../../src/seed/create-admin.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,cAAc,CAAC;AACjD,OAAO,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AACvD,OAAO,EAAE,kBAAkB,EAAE,MAAM,6BAA6B,CAAC;AAEjE,MAAM,MAAM,GAAG,kBAAkB,EAAE,CAAC;AAEpC,KAAK,UAAU,IAAI;IACjB,MAAM,KAAK,GAAG,iBAAiB,CAAC,aAAa,CAAC,CAAC;IAC/C,MAAM,QAAQ,GAAG,aAAa,CAAC;IAC/B,MAAM,IAAI,GAAG,WAAW,CAAC;IACzB,MAAM,IAAI,GAAG,OAAO,CAAC;IAErB,MAAM,YAAY,GAAG,MAAM,YAAY,CAAC,QAAQ,CAAC,CAAC;IAElD,MAAM,QAAQ,GAAG,MAAM,MAAM,CAAC,SAAS,CAAC,UAAU,CAAC,EAAE,KAAK,EAAE,EAAE,KAAK,EAAE,EAAE,CAAC,CAAC;IACzE,IAAI,QAAQ,EAAE,CAAC;QACb,MAAM,OAAO,GAAG,MAAM,MAAM,CAAC,SAAS,CAAC,MAAM,CAAC;YAC5C,KAAK,EAAE,EAAE,EAAE,EAAE,QAAQ,CAAC,EAAE,EAAE;YAC1B,IAAI,EAAE;gBACJ,YAAY;gBACZ,IAAI;gBACJ,IAAI;aACL;SACF,CAAC,CAAC;QACH,OAAO,CAAC,GAAG,CAAC,+CAA+C,OAAO,CAAC,KAAK,SAAS,OAAO,CAAC,EAAE,GAAG,CAAC,CAAC;IAClG,CAAC;SAAM,CAAC;QACN,MAAM,IAAI,GAAG,MAAM,MAAM,CAAC,SAAS,CAAC,MAAM,CAAC;YACzC,IAAI,EAAE;gBACJ,KAAK;gBACL,YAAY;gBACZ,IAAI;gBACJ,IAAI;aACL;SACF,CAAC,CAAC;QACH,OAAO,CAAC,GAAG,CAAC,8BAA8B,IAAI,CAAC,KAAK,SAAS,IAAI,CAAC,EAAE,WAAW,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC;IAC/F,CAAC;AACH,CAAC;AAED,IAAI,CAAC;IACH,MAAM,IAAI,EAAE,CAAC;AACf,CAAC;AAAC,OAAO,CAAC,EAAE,CAAC;IACX,OAAO,CAAC,KAAK,CAAC,sBAAsB,EAAE,CAAC,CAAC,CAAC;IACzC,OAAO,CAAC,QAAQ,GAAG,CAAC,CAAC;AACvB,CAAC;QAAS,CAAC;IACT,MAAM,MAAM,CAAC,WAAW,EAAE,CAAC;AAC7B,CAAC"}
+904
View File
@@ -0,0 +1,904 @@
export const CATEGORIES = [
{
slug: "workwear",
code: "IP-C01",
name: "پوشاک کار و البسه صنعتی",
en: "INDUSTRIAL WORKWEAR",
shortDesc: "لباس‌کار صنعتی با پارچه فلامنت کجراه اعلا، دوخت سه سوزنه و آستر عرق‌گیر؛ مناسب محیط‌های کارگاهی و صنعتی.",
fullDesc: "مجموعه کامل پوشاک کار صنعتی شامل کاپشن و شلوار مهندسی، لباس جوشکاری، پیش‌بند دوبنده و تی‌شرت کار. تمامی مدل‌ها با پارچه فلامنت کجراه اعلا و کتان مقاوم، دوخت صنعتی سه سوزنه پیوسته برای جلوگیری از شکافتگی درزها و آستر عرق‌گیر اختصاصی تولید می‌شوند. موجود در سایزهای M تا 4XL.",
icon: "Shirt",
products: [
{
code: "IP-W01",
name: "لباسکار مدل آلفا",
en: "ALPHA WORKWEAR",
desc: "کاپشن و شلوار مهندسی با جیب‌های پاکتی و زیپ‌دار، نوار مغزی تزئینی و طراحی ارگونومیک برای تیم‌های فنی و مهندسی.",
specs: ["فلامنت کجراه اعلا", "دوخت سه سوزنه", "آستر عرق‌گیر", "سایز M تا 4XL"],
variants: [
"طوسی/آبی",
"مشکی/قرمز",
"مشکی/زرد",
"کرم/سرمه‌ای",
],
},
{
code: "IP-W02",
name: "لباسکار مدل اورجینال",
en: "ORIGINAL WORKWEAR",
desc: "کاپشن و شلوار استاندارد با دوام بالا، مناسب کادر فنی کارخانجات و خطوط تولید با ترکیب‌های صنعتی دورنگ.",
specs: ["کتان مقاوم", "دوخت سه سوزنه", "آستر عرق‌گیر", "سایز M تا 4XL"],
variants: ["ترکیب‌های صنعتی دورنگ"],
},
{
code: "IP-W03",
name: "لباسکار مدل بوفالو",
en: "BUFFALO WORKWEAR",
desc: "طراحی اسپرت با برش‌های تقویتی روی شانه و بازو، زیپ مخفی محافظ‌دار؛ مناسب محیط‌های صنعتی فعال.",
specs: ["فلامنت کجراه اعلا", "زیپ مخفی محافظ‌دار", "برش تقویتی شانه", "سایز M تا 4XL"],
variants: [
"سرمه‌ای/زرد",
"طوسی/قرمز",
"طوسی/خردلی",
"آبی/مشکی",
],
},
{
code: "IP-W04",
name: "لباسکار ست ورک",
en: "SET WORK",
desc: "ست اداری/کارگاهی با انعطاف بالا جهت فعالیت‌های فنی و تعمیراتی؛ قابل استفاده در محیط‌های ستادی و عملیاتی.",
specs: ["کتان مقاوم", "دوخت سه سوزنه", "طراحی منعطف", "سایز M تا 4XL"],
variants: ["ترکیب‌های چندگانه کارگاهی"],
},
{
code: "IP-W05",
name: "لباسکار جوشکاری",
en: "WELDING WORKWEAR",
desc: "متریال سنگین کتان یا چرم جهت مقاومت در برابر پاشش جرقه‌های مذاب؛ طراحی‌شده برای جوشکاران صنعتی.",
specs: ["مقاوم به جرقه مذاب", "کتان سنگین / چرم", "دوخت صنعتی", "سایز M تا 4XL"],
},
{
code: "IP-W06",
name: "پیش‌بند دوبنده",
en: "BIB OVERALLS",
desc: "آزادی عمل کامل کتف و شانه با جیب‌های چندمنظوره ابزار بر روی پیش‌سینه؛ ایده‌آل برای کارهای تعمیراتی و مونتاژ.",
specs: ["آزادی حرکت شانه", "جیب ابزار پیش‌سینه", "دوخت سه سوزنه", "سایز M تا 4XL"],
variants: ["سرمه‌ای", "خاکستری"],
},
{
code: "IP-W07",
name: "تی‌شرت صنعتی",
en: "INDUSTRIAL T-SHIRT",
desc: "تی‌شرت یقه‌دار جودون / پنبه‌ای مناسب فصول گرم و زیرپوش کاپشن کارگاهی در سوله‌های سرپوشیده.",
specs: ["پنبه / جودون", "یقه‌دار", "مناسب فصول گرم", "سایز M تا 4XL"],
},
],
},
{
slug: "safety-footwear",
code: "IP-C02",
name: "پایپوش و کفش ایمنی",
en: "SAFETY FOOTWEAR",
shortDesc: "کفش‌های اداری و کفش‌های ایمنی کارگری؛ راحت و شکیل برای محیط اداری، مقاوم و ضد لغزش برای کارگاه.",
fullDesc: "پایپوش ایمنی شامل کفش‌های اداری برای محیط‌های اداری و سبک صنعتی و کفش‌های ایمنی کارگری برای کارگاه‌ها و پروژه‌های ساختمانی؛ با زیره مقاوم و مواد مقاوم در برابر سایش و مواد شیمیایی سبک.",
icon: "Footprints",
groups: [
{ slug: "office", name: "کفش اداری", desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم." },
{ slug: "worker", name: "کفش ایمنی کارگری", desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک." },
],
products: [
{
code: "IP-F01",
group: "office",
name: "کفش اداری مدل ۱۱۷۴",
en: "OFFICE SHOE 1174",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم نبوک", "بنددار", "زیره مقاوم"],
image: "/images/products/shoes/office/1.webp",
},
{
code: "IP-F02",
group: "office",
name: "کفش اداری بی‌بند مدل ۶",
en: "SLIP-ON OFFICE SHOE",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "بدون بند", "زیره مقاوم"],
image: "/images/products/shoes/office/2.webp",
},
{
code: "IP-F03",
group: "office",
name: "کفش اداری بنددار مشکی",
en: "LACE-UP OFFICE SHOE",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "بنددار", "زیره مقاوم"],
image: "/images/products/shoes/office/3.webp",
},
{
code: "IP-F04",
group: "office",
name: "کفش اداری بی‌بند AAEA075",
en: "SLIP-ON OFFICE SHOE AAEA075",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "بدون بند", "زیره مقاوم"],
image: "/images/products/shoes/office/4.webp",
},
{
code: "IP-F05",
group: "office",
name: "کفش اداری شبرو",
en: "SHEBRO OFFICE SHOE",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "بنددار", "زیره مقاوم"],
image: "/images/products/shoes/office/5.webp",
},
{
code: "IP-F06",
group: "office",
name: "کفش اداری بی‌بند کلاسیک",
en: "CLASSIC SLIP-ON OFFICE SHOE",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "بدون بند", "زیره مقاوم"],
image: "/images/products/shoes/office/6.webp",
},
{
code: "IP-F07",
group: "office",
name: "کفش اداری کالج",
en: "LOAFER OFFICE SHOE",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "کالج", "زیره مقاوم"],
image: "/images/products/shoes/office/7.webp",
},
{
code: "IP-F08",
group: "office",
name: "کفش اداری دیپلمات",
en: "DIPLOMAT OFFICE SHOE",
desc: "مناسب محیط‌های اداری و سبک صنعتی، راحت، سبک و شکیل با زیره مقاوم.",
specs: ["چرم طبیعی", "بنددار", "طراحی رسمی"],
image: "/images/products/shoes/office/8.webp",
},
{
code: "IP-F09",
group: "worker",
name: "کفش ایمنی کارگری مدل ۱",
en: "WORKER SAFETY SHOE",
desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک.",
specs: ["مقاوم به سایش", "زیره ضد لغزش"],
image: "/images/products/shoes/worker/1.png",
},
{
code: "IP-F10",
group: "worker",
name: "کفش ایمنی کارگری مدل ۲",
en: "WORKER SAFETY SHOE",
desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک.",
specs: ["مقاوم به سایش", "زیره ضد لغزش"],
image: "/images/products/shoes/worker/2.png",
},
{
code: "IP-F11",
group: "worker",
name: "کفش ایمنی کارگری مدل ۹۰",
en: "WORKER SAFETY SHOE 90",
desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک.",
specs: ["مقاوم به سایش", "زیره ضد لغزش"],
image: "/images/products/shoes/worker/3.png",
},
{
code: "IP-F12",
group: "worker",
name: "کفش ایمنی پاتن پدیده تبریز مدل رایکا S1017",
en: "PATEN PADIDEH RAYKA S1017",
desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک.",
specs: ["پاتن پدیده تبریز", "مقاوم به سایش", "زیره ضد لغزش"],
image: "/images/products/shoes/worker/4.png",
},
{
code: "IP-F13",
group: "worker",
name: "کفش ایمنی پیما مدل دنا",
en: "PAYMA DENA SAFETY SHOE",
desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک.",
specs: ["پیما", "مقاوم به سایش", "زیره ضد لغزش"],
image: "/images/products/shoes/worker/5.png",
},
{
code: "IP-F14",
group: "worker",
name: "کفش کار کارگری ساق‌دار",
en: "WORKER SAFETY BOOT",
desc: "مناسب کارگاه‌ها و پروژه‌های ساختمانی، مقاوم در برابر سایش و مواد شیمیایی سبک.",
specs: ["ساق‌دار", "مقاوم به سایش", "زیره ضد لغزش"],
image: "/images/products/shoes/worker/6.png",
},
],
},
{
slug: "protective-gloves",
code: "IP-C03",
name: "دستکش‌های حفاظتی",
en: "PROTECTIVE GLOVES",
shortDesc: "دستکش‌های ضد برش، چرم، ضد اسید و ضد حلال برای کارهای سنگین صنعتی، جوشکاری و تماس با مواد شیمیایی.",
fullDesc: "دستکش‌های حفاظت فردی شامل مدل‌های ضد برش، چرم، ضد اسید و ضد حلال؛ از برندهای استادکار، امریکن سیفتی، ماکسی درای و NM Safety. هر مدل متناسب با نوع خطر محیط کار انتخاب شده است.",
icon: "Hand",
groups: [
{ slug: "cut", name: "دستکش ضد برش", desc: "ایمن در برابر تیغه‌ها و فلزات تیز." },
{ slug: "leather", name: "دستکش چرم", desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری." },
{ slug: "acid", name: "دستکش ضد اسید", desc: "محافظت کامل در برابر اسیدها و بازها." },
{ slug: "solvent", name: "دستکش ضد حلال", desc: "مقاومت بالا در برابر تماس با مواد شیمیایی." },
],
products: [
{
code: "IP-G01",
group: "cut",
name: "دستکش ضد برش لاتکسی",
en: "LATEX CUT-RESISTANT GLOVE",
desc: "ایمن در برابر تیغه‌ها و فلزات تیز.",
specs: ["ضد برش", "پوشش لاتکس"],
image: "/images/products/gloves/cut/1.webp",
},
{
code: "IP-G02",
group: "cut",
name: "دستکش ضد برش مدل ۲",
en: "CUT-RESISTANT GLOVE",
desc: "ایمن در برابر تیغه‌ها و فلزات تیز.",
specs: ["ضد برش"],
image: "/images/products/gloves/cut/2.webp",
},
{
code: "IP-G03",
group: "cut",
name: "دستکش ضد برش مدل ۳",
en: "CUT-RESISTANT GLOVE",
desc: "ایمن در برابر تیغه‌ها و فلزات تیز.",
specs: ["ضد برش"],
image: "/images/products/gloves/cut/3.webp",
},
{
code: "IP-G04",
group: "cut",
name: "دستکش ضد برش استادکار ۱۲ جفتی",
en: "OSTADKAR CUT-RESISTANT GLOVE",
desc: "ایمن در برابر تیغه‌ها و فلزات تیز.",
specs: ["ضد برش", "استادکار", "بسته ۱۲ جفتی"],
image: "/images/products/gloves/cut/4.webp",
},
{
code: "IP-G05",
group: "cut",
name: "دستکش ضد برش تانگ وانگ",
en: "TANG WANG CUT-RESISTANT GLOVE",
desc: "ایمن در برابر تیغه‌ها و فلزات تیز.",
specs: ["ضد برش", "تانگ وانگ"],
image: "/images/products/gloves/cut/5.webp",
},
{
code: "IP-G06",
group: "leather",
name: "دستکش چرم مدل ۰۷",
en: "LEATHER GLOVE",
desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری.",
specs: ["چرم"],
image: "/images/products/gloves/leather/1.webp",
},
{
code: "IP-G07",
group: "leather",
name: "دستکش چرم BMW",
en: "BMW LEATHER GLOVE",
desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری.",
specs: ["چرم", "ساق بلند"],
image: "/images/products/gloves/leather/2.webp",
},
{
code: "IP-G08",
group: "leather",
name: "دستکش کف چرم دوبل ساق پارچه‌ای",
en: "DOUBLE-PALM LEATHER GLOVE, FABRIC CUFF",
desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری.",
specs: ["کف چرم دوبل", "ساق پارچه‌ای"],
image: "/images/products/gloves/leather/3.webp",
},
{
code: "IP-G09",
group: "leather",
name: "دستکش کف چرم دوبل ساق چرم",
en: "DOUBLE-PALM LEATHER GLOVE, LEATHER CUFF",
desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری.",
specs: ["کف چرم دوبل", "ساق چرم"],
image: "/images/products/gloves/leather/4.webp",
},
{
code: "IP-G10",
group: "leather",
name: "دستکش هوبارت امریکن سیفتی",
en: "AMERICAN SAFETY HOBART GLOVE",
desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری.",
specs: ["چرم", "جوشکاری", "EN 388 / EN 407"],
image: "/images/products/gloves/leather/5.webp",
},
{
code: "IP-G11",
group: "leather",
name: "دستکش هوبارت طرح فرانسه",
en: "FRENCH-STYLE HOBART GLOVE",
desc: "محافظ دست در برابر حرارت، جرقه و سایش در کارهای سنگین و جوشکاری.",
specs: ["چرم", "جوشکاری"],
image: "/images/products/gloves/leather/6.webp",
},
{
code: "IP-G12",
group: "acid",
name: "دستکش ضد اسید مدل ۱",
en: "ACID-RESISTANT GLOVE",
desc: "محافظت کامل در برابر اسیدها و بازها.",
specs: ["ضد اسید"],
image: "/images/products/gloves/acid/1.webp",
},
{
code: "IP-G13",
group: "acid",
name: "دستکش ضد اسید مدل ۲",
en: "ACID-RESISTANT GLOVE",
desc: "محافظت کامل در برابر اسیدها و بازها.",
specs: ["ضد اسید"],
image: "/images/products/gloves/acid/2.webp",
},
{
code: "IP-G14",
group: "acid",
name: "دستکش ضد اسید مدل ۳",
en: "ACID-RESISTANT GLOVE",
desc: "محافظت کامل در برابر اسیدها و بازها.",
specs: ["ضد اسید"],
image: "/images/products/gloves/acid/3.webp",
},
{
code: "IP-G15",
group: "acid",
name: "دستکش ضد اسید مقاوم شیمیایی",
en: "CHEMICAL-RESISTANT GLOVE",
desc: "محافظت کامل در برابر اسیدها و بازها.",
specs: ["ضد اسید", "مقاوم شیمیایی", "ساق بلند"],
image: "/images/products/gloves/acid/4.webp",
},
{
code: "IP-G16",
group: "solvent",
name: "دستکش ضد حلال مدل ۱۳",
en: "SOLVENT-RESISTANT GLOVE",
desc: "مقاومت بالا در برابر تماس با مواد شیمیایی.",
specs: ["ضد حلال"],
image: "/images/products/gloves/solvent/1.webp",
},
{
code: "IP-G17",
group: "solvent",
name: "دستکش ماکسی درای پلاس 56-530",
en: "MAXIDRY PLUS 56-530",
desc: "مقاومت بالا در برابر تماس با مواد شیمیایی.",
specs: ["ضد حلال", "MaxiDry Plus"],
image: "/images/products/gloves/solvent/2.webp",
},
{
code: "IP-G18",
group: "solvent",
name: "دستکش ضد حلال نیتریلی",
en: "NITRILE SOLVENT-RESISTANT GLOVE",
desc: "مقاومت بالا در برابر تماس با مواد شیمیایی.",
specs: ["ضد حلال", "نیتریل"],
image: "/images/products/gloves/solvent/3.webp",
},
{
code: "IP-G19",
group: "solvent",
name: "دستکش نیتریل آزمایشگاهی ضد حلال NM Safety",
en: "NM SAFETY NITRILE LAB GLOVE",
desc: "مقاومت بالا در برابر تماس با مواد شیمیایی.",
specs: ["ضد حلال", "نیتریل", "آزمایشگاهی"],
image: "/images/products/gloves/solvent/4.webp",
},
],
},
{
slug: "safety-helmets",
code: "IP-C04",
name: "کلاه ایمنی",
en: "SAFETY HELMETS",
shortDesc: "کلاه‌های ایمنی کارگری، مهندسی، کار در ارتفاع و کپ ایمنی؛ مقاوم در برابر ضربه و سقوط اجسام.",
fullDesc: "انواع کلاه ایمنی صنعتی شامل مدل‌های کارگری، مهندسی، کار در ارتفاع با بند چانه قابل تنظیم و کپ ایمنی سبک. با پوسته ضربه‌گیر مقاوم، رگلاژ داخلی قابل تنظیم و تنوع رنگی استاندارد HSE.",
icon: "HardHat",
groups: [
{ slug: "worker", name: "کلاه کارگری", desc: "محافظت از سر در محیط‌های صنعتی و کارگاه‌ها، مقاوم در برابر ضربه و سقوط اجسام." },
{ slug: "engineering", name: "کلاه مهندسی", desc: "مناسب محیط‌های اداری و صنعتی سبک، راحت و شکیل با تهویه مناسب." },
{ slug: "height", name: "کار در ارتفاع", desc: "دارای بند چانه قابل تنظیم برای ثبات بیشتر هنگام کار در ارتفاع." },
{ slug: "cap", name: "کپ ایمنی", desc: "سبک و راحت، مناسب استفاده روزمره در محیط‌های صنعتی و اداری." },
],
products: [
{
code: "IP-H01",
group: "worker",
name: "کلاه ایمنی کارگری آبی",
en: "WORKER SAFETY HELMET",
desc: "محافظت از سر در محیط‌های صنعتی و کارگاه‌ها، مقاوم در برابر ضربه و سقوط اجسام.",
specs: ["پوسته ضربه‌گیر", "رگلاژ قابل تنظیم"],
image: "/images/products/helmets/2.webp",
},
{
code: "IP-H02",
group: "engineering",
name: "کلاه ایمنی مهندسی پادکس",
en: "PADEX ENGINEERING HELMET",
desc: "مناسب محیط‌های اداری و صنعتی سبک، راحت و شکیل با تهویه مناسب.",
specs: ["پادکس", "تهویه مناسب", "رگلاژ قابل تنظیم"],
image: "/images/products/helmets/11.webp",
},
{
code: "IP-H03",
group: "engineering",
name: "کلاه ایمنی مهندسی پادکس PADX",
en: "PADEX PADX ENGINEERING HELMET",
desc: "مناسب محیط‌های اداری و صنعتی سبک، راحت و شکیل با تهویه مناسب.",
specs: ["پادکس", "تهویه مناسب", "رگلاژ قابل تنظیم"],
image: "/images/products/helmets/12.webp",
},
{
code: "IP-H04",
group: "engineering",
name: "کلاه ایمنی مهندس پادکس (نمای داخلی)",
en: "PADEX HELMET HARNESS",
desc: "مناسب محیط‌های اداری و صنعتی سبک، راحت و شکیل با تهویه مناسب.",
specs: ["پادکس", "یراق داخلی", "رگلاژ قابل تنظیم"],
image: "/images/products/helmets/10.webp",
},
{
code: "IP-H05",
group: "height",
name: "کلاه ایمنی کار در ارتفاع با عینک",
en: "HEIGHT HELMET WITH VISOR",
desc: "دارای بند چانه قابل تنظیم برای ثبات بیشتر هنگام کار در ارتفاع.",
specs: ["بند چانه", "عینک داخلی", "رگلاژ قابل تنظیم"],
image: "/images/products/helmets/1.webp",
},
{
code: "IP-H06",
group: "height",
name: "کلاه ایمنی کار در ارتفاع uvex",
en: "UVEX HEIGHT HELMET",
desc: "دارای بند چانه قابل تنظیم برای ثبات بیشتر هنگام کار در ارتفاع.",
specs: ["uvex", "بند چانه", "تهویه مناسب"],
image: "/images/products/helmets/3.webp",
},
{
code: "IP-H07",
group: "height",
name: "کلاه ایمنی کار در ارتفاع سبز",
en: "HEIGHT SAFETY HELMET",
desc: "دارای بند چانه قابل تنظیم برای ثبات بیشتر هنگام کار در ارتفاع.",
specs: ["بند چانه", "رگلاژ قابل تنظیم"],
image: "/images/products/helmets/4.webp",
},
{
code: "IP-H08",
group: "height",
name: "کلاه ایمنی صنعتی MK8",
en: "MK8 INDUSTRIAL HELMET",
desc: "دارای بند چانه قابل تنظیم برای ثبات بیشتر هنگام کار در ارتفاع.",
specs: ["MK8", "بند چانه", "تهویه مناسب"],
image: "/images/products/helmets/9.webp",
},
{
code: "IP-H09",
group: "cap",
name: "کپ ایمنی ضربه‌گیر",
en: "SAFETY BUMP CAP",
desc: "سبک و راحت، مناسب استفاده روزمره در محیط‌های صنعتی و اداری.",
specs: ["نقاب‌دار", "ضربه‌گیر داخلی", "سبک‌وزن"],
image: "/images/products/helmets/5.webp",
},
],
},
{
slug: "eye-protection",
code: "IP-C05",
name: "عینک ایمنی و صنعتی",
en: "EYE PROTECTION",
shortDesc: "عینک‌های شفاف و دودی و گاگل‌های محافظتی با ویژگی‌های ضد ضربه، ضد خش، ضد بخار و UV.",
fullDesc: "عینک‌های ایمنی صنعتی شامل عینک‌های شفاف، دودی و UV و گاگل‌های کش‌دار از برندهای uvex، توتاص، کاناسیف و تک پلاست. ضد ضربه، ضد خش، ضد بخار و قابل تنظیم برای انواع سایز صورت.",
icon: "Glasses",
groups: [
{ slug: "clear", name: "عینک شفاف", desc: "محافظت از چشم‌ها در برابر برخورد اجسام و ابزار؛ ضد خش با دید واضح." },
{ slug: "tinted", name: "عینک دودی و UV", desc: "محافظت در برابر اشعه مضر خورشید و نور شدید." },
{ slug: "goggle", name: "گاگل", desc: "ضد بخار و ضد ضربه؛ جلوگیری از ایجاد مه در محیط‌های گرم یا مرطوب." },
],
products: [
{
code: "IP-E01",
group: "clear",
name: "عینک ایمنی شفاف دسته قابل تنظیم",
en: "ADJUSTABLE CLEAR SAFETY GLASSES",
desc: "محافظت از چشم‌ها در برابر برخورد اجسام و ابزار؛ قابل تنظیم برای انواع سایز صورت.",
specs: ["ضد ضربه", "قابل تنظیم"],
image: "/images/products/eyewear/1.webp",
},
{
code: "IP-E02",
group: "clear",
name: "عینک ایمنی روطبی",
en: "OVER-SPEC SAFETY GLASSES",
desc: "محافظت از چشم‌ها در برابر برخورد اجسام و ابزار؛ قابل استفاده روی عینک طبی.",
specs: ["ضد ضربه", "روطبی"],
image: "/images/products/eyewear/4.webp",
},
{
code: "IP-E03",
group: "clear",
name: "عینک ایمنی uvex i-5",
en: "UVEX I-5 SAFETY GLASSES",
desc: "محافظت از چشم‌ها در برابر برخورد اجسام و ابزار؛ ضد خش با دید واضح.",
specs: ["uvex", "ضد ضربه", "ضد خش"],
image: "/images/products/eyewear/5.webp",
},
{
code: "IP-E04",
group: "clear",
name: "عینک شیشه سفید تک پلاست",
en: "TAK PLAST CLEAR GLASSES",
desc: "محافظت از چشم‌ها در برابر برخورد اجسام و ابزار؛ دارای محافظ کناری.",
specs: ["تک پلاست", "محافظ کناری"],
image: "/images/products/eyewear/11.webp",
},
{
code: "IP-E05",
group: "tinted",
name: "عینک ایمنی uvex دودی",
en: "UVEX TINTED SAFETY GLASSES",
desc: "محافظت در برابر اشعه مضر خورشید و نور شدید.",
specs: ["uvex", "شیشه UV", "ضد ضربه"],
image: "/images/products/eyewear/6.webp",
},
{
code: "IP-E06",
group: "tinted",
name: "عینک ایمنی توتاص AT113",
en: "TOTAS AT113",
desc: "محافظت در برابر اشعه مضر خورشید و نور شدید.",
specs: ["توتاص", "شیشه UV", "ضد ضربه"],
image: "/images/products/eyewear/7.webp",
},
{
code: "IP-E07",
group: "tinted",
name: "عینک ایمنی کاناسیف 20105",
en: "CANASAFE 20105",
desc: "محافظت در برابر اشعه مضر و نور شدید جوشکاری.",
specs: ["کاناسیف", "شیشه UV", "قابل تنظیم"],
image: "/images/products/eyewear/9.webp",
},
{
code: "IP-E08",
group: "tinted",
name: "عینک توتاص AT116",
en: "TOTAS AT116",
desc: "محافظت در برابر اشعه مضر خورشید و نور شدید.",
specs: ["توتاص", "شیشه UV", "روطبی"],
image: "/images/products/eyewear/10.webp",
},
{
code: "IP-E09",
group: "goggle",
name: "گاگل uvex ultravision",
en: "UVEX ULTRAVISION GOGGLE",
desc: "ضد بخار و ضد ضربه؛ جلوگیری از ایجاد مه در محیط‌های گرم یا مرطوب.",
specs: ["uvex", "ضد بخار", "کش‌دار"],
image: "/images/products/eyewear/2.webp",
},
{
code: "IP-E10",
group: "goggle",
name: "گاگل ایمنی کش‌دار",
en: "SAFETY GOGGLE",
desc: "ضد بخار و ضد ضربه؛ جلوگیری از ایجاد مه در محیط‌های گرم یا مرطوب.",
specs: ["ضد بخار", "کش‌دار"],
image: "/images/products/eyewear/3.webp",
},
{
code: "IP-E11",
group: "goggle",
name: "گاگل ایمنی توتاص ATBM",
en: "TOTAS ATBM GOGGLE",
desc: "ضد بخار و ضد ضربه؛ جلوگیری از ایجاد مه در محیط‌های گرم یا مرطوب.",
specs: ["توتاص", "ضد بخار", "کش‌دار"],
image: "/images/products/eyewear/8.webp",
},
],
},
{
slug: "hearing-protection",
code: "IP-C06",
name: "حفاظت شنوایی",
en: "HEARING PROTECTION",
shortDesc: "ایرماف روگوشی با کاهش ۲۸ دسی‌بل و ایرپلاگ‌های اسفنجی و سیلیکونی برای محیط‌های پرسروصدا.",
fullDesc: "تجهیزات حفاظت شنوایی شامل ایرماف (محافظ روگوشی) با کاهش تراز صدا تا ۲۸ دسی‌بل و ایرپلاگ (داخل‌گوشی) در مدل‌های اسفنجی فرم‌گیر و پله‌ای سیلیکونی. مناسب محیط‌های با آلودگی صوتی بالای ۸۵ دسی‌بل، کمپرسورخانه‌ها و خطوط تولید سنگین.",
icon: "Ear",
groups: [
{ slug: "earmuff", name: "ایرماف", desc: "کاهش صدا تا ۲۸ دسی‌بل، مناسب محیط‌های صنعتی و کارگاهی، قابل تنظیم و راحت برای استفاده طولانی." },
{ slug: "earplug", name: "ایرپلاگ", desc: "محافظت در برابر صداهای شدید و نویز محیط، سبک و راحت، مدل‌های یکبار مصرف و چندبار مصرف." },
],
products: [
{
code: "IP-HP01",
group: "earmuff",
name: "ایرماف هلبرگ",
en: "HELLBERG EARMUFF",
desc: "کاهش صدا تا ۲۸ دسی‌بل، مناسب محیط‌های صنعتی و کارگاهی، قابل تنظیم و راحت برای استفاده طولانی.",
specs: ["Hellberg", "هدبند قابل تنظیم", "بالشتک نرم"],
image: "/images/products/hearing/1.webp",
},
{
code: "IP-HP02",
group: "earmuff",
name: "ایرماف uvex K2",
en: "UVEX K2 EARMUFF",
desc: "کاهش صدا تا ۲۸ دسی‌بل، مناسب محیط‌های صنعتی و کارگاهی، قابل تنظیم و راحت برای استفاده طولانی.",
specs: ["uvex", "هدبند قابل تنظیم", "بالشتک نرم"],
image: "/images/products/hearing/2.webp",
},
{
code: "IP-HP03",
group: "earmuff",
name: "ایرماف بوفالو 110",
en: "BUFFALO 110 EARMUFF",
desc: "کاهش صدا تا ۲۸ دسی‌بل، مناسب محیط‌های صنعتی و کارگاهی، قابل تنظیم و راحت برای استفاده طولانی.",
specs: ["بوفالو", "هدبند قابل تنظیم", "بالشتک نرم"],
image: "/images/products/hearing/4.webp",
},
{
code: "IP-HP04",
group: "earmuff",
name: "گوشی صداگیر 3M",
en: "3M EARMUFF",
desc: "کاهش صدا تا ۲۸ دسی‌بل، مناسب محیط‌های صنعتی و کارگاهی، قابل تنظیم و راحت برای استفاده طولانی.",
specs: ["3M", "هدبند قابل تنظیم", "بالشتک نرم"],
image: "/images/products/hearing/8.webp",
},
{
code: "IP-HP05",
group: "earplug",
name: "ایرپلاگ کاستا مکس فیت MAXFIT",
en: "COSTA MAXFIT EARPLUG",
desc: "محافظت در برابر صداهای شدید و نویز محیط، سبک و راحت.",
specs: ["سیلیکونی پله‌ای", "بنددار", "چندبار مصرف"],
image: "/images/products/hearing/3.webp",
},
{
code: "IP-HP06",
group: "earplug",
name: "ایرپلاگ اسفنجی Bilsom 303L",
en: "BILSOM 303L FOAM EARPLUG",
desc: "محافظت در برابر صداهای شدید و نویز محیط، سبک و راحت.",
specs: ["اسفنجی", "بنددار / بدون بند", "یکبار مصرف"],
image: "/images/products/hearing/5.webp",
},
{
code: "IP-HP07",
group: "earplug",
name: "ایرپلاگ اسفنجی ماگما",
en: "MAGMA FOAM EARPLUG",
desc: "محافظت در برابر صداهای شدید و نویز محیط، سبک و راحت.",
specs: ["اسفنجی", "یکبار مصرف"],
image: "/images/products/hearing/6.webp",
},
{
code: "IP-HP08",
group: "earplug",
name: "ایرپلاگ مکس فیت با قاب",
en: "MAXFIT EARPLUG WITH CASE",
desc: "محافظت در برابر صداهای شدید و نویز محیط، سبک و راحت.",
specs: ["سیلیکونی پله‌ای", "بنددار", "قاب نگهداری"],
image: "/images/products/hearing/7.webp",
},
],
},
{
slug: "respiratory-protection",
code: "IP-C07",
name: "حفاظت تنفسی",
en: "RESPIRATORY PROTECTION",
shortDesc: "ماسک‌های نیم‌صورت، تمام‌صورت، شیمیایی، P2/P3 و فیلتردار برای محافظت در برابر گازها و ذرات.",
fullDesc: "تجهیزات حفاظت تنفسی شامل ماسک‌های نیم‌صورت، تمام‌صورت، شیمیایی با کارتریج تخصصی، ماسک‌های فیلتردار P2/P3 برای ذرات میکرونی، ماسک‌های با فیلتر تعویضی اقتصادی و ماسک‌های سه‌لایه بهداشتی. مناسب کار با حلال‌های فرار، غبارهای معدنی، رنگ‌پاشی و خطوط شیمیایی.",
icon: "ShieldPlus",
groups: [
{ slug: "half", name: "ماسک نیم‌صورت", desc: "پوشش‌دهی بینی و دهان با فیلتر قابل تعویض؛ مناسب محیط‌های صنعتی با آلودگی متوسط و بخارات شیمیایی." },
{ slug: "full", name: "ماسک تمام‌صورت", desc: "محافظت کامل از صورت و چشم‌ها، مناسب کار با مواد شیمیایی و محیط‌های پرخطر." },
{ slug: "particulate", name: "ماسک فیلتردار P2/P3", desc: "محافظت در برابر گرد و غبار و ذرات معلق در هوا." },
{ slug: "medical", name: "ماسک سه‌لایه", desc: "ماسک سبک و راحت، مناسب استفاده روزمره و محیط‌های با آلودگی کم." },
],
products: [
{
code: "IP-R01",
group: "half",
name: "ماسک نیم‌صورت با فیلتر تعویضی",
en: "HALF-FACE RESPIRATOR WITH FILTERS",
desc: "پوشش‌دهی بینی و دهان با فیلتر قابل تعویض برای استفاده طولانی‌مدت.",
specs: ["نیم‌صورت", "فیلتر تعویضی", "دو کارتریج"],
image: "/images/products/respiratory/5.webp",
},
{
code: "IP-R02",
group: "half",
name: "ماسک نیم‌صورت نورث 5500",
en: "NORTH 5500 HALF MASK",
desc: "پوشش‌دهی بینی و دهان، مناسب محیط‌های صنعتی با آلودگی متوسط.",
specs: ["North", "نیم‌صورت", "فیلتر تعویضی"],
image: "/images/products/respiratory/6.webp",
},
{
code: "IP-R03",
group: "half",
name: "ماسک شیمیایی نیم‌صورت 3M",
en: "3M HALF-FACE RESPIRATOR",
desc: "محافظت در برابر بخارات و گازهای شیمیایی با کارتریج و فیلتر قابل تعویض.",
specs: ["3M", "کارتریج شیمیایی", "فیلتر تعویضی"],
image: "/images/products/respiratory/7.webp",
},
{
code: "IP-R04",
group: "half",
name: "ماسک نیم‌صورت نورث 7700",
en: "NORTH 7700 HALF MASK",
desc: "پوشش‌دهی بینی و دهان با بدنه سیلیکونی، مناسب استفاده طولانی‌مدت.",
specs: ["North", "سیلیکونی", "فیلتر تعویضی"],
image: "/images/products/respiratory/11.webp",
},
{
code: "IP-R05",
group: "half",
name: "ماسک نیم‌صورت نورث 7700 (نمای جانبی)",
en: "NORTH 7700 HALF MASK",
desc: "پوشش‌دهی بینی و دهان با بدنه سیلیکونی، مناسب استفاده طولانی‌مدت.",
specs: ["North", "سیلیکونی", "فیلتر تعویضی"],
image: "/images/products/respiratory/10.webp",
},
{
code: "IP-R06",
group: "full",
name: "ماسک تمام‌صورت",
en: "FULL-FACE RESPIRATOR",
desc: "محافظت کامل از صورت و چشم‌ها، مناسب کار با مواد شیمیایی و محیط‌های پرخطر.",
specs: ["تمام‌صورت", "شیشه ضد ضربه", "فیلتر تعویضی"],
image: "/images/products/respiratory/4.webp",
},
{
code: "IP-R07",
group: "full",
name: "ماسک تنفسی دراگر",
en: "DRÄGER FULL-FACE RESPIRATOR",
desc: "محافظت کامل از صورت و چشم‌ها، مناسب کار با مواد شیمیایی و محیط‌های پرخطر.",
specs: ["Dräger", "تمام‌صورت", "فیلتر چندمنظوره"],
image: "/images/products/respiratory/8.webp",
},
{
code: "IP-R08",
group: "particulate",
name: "ماسک فیلتردار تاشو",
en: "FOLDABLE PARTICULATE MASK",
desc: "محافظت در برابر گرد و غبار و ذرات معلق در هوا.",
specs: ["P2", "تاشو", "یکبار مصرف"],
image: "/images/products/respiratory/1.webp",
},
{
code: "IP-R09",
group: "particulate",
name: "ماسک فیلتردار سوپاپ‌دار",
en: "VALVED PARTICULATE MASK",
desc: "محافظت در برابر گرد و غبار و ذرات معلق در هوا.",
specs: ["P2 / P3", "سوپاپ بازدمی", "یکبار مصرف"],
image: "/images/products/respiratory/2.webp",
},
{
code: "IP-R10",
group: "particulate",
name: "ماسک فیلتردار دراگر سوپاپ‌دار",
en: "DRÄGER VALVED PARTICULATE MASK",
desc: "محافظت در برابر گرد و غبار و ذرات معلق در هوا.",
specs: ["Dräger", "سوپاپ بازدمی", "P2 / P3"],
image: "/images/products/respiratory/3.webp",
},
{
code: "IP-R11",
group: "medical",
name: "ماسک سه‌لایه پزشکی",
en: "THREE-LAYER MEDICAL MASK",
desc: "ماسک سبک و راحت، مناسب استفاده روزمره و محیط‌های با آلودگی کم.",
specs: ["سه‌لایه", "یکبار مصرف", "بسته ۵۰ عددی"],
image: "/images/products/respiratory/9.webp",
},
],
},
{
slug: "traffic-equipment",
code: "IP-C08",
name: "تجهیزات ترافیکی و ایمنی محیطی",
en: "TRAFFIC & SITE SAFETY",
shortDesc: "مخروط، نیوجرسی، استوانه، سرعت‌گیر، آینه محدب و سایر تجهیزات ایمن‌سازی محوطه صنعتی.",
fullDesc: "تجهیزات ترافیکی و ایمنی محیطی شامل مخروط ترافیکی، نیوجرسی پلاستیکی، استوانه و بولارد، چراغ و تابلوهای هشداردهنده، باتوم ترافیکی، نوارهای خطر، سرعت‌گیر لاستیکی، آینه‌های محدب، محافظ گوشه ستون و گل‌میخ خورشیدی. مناسب ایمن‌سازی محوطه کارخانه، انبارها، رمپ‌ها و پارکینگ‌ها.",
icon: "TriangleAlert",
products: [
{
code: "IP-T01",
name: "مخروط ترافیکی",
en: "TRAFFIC CONE",
desc: "PVC انعطاف‌پذیر با شبرنگ‌های استاندارد روز و شب؛ مقاوم در برابر واژگونی و ضربه خودرو.",
specs: ["PVC انعطاف‌پذیر", "شبرنگ استاندارد", "مقاوم به واژگونی", "قابل رؤیت شبانه"],
},
{
code: "IP-T02",
name: "نیوجرسی پلاستیکی",
en: "NEW JERSEY BARRIER",
desc: "بدنه پلی‌اتیلنی مدولار قابل اتصال با قابلیت پرشوندگی با آب یا ماسه جهت تثبیت و ایجاد حائل.",
specs: ["پلی‌اتیلن مدولار", "قابل اتصال", "پرشدنی با آب/ماسه", "مقاوم UV"],
},
{
code: "IP-T03",
name: "استوانه ترافیکی",
en: "TRAFFIC BOLLARD",
desc: "پلی‌اورتان ارتجاعی انعطاف‌پذیر پس از ضربه؛ مجهز به حلقه‌های شبرنگ هشدار برای تفکیک مسیر.",
specs: ["پلی‌اورتان ارتجاعی", "بازگشت پس از ضربه", "شبرنگ هشدار", "نصب آسان"],
},
{
code: "IP-T04",
name: "چراغ و تابلوی هشدار",
en: "WARNING LIGHT & SIGN",
desc: "چراغ‌های چشمک‌زن سولار، تابلوی دستی ایست/حرکت و تابلوهای علائم هشداردهنده ترافیکی.",
specs: ["سولار / باتری", "LED چشمک‌زن", "تابلوی Stop/Go", "علائم استاندارد"],
},
{
code: "IP-T05",
name: "باتوم ترافیکی",
en: "TRAFFIC BATON",
desc: "باتوم LED دار دستی جهت هدایت ترافیک در شب و محیط‌های کم‌نور؛ سبک و ارگونومیک.",
specs: ["LED داخلی", "قابل رؤیت شبانه", "سبک‌وزن", "ارگونومیک"],
},
{
code: "IP-T06",
name: "نوار خطر",
en: "CAUTION TAPE",
desc: "نوار شطرنجی و خط‌کشی زرد/قرمز هشدار محوطه گودبرداری و مناطق خطرناک با رول‌های بازتابنده نور.",
specs: ["زرد / قرمز هشدار", "بازتابنده نور", "رول بلند", "مقاوم به پارگی"],
},
{
code: "IP-T07",
name: "سرعت‌گیر لاستیکی",
en: "RUBBER SPEED BUMP",
desc: "قطعات لاستیکی سنگین مدولار با مقاومت وزنی بالا و المان‌های بازتابش شبانه؛ نصب آسان.",
specs: ["لاستیکی مدولار", "مقاومت وزنی بالا", "بازتاب شبانه", "نصب پیچی"],
},
{
code: "IP-T08",
name: "آینه محدب ترافیکی",
en: "CONVEX TRAFFIC MIRROR",
desc: "آینه نشکن فریم‌دار و کلاه‌دار جهت پوشش نقاط کور پیچ‌ها، تقاطع‌ها و درب انبار.",
specs: ["نشکن", "فریم‌دار و کلاه‌دار", "پوشش نقاط کور", "مقاوم به آب و باد"],
},
{
code: "IP-T09",
name: "محافظ گوشه ستون",
en: "CORNER GUARD",
desc: "ضربه‌گیر لاستیکی شبرنگ‌دار جهت نصب روی ستون‌ها برای ممانعت از آسیب لیفتراک و خودروهای سنگین.",
specs: ["لاستیکی ضربه‌گیر", "شبرنگ‌دار", "نصب دیواری", "محافظ ستون"],
},
{
code: "IP-T10",
name: "گل‌میخ ترافیکی خورشیدی",
en: "SOLAR ROAD STUD",
desc: "بدنه آلومینیومی مستحکم مجهز به پنل خورشیدی و LED جهت تعیین مسیر و خط‌کشی شبانه.",
specs: ["آلومینیوم مستحکم", "پنل خورشیدی", "LED", "مقاوم به عبور خودرو"],
},
],
},
];
//# sourceMappingURL=categories.js.map
File diff suppressed because one or more lines are too long
+268
View File
@@ -0,0 +1,268 @@
export const SECTIONS = {
settings: {
name: "ایمن پیشگامان",
nameEn: "Imen Pishgaman Safety",
title: "ایمن پیشگامان | تجهیزات ایمنی و حفاظت فردی صنعتی",
description: "ایمن پیشگامان — تأمین‌کننده تخصصی تجهیزات حفاظت فردی (PPE)، بازرسی، آموزش و راهکارهای ایمنی صنعتی برای سازمان‌هایی که جان انسان‌ها را جدی می‌گیرند.",
phone: "+98-21-91008800",
phoneDisplay: "۰۲۱ - ۹۱ ۰۰ ۸۸ ۰۰",
email: "info@imenpishgaman.ir",
address: {
street: "خیابان کارگر شمالی، خیابان فر، کوچه دوم، پلاک ۱۲",
locality: "تهران",
country: "IR",
},
workingHours: "شنبه تا پنجشنبه — ۸:۰۰ تا ۱۷:۰۰",
openingHours: {
days: ["Saturday", "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday"],
opens: "08:00",
closes: "17:00",
},
foundingDate: "2007",
socials: [
{ type: "website", url: "/" },
{ type: "email", url: "mailto:info@imenpishgaman.ir" },
{ type: "phone", url: "tel:+982191008800" },
],
ogImage: {
url: "asset:hero.jpg",
alt: "کارگر صنعتی با تجهیزات ایمنی کامل",
width: 1792,
height: 1008,
},
},
hero: {
enabled: true,
badge: "تأمین‌کننده رسمی تجهیزات حفاظت فردی (PPE)",
title: "ایمنی یعنی",
titleHighlight: "بازگشت به خانه",
intro: "ایمن پیشگامان با بیش از ۱۸ سال تجربه، تأمین‌کننده تخصصی تجهیزات ایمنی و حفاظت فردی برای سازمان‌هایی است که جان انسان‌ها را جدی می‌گیرند؛ از کلاه ایمنی تا هارنس نجات، از مشاوره تا بازرسی و آموزش.",
primaryCta: { label: "درخواست مشاوره رایگان", href: "#contact" },
secondaryCta: { label: "مشاهده محصولات", href: "#products" },
chips: [
{ icon: "ShieldCheck", label: "ISO 9001:2015" },
{ icon: "BadgeCheck", label: "CE CERTIFIED" },
{ icon: "Award", label: "EN STANDARDS" },
],
miniStats: [
{ value: "۱۸+", label: "سال تجربه در صنعت ایمنی" },
{ value: "۸۵۰+", label: "سازمان تحت پوشش" },
{ value: "۹۸٪", label: "رضایت مشتریان" },
],
image: { url: "asset:hero.jpg", alt: "کارگر صنعتی با تجهیزات ایمنی کامل" },
lastInspection: "۱۴۰۴/۰۸/۱۲",
},
tape: {
enabled: true,
items: [
"ISO 9001:2015",
"CE CERTIFIED",
"گارانتی اصالت کالا",
"تحویل سراسری کشوری",
"مشاوره و بازرسی تخصصی رایگان",
"EN STANDARDS",
"پشتیبانی ۲۴/۷ قراردادهای سازمانی",
"تست نمونه قبل از خرید",
],
},
stats: {
enabled: true,
items: [
{ end: 18, suffix: "+", label: "سال تجربه در صنعت ایمنی", note: "SINCE 2007" },
{ end: 2400, suffix: "+", label: "کد کالای ایمنی", note: "PPE CATALOG" },
{ end: 850, suffix: "+", label: "مشتری سازمانی فعال", note: "B2B CLIENTS" },
{ end: 98, suffix: "٪", label: "رضایت مشتریان", note: "SATISFACTION" },
],
},
productsIntro: {
enabled: true,
head: {
tag: "۰۱ — محصولات",
title: "خط اول دفاع،\nتجهیزات ماست",
highlight: "",
desc: "هر محصول پیش از عرضه، زیر ذره‌بین کنترل کیفیت و تطبیق با استانداردهای جهانی قرار می‌گیرد.",
},
ctaLabel: "دریافت کاتالوگ کامل",
trust: [
{
icon: "BadgeCheck",
title: "گارانتی اصالت کالا",
desc: "تمام محصولات با فاکتور رسمی و کد رهگیری اصالت",
},
{
icon: "PackageCheck",
title: "تست نمونه قبل از خرید",
desc: "نمونه‌های نمایشی برای ارزیابی تیم HSE شما",
},
{
icon: "ShieldCheck",
title: "امکان قرارداد سالانه",
desc: "قیمت ثابت و تأمین مستمر برای سازمان‌های بزرگ",
},
],
},
about: {
enabled: true,
head: {
tag: "۰۲ — درباره ما",
title: "ایمنی برای ما شعار نیست؛",
highlight: "قرارداد است.",
desc: "",
},
body: "از سال ۱۳۸۶، زمانی که اولین کلاه ایمنی را به یک کارگاه کوچک در جنوب تهران فروختیم، باور ما همین یک جمله بود: پشت هر تجهیز ایمنی، یک خانواده هست که منتظر بازگشت عزیزش است. امروز با بیش از ۸۵۰ سازمان، از پالایشگاه‌ها تا معادن و سایت‌های ساختمانی، در کنار کسانی هستیم که ایمنی را یک خط قرمز می‌دانند.",
image: { url: "asset:about.jpg", alt: "انبار تجهیزات ایمنی ایمن پیشگامان" },
badge: { value: "۱۸+", label: "سال حفاظت از\nجان نیروی کار" },
timeline: [
{ year: "۱۳۸۶", text: "تأسیس ایمن پیشگامان در تهران با تمرکز بر تجهیزات حفاظت فردی" },
{ year: "۱۳۹۲", text: "توسعه شبکه توزیع به تمام ۳۱ استان کشور" },
{ year: "۱۳۹۸", text: "راه‌اندازی آزمایشگاه کنترل کیفیت و تست تجهیزات" },
{ year: "۱۴۰۲", text: "افتتاح مرکز تخصصی آموزش و بازرسی HSE" },
],
features: [
{ icon: "Globe", label: "نماینده رسمی ۴۰+ برند جهانی" },
{ icon: "Users", label: "تیم مهندسی و بازرسی HSE" },
{ icon: "Headset", label: "پشتیبانی ۲۴/۷ قراردادها" },
],
},
services: {
enabled: true,
head: {
tag: "۰۳ — خدمات",
title: "فراتر از تأمین؛\nهمراهی کامل ایمنی",
highlight: "",
desc: "ما در ایمن پیشگامان، تجهیزات را تحویل می‌دهیم و کنار شما می‌مانیم؛ از نخستین ارزیابی ریسک تا آخرین تست دوره‌ای.",
},
items: [
{
icon: "ClipboardCheck",
title: "بازرسی و ارزیابی ریسک",
desc: "تیم مهندسی ما با بازدید از سایت شما، خطرات را شناسایی، اولویت‌بندی و برای هر کدام راهکار اجرایی مشخص با برآورد هزینه ارائه می‌دهد.",
items: [
"ارزیابی HAZOP و HAZID",
"شناسایی و اولویت‌بندی خطرات",
"گزارش مدیریتی با راهکار اجرایی",
],
},
{
icon: "GraduationCap",
title: "آموزش تخصصی ایمنی",
desc: "از دوره‌های عمومی تا تربیت مربی؛ آموزش‌های عملی و میدانی که ایمنی را از دفتر کلان‌ها به رفتار روزمره پرسنل تبدیل می‌کند.",
items: [
"دوره‌های عمومی و تخصصی HSE",
"تربیت مربی ایمنی سایت",
"مانور و شبیه‌سازی شرایط اضطراری",
],
},
{
icon: "Gauge",
title: "تست و کالیبراسیون تجهیزات",
desc: "تجهیزات ایمنی فقط وقتی قابل اعتمادند که تست شده باشند. تست دوره‌ای، سرویس و صدور گواهی معتبر را به تیم تخصصی ما بسپارید.",
items: [
"تست هارنس و لاین نجات",
"کالیبراسیون آشکارسازهای گاز",
"سرویس دوره‌ای و صدور گواهی",
],
},
{
icon: "Truck",
title: "تأمین و لجستیک سازمانی",
desc: "با قرارداد سالانه، قیمت‌گذاری شفاف و انبار محلی در سایت شما، نگرانی کمبود تجهیزات را از فهرست دغدغه‌هایتان حذف کنید.",
items: [
"قرارداد سالانه با قیمت ثابت",
"انبار محلی در سایت شما",
"تحویل سراسری در ۴۸ ساعت",
],
},
],
},
standards: {
enabled: true,
head: {
tag: "۰۴ — استانداردها",
title: "مهرتأیید جهانی\nروی هر محصول",
highlight: "",
desc: "ما فقط تجهیزاتی را عرضه می‌کنیم که تأییدیه معتبر بین‌المللی و تست آزمایشگاهی داشته باشند؛ بدون استثنا.",
},
note: "شماره سریال تمام محصولات در پایگاه داده استانداردهای اروپا قابل استعلام است و گواهی تست هر بچ تحویل مشتری می‌شود.",
ctaLabel: "درخواست گواهی تست محصولات",
items: [
{ code: "EN 397", label: "کلاه ایمنی صنعتی" },
{ code: "EN 388", label: "دستکش‌های مکانیکی" },
{ code: "EN 166", label: "محافظ چشم و صورت" },
{ code: "EN 361", label: "هارنس ضدسقوط" },
{ code: "ISO 20345", label: "کفش ایمنی" },
{ code: "ISO 9001", label: "سیستم مدیریت کیفیت" },
],
},
industries: {
enabled: true,
head: {
tag: "۰۵ — صنایع",
title: "حضور در سخت‌ترین\nمیدان‌های کاری",
highlight: "",
desc: "جایی که دمای محیط از ۵۰ درجه گذر می‌کند یا ارتفاع کار به ده‌ها متر می‌رسد، تجهیزات ما باید بی‌نقص عمل کنند — و عمل می‌کنند.",
},
items: [
{ name: "نفت و گاز", nameEn: "OIL & GAS", count: "۱۴۰+", image: { url: "asset:industries/oil-gas.jpg", alt: "نفت و گاز" } },
{ name: "ساختمان و عمران", nameEn: "CONSTRUCTION", count: "۲۱۰+", image: { url: "asset:industries/construction.jpg", alt: "ساختمان و عمران" } },
{ name: "پتروشیمی", nameEn: "PETROCHEMICAL", count: "۹۰+", image: { url: "asset:industries/petrochemical.jpg", alt: "پتروشیمی" } },
{ name: "صنایع معدنی", nameEn: "MINING", count: "۷۵+", image: { url: "asset:industries/mining.jpg", alt: "صنایع معدنی" } },
{ name: "برق و انرژی", nameEn: "POWER & ENERGY", count: "۶۰+", image: { url: "asset:industries/power-energy.jpg", alt: "برق و انرژی" } },
{ name: "حمل‌ونقل و لجستیک", nameEn: "TRANSPORT", count: "۴۵+", image: { url: "asset:industries/transport.jpg", alt: "حمل‌ونقل و لجستیک" } },
],
},
testimonials: {
enabled: true,
head: { tag: "۰۶ — اعتماد", title: "آنچه مشتریان ما می‌گویند", highlight: "", desc: "" },
items: [
{
text: "ایمن پیشگامان فقط تأمین‌کننده نیست؛ شریک ایمنی ماست. بازرسی‌های دوره‌ای و آموزش‌های میدانی‌شان نرخ حوادث سایت را به کمترین رقم تاریخ مجموعه رساند.",
name: "مهندس رضا کاظمی",
role: "مدیر HSE — مجتمع پتروشیمی خلیج فارس",
},
{
text: "کیفیت تجهیزات و سرعت پاسخ‌گویی در سطحی بود که قرارداد سالانه را بدون هیچ تردیدی تمدید کردیم؛ از خط تولید تا دفتر مرکزی.",
name: "سارا محمدی",
role: "سرپرست تدارکات — هلدینگ ساختمانی آرکان",
},
{
text: "۱۴۰ کیلومتر دورتر از سایت، در عرض ۲۴ ساعت تجهیزات حیاتی را تحویل گرفتیم. به این می‌گویند شریک واقعی کاری.",
name: "امیرحسین راد",
role: "مدیر پروژه — صنایع معدنی کاوه",
},
],
},
contact: {
enabled: true,
head: {
tag: "۰۷ — تماس",
title: "بیایید ایمنی را\nبا هم جدی بگیریم",
highlight: "",
desc: "فرم را پر کنید تا کارشناسان ما برای هماهنگی جلسه بازدید رایگان سایت شما تماس بگیرند؛ یا مستقیم با ما در ارتباط باشید.",
},
emergencyTitle: "پاسخ‌گویی اضطراری ۲۴/۷",
emergencyText: "برای مشتریان دارای قرارداد سازمانی، خط ویژه حوادث و تأمین فوری تجهیزات در تمام ساعات شبانه‌روز فعال است.",
formTag: "// فرم درخواست مشاوره",
formTitle: "در کمتر از ۲۴ ساعت\nبا شما تماس می‌گیریم",
successTitle: "درخواست شما ثبت شد",
successText: "کارشناسان ما تا ۲۴ ساعت آینده برای هماهنگی جلسه بازدید با شما تماس می‌گیرند.",
},
footer: {
enabled: true,
about: "تأمین‌کننده تخصصی تجهیزات حفاظت فردی و راهکارهای ایمنی صنعتی؛ همراه سازمان‌ها از سال ۱۳۸۶ در مسیر صفر شدن حوادث کاری.",
copyright: "© ۱۴۰۴ ایمن پیشگامان — تمامی حقوق محفوظ است.",
certLine: "ISO 9001:2015 — CE CERTIFIED PPE SUPPLIER",
emergencyNote: "پشتیبانی اضطراری: ۲۴/۷",
},
};
export const CATEGORY_COVERS = {
workwear: "products/vest.jpg",
"safety-footwear": "products/shoes.jpg",
"protective-gloves": "products/gloves.jpg",
"safety-helmets": "products/helmet.jpg",
"eye-protection": "products/goggles.jpg",
"hearing-protection": "products/hearing.jpg",
"respiratory-protection": "products/respiratory.jpg",
"traffic-equipment": "products/traffic.jpg",
};
//# sourceMappingURL=sections.js.map
File diff suppressed because one or more lines are too long
+270
View File
@@ -0,0 +1,270 @@
import { env } from "../config/env.js";
import { mkdir, readFile, writeFile } from "node:fs/promises";
import path from "node:path";
import { fileURLToPath } from "node:url";
import { normalizeIrMobile, SECTION_KEYS, sectionSchemas } from "@imen/shared";
import { hashPassword } from "../auth/auth.service.js";
import { S3Storage, toWebp } from "../media/s3-storage.js";
import { createPrismaClient } from "../prisma/prisma.service.js";
import { CATEGORIES } from "./data/categories.js";
import { CATEGORY_COVERS, SECTIONS } from "./data/sections.js";
const ASSETS_DIR = process.env.SEED_ASSETS_DIR ??
path.resolve(path.dirname(fileURLToPath(import.meta.url)), "../../seed-assets");
const OVERWRITE_SECTIONS = ["1", "true"].includes(process.env.SEED_OVERWRITE_SECTIONS ?? "");
const prisma = createPrismaClient();
const storage = new S3Storage();
const uploaded = new Map();
async function asset(rel, alt = "") {
const cached = uploaded.get(rel);
if (cached)
return cached;
const key = `seed/${rel.replace(/\.[^.]+$/, "")}.webp`;
let media = await prisma.media.findUnique({ where: { key } });
if (!media) {
const image = await toWebp(await readFile(path.join(ASSETS_DIR, rel)));
try {
await storage.put(key, image.data, "image/webp");
}
catch {
try {
const targetPath = path.resolve(ASSETS_DIR, "../../.s3data/imen-media", key);
await mkdir(path.dirname(targetPath), { recursive: true });
await writeFile(targetPath, image.data);
}
catch { }
}
media = await prisma.media.create({
data: {
key,
mime: "image/webp",
size: image.size,
width: image.width,
height: image.height,
alt,
originalName: path.basename(rel),
},
});
}
const result = { id: media.id, url: storage.publicUrl(key) };
uploaded.set(rel, result);
return result;
}
async function resolveAssets(value) {
if (Array.isArray(value))
return Promise.all(value.map(resolveAssets));
if (value && typeof value === "object") {
const entries = await Promise.all(Object.entries(value).map(async ([k, v]) => {
if (k === "url" && typeof v === "string" && v.startsWith("asset:")) {
return [k, (await asset(v.slice("asset:".length))).url];
}
return [k, await resolveAssets(v)];
}));
return Object.fromEntries(entries);
}
return value;
}
async function seedSections() {
for (const key of SECTION_KEYS) {
const exists = await prisma.siteSection.findUnique({ where: { key } });
if (exists && !OVERWRITE_SECTIONS)
continue;
const data = sectionSchemas[key].parse(await resolveAssets(SECTIONS[key]));
await prisma.siteSection.upsert({ where: { key }, create: { key, data }, update: { data } });
console.log(` section ${key}`);
}
}
async function seedCatalog() {
for (const [ci, c] of CATEGORIES.entries()) {
if (await prisma.category.findUnique({ where: { slug: c.slug } }))
continue;
const coverPath = CATEGORY_COVERS[c.slug];
const cover = coverPath ? await asset(coverPath, c.name) : null;
const category = await prisma.category.create({
data: {
slug: c.slug,
code: c.code,
name: c.name,
nameEn: c.en,
shortDesc: c.shortDesc,
fullDesc: c.fullDesc,
icon: c.icon,
coverImageId: cover?.id ?? null,
sortOrder: ci,
groups: {
create: (c.groups ?? []).map((g, i) => ({
slug: g.slug,
name: g.name,
desc: g.desc,
sortOrder: i,
})),
},
},
include: { groups: true },
});
const groupIds = new Map(category.groups.map((g) => [g.slug, g.id]));
for (const [pi, p] of c.products.entries()) {
const image = p.image ? await asset(p.image.replace(/^\/images\//, ""), p.name) : null;
await prisma.product.create({
data: {
categoryId: category.id,
groupId: p.group ? (groupIds.get(p.group) ?? null) : null,
code: p.code,
slug: p.code.toLowerCase(),
name: p.name,
nameEn: p.en,
desc: p.desc,
specs: [...p.specs],
variants: [...(p.variants ?? [])],
imageId: image?.id ?? null,
sortOrder: pi,
},
});
}
console.log(` category ${c.slug} (${c.products.length} products)`);
}
}
async function seedAdmin() {
if (!env.ADMIN_PHONE || !env.ADMIN_PASSWORD) {
console.log(" ADMIN_PHONE / ADMIN_PASSWORD not set — skipping admin user");
return;
}
const phone = normalizeIrMobile(env.ADMIN_PHONE);
if (!/^09\d{9}$/.test(phone)) {
console.log(` ADMIN_PHONE invalid (${env.ADMIN_PHONE}) — skipping admin user`);
return;
}
const existing = await prisma.adminUser.findUnique({ where: { phone } });
if (existing)
return;
const legacy = await prisma.adminUser.findFirst({
where: { role: "ADMIN", phone: { contains: "@" } },
orderBy: { id: "asc" },
});
if (legacy) {
await prisma.adminUser.update({
where: { id: legacy.id },
data: { phone, name: env.ADMIN_NAME, passwordHash: await hashPassword(env.ADMIN_PASSWORD) },
});
console.log(` admin user migrated to ${phone}`);
return;
}
await prisma.adminUser.create({
data: {
phone,
name: env.ADMIN_NAME,
role: "ADMIN",
passwordHash: await hashPassword(env.ADMIN_PASSWORD),
},
});
console.log(` admin user ${phone}`);
}
async function seedMessages() {
const count = await prisma.contactMessage.count();
if (count > 0)
return;
const samples = [
{
name: "مهندس رضا کاظمی",
org: "مجتمع پتروشیمی خلیج فارس",
phone: "09121112233",
message: "درخواست پیش‌فاکتور ۵۰۰ عدد هارنس ایمنی دو قلاب و کلاه ایمنی استاندارد EN 397 برای فاز ۲ پتروشیمی.",
status: "NEW",
createdAt: new Date(Date.now() - 1000 * 60 * 35),
},
{
name: "سارا محمدی",
org: "هلدینگ ساختمانی آرکان",
phone: "09122223344",
message: "استعلام قیمت و هماهنگی جلسه بازدید جهت عقد قرارداد سالانه تأمین تجهیزات حفاظت فردی ۱۲ پروژه فعال.",
status: "NEW",
createdAt: new Date(Date.now() - 1000 * 60 * 120),
},
{
name: "امیرحسین راد",
org: "صنایع معدنی کاوه",
phone: "09123334455",
message: "درخواست تأمین فوری ۲۰۰ جفت دستکش ایمنی ضدبرش و کفش ایمنی ضداسید و پنجه کامپوزیت برای سایت یزد.",
status: "READ",
createdAt: new Date(Date.now() - 1000 * 60 * 60 * 8),
},
{
name: "مهندس علیرضا بهرامی",
org: "شرکت نفت و گاز پارس",
phone: "09124445566",
message: "تقاضای ارسال کاتالوگ و نمونه عینک ایمنی استاندارد EN 166 و محافظ گوش ایرماف جهت آزمایش واحد HSE.",
status: "NEW",
createdAt: new Date(Date.now() - 1000 * 60 * 60 * 24),
},
{
name: "مریم رضایی",
org: "داروسازی رازک",
phone: "09125556677",
message: "درخواست مشاوره تخصصی در رابطه با ماسک‌های فیلتردار ذرات شیمیایی و لباس‌های یکبار مصرف آزمایشگاهی.",
status: "READ",
createdAt: new Date(Date.now() - 1000 * 60 * 60 * 36),
},
{
name: "مهندس مهدی یوسفی",
org: "فولاد مبارکه اصفهان",
phone: "09126667788",
message: "درخواست برگزاری جلسه فنی برای تمدید قرارداد تأمین لباس کار نسوز، شیلد محافظ صورت و پابند نسوز.",
status: "ARCHIVED",
createdAt: new Date(Date.now() - 1000 * 60 * 60 * 72),
},
{
name: "پیمان نادری",
org: "خطوط لوله و مخابرات نفت",
phone: "09127778899",
message: "استعلام موجودی تجهیزات نجات در فضاهای بسته، سه‌پایه نجات (Tripod) و وینچ همراه با گواهی کالیبراسیون.",
status: "NEW",
createdAt: new Date(Date.now() - 1000 * 60 * 60 * 96),
},
{
name: "دکتر مجید اسدی",
org: "سیمان تهران",
phone: "09128889900",
message: "درخواست برگزاری دوره آموزشی کار در ارتفاع برای پرسنل پیمانکار و بازرسی دوره‌ای خطوط حیات (Lifeline).",
status: "READ",
createdAt: new Date(Date.now() - 1000 * 60 * 60 * 120),
},
];
for (const msg of samples) {
await prisma.contactMessage.create({ data: msg });
}
console.log(` seeded ${samples.length} sample contact messages`);
}
async function main() {
if (env.S3_ENSURE_BUCKET) {
try {
await storage.ensureBucket();
}
catch {
console.log(" ensureBucket skipped");
}
}
console.log("seeding sections…");
await seedSections();
console.log("seeding catalog…");
await seedCatalog();
console.log("seeding admin…");
await seedAdmin();
console.log("seeding messages…");
await seedMessages();
const [categories, products, media] = await Promise.all([
prisma.category.count(),
prisma.product.count(),
prisma.media.count(),
]);
console.log(`done: ${categories} categories, ${products} products, ${media} media files`);
}
try {
await main();
}
catch (e) {
console.error(e);
process.exitCode = 1;
}
finally {
await prisma.$disconnect();
}
//# sourceMappingURL=seed.js.map
File diff suppressed because one or more lines are too long