first
This commit is contained in:
@@ -0,0 +1,45 @@
|
||||
import mongoose from "mongoose";
|
||||
|
||||
import { CategoryModel } from "../../modules/category/models/category.model";
|
||||
|
||||
// Create the Category model
|
||||
|
||||
export async function backfillHierarchy() {
|
||||
try {
|
||||
console.log("Starting hierarchy backfill...");
|
||||
|
||||
// Fetch all categories
|
||||
const categories = await CategoryModel.find();
|
||||
|
||||
// Helper function to recursively update hierarchy
|
||||
const updateHierarchy = async (categoryId: mongoose.Types.ObjectId, parentHierarchy: mongoose.Types.ObjectId[] = []) => {
|
||||
const category = await CategoryModel.findById(categoryId);
|
||||
|
||||
if (!category) return;
|
||||
|
||||
const currentHierarchy = [...parentHierarchy, category._id];
|
||||
|
||||
// Update the category's hierarchy
|
||||
category.hierarchy = currentHierarchy;
|
||||
await category.save();
|
||||
|
||||
// Find child categories and update their hierarchy
|
||||
const childCategories = await CategoryModel.find({ parent: category._id });
|
||||
for (const child of childCategories) {
|
||||
await updateHierarchy(child._id, currentHierarchy);
|
||||
}
|
||||
};
|
||||
|
||||
// Find all top-level categories (categories with no parent)
|
||||
const topLevelCategories = categories.filter((category) => !category.parent);
|
||||
|
||||
// Update hierarchy for all top-level categories and their descendants
|
||||
for (const topCategory of topLevelCategories) {
|
||||
await updateHierarchy(topCategory._id);
|
||||
}
|
||||
|
||||
console.log("Hierarchy backfill completed successfully!");
|
||||
} catch (err) {
|
||||
console.error("Error during hierarchy backfill:", err);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { BlogCategoryModel } from "../../modules/blog/models/blogCategory.model";
|
||||
|
||||
export const blogCategorySeeder = async (logger: Logger) => {
|
||||
try {
|
||||
const categories = [
|
||||
{
|
||||
title_fa: "الکترونیک",
|
||||
slug: "electronics",
|
||||
description: "آخرین اخبار و مقالات مربوط به محصولات الکترونیکی",
|
||||
},
|
||||
{
|
||||
title_fa: "مد و پوشاک",
|
||||
slug: "fashion",
|
||||
description: "مقالات درباره مد، پوشاک و جدیدترین ترندهای فشن",
|
||||
},
|
||||
{
|
||||
title_fa: "خانه و آشپزخانه",
|
||||
slug: "home-kitchen",
|
||||
description: "راهنماییها و مقالات مرتبط با محصولات خانه و آشپزخانه",
|
||||
},
|
||||
{
|
||||
title_fa: "زیبایی و سلامت",
|
||||
slug: "beauty-health",
|
||||
description: "مقالات درباره زیبایی، مراقبت از پوست و سلامت",
|
||||
},
|
||||
{
|
||||
title_fa: "بازی و سرگرمی",
|
||||
slug: "gaming-entertainment",
|
||||
description: "آخرین اخبار و مقالات مربوط به بازیها و سرگرمیها",
|
||||
},
|
||||
];
|
||||
|
||||
logger.info("start seeding Blog categories.");
|
||||
|
||||
await BlogCategoryModel.insertMany(categories);
|
||||
logger.info("Blog categories seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding blog categories:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,239 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { AdminModel } from "../../modules/admin/models/admin.model";
|
||||
import { IBlog } from "../../modules/blog/models/Abstraction/IBlog";
|
||||
import { BlogModel } from "../../modules/blog/models/blog.model";
|
||||
import { BlogCategoryModel } from "../../modules/blog/models/blogCategory.model";
|
||||
import { fakeImageGenerator } from "../data/product";
|
||||
|
||||
export const blogSeeder = async (logger: Logger) => {
|
||||
try {
|
||||
const admin = await AdminModel.findOne({ userName: "defaultAdmin" });
|
||||
const categories = await BlogCategoryModel.find();
|
||||
|
||||
if (categories.length === 0) {
|
||||
logger.error("No blog categories found. Please run the blogCategorySeeder first.");
|
||||
throw new Error("No blog categories found. Please run the blogCategorySeeder first.");
|
||||
}
|
||||
|
||||
const blogs: IBlog[] = [];
|
||||
|
||||
categories.forEach((category) => {
|
||||
switch (category.slug) {
|
||||
case "electronics":
|
||||
blogs.push(
|
||||
{
|
||||
title_fa: "برترین گوشیهای هوشمند سال ۲۰۲۴",
|
||||
slug: "top-smartphones-2024",
|
||||
category: category._id,
|
||||
description: "مروری بر بهترین گوشیهای هوشمند عرضه شده در سال ۲۰۲۴.",
|
||||
content:
|
||||
"در سال ۲۰۲۴، شرکتهای بزرگ تکنولوژی گوشیهای هوشمند جدیدی معرفی کردند که شامل ویژگیها و قابلیتهای پیشرفتهای هستند...",
|
||||
author: admin!._id,
|
||||
tags: ["گوشی", "هوشمند", "تکنولوژی"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "راهنمای خرید لپتاپ مناسب برای دانشجویان",
|
||||
slug: "laptop-buying-guide-for-students",
|
||||
category: category._id,
|
||||
description: "نکاتی که دانشجویان باید هنگام خرید لپتاپ مد نظر داشته باشند.",
|
||||
content:
|
||||
"برای دانشجویان، انتخاب لپتاپ مناسب اهمیت زیادی دارد. عواملی مانند وزن، عمر باتری، قدرت پردازش و قیمت باید در نظر گرفته شوند...",
|
||||
author: admin!._id,
|
||||
tags: ["لپتاپ", "خرید", "راهنما"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "تکنولوژیهای نوین در تلویزیونهای هوشمند",
|
||||
slug: "innovative-technologies-in-smart-tvs",
|
||||
category: category._id,
|
||||
description: "بررسی آخرین تکنولوژیهای موجود در تلویزیونهای هوشمند.",
|
||||
content:
|
||||
"تلویزیونهای هوشمند امروزه با تکنولوژیهای پیشرفتهای مانند 4K، OLED، HDR و سیستمهای هوش مصنوعی مجهز شدهاند که تجربه تماشای شما را بهبود میبخشند...",
|
||||
author: admin!._id,
|
||||
tags: ["تلویزیون", "هوشمند", "تکنولوژی"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
);
|
||||
break;
|
||||
|
||||
case "fashion":
|
||||
blogs.push(
|
||||
{
|
||||
title_fa: "جدیدترین ترندهای مد بهار ۲۰۲۴",
|
||||
slug: "latest-spring-fashion-trends-2024",
|
||||
category: category._id,
|
||||
description: "مروری بر جدیدترین ترندهای مد فصل بهار ۲۰۲۴.",
|
||||
content:
|
||||
"فصل بهار ۲۰۲۴ با ورود رنگهای شاد، الگوهای گلدار و پارچههای سبک همراه است. این ساله تاکید بیشتری بر روی راحتی و استایل کلاسیک دیده میشود...",
|
||||
author: admin!._id,
|
||||
tags: ["مد", "بهار", "ترند"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "چگونه لباس مناسب را برای یک مراسم رسمی انتخاب کنیم",
|
||||
slug: "choosing-suitable-clothes-for-formal-events",
|
||||
category: category._id,
|
||||
description: "نکاتی برای انتخاب لباس مناسب جهت شرکت در مراسمهای رسمی.",
|
||||
content:
|
||||
"انتخاب لباس مناسب برای مراسمهای رسمی میتواند تاثیر زیادی بر روی حضور شما داشته باشد. در این مقاله به بررسی نکاتی که باید هنگام انتخاب لباس رسمی در نظر بگیرید میپردازیم...",
|
||||
author: admin!._id,
|
||||
tags: ["لباس", "رسمی", "راهنما"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "استایلهای مردانه محبوب در سال ۲۰۲۴",
|
||||
slug: "popular-mens-fashion-styles-2024",
|
||||
category: category._id,
|
||||
description: "بررسی استایلهای محبوب و جدید در مد مردانه سال ۲۰۲۴.",
|
||||
content:
|
||||
"مد مردانه در سال ۲۰۲۴ با ترکیب کلاسیک و مدرن، سبکهای متنوعی را ارائه میدهد. از کت و شلوارهای شیک گرفته تا استایلهای کژوال و خیابانی، انتخابهای زیادی وجود دارد...",
|
||||
author: admin!._id,
|
||||
tags: ["مد", "مردانه", "استایل"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
);
|
||||
break;
|
||||
|
||||
case "home-kitchen":
|
||||
blogs.push(
|
||||
{
|
||||
title_fa: "بهترین لوازم آشپزخانه برای هر خانه",
|
||||
slug: "best-kitchen-appliances-for-every-home",
|
||||
category: category._id,
|
||||
description: "نکاتی برای انتخاب بهترین لوازم آشپزخانه مناسب برای خانههای مختلف.",
|
||||
content:
|
||||
"لوازم آشپزخانه نقش مهمی در راحتی و کارایی خانه دارند. از ماشین لباسشویی گرفته تا فرهای هوشمند، انتخاب صحیح میتواند تجربه آشپزی شما را بهبود بخشد...",
|
||||
author: admin!._id,
|
||||
tags: ["آشپزخانه", "لوازم", "راهنما"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "نکات طراحی داخلی خانه برای فضاهای کوچک",
|
||||
slug: "interior-design-tips-for-small-spaces",
|
||||
category: category._id,
|
||||
description: "راهنماییهایی برای طراحی داخلی مناسب فضاهای کوچک خانه.",
|
||||
content:
|
||||
"طراحی داخلی فضاهای کوچک نیازمند استفاده بهینه از فضا و انتخاب مبلمان چندکاره است. در این مقاله به بررسی نکاتی که میتواند به شما در طراحی منزل کوچک کمک کند میپردازیم...",
|
||||
author: admin!._id,
|
||||
tags: ["طراحی داخلی", "خانه کوچک", "نکات"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "روشهای سازماندهی و بهینهسازی فضای آشپزخانه",
|
||||
slug: "organizing-and-optimizing-kitchen-space",
|
||||
category: category._id,
|
||||
description: "نکاتی برای سازماندهی و بهینهسازی فضای آشپزخانه.",
|
||||
content:
|
||||
"یک آشپزخانه سازماندهی شده نه تنها زیبایی دارد بلکه کارایی بیشتری نیز دارد. از استفاده از کشوهای چندمنظوره تا نگهداری مناسب ابزارهای آشپزی، این مقاله به شما کمک میکند تا آشپزخانهتان را بهینه کنید...",
|
||||
author: admin!._id,
|
||||
tags: ["آشپزخانه", "سازماندهی", "بهینهسازی"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
);
|
||||
break;
|
||||
|
||||
case "beauty-health":
|
||||
blogs.push(
|
||||
{
|
||||
title_fa: "رازهای داشتن پوستی سالم و درخشان",
|
||||
slug: "secrets-to-healthy-glowing-skin",
|
||||
category: category._id,
|
||||
description: "نکاتی برای داشتن پوستی سالم، درخشان و زیبا.",
|
||||
content:
|
||||
"پوستی سالم نیازمند مراقبتهای منظم و استفاده از محصولات مناسب است. در این مقاله به بررسی رازهایی که میتواند به شما کمک کند پوستی درخشان و زیبا داشته باشید میپردازیم...",
|
||||
author: admin!._id,
|
||||
tags: ["زیبایی", "سلامت پوست", "راهنما"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "فواید ورزش منظم برای سلامت روانی",
|
||||
slug: "benefits-of-regular-exercise-for-mental-health",
|
||||
category: category._id,
|
||||
description: "بررسی فواید ورزش منظم بر سلامت روانی انسان.",
|
||||
content:
|
||||
"ورزش نه تنها به بهبود سلامت جسمی کمک میکند بلکه تاثیرات مثبت زیادی بر سلامت روانی دارد. از کاهش استرس تا افزایش اعتماد به نفس، در این مقاله به بررسی این فواید میپردازیم...",
|
||||
author: admin!._id,
|
||||
tags: ["ورزش", "سلامت روان", "فواید"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "مراقبت از موهای خشک و آسیبدیده",
|
||||
slug: "caring-for-dry-damaged-hair",
|
||||
category: category._id,
|
||||
description: "نکاتی برای مراقبت و ترمیم موهای خشک و آسیبدیده.",
|
||||
content:
|
||||
"موهای خشک و آسیبدیده نیازمند مراقبت ویژهای هستند. از استفاده از شامپوهای مرطوبکننده تا ماسکهای تغذیهکننده، در این مقاله به بررسی روشهایی که میتواند به ترمیم و تقویت موهای شما کمک کند میپردازیم...",
|
||||
author: admin!._id,
|
||||
tags: ["مو", "زیبایی", "مراقبت"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
);
|
||||
break;
|
||||
|
||||
case "gaming-entertainment":
|
||||
blogs.push(
|
||||
{
|
||||
title_fa: "پربازترین بازیهای ویدیویی سال ۲۰۲۴",
|
||||
slug: "most-played-video-games-2024",
|
||||
category: category._id,
|
||||
description: "مروری بر پربازترین و محبوبترین بازیهای ویدیویی عرضه شده در سال ۲۰۲۴.",
|
||||
content:
|
||||
"سال ۲۰۲۴ با عرضه بازیهای ویدیویی هیجانانگیزی همراه بوده است. از بازیهای اکشن گرفته تا RPGها، این مقاله به معرفی پربازترین و محبوبترین بازیهای سال میپردازد...",
|
||||
author: admin!._id,
|
||||
tags: ["بازی", "ویدیوئی", "مرور"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "نکاتی برای بهبود مهارتهای بازیهای رقابتی",
|
||||
slug: "tips-to-improve-competitive-gaming-skills",
|
||||
category: category._id,
|
||||
description: "راهنماییهایی برای ارتقاء مهارتها و موفقیت در بازیهای رقابتی.",
|
||||
content:
|
||||
"بازیهای رقابتی نیازمند تمرین مداوم و استراتژیهای هوشمندانه هستند. در این مقاله به بررسی نکاتی میپردازیم که میتواند به شما کمک کند مهارتهای بازی رقابتی خود را بهبود ببخشید...",
|
||||
author: admin!._id,
|
||||
tags: ["بازی", "رقابتی", "مهارت"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
{
|
||||
title_fa: "بررسی جدیدترین کنسولهای بازی",
|
||||
slug: "review-of-latest-gaming-consoles",
|
||||
category: category._id,
|
||||
description: "مروری بر جدیدترین کنسولهای بازی و ویژگیهای آنها.",
|
||||
content:
|
||||
"کنسولهای بازی جدید با تکنولوژیهای پیشرفتهای عرضه شدهاند که تجربه بازی را به سطح بالاتری میبرند. در این مقاله به بررسی ویژگیها و عملکرد جدیدترین کنسولهای بازی میپردازیم...",
|
||||
author: admin!._id,
|
||||
tags: ["کنسول", "بازی", "مرور"],
|
||||
imageUrl: fakeImageGenerator(),
|
||||
view: 0,
|
||||
},
|
||||
);
|
||||
break;
|
||||
|
||||
default:
|
||||
console.warn(`No seeder defined for category slug: ${category.slug}`);
|
||||
break;
|
||||
}
|
||||
});
|
||||
|
||||
// Insert Blogs
|
||||
await BlogModel.insertMany(blogs);
|
||||
logger.info("Blogs seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding blogs:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,138 @@
|
||||
import { Types } from "mongoose";
|
||||
|
||||
import { StatusEnum } from "../../common/enums/status.enum";
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { BrandModel } from "../../modules/brand/models/brand.model";
|
||||
import { CategoryModel } from "../../modules/category/models/category.model";
|
||||
|
||||
interface IBrandSeed {
|
||||
title_fa: string;
|
||||
title_en: string;
|
||||
// category: Types.ObjectId;
|
||||
}
|
||||
|
||||
const brandSeedMap: { [key: string]: IBrandSeed[] } = {
|
||||
"گوشی موبایل": [
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "اپل", title_en: "Apple" },
|
||||
{ title_fa: "شیائومی", title_en: "Xiaomi" },
|
||||
{ title_fa: "هواوی", title_en: "Huawei" },
|
||||
{ title_fa: "نوکیا", title_en: "Nokia" },
|
||||
],
|
||||
تبلت: [
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "اپل", title_en: "Apple" },
|
||||
{ title_fa: "مایکروسافت", title_en: "Microsoft" },
|
||||
{ title_fa: "لنوو", title_en: "Lenovo" },
|
||||
{ title_fa: "هواوی", title_en: "Huawei" },
|
||||
],
|
||||
"خودکار و خودنویس": [
|
||||
{ title_fa: "پایلوت", title_en: "Pilot" },
|
||||
{ title_fa: "شیفر", title_en: "Sheaffer" },
|
||||
{ title_fa: "پارکر", title_en: "Parker" },
|
||||
{ title_fa: "لامی", title_en: "Lamy" },
|
||||
],
|
||||
لامپ: [
|
||||
{ title_fa: "فیلیپس", title_en: "Philips" },
|
||||
{ title_fa: "شیائومی", title_en: "Xiaomi" },
|
||||
{ title_fa: "اپتونیک", title_en: "Optonique" },
|
||||
{ title_fa: "نورکالا", title_en: "NoorKala" },
|
||||
],
|
||||
اسپیکر: [
|
||||
{ title_fa: "جی بی ال", title_en: "JBL" },
|
||||
{ title_fa: "سونی", title_en: "Sony" },
|
||||
],
|
||||
|
||||
تلویزیون: [
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "ال جی", title_en: "LG" },
|
||||
{ title_fa: "سونی", title_en: "Sony" },
|
||||
{ title_fa: "پاناسونیک", title_en: "Panasonic" },
|
||||
],
|
||||
"دوربین عکاسی": [
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "ال جی", title_en: "LG" },
|
||||
{ title_fa: "سونی", title_en: "Sony" },
|
||||
{ title_fa: "پاناسونیک", title_en: "Nikon" },
|
||||
],
|
||||
"ساعت هوشمند": [
|
||||
{ title_fa: "شیائومی", title_en: "Xiaomi" },
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "اپل", title_en: "Apple" },
|
||||
{ title_fa: "هواوی", title_en: "Huawei" },
|
||||
],
|
||||
هدفون: [
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "ال جی", title_en: "LG" },
|
||||
{ title_fa: "سونی", title_en: "Sony" },
|
||||
{ title_fa: "بوز", title_en: "Bose" },
|
||||
],
|
||||
"پاور بانک": [
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "آنکر", title_en: "Anker" },
|
||||
],
|
||||
"لپ تاپ": [
|
||||
{ title_fa: "ایسر", title_en: "Acer" },
|
||||
{ title_fa: "ایسوس", title_en: "Asus" },
|
||||
{ title_fa: "اپل", title_en: "Apple" },
|
||||
{ title_fa: "لنوو", title_en: "Lenovo" },
|
||||
],
|
||||
"لباس زنانه": [
|
||||
{ title_fa: "زارا", title_en: "Zara" },
|
||||
{ title_fa: "H&M", title_en: "H&M" },
|
||||
{ title_fa: "گوچی", title_en: "Gucci" },
|
||||
{ title_fa: "دیور", title_en: "Dior" },
|
||||
],
|
||||
"لوازم آشپزخانه": [
|
||||
{ title_fa: "بوش", title_en: "Bosch" },
|
||||
{ title_fa: "فیلیپس", title_en: "Philips" },
|
||||
{ title_fa: "سامسونگ", title_en: "Samsung" },
|
||||
{ title_fa: "پاناسونیک", title_en: "Panasonic" },
|
||||
{ title_fa: "ال جی", title_en: "LG" },
|
||||
],
|
||||
"پلی استیشن": [{ title_fa: "سونی", title_en: "Sony" }],
|
||||
متفرقه: [{ title_fa: "متفرقه", title_en: "malicious" }],
|
||||
};
|
||||
|
||||
export const seedBrands = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("Brands seeding started");
|
||||
|
||||
const categoryMap: { [key: string]: Types.ObjectId } = {};
|
||||
|
||||
// Fetch all categories once
|
||||
const categories = await CategoryModel.find();
|
||||
categories.forEach((category) => {
|
||||
categoryMap[category.title_fa] = category._id;
|
||||
});
|
||||
|
||||
const brandDocuments = [];
|
||||
|
||||
// Prepare brand documents in bulk
|
||||
for (const [categoryTitle, brands] of Object.entries(brandSeedMap)) {
|
||||
const categoryId = categoryMap[categoryTitle];
|
||||
|
||||
if (categoryId) {
|
||||
for (const brand of brands) {
|
||||
const { title_fa, title_en } = brand;
|
||||
brandDocuments.push({
|
||||
title_fa,
|
||||
title_en,
|
||||
category: categoryId,
|
||||
status: StatusEnum.Approved,
|
||||
});
|
||||
}
|
||||
} else {
|
||||
logger.warn(`Category '${categoryTitle}' not found`);
|
||||
}
|
||||
}
|
||||
|
||||
// Bulk insert
|
||||
if (brandDocuments.length > 0) {
|
||||
await BrandModel.insertMany(brandDocuments);
|
||||
}
|
||||
logger.info("Brands seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding brands:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,98 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { ColorModel } from "../../modules/category/models/color.model";
|
||||
import { MeterageModel } from "../../modules/category/models/meterage.model";
|
||||
import { SizeModel } from "../../modules/category/models/size.model";
|
||||
|
||||
const colors = [
|
||||
{ name: "قرمز", hexColor: "#FF0000" },
|
||||
{ name: "سبز", hexColor: "#00FF00" },
|
||||
{ name: "آبی", hexColor: "#0000FF" },
|
||||
{ name: "مشکی", hexColor: "#000000" },
|
||||
{ name: "سفید", hexColor: "#FFFFFF" },
|
||||
{ name: "زرد", hexColor: "#FFFF00" },
|
||||
{ name: "بنفش", hexColor: "#800080" },
|
||||
{ name: "نارنجی", hexColor: "#FFA500" },
|
||||
{ name: "صورتی", hexColor: "#FFC0CB" },
|
||||
{ name: "خاکستری", hexColor: "#808080" },
|
||||
];
|
||||
|
||||
const sizes = [
|
||||
{ value: "XS" },
|
||||
{ value: "S" },
|
||||
{ value: "M" },
|
||||
{ value: "L" },
|
||||
{ value: "XL" },
|
||||
{ value: "XXL" },
|
||||
{ value: "3XL" },
|
||||
{ value: "4XL" },
|
||||
{ value: "5XL" },
|
||||
{ value: "6XL" },
|
||||
];
|
||||
|
||||
const meterages = [
|
||||
{ value: "1" },
|
||||
{ value: "2" },
|
||||
{ value: "3" },
|
||||
{ value: "4" },
|
||||
{ value: "5" },
|
||||
{ value: "10" },
|
||||
{ value: "15" },
|
||||
{ value: "20" },
|
||||
{ value: "25" },
|
||||
{ value: "30" },
|
||||
];
|
||||
|
||||
const seedColors = async () => {
|
||||
try {
|
||||
console.log("Seeding colors...");
|
||||
await ColorModel.deleteMany({});
|
||||
for (const color of colors) {
|
||||
await ColorModel.create(color);
|
||||
}
|
||||
console.log("Colors seeded successfully");
|
||||
} catch (error) {
|
||||
console.error("Error seeding colors:", error);
|
||||
}
|
||||
};
|
||||
|
||||
const seedSizes = async () => {
|
||||
try {
|
||||
console.log("Seeding sizes...");
|
||||
await SizeModel.deleteMany({});
|
||||
|
||||
for (const size of sizes) {
|
||||
await SizeModel.create(size);
|
||||
}
|
||||
console.log("Sizes seeded successfully");
|
||||
} catch (error) {
|
||||
console.error("Error seeding sizes:", error);
|
||||
}
|
||||
};
|
||||
|
||||
const seedMeterages = async () => {
|
||||
try {
|
||||
console.log("Seeding meterages...");
|
||||
await MeterageModel.deleteMany({});
|
||||
for (const meterage of meterages) {
|
||||
await MeterageModel.create(meterage);
|
||||
}
|
||||
console.log("Meterages seeded successfully");
|
||||
} catch (error) {
|
||||
console.error("Error seeding meterages:", error);
|
||||
}
|
||||
};
|
||||
|
||||
// Seed function
|
||||
export const seedCatVariant = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("Categories variant seeding started");
|
||||
|
||||
await seedColors();
|
||||
await seedSizes();
|
||||
await seedMeterages();
|
||||
|
||||
console.log("Seeding complete!");
|
||||
} catch (error) {
|
||||
logger.error("Seeding error:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,556 @@
|
||||
import { faker } from "@faker-js/faker";
|
||||
import { Types } from "mongoose";
|
||||
|
||||
faker.locale = "fa";
|
||||
import { CategoryThemeEnum } from "../../common/enums/category.enum";
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { AttributeValueModel } from "../../modules/category/models/attributeValue.model";
|
||||
import { CategoryModel } from "../../modules/category/models/category.model";
|
||||
import { CategoryAttributeModel } from "../../modules/category/models/CategoryAttribute.model";
|
||||
import { ColorModel } from "../../modules/category/models/color.model";
|
||||
import { MeterageModel } from "../../modules/category/models/meterage.model";
|
||||
import { SizeModel } from "../../modules/category/models/size.model";
|
||||
|
||||
interface ICategorySeed {
|
||||
title_fa: string;
|
||||
title_en: string;
|
||||
icon: string;
|
||||
imageUrl: string;
|
||||
description: string;
|
||||
leaf: boolean;
|
||||
theme?: CategoryThemeEnum;
|
||||
parent?: Types.ObjectId;
|
||||
}
|
||||
|
||||
interface ICategoryAttributeSeed {
|
||||
title: string;
|
||||
hint?: string;
|
||||
type: string;
|
||||
multiple: boolean;
|
||||
required: boolean;
|
||||
}
|
||||
|
||||
const rootCategories: ICategorySeed[] = [
|
||||
{
|
||||
title_fa: "موبایل و تبلت",
|
||||
icon: "mobile",
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
description: "لوازم جانبی",
|
||||
title_en: "mobile",
|
||||
leaf: false,
|
||||
},
|
||||
{
|
||||
title_fa: "لوازم تحریر و اداری",
|
||||
icon: "stationery",
|
||||
description: "انواع لوازم تحریر و اداری",
|
||||
title_en: "stationery-office",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "برق و الکتریکی",
|
||||
icon: "electric",
|
||||
description: "لوازم برق و الکتریکی",
|
||||
title_en: "electric-electrical",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "لوازم و ابزارآلات",
|
||||
icon: "tools",
|
||||
description: "انواع لوازم و ابزارآلات",
|
||||
title_en: "tools-equipment",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "صوت و تصویر",
|
||||
icon: "audio-visual",
|
||||
description: "انواع لوازم صوتی و تصویری",
|
||||
title_en: "audio-visual",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "کامپیوتر",
|
||||
icon: "computer",
|
||||
description: "انواع کامپیوتر و لوازم جانبی",
|
||||
title_en: "computer",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "کنسول بازی",
|
||||
icon: "console",
|
||||
description: "انواع کنسول بازی و لوازم جانبی",
|
||||
title_en: "game-console",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "ورزش و سفر",
|
||||
icon: "sports",
|
||||
description: "لوازم ورزشی و سفر",
|
||||
title_en: "sports-travel",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{ title_fa: "پوشاک و مد", icon: "fashion", description: "لباس و مد", title_en: "fashion", leaf: false, imageUrl: faker.image.imageUrl() },
|
||||
{
|
||||
title_fa: "لوازم خانگی",
|
||||
icon: "home-appliances",
|
||||
description: "لوازم خانه",
|
||||
title_en: "home-appliances",
|
||||
leaf: false,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "متفرقه",
|
||||
icon: "malicious",
|
||||
description: "متفرقه",
|
||||
title_en: "malicious",
|
||||
leaf: true,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
];
|
||||
|
||||
const subcategories: { [key: string]: ICategorySeed[] } = {
|
||||
"موبایل و تبلت": [
|
||||
{
|
||||
title_fa: "گوشی موبایل",
|
||||
icon: "phone",
|
||||
description: "انواع گوشی های موبایل",
|
||||
title_en: "mobile-phones",
|
||||
leaf: true,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
theme: CategoryThemeEnum.Colored,
|
||||
},
|
||||
{
|
||||
title_fa: "تبلت",
|
||||
icon: "tablet",
|
||||
description: "انواع تبلت ها",
|
||||
title_en: "tablets",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Colored,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "ساعت هوشمند",
|
||||
icon: "watch",
|
||||
description: "انواع ساعت هوشمند",
|
||||
title_en: "smart-watch",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Colored,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "پاور بانک",
|
||||
icon: "watch",
|
||||
description: "انواع پاور بانک",
|
||||
title_en: "power-banks",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"لوازم تحریر و اداری": [
|
||||
{
|
||||
title_fa: "خودکار و خودنویس",
|
||||
icon: "pen",
|
||||
description: "انواع خودکار و خودنویس",
|
||||
title_en: "pens",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Colored,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "دفتر و کاغذ",
|
||||
icon: "paper",
|
||||
description: "انواع دفتر و کاغذ",
|
||||
title_en: "paper-notebooks",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Colored,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"برق و الکتریکی": [
|
||||
{
|
||||
title_fa: "لامپ",
|
||||
icon: "bulb",
|
||||
description: "انواع لامپ ها",
|
||||
title_en: "bulbs",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "کابل و سیم",
|
||||
icon: "cable",
|
||||
description: "انواع کابل و سیم",
|
||||
title_en: "cables-wires",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"لوازم و ابزارآلات": [
|
||||
{
|
||||
title_fa: "آچار و پیچ گوشتی",
|
||||
icon: "wrench",
|
||||
description: "انواع آچار و پیچ گوشتی",
|
||||
title_en: "wrenches-screwdrivers",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "دریل",
|
||||
icon: "drill",
|
||||
description: "انواع دریل ها",
|
||||
title_en: "drills",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"صوت و تصویر": [
|
||||
{
|
||||
title_fa: "تلویزیون",
|
||||
icon: "tv",
|
||||
description: "انواع تلویزیون",
|
||||
title_en: "televisions",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "اسپیکر",
|
||||
icon: "speaker",
|
||||
description: "انواع اسپیکر",
|
||||
title_en: "speakers",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "هدفون",
|
||||
icon: "headphone",
|
||||
description: "انواع هدفون",
|
||||
title_en: "headphones",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Colored,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "دوربین عکاسی",
|
||||
icon: "camera",
|
||||
description: "انواع دوربین عکاسی",
|
||||
title_en: "cameras",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
کامپیوتر: [
|
||||
{
|
||||
title_fa: "لپ تاپ",
|
||||
icon: "laptop",
|
||||
description: "انواع لپ تاپ",
|
||||
title_en: "laptops",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "موس و کیبورد",
|
||||
icon: "mouse-keyboard",
|
||||
description: "انواع موس و کیبورد",
|
||||
title_en: "mouse-keyboards",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"کنسول بازی": [
|
||||
{
|
||||
title_fa: "پلی استیشن",
|
||||
icon: "playstation",
|
||||
description: "انواع پلی استیشن",
|
||||
title_en: "playstations",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "ایکس باکس",
|
||||
icon: "xbox",
|
||||
description: "انواع ایکس باکس",
|
||||
title_en: "xbox",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"ورزش و سفر": [
|
||||
{
|
||||
title_fa: "تجهیزات ورزشی",
|
||||
icon: "sports-equipment",
|
||||
description: "انواع تجهیزات ورزشی",
|
||||
title_en: "sports-equipment",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "لوازم سفر",
|
||||
icon: "travel",
|
||||
description: "انواع لوازم سفر",
|
||||
title_en: "travel-equipment",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"پوشاک و مد": [
|
||||
{
|
||||
title_fa: "لباس زنانه",
|
||||
icon: "women-clothing",
|
||||
description: "انواع لباس زنانه",
|
||||
title_en: "women-clothing",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "لباس مردانه",
|
||||
icon: "men-clothing",
|
||||
description: "انواع لباس مردانه",
|
||||
title_en: "men-clothing",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.Sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
"لوازم خانگی": [
|
||||
{
|
||||
title_fa: "لوازم آشپزخانه",
|
||||
icon: "kitchen-appliances",
|
||||
description: "انواع لوازم آشپزخانه",
|
||||
title_en: "kitchen-appliances",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
{
|
||||
title_fa: "لوازم نظافت",
|
||||
icon: "cleaning-appliances",
|
||||
description: "انواع لوازم نظافت",
|
||||
title_en: "cleaning-appliances",
|
||||
leaf: true,
|
||||
theme: CategoryThemeEnum.No_color_No_sized,
|
||||
imageUrl: faker.image.imageUrl(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
const categoryAttributesMap: { [key: string]: ICategoryAttributeSeed[] } = {
|
||||
"گوشی موبایل": [
|
||||
{ title: "باتری", hint: "ظرفیت باتری", type: "select", multiple: false, required: true },
|
||||
{ title: "دوربین", hint: "کیفیت دوربین", type: "select", multiple: false, required: true },
|
||||
{ title: "سیستم عامل", hint: "نوع سیستم عامل", type: "select", multiple: false, required: true },
|
||||
{ title: "حافظه داخلی موبایل", hint: "ظرفیت حافظه", type: "select", multiple: false, required: true },
|
||||
{ title: "پشتیبانی از 5G", hint: "آیا پشتیبانی میکند؟", type: "checkbox", multiple: false, required: false },
|
||||
],
|
||||
تبلت: [
|
||||
{ title: "اندازه صفحه تبلت", hint: "اینچ", type: "select", multiple: false, required: true },
|
||||
{ title: "پردازنده تبلت", hint: "نوع پردازنده", type: "select", multiple: false, required: true },
|
||||
{ title: "دوربین جلو", hint: "کیفیت دوربین جلو", type: "select", multiple: false, required: false },
|
||||
{ title: "ظرفیت باتری", hint: "میلیآمپر ساعت", type: "select", multiple: false, required: true },
|
||||
{ title: "اتصال به شبکه", hint: "نوع شبکه", type: "select", multiple: false, required: false },
|
||||
],
|
||||
"خودکار و خودنویس": [
|
||||
{ title: "نوع جوهر", hint: "جوهر مورد استفاده", type: "select", multiple: false, required: true },
|
||||
{ title: "ضخامت نوشتاری", hint: "ضخامت نوک", type: "select", multiple: false, required: true },
|
||||
{ title: "قابلیت شارژ مجدد", hint: "آیا قابل شارژ است؟", type: "checkbox", multiple: false, required: false },
|
||||
{ title: "جنس بدنه خودکار", hint: "جنس بدنه خودکار", type: "select", multiple: false, required: true },
|
||||
{ title: "رنگ جوهر", hint: "رنگ جوهر خودکار", type: "select", multiple: false, required: true },
|
||||
],
|
||||
لامپ: [
|
||||
{ title: "نوع لامپ", hint: "نوع لامپ (LED، هالوژن و غیره)", type: "select", multiple: false, required: true },
|
||||
{ title: "توان مصرفی لامپ", hint: "وات", type: "select", multiple: false, required: true },
|
||||
{ title: "رنگ نور", hint: "رنگ نور", type: "select", multiple: false, required: true },
|
||||
{ title: "طول عمر", hint: "ساعت", type: "select", multiple: false, required: true },
|
||||
{ title: "قابلیت تنظیم شدت نور", hint: "آیا قابل تنظیم است؟", type: "checkbox", multiple: false, required: false },
|
||||
],
|
||||
تلویزیون: [
|
||||
{ title: "اندازه صفحه تلویزیون", hint: "اینچ", type: "select", multiple: false, required: true },
|
||||
{ title: "رزولوشن", hint: "کیفیت تصویر", type: "select", multiple: false, required: true },
|
||||
{ title: "نوع صفحه", hint: "LED, OLED, QLED", type: "select", multiple: false, required: true },
|
||||
{ title: "هوشمند", hint: "آیا هوشمند است؟", type: "checkbox", multiple: false, required: false },
|
||||
{ title: "درگاههای ارتباطی", hint: "نوع و تعداد درگاهها", type: "select", multiple: true, required: true },
|
||||
],
|
||||
"لپ تاپ": [
|
||||
{ title: "پردازنده لپ تاپ", hint: "نوع پردازنده", type: "select", multiple: false, required: true },
|
||||
{ title: "حافظه رم", hint: "ظرفیت حافظه رم", type: "select", multiple: false, required: true },
|
||||
{ title: "حافظه داخلی", hint: "ظرفیت حافظه", type: "select", multiple: false, required: true },
|
||||
{ title: "اندازه صفحه", hint: "اینچ", type: "select", multiple: false, required: true },
|
||||
{ title: "کارت گرافیک", hint: "نوع کارت گرافیک", type: "select", multiple: false, required: true },
|
||||
],
|
||||
"لباس زنانه": [
|
||||
{ title: "جنس پارچه", hint: "نوع پارچه", type: "select", multiple: false, required: true },
|
||||
{ title: "نوع یقه", hint: "یقه لباس", type: "select", multiple: false, required: true },
|
||||
{ title: "نوع آستین", hint: "آستین لباس", type: "select", multiple: false, required: true },
|
||||
{ title: "مدل لباس", hint: "نوع و مدل لباس", type: "select", multiple: false, required: true },
|
||||
{ title: "نوع شستشو", hint: "نحوه شستشو", type: "select", multiple: false, required: false },
|
||||
],
|
||||
"لوازم آشپزخانه": [
|
||||
{ title: "توان مصرفی", hint: "توان لوازم برقی", type: "select", multiple: false, required: true },
|
||||
{ title: "جنس بدنه", hint: "جنس بدنه دستگاه", type: "select", multiple: false, required: true },
|
||||
{ title: "ظرفیت", hint: "ظرفیت دستگاه", type: "select", multiple: false, required: true },
|
||||
{ title: "قابلیت تنظیم", hint: "آیا قابلیت تنظیم دارد؟", type: "checkbox", multiple: false, required: false },
|
||||
{ title: "نوع کاربری", hint: "کاربری دستگاه", type: "select", multiple: false, required: true },
|
||||
],
|
||||
// Add more categories as needed
|
||||
};
|
||||
|
||||
const attributeValuesMap: { [key: string]: string[] } = {
|
||||
باتری: ["3000mAh", "4000mAh", "5000mAh", "6000mAh", "7000mAh"],
|
||||
دوربین: ["12MP", "16MP", "20MP", "48MP", "108MP"],
|
||||
"سیستم عامل": ["اندروید", "iOS", "ویندوز", "لینوکس", "سایر"],
|
||||
"حافظه داخلی موبایل": ["32GB", "64GB", "128GB", "256GB", "512GB"],
|
||||
"پشتیبانی از 5G": ["بله", "خیر"],
|
||||
"اندازه صفحه تبلت": ["7 اینچ", "10 اینچ", "13 اینچ", "15 اینچ", "17 اینچ"],
|
||||
"پردازنده تبلت": ["Intel", "AMD", "Apple M1", "Qualcomm", "MediaTek"],
|
||||
"دوربین جلو": ["5MP", "8MP", "12MP", "16MP", "20MP"],
|
||||
"ظرفیت باتری": ["2000mAh", "3000mAh", "4000mAh", "5000mAh", "6000mAh"],
|
||||
"اتصال به شبکه": ["WiFi", "4G", "5G", "Ethernet", "بلوتوث"],
|
||||
"نوع جوهر": ["ژل", "روغنی", "آبی", "خودکار", "پلاستیکی"],
|
||||
"ضخامت نوشتاری": ["0.5mm", "0.7mm", "1.0mm", "1.2mm", "1.5mm"],
|
||||
"قابلیت شارژ مجدد": ["بله", "خیر"],
|
||||
"جنس بدنه خودکار": ["فلز", "پلاستیک", "چوب", "سرامیک", "کربن"],
|
||||
"رنگ جوهر": ["مشکی", "آبی", "قرمز", "سبز", "بنفش"],
|
||||
"نوع لامپ": ["LED", "هالوژن", "فلورسنت", "رشتهای", "پلاسما"],
|
||||
"توان مصرفی لامپ": ["5W", "10W", "15W", "20W", "25W"],
|
||||
"رنگ نور": ["سفید", "زرد", "آبی", "سبز", "قرمز"],
|
||||
"طول عمر": ["1000 ساعت", "5000 ساعت", "10000 ساعت", "20000 ساعت", "50000 ساعت"],
|
||||
"قابلیت تنظیم شدت نور": ["بله", "خیر"],
|
||||
"اندازه صفحه تلویزیون": ["20 اینچ", "32 اینچ", "40 اینچ", "60 اینچ", "70 اینچ"],
|
||||
رزولوشن: ["720p", "1080p", "4K", "8K", "HDR"],
|
||||
"نوع صفحه": ["LED", "OLED", "QLED", "Plasma", "LCD"],
|
||||
هوشمند: ["بله", "خیر"],
|
||||
"درگاههای ارتباطی": ["HDMI", "USB", "Bluetooth", "WiFi", "Ethernet"],
|
||||
"پردازنده لپ تاپ": ["Intel", "AMD", "Apple M1", "Qualcomm", "Apple M2"],
|
||||
"حافظه رم": ["4GB", "8GB", "16GB", "32GB", "64GB"],
|
||||
"حافظه داخلی": ["128GB", "256GB", "512GB", "1TB"],
|
||||
"اندازه صفحه": ["14 اینچ", "12 اینچ", "16 اینچ"],
|
||||
"کارت گرافیک": ["NVIDIA", "AMD", "Intel", "Apple M1", "ARM Mali"],
|
||||
"جنس پارچه": ["پنبه", "پلیاستر", "نایلون", "ریون", "کتان"],
|
||||
"نوع یقه": ["گرد", "هفت", "ایستاده", "دکمهای", "یقه اسکی"],
|
||||
"نوع آستین": ["کوتاه", "بلند", "سهربع", "بیآستین", "کشباف"],
|
||||
"مدل لباس": ["تیشرت", "پیراهن", "ژاکت", "هودی", "پلیور"],
|
||||
"نوع شستشو": ["ماشینی", "دستی", "خشکشویی", "آب سرد", "آب گرم"],
|
||||
"توان مصرفی": ["150W", "200W", "400W"],
|
||||
"جنس بدنه": ["فلز", "پلاستیک", "چوب", "سرامیک", "کربن"],
|
||||
ظرفیت: ["1 لیتر", "2 لیتر", "3 لیتر", "4 لیتر", "5 لیتر"],
|
||||
"قابلیت تنظیم": ["بله", "خیر"],
|
||||
"نوع کاربری": ["آبمیوهگیری", "مخلوطکن", "آسیاب", "کبابپز", "زودپز"],
|
||||
// Add more attributes and their values as needed
|
||||
};
|
||||
|
||||
export const seedCategories = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("Categories seeding started");
|
||||
|
||||
const colors = (await ColorModel.find()).map((color) => color._id);
|
||||
const sizes = (await SizeModel.find()).map((size) => size._id);
|
||||
const meterages = (await MeterageModel.find()).map((meterage) => meterage._id);
|
||||
|
||||
const createdCategories: { [key: string]: Types.ObjectId } = {};
|
||||
const createdSubCategories: { [key: string]: Types.ObjectId } = {};
|
||||
|
||||
// Create root categories
|
||||
for (const category of rootCategories) {
|
||||
const { title_fa, icon, description, title_en, leaf, imageUrl } = category;
|
||||
|
||||
const rootCategory = new CategoryModel({ title_fa, icon, title_en, description, leaf, imageUrl });
|
||||
await rootCategory.save();
|
||||
|
||||
createdCategories[title_fa] = rootCategory._id;
|
||||
}
|
||||
|
||||
// Create subcategories
|
||||
for (const [rootName, subs] of Object.entries(subcategories)) {
|
||||
const parentId = createdCategories[rootName];
|
||||
if (parentId) {
|
||||
for (const subcategory of subs) {
|
||||
const { title_fa, icon, description, title_en, leaf, theme, imageUrl } = subcategory;
|
||||
|
||||
const catVariants =
|
||||
theme === CategoryThemeEnum.Colored
|
||||
? [...colors]
|
||||
: theme === CategoryThemeEnum.Meterage
|
||||
? [...meterages]
|
||||
: theme === CategoryThemeEnum.Sized
|
||||
? [...sizes]
|
||||
: [];
|
||||
|
||||
const subCategoryDoc = new CategoryModel({
|
||||
title_fa,
|
||||
icon,
|
||||
imageUrl,
|
||||
title_en,
|
||||
description,
|
||||
leaf,
|
||||
theme,
|
||||
variants: catVariants,
|
||||
parent: parentId,
|
||||
});
|
||||
await subCategoryDoc.save();
|
||||
|
||||
// Save the subcategory ID for later use
|
||||
createdSubCategories[title_fa] = subCategoryDoc._id;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const createdAttributes: { [key: string]: number } = {};
|
||||
|
||||
// Generate attributes for each subcategory
|
||||
for (const [subcategoryTitle, attributes] of Object.entries(categoryAttributesMap)) {
|
||||
const subcategoryId = createdSubCategories[subcategoryTitle];
|
||||
if (subcategoryId) {
|
||||
for (const attr of attributes) {
|
||||
const attributeDoc = new CategoryAttributeModel({
|
||||
category: subcategoryId,
|
||||
title: attr.title,
|
||||
hint: attr.hint,
|
||||
type: attr.type,
|
||||
multiple: attr.multiple,
|
||||
required: attr.required,
|
||||
});
|
||||
await attributeDoc.save();
|
||||
createdAttributes[attr.title] = attributeDoc._id;
|
||||
}
|
||||
} else {
|
||||
logger.warn(`Subcategory '${subcategoryTitle}' not found.`);
|
||||
}
|
||||
}
|
||||
// Generate values for each attribute
|
||||
for (const [attributeTitle, attributeId] of Object.entries(createdAttributes)) {
|
||||
const values = attributeValuesMap[attributeTitle] || [];
|
||||
|
||||
for (const valueText of values) {
|
||||
await AttributeValueModel.create({
|
||||
attribute: attributeId,
|
||||
text: valueText,
|
||||
});
|
||||
|
||||
// await valueDoc.save();
|
||||
}
|
||||
}
|
||||
|
||||
logger.info("Categories, subcategories, attributes, and values seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding categories:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,17 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { ContractModel } from "../../modules/admin/models/contract.model";
|
||||
|
||||
export const contractSeeder = async (logger: Logger) => {
|
||||
try {
|
||||
const existContract = await ContractModel.exists({});
|
||||
if (existContract) return;
|
||||
|
||||
await ContractModel.create({
|
||||
content: "متن قرار داد را اینجا قرار دهید",
|
||||
});
|
||||
|
||||
logger.info("Contract collection seeded!");
|
||||
} catch (error) {
|
||||
logger.error("Contract collection seed failed!", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,68 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { PermissionEnum } from "../../modules/admin/models/Abstraction/IPermission";
|
||||
import { RoleEnum } from "../../modules/admin/models/Abstraction/IRole";
|
||||
import { AdminModel } from "../../modules/admin/models/admin.model";
|
||||
import { PermissionModel } from "../../modules/admin/models/permission.model";
|
||||
import { RoleModel } from "../../modules/admin/models/role.model";
|
||||
import { ShipmentModel } from "../../modules/shipment/models/shipment.model";
|
||||
import { OwnerRef } from "../../modules/shop/models/Abstraction/IShop";
|
||||
import { ShopModel } from "../../modules/shop/models/shop.model";
|
||||
|
||||
const createDefaultAdmin = async (logger: Logger) => {
|
||||
logger.info("createDefaultAdmin started", "SEED");
|
||||
const email = process.env.DEFAULT_ADMIN_EMAIL;
|
||||
const password = process.env.DEFAULT_ADMIN_PASSWORD;
|
||||
|
||||
if (!email || !password) {
|
||||
throw new Error("Default admin credentials are not set in the environment variables");
|
||||
}
|
||||
// Create permissions based on the enum
|
||||
const permissions = Object.values(PermissionEnum);
|
||||
|
||||
const createdPermissions = await Promise.all(
|
||||
permissions.map(async (perm) => {
|
||||
const existingPermission = await PermissionModel.findOne({ name: perm });
|
||||
if (!existingPermission) {
|
||||
return PermissionModel.create({ name: perm });
|
||||
}
|
||||
return existingPermission;
|
||||
}),
|
||||
);
|
||||
|
||||
// create or find the SUPERADMIN role
|
||||
let superAdminRole = await RoleModel.findOne({ name: RoleEnum.SUPERADMIN });
|
||||
if (!superAdminRole) {
|
||||
superAdminRole = await RoleModel.create({
|
||||
name: RoleEnum.SUPERADMIN,
|
||||
});
|
||||
logger.info("SUPERADMIN role created", "SEED");
|
||||
} else {
|
||||
logger.warn("SUPERADMIN role already exists", "SEED");
|
||||
}
|
||||
|
||||
let admin = await AdminModel.findOne({ email });
|
||||
if (!admin) {
|
||||
admin = await AdminModel.create({
|
||||
email,
|
||||
password,
|
||||
fullName: "defaultAdmin",
|
||||
userName: "defaultAdmin",
|
||||
permissions: createdPermissions.map((perm) => perm._id),
|
||||
role: superAdminRole._id,
|
||||
});
|
||||
const shipments = (await ShipmentModel.find()).map((shipper) => shipper._id);
|
||||
|
||||
await ShopModel.create({
|
||||
owner: admin._id.toString(),
|
||||
ownerRef: OwnerRef.ADMIN,
|
||||
shipmentMethod: shipments,
|
||||
shopDescription: "فروشگاه شینان",
|
||||
shopName: "شینان",
|
||||
});
|
||||
logger.info("Default admin user and native shop created", "SEED");
|
||||
} else {
|
||||
logger.warn("Default admin user and native shop already exists", "SEED");
|
||||
}
|
||||
};
|
||||
|
||||
export { createDefaultAdmin };
|
||||
@@ -0,0 +1,36 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { FaqModel } from "../../modules/faq/models/faq.model";
|
||||
|
||||
export const seedFaqs = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("start seeding the FAQ");
|
||||
const faqs = [
|
||||
{
|
||||
question: "چگونه میتوانم سفارش خود را پیگیری کنم؟",
|
||||
answer: "برای پیگیری سفارش خود، میتوانید به حساب کاربری خود وارد شوید و از قسمت سفارشات من، وضعیت سفارش خود را مشاهده کنید.",
|
||||
},
|
||||
{
|
||||
question: "آیا امکان بازگشت کالا وجود دارد؟",
|
||||
answer: "بله، در صورت داشتن شرایط بازگشت، میتوانید کالا را تا ۷ روز پس از تحویل بازگردانید.",
|
||||
},
|
||||
{
|
||||
question: "چگونه میتوانم حساب کاربری ایجاد کنم؟",
|
||||
answer: "برای ایجاد حساب کاربری، کافیست در صفحه اصلی سایت به قسمت ثبت نام مراجعه کرده و اطلاعات خود را وارد کنید.",
|
||||
},
|
||||
{
|
||||
question: "روشهای پرداخت چگونه است؟",
|
||||
answer: "پرداختها میتواند از طریق کارتهای شتاب، درگاههای بانکی و پرداخت در محل انجام شود.",
|
||||
},
|
||||
{
|
||||
question: "چگونه میتوانم از کد تخفیف استفاده کنم؟",
|
||||
answer: "هنگام پرداخت، در قسمت کد تخفیف، کد خود را وارد کنید و سپس دکمه اعمال را بزنید.",
|
||||
},
|
||||
];
|
||||
|
||||
await FaqModel.insertMany(faqs);
|
||||
|
||||
logger.info("FAQ data seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding FAQ data:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,62 @@
|
||||
import "reflect-metadata";
|
||||
import { config } from "dotenv";
|
||||
config();
|
||||
import mongoose from "mongoose";
|
||||
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { connectMongo } from "../connection";
|
||||
// import { backfillHierarchy } from "./backfillHierarchy";
|
||||
import { blogCategorySeeder } from "./blogCategorySeeder";
|
||||
import { blogSeeder } from "./blogSeeder";
|
||||
import { contractSeeder } from "./contractSeeder";
|
||||
// import { seedMedia } from "./mediaSeeder";
|
||||
import { seedCityAndProvince } from "./iranCityseeder";
|
||||
import { SeedPricing } from "./pricingSeeder";
|
||||
import { clearDatabase } from "../clearDatabase";
|
||||
import { backfillHierarchy } from "./backfillHierarchy";
|
||||
import { createDefaultAdmin } from "./defaultAdmin";
|
||||
import { seedFaqs } from "./faqSeeder";
|
||||
import { seedMedia } from "./mediaSeeder";
|
||||
import { seedPaymentMethods } from "./pgSeeder";
|
||||
import { ReportQuesSeeder } from "./reportQuestion";
|
||||
import { createDefaultRoles } from "./roleSeeder";
|
||||
import { SeedShipment } from "./shipmentSeeder";
|
||||
import { seedTicketCategories } from "./ticketSeeder";
|
||||
import { seedWarranty } from "./warrantySeeders";
|
||||
|
||||
const logger = new Logger("Seeder");
|
||||
|
||||
const seedDatabase = async () => {
|
||||
try {
|
||||
await connectMongo();
|
||||
logger.info("connected to mongodb");
|
||||
await clearDatabase(logger);
|
||||
await backfillHierarchy();
|
||||
await blogCategorySeeder(logger);
|
||||
await blogSeeder(logger);
|
||||
await contractSeeder(logger);
|
||||
await createDefaultAdmin(logger);
|
||||
await seedFaqs(logger);
|
||||
await seedCityAndProvince(logger);
|
||||
await SeedPricing(logger);
|
||||
await seedMedia(logger);
|
||||
await seedPaymentMethods(logger);
|
||||
await ReportQuesSeeder(logger);
|
||||
await createDefaultRoles(logger);
|
||||
await SeedShipment(logger);
|
||||
await seedTicketCategories(logger);
|
||||
await seedWarranty(logger);
|
||||
logger.info("Seeding completed");
|
||||
process.exit(0);
|
||||
} catch (error) {
|
||||
//
|
||||
console.error("Error during seeding:", error);
|
||||
logger.error("Error during seeding:", error);
|
||||
process.exit(1);
|
||||
} finally {
|
||||
//
|
||||
await mongoose.connection.close();
|
||||
}
|
||||
};
|
||||
|
||||
seedDatabase();
|
||||
@@ -0,0 +1,39 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { CityModel } from "../../modules/address/models/city.model";
|
||||
import { ProvinceModel } from "../../modules/address/models/province.model";
|
||||
import province from "../data/json/ostan.json";
|
||||
import city from "../data/json/shahr.json";
|
||||
|
||||
interface IProvince {
|
||||
id: number;
|
||||
name: string;
|
||||
}
|
||||
interface ICities extends IProvince {
|
||||
ostan: number;
|
||||
}
|
||||
|
||||
const provinces: IProvince[] = province;
|
||||
const cities: ICities[] = city;
|
||||
|
||||
export const seedCityAndProvince = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("start seeding the city and province", "SEED");
|
||||
|
||||
for (const province of provinces) {
|
||||
await ProvinceModel.create({
|
||||
name: province.name,
|
||||
});
|
||||
}
|
||||
|
||||
for (const city of cities) {
|
||||
await CityModel.create({
|
||||
name: city.name,
|
||||
province: city.ostan,
|
||||
});
|
||||
}
|
||||
|
||||
logger.info("city and province seeding completed", "SEED");
|
||||
} catch (error) {
|
||||
logger.error("error in seeding the city and province", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,46 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { JobType } from "../../modules/job/models/Abstraction/IJob";
|
||||
import { JobModel } from "../../modules/job/models/job.model";
|
||||
|
||||
export const seedJobs = async (logger: Logger) => {
|
||||
const jobs = [
|
||||
{
|
||||
title: "برنامهنویس وب",
|
||||
description: "ما به دنبال یک برنامهنویس وب با تجربه در React و Node.js هستیم.",
|
||||
location: "تهران",
|
||||
type: JobType.FullTime,
|
||||
},
|
||||
{
|
||||
title: "طراح UI/UX",
|
||||
description: "نیازمند یک طراح UI/UX با تجربه برای بهبود تجربه کاربری وبسایت هستیم.",
|
||||
location: "اصفهان",
|
||||
type: JobType.Contract,
|
||||
},
|
||||
{
|
||||
title: "کارشناس فروش",
|
||||
description: "به یک کارشناس فروش برای توسعه بازار و جذب مشتری نیازمندیم.",
|
||||
location: "شیراز",
|
||||
type: JobType.PartTime,
|
||||
},
|
||||
{
|
||||
title: "مدیر پروژه",
|
||||
description: "نیازمند مدیر پروژهای با تجربه در مدیریت تیمهای فنی برای مدیریت پروژههای IT.",
|
||||
location: "مشهد",
|
||||
type: JobType.FullTime,
|
||||
},
|
||||
{
|
||||
title: "تحلیلگر داده",
|
||||
description: "به یک تحلیلگر داده برای تحلیل و بررسی دادههای شرکت نیاز داریم.",
|
||||
location: "تبریز",
|
||||
type: JobType.Contract,
|
||||
},
|
||||
];
|
||||
|
||||
try {
|
||||
logger.info("start seeding the jobs");
|
||||
await JobModel.insertMany(jobs);
|
||||
logger.info("Job seeding completed!");
|
||||
} catch (error) {
|
||||
logger.error("Job seeding failed: ", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,193 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { BannerModel } from "../../modules/admin/models/media.model";
|
||||
|
||||
export async function seedMedia(logger: Logger) {
|
||||
try {
|
||||
// await SliderModel.deleteMany({});
|
||||
// await BannerModel.deleteMany({});
|
||||
// logger.info("Cleared existing data");
|
||||
|
||||
// // Seed Sliders
|
||||
// const sliders = [
|
||||
// {
|
||||
// displayLocation: DisplayLocations.Mobile,
|
||||
// imageUrl: "https://loremflickr.com/1920/1080",
|
||||
// altText: "اسلایدر ۱",
|
||||
// title: "خوش آمدید به اسلایدر ۱",
|
||||
// linkUrl: "/slider1",
|
||||
// isActive: true,
|
||||
// },
|
||||
// {
|
||||
// displayLocation: DisplayLocations.Mobile,
|
||||
// imageUrl: "https://loremflickr.com/1920/1080",
|
||||
// altText: "اسلایدر ۲",
|
||||
// title: "اسلایدر ۲ را کشف کنید",
|
||||
// linkUrl: "/slider2",
|
||||
// isActive: true,
|
||||
// },
|
||||
// {
|
||||
// displayLocation: DisplayLocations.Desktop,
|
||||
// imageUrl: "https://loremflickr.com/1920/1080",
|
||||
// altText: "اسلایدر ۳",
|
||||
// title: "بیشتر درباره اسلایدر ۳ بدانید",
|
||||
// linkUrl: "/slider3",
|
||||
// isActive: true,
|
||||
// },
|
||||
// {
|
||||
// displayLocation: DisplayLocations.Desktop,
|
||||
// imageUrl: "https://loremflickr.com/1920/1080",
|
||||
// altText: "اسلایدر ۴",
|
||||
// title: "اسلایدر جدید و جذاب",
|
||||
// linkUrl: "/slider4",
|
||||
// isActive: true,
|
||||
// },
|
||||
// ];
|
||||
|
||||
// for (const slider of sliders) {
|
||||
// await SliderModel.create(slider);
|
||||
// }
|
||||
|
||||
// logger.info(" Sliders Seeded");
|
||||
|
||||
const existingBanners = await BannerModel.countDocuments({});
|
||||
if (existingBanners && existingBanners == 16) return;
|
||||
|
||||
await BannerModel.deleteMany({});
|
||||
|
||||
const banners = [
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر ۱",
|
||||
title: "خوش آمدید به صفحه اصلی",
|
||||
linkUrl: "/banner1",
|
||||
isActive: true,
|
||||
order: 1,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر ۲",
|
||||
title: "درباره ما بیشتر بدانید",
|
||||
linkUrl: "/banner2",
|
||||
isActive: true,
|
||||
order: 2,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر ۳",
|
||||
title: "تماس با ما",
|
||||
linkUrl: "/banner3",
|
||||
isActive: true,
|
||||
order: 3,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر ۴",
|
||||
title: "خدمات ما را کشف کنید",
|
||||
linkUrl: "/banner4",
|
||||
isActive: true,
|
||||
order: 4,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر ۵",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner5",
|
||||
isActive: true,
|
||||
order: 5,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 6",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner6",
|
||||
isActive: true,
|
||||
order: 6,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 7",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner7",
|
||||
isActive: true,
|
||||
order: 7,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 8",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner8",
|
||||
isActive: true,
|
||||
order: 8,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 9",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner9",
|
||||
isActive: true,
|
||||
order: 9,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 10",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner10",
|
||||
isActive: true,
|
||||
order: 10,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 11",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner11",
|
||||
isActive: true,
|
||||
order: 11,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 12",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner12",
|
||||
isActive: true,
|
||||
order: 12,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 13",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner13",
|
||||
isActive: true,
|
||||
order: 13,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 14",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner14",
|
||||
isActive: true,
|
||||
order: 14,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 15",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner15",
|
||||
isActive: true,
|
||||
order: 15,
|
||||
},
|
||||
{
|
||||
imageUrl: "https://storage.shinan.ir/banner-placeholder.png",
|
||||
altText: "بنر 16",
|
||||
title: "محصولات ما را مشاهده کنید",
|
||||
linkUrl: "/banner16",
|
||||
isActive: true,
|
||||
order: 16,
|
||||
},
|
||||
];
|
||||
|
||||
await BannerModel.insertMany(banners);
|
||||
logger.info("Banners seeding completed!");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding the Medias: ", error);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
import { PaymentMethodType } from "../../common/enums/payment.enum";
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { PaymentMethodModel } from "../../modules/payment/models/paymentMethod.model";
|
||||
|
||||
// Define payment method data
|
||||
const paymentMethods = [
|
||||
{
|
||||
title_fa: "پرداخت اینترنتی",
|
||||
title_en: "Internet Payment Gateway (IPG)",
|
||||
description: "پرداخت آنلاین با تمامی کارتهای بانکی",
|
||||
provider: "Zarinpal",
|
||||
isActive: true,
|
||||
type: PaymentMethodType.Online,
|
||||
},
|
||||
{
|
||||
title_fa: "پرداخت اینترنتی",
|
||||
title_en: "Internet Payment Gateway (IPG)",
|
||||
description: "پرداخت آنلاین با تمامی کارتهای بانکی",
|
||||
provider: "asanPardakht",
|
||||
isActive: false,
|
||||
type: PaymentMethodType.Online,
|
||||
},
|
||||
{
|
||||
title_fa: "پرداخت در محل (با کارت بانکی)",
|
||||
title_en: "POS",
|
||||
description: "هنگام تحویل از طریق کارتهای بانکی",
|
||||
isActive: false,
|
||||
type: PaymentMethodType.POS,
|
||||
},
|
||||
{
|
||||
title_fa: "کیف پول",
|
||||
title_en: "Wallet",
|
||||
isActive: false,
|
||||
type: PaymentMethodType.Wallet,
|
||||
},
|
||||
// Add more payment methods as necessary
|
||||
];
|
||||
|
||||
// Seeder function to insert the payment methods
|
||||
export const seedPaymentMethods = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("PaymentMethods seeding started");
|
||||
|
||||
await PaymentMethodModel.insertMany(paymentMethods);
|
||||
|
||||
logger.info("Payment methods seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding payment methods:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,27 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { IPricing, PricingTypeEnum } from "../../modules/pricing/models/Abstraction/IPricing";
|
||||
import { PricingModel } from "../../modules/pricing/models/pricing.model";
|
||||
|
||||
export const SeedPricing = async (logger: Logger) => {
|
||||
const pricing: IPricing[] = [
|
||||
{ type: PricingTypeEnum.INSERT_FEE, price: 100_000 },
|
||||
{ type: PricingTypeEnum.PHOTOGRAPHY_FEE, price: 150_000 },
|
||||
{ type: PricingTypeEnum.UNBOXING_VIDEO_FEE, price: 200_000 },
|
||||
{ type: PricingTypeEnum.EXPERT_REVIEWS_FEE, price: 200_000 },
|
||||
];
|
||||
|
||||
try {
|
||||
logger.info("Pricing seeding started");
|
||||
|
||||
const existPricing = await PricingModel.countDocuments({});
|
||||
if (existPricing && existPricing == 4) return;
|
||||
|
||||
await PricingModel.deleteMany({});
|
||||
|
||||
await PricingModel.insertMany(pricing);
|
||||
|
||||
logger.info("Pricing seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Failed to Pricing:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,325 @@
|
||||
import { faker } from "@faker-js/faker";
|
||||
|
||||
faker.locale = "fa";
|
||||
import { ProductMarketStatus } from "../../common/enums/product.enum";
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { BrandModel } from "../../modules/brand/models/brand.model";
|
||||
import { AttributeValueModel } from "../../modules/category/models/attributeValue.model";
|
||||
import { CategoryModel } from "../../modules/category/models/category.model";
|
||||
import { CategoryAttributeModel } from "../../modules/category/models/CategoryAttribute.model";
|
||||
import { ColorModel } from "../../modules/category/models/color.model";
|
||||
import { MeterageModel } from "../../modules/category/models/meterage.model";
|
||||
import { SizeModel } from "../../modules/category/models/size.model";
|
||||
import { ISpecifications } from "../../modules/product/models/Abstraction/IProduct";
|
||||
import { ProductModel } from "../../modules/product/models/product.model";
|
||||
import { ProductVariantModel } from "../../modules/product/models/productVariant.model";
|
||||
import { SellerModel } from "../../modules/seller/models/seller.model";
|
||||
import { ShipmentModel } from "../../modules/shipment/models/shipment.model";
|
||||
import { ShopModel } from "../../modules/shop/models/shop.model";
|
||||
import { WalletModel } from "../../modules/wallet/models/wallet.model";
|
||||
import { WarrantyModel } from "../../modules/warranty/models/warranty.model";
|
||||
import { TimeService } from "../../utils/time.service";
|
||||
import { CreateFakeSellerData, createFakeShopData, fakeProductsData } from "../data/product";
|
||||
|
||||
type ProductCategory =
|
||||
| "mobile"
|
||||
| "stationery"
|
||||
| "electric-electrical"
|
||||
| "tools-equipment"
|
||||
| "audio-visual"
|
||||
| "computer"
|
||||
| "game-console"
|
||||
| "sports-travel"
|
||||
| "fashion"
|
||||
| "home-appliances"
|
||||
| "mobile-phones"
|
||||
| "tablets"
|
||||
| "pens"
|
||||
| "paper-notebooks"
|
||||
| "bulbs"
|
||||
| "cables-wires"
|
||||
| "wrenches-screwdrivers"
|
||||
| "drills"
|
||||
| "televisions"
|
||||
| "speakers"
|
||||
| "laptops"
|
||||
| "mouse-keyboards"
|
||||
| "playstations"
|
||||
| "xbox"
|
||||
| "sports-equipment"
|
||||
| "cameras"
|
||||
| "headphones"
|
||||
| "travel-equipment"
|
||||
| "women-clothing"
|
||||
| "men-clothing"
|
||||
| "kitchen-appliances"
|
||||
| "smart-watch"
|
||||
| "power-banks"
|
||||
| "cleaning-appliances"
|
||||
| "malicious";
|
||||
|
||||
type ProductBrand =
|
||||
| "Samsung"
|
||||
| "LG"
|
||||
| "Bosch"
|
||||
| "Apple"
|
||||
| "Asus"
|
||||
| "Xiaomi"
|
||||
| "Sony"
|
||||
| "JBL"
|
||||
| "Bose"
|
||||
| "Huawei"
|
||||
| "Nokia"
|
||||
| "Nikon"
|
||||
| "Panasonic"
|
||||
| "Anker"
|
||||
| "Microsoft"
|
||||
| "Lenovo"
|
||||
| "Pilot"
|
||||
| "Sheaffer"
|
||||
| "Parker"
|
||||
| "Lamy"
|
||||
| "Parker"
|
||||
| "Philips"
|
||||
| "Optonique"
|
||||
| "NoorKala"
|
||||
| "Acer"
|
||||
| "Zara"
|
||||
| "H&M"
|
||||
| "Gucci"
|
||||
| "Dior"
|
||||
| "Gucci"
|
||||
| "Gucci"
|
||||
| "malicious";
|
||||
|
||||
const productMapping = (productModel: string) => {
|
||||
let category: ProductCategory;
|
||||
let brand: ProductBrand;
|
||||
|
||||
switch (productModel) {
|
||||
case "SAMSUNG123":
|
||||
case "SAMGALTAB567":
|
||||
brand = "Samsung";
|
||||
category = productModel === "SAMSUNG123" ? "televisions" : "tablets";
|
||||
break;
|
||||
|
||||
case "LGWASH456":
|
||||
brand = "LG";
|
||||
category = "kitchen-appliances";
|
||||
break;
|
||||
|
||||
case "LGOLED789":
|
||||
brand = "LG";
|
||||
category = "televisions";
|
||||
break;
|
||||
|
||||
case "BOSCHFRIDGE789":
|
||||
brand = "Bosch";
|
||||
category = "kitchen-appliances";
|
||||
break;
|
||||
|
||||
case "IPHONE13PRO":
|
||||
case "APPLEWATCH123":
|
||||
brand = "Apple";
|
||||
category = productModel === "IPHONE13PRO" ? "mobile-phones" : "smart-watch";
|
||||
break;
|
||||
|
||||
case "ASUSLAP234":
|
||||
brand = "Asus";
|
||||
category = "laptops";
|
||||
break;
|
||||
|
||||
case "MI11PRO":
|
||||
brand = "Xiaomi";
|
||||
category = "mobile-phones";
|
||||
break;
|
||||
|
||||
case "SONYWH123":
|
||||
case "SONYCAM456":
|
||||
case "SONYSPK234":
|
||||
brand = "Sony";
|
||||
category = productModel === "SONYWH123" ? "headphones" : productModel === "SONYCAM456" ? "cameras" : "speakers";
|
||||
break;
|
||||
|
||||
case "JBLSPK789":
|
||||
brand = "JBL";
|
||||
category = "speakers";
|
||||
break;
|
||||
|
||||
case "NIKONCAM123":
|
||||
brand = "Nikon";
|
||||
category = "cameras";
|
||||
break;
|
||||
|
||||
case "BOSEWH789":
|
||||
brand = "Bose";
|
||||
category = "headphones";
|
||||
break;
|
||||
|
||||
case "HUAWEITAB1":
|
||||
brand = "Huawei";
|
||||
category = "tablets";
|
||||
break;
|
||||
|
||||
case "NOKIAG20":
|
||||
brand = "Nokia";
|
||||
category = "mobile-phones";
|
||||
break;
|
||||
|
||||
case "PANAMW234":
|
||||
brand = "Panasonic";
|
||||
category = "kitchen-appliances";
|
||||
break;
|
||||
|
||||
case "ANKERPB100":
|
||||
brand = "Anker";
|
||||
category = "power-banks";
|
||||
break;
|
||||
|
||||
case "PS5DISC":
|
||||
brand = "Sony";
|
||||
category = "playstations";
|
||||
break;
|
||||
|
||||
default:
|
||||
brand = "malicious";
|
||||
category = "malicious";
|
||||
}
|
||||
|
||||
return { brand, category };
|
||||
};
|
||||
const getBrandAndCategoryForProduct = async (product: (typeof fakeProductsData)[0]) => {
|
||||
const { brand: brandName, category: categoryName } = productMapping(product.model) || {};
|
||||
|
||||
const category = await CategoryModel.findOne({ title_en: categoryName });
|
||||
|
||||
if (!category) {
|
||||
throw new Error(`Category not found for product: ${product.title_fa}`);
|
||||
}
|
||||
const brand = await BrandModel.findOne({ title_en: brandName, category: category._id.toString() });
|
||||
|
||||
if (!brand) {
|
||||
throw new Error(`Brand not found for product: ${product.title_fa}`);
|
||||
}
|
||||
|
||||
return { brand, category };
|
||||
};
|
||||
|
||||
const createFakeProductVariant = (
|
||||
productId: number,
|
||||
shopId: string,
|
||||
warrantyId: number,
|
||||
colorId?: number,
|
||||
sizeId?: number,
|
||||
meterageId?: number,
|
||||
) => {
|
||||
return new ProductVariantModel({
|
||||
product: productId,
|
||||
rate: faker.datatype.float({ min: 1, max: 5 }),
|
||||
warranty: warrantyId,
|
||||
shop: shopId,
|
||||
color: colorId,
|
||||
size: sizeId,
|
||||
meterage: meterageId,
|
||||
sellerSpecialCode: crypto.randomUUID().slice(0, 6).toUpperCase(),
|
||||
market_status: faker.helpers.arrayElement([ProductMarketStatus.Marketable]),
|
||||
postingTime: faker.datatype.number({ min: 1, max: 10 }),
|
||||
price: {
|
||||
order_limit: faker.datatype.number({ min: 1, max: 10 }),
|
||||
retailPrice: faker.datatype.number({ min: 10000, max: 100000000 }),
|
||||
is_specialSale: true,
|
||||
discount_percent: faker.datatype.number({ min: 1, max: 50 }),
|
||||
specialSale_order_limit: faker.datatype.number({ min: 1, max: 5 }),
|
||||
specialSale_quantity: faker.datatype.number({ min: 1, max: 5 }),
|
||||
specialSale_endDate: TimeService.convertGregorianToPersian(faker.date.future()),
|
||||
},
|
||||
saleFormat: {
|
||||
retail: true,
|
||||
wholeSale: [
|
||||
{ from: 10, to: 30, price: faker.datatype.number({ min: 10000, max: 100000000 }) },
|
||||
{ from: 30, to: 50, price: faker.datatype.number({ min: 10000, max: 100000000 }) },
|
||||
{ from: 50, to: 100, price: faker.datatype.number({ min: 10000, max: 100000000 }) },
|
||||
],
|
||||
},
|
||||
stock: faker.datatype.number({ min: 20, max: 100 }),
|
||||
dimensions: {
|
||||
package_weight: faker.datatype.number({ min: 1, max: 5 }),
|
||||
package_height: faker.datatype.number({ min: 10, max: 100 }),
|
||||
package_length: faker.datatype.number({ min: 10, max: 100 }),
|
||||
package_width: faker.datatype.number({ min: 10, max: 100 }),
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
export const seedProduct = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("start seeding products");
|
||||
|
||||
// Fetch warranties and shipment methods
|
||||
const warranties = await WarrantyModel.find().limit(10);
|
||||
const shipments = (await ShipmentModel.find()).map((shipper) => shipper._id);
|
||||
const colors = (await ColorModel.find()).map((color) => color._id);
|
||||
const sizes = (await SizeModel.find()).map((size) => size._id);
|
||||
const meterages = (await MeterageModel.find()).map((meterage) => meterage._id);
|
||||
|
||||
if (!warranties.length) {
|
||||
throw new Error("No warranties found in the database. Please seed them first.");
|
||||
}
|
||||
|
||||
const remainingProducts = [...fakeProductsData];
|
||||
|
||||
for (let i = 0; i < 10; i++) {
|
||||
// Create fake seller
|
||||
const seller = await SellerModel.create(CreateFakeSellerData());
|
||||
await WalletModel.create({ seller: seller._id.toString() });
|
||||
const shop = await ShopModel.create(createFakeShopData(faker.helpers.arrayElements(shipments, 3), seller._id.toString()));
|
||||
|
||||
const sellerProducts = remainingProducts.splice(0, 5);
|
||||
|
||||
for (const productData of sellerProducts) {
|
||||
// Get the correct brand and category for the product
|
||||
const { brand, category } = await getBrandAndCategoryForProduct(productData);
|
||||
const catAttributes = await CategoryAttributeModel.find({ category: category._id.toString() });
|
||||
const attributeValues = await AttributeValueModel.find({ attribute: { $in: catAttributes.map((att) => att._id) } });
|
||||
|
||||
const specifications: ISpecifications[] = catAttributes.map((catAttr) => {
|
||||
const valuesForAttribute = attributeValues
|
||||
.filter((attValue) => attValue.attribute.toString() === catAttr._id.toString())
|
||||
.map((attValue) => attValue.text);
|
||||
|
||||
return {
|
||||
title: catAttr.title,
|
||||
values: valuesForAttribute,
|
||||
};
|
||||
});
|
||||
|
||||
const product = await new ProductModel({
|
||||
...productData,
|
||||
shop: shop._id,
|
||||
specifications,
|
||||
brand: brand._id.toString(),
|
||||
category: category._id.toString(),
|
||||
}).save();
|
||||
|
||||
for (let k = 0; k < 3; k++) {
|
||||
const variant = await createFakeProductVariant(
|
||||
product._id,
|
||||
shop._id.toString(),
|
||||
faker.helpers.arrayElement(warranties)._id,
|
||||
productData.color ? faker.helpers.arrayElement(colors) : undefined,
|
||||
productData.size ? faker.helpers.arrayElement(sizes) : undefined,
|
||||
productData.meterage ? faker.helpers.arrayElement(meterages) : undefined,
|
||||
).save();
|
||||
product.variants.push(variant._id);
|
||||
await product.save();
|
||||
}
|
||||
}
|
||||
|
||||
if (remainingProducts.length < 5) break;
|
||||
}
|
||||
logger.info("Seeding product completed!");
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
logger.error("Failed to seed product and variant:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,61 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { ReportQuestionModel } from "../../modules/product/models/reportQuestion.model";
|
||||
|
||||
const Questions = [
|
||||
{
|
||||
title: "نام کالا نادرست است",
|
||||
type: "checkbox",
|
||||
},
|
||||
{
|
||||
title: "عکس کالا نامناسب است",
|
||||
type: "checkbox",
|
||||
},
|
||||
{
|
||||
title: "مشخصات کالا نادرست است",
|
||||
type: "checkbox",
|
||||
},
|
||||
{
|
||||
title: "توضیحات کالا نادرست است",
|
||||
type: "checkbox",
|
||||
},
|
||||
{
|
||||
title: "کالا غیراصل است",
|
||||
type: "checkbox",
|
||||
},
|
||||
{
|
||||
title: "کالا ناقض قوانین جمهوری اسلامی است",
|
||||
type: "checkbox",
|
||||
},
|
||||
{
|
||||
title: "کالا تکراری است",
|
||||
type: "checkbox",
|
||||
// related_questions: [relatedQues._id],
|
||||
},
|
||||
];
|
||||
|
||||
export const ReportQuesSeeder = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("ReportQuestion seeding started");
|
||||
|
||||
await ReportQuestionModel.deleteMany();
|
||||
for (const question of Questions) {
|
||||
await ReportQuestionModel.create(question);
|
||||
}
|
||||
|
||||
// const relatedQues = await ReportQuestionModel.create({
|
||||
// title: "کد کالای مشابه ",
|
||||
// type: "number",
|
||||
// placeholder: "https://shinan.ir/product/SHP-313420/",
|
||||
// });
|
||||
|
||||
// await ReportQuestionModel.create({
|
||||
// title: "کالا تکراری است",
|
||||
// type: "checkbox",
|
||||
// related_questions: [relatedQues._id],
|
||||
// });
|
||||
|
||||
logger.info("report questions seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("error seeding the report questions:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,36 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { RoleEnum } from "../../modules/admin/models/Abstraction/IRole";
|
||||
import { RoleModel } from "../../modules/admin/models/role.model";
|
||||
|
||||
const createDefaultRoles = async (logger: Logger) => {
|
||||
logger.info("create roles started", "SEED");
|
||||
|
||||
// const roles = Object.values(RoleEnum);
|
||||
const rolesWithPermissions = [
|
||||
{
|
||||
role: RoleEnum.SUPERADMIN,
|
||||
},
|
||||
{
|
||||
role: RoleEnum.MODERATOR,
|
||||
},
|
||||
{
|
||||
role: RoleEnum.EDITOR,
|
||||
},
|
||||
];
|
||||
const createdRoles = await Promise.all(
|
||||
rolesWithPermissions.map(async ({ role }) => {
|
||||
const existingRole = await RoleModel.findOne({ name: role });
|
||||
if (!existingRole) {
|
||||
return RoleModel.create({ name: role });
|
||||
}
|
||||
return existingRole;
|
||||
}),
|
||||
);
|
||||
if (createdRoles) {
|
||||
logger.info("Default roles created", "SEED");
|
||||
} else {
|
||||
logger.warn("Default roles already exists", "SEED");
|
||||
}
|
||||
};
|
||||
|
||||
export { createDefaultRoles };
|
||||
@@ -0,0 +1,75 @@
|
||||
import { DeliveryType } from "../../common/enums/shipment.enum";
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { ShipmentModel } from "../../modules/shipment/models/shipment.model";
|
||||
|
||||
export const SeedShipment = async (logger: Logger) => {
|
||||
const providers = [
|
||||
{
|
||||
name: "پست",
|
||||
description: "ارسال توسط پست",
|
||||
costs: [
|
||||
{ weightRange: { min: 0, max: 1 }, cost_first: 40000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 1, max: 5 }, cost_first: 80000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 5, max: 10 }, cost_first: 100000, cost_rest: 2000 },
|
||||
],
|
||||
deliveryTime: 5, // Standard (3-5 days)
|
||||
deliveryType: DeliveryType.Standard,
|
||||
},
|
||||
{
|
||||
name: "چاپار",
|
||||
description: "ارائه بهترین راه حل های جهانی لجستیک چاپار",
|
||||
costs: [
|
||||
{ weightRange: { min: 0, max: 2 }, cost_first: 40000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 2, max: 6 }, cost_first: 80000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 6, max: 12 }, cost_first: 100000, cost_rest: 2000 },
|
||||
],
|
||||
deliveryTime: 6, // Standard (4-6 days)
|
||||
deliveryType: DeliveryType.Standard,
|
||||
},
|
||||
{
|
||||
name: "پیک",
|
||||
description: "ارسال توسط پیک",
|
||||
costs: [
|
||||
{ weightRange: { min: 0, max: 1 }, cost_first: 40000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 1, max: 3 }, cost_first: 80000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 3, max: 6 }, cost_first: 100000, cost_rest: 2000 },
|
||||
],
|
||||
deliveryTime: 0, // Same Day
|
||||
deliveryType: DeliveryType.SameDay,
|
||||
},
|
||||
{
|
||||
name: "تیپاکس",
|
||||
description: "ارسال بسته های پستی در سریعترین زمان، از درب منزل با امکان پرداخت هزینه بعد از ارسال و پوشش تمام نقاط ایران",
|
||||
costs: [
|
||||
{ weightRange: { min: 0, max: 1 }, cost_first: 40000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 1, max: 5 }, cost_first: 80000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 5, max: 10 }, cost_first: 100000, cost_rest: 2000 },
|
||||
],
|
||||
deliveryTime: 2, // Express (1-2 days)
|
||||
deliveryType: DeliveryType.Express,
|
||||
},
|
||||
{
|
||||
name: "باربری",
|
||||
description: "ارسال توسط باربری",
|
||||
costs: [
|
||||
{ weightRange: { min: 0, max: 10 }, cost_first: 40000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 10, max: 20 }, cost_first: 80000, cost_rest: 2000 },
|
||||
{ weightRange: { min: 20, max: 50 }, cost_first: 100000, cost_rest: 2000 },
|
||||
],
|
||||
deliveryTime: 7, // Freight (5-7 days)
|
||||
deliveryType: DeliveryType.Standard,
|
||||
},
|
||||
];
|
||||
|
||||
try {
|
||||
logger.info("ShipmentMethod seeding started");
|
||||
|
||||
for (const provider of providers) {
|
||||
await ShipmentModel.create(provider);
|
||||
}
|
||||
|
||||
logger.info("Shipment Providers seeded successfully");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding Shipment providers:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,38 @@
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { TicketCategoryModel } from "../../modules/ticket/models/ticketCategory.model";
|
||||
|
||||
// Define ticket categories to seed
|
||||
const ticketCategories = [
|
||||
{
|
||||
title_fa: "مشکل فنی",
|
||||
description: "مشکلات مربوط به سیستم، سایت یا فروشگاه.",
|
||||
},
|
||||
{
|
||||
title_fa: "مشکلات مالی",
|
||||
description: "مشکلات مربوط به پرداختها و مسائل مالی.",
|
||||
},
|
||||
{
|
||||
title_fa: "پشتیبانی محصول",
|
||||
description: "سوالات و پشتیبانیهای مربوط به محصولات.",
|
||||
},
|
||||
{
|
||||
title_fa: "مشکلات ارسال",
|
||||
description: "مشکلات مربوط به ارسال سفارشات و حمل و نقل.",
|
||||
},
|
||||
{
|
||||
title_fa: "درخواست راهنمایی",
|
||||
description: "درخواستها برای راهنمایی و کمک در مورد مسائل مختلف.",
|
||||
},
|
||||
];
|
||||
|
||||
export const seedTicketCategories = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("start seeding the ticket category");
|
||||
|
||||
await TicketCategoryModel.insertMany(ticketCategories);
|
||||
|
||||
logger.info("Ticket categories seeded successfully!");
|
||||
} catch (error) {
|
||||
logger.error("Failed to seed ticket categories:", error);
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,47 @@
|
||||
import { faker } from "@faker-js/faker"; // Use faker for generating random data
|
||||
|
||||
import { StatusEnum } from "../../common/enums/status.enum";
|
||||
import { Logger } from "../../core/logging/logger";
|
||||
import { WarrantyModel } from "../../modules/warranty/models/warranty.model";
|
||||
|
||||
const warrantyNames = [
|
||||
"Iran Warranty Co.",
|
||||
"Pars Guarantee",
|
||||
"Tehran Warranty Services",
|
||||
"Safir Warranty",
|
||||
"Farda Warranty Solutions",
|
||||
"Aryan Protection",
|
||||
"Mehr Warranty",
|
||||
"Saman Warranty Group",
|
||||
"Persian Warranty Solutions",
|
||||
"Shahab After Sales",
|
||||
"Payam Warranty",
|
||||
"Kavir Protection",
|
||||
"Tajrish Warranty",
|
||||
"Sina Warranty",
|
||||
"Atlas Warranty Services",
|
||||
"Sepahan Warranty",
|
||||
"Kish Warranty Group",
|
||||
"Navid Warranty Solutions",
|
||||
"Alborz Protection Services",
|
||||
"Raha Warranty Solutions",
|
||||
];
|
||||
|
||||
export const seedWarranty = async (logger: Logger) => {
|
||||
try {
|
||||
logger.info("Warranty seeding started");
|
||||
|
||||
for (const name of warrantyNames) {
|
||||
await WarrantyModel.create({
|
||||
name,
|
||||
status: StatusEnum.Approved,
|
||||
duration: faker.datatype.number({ min: 1, max: 36 }) + " months",
|
||||
logoUrl: faker.image.business(),
|
||||
});
|
||||
}
|
||||
|
||||
logger.info("Warranty seeding complete!");
|
||||
} catch (error) {
|
||||
logger.error("Error seeding warranties:", error);
|
||||
}
|
||||
};
|
||||
Reference in New Issue
Block a user