This commit is contained in:
Your Name committed 2026-06-07 17:17:01 +07:00
1 parent d325cd8763
commit c6bf2f70ac
45 files changed
+5195 -338

No files matched your search

+712
View File
@@ -0,0 +1,712 @@
import { PrismaClient } from '@prisma/client';
import { Pool } from 'pg';
import { PrismaPg } from '@prisma/adapter-pg';
const pool = new Pool({ connectionString: process.env.DATABASE_URL });
const adapter = new PrismaPg(pool);
const prisma = new PrismaClient({ adapter });
async function main() {
console.log("🌱 Seeding Dynamic Page Builder...");
// 1. Create the HomePage
const page = await prisma.page.upsert({
where: { slug: "home" },
update: {},
create: {
slug: "home",
title: "Home Page",
isPublished: true,
}
});
console.log(`✅ Created page: ${page.title} (slug: ${page.slug})`);
// Clear existing sections for home page so we don't duplicate
await prisma.pageSection.deleteMany({
where: { pageId: page.id }
});
// 2. Create default sections: HERO, CATEGORIES, PRODUCTS, BANNER, TEXT
// Section 1: Hero
await prisma.pageSection.create({
data: {
pageId: page.id,
type: "HERO",
order: 1,
isActive: true,
payload: {
tagline: "VIBRANT ELEGANCE COLLECTION",
title: "Inhale [Serenity]",
description: "Crafting premium sensory experiences that transform your space into a sanctuary of peace.",
imageUrl: "/images/hero.png",
buttonText: "Explore Collection",
buttonLink: "/shop"
}
}
});
// Section 2: Categories
await prisma.pageSection.create({
data: {
pageId: page.id,
type: "CATEGORIES",
order: 2,
isActive: true,
payload: {
title: "Our Collections",
subtitle: "Discover the perfect scent for every moment"
}
}
});
// Section 3: Products (Featured Picks)
await prisma.pageSection.create({
data: {
pageId: page.id,
type: "PRODUCTS",
order: 3,
isActive: true,
payload: {
title: "Featured Picks",
subtitle: "Hand-picked fragrances recommended just for you",
type: "featured",
limit: 3
}
}
});
// Section 4: Banner
await prisma.pageSection.create({
data: {
pageId: page.id,
type: "BANNER",
order: 4,
isActive: true,
payload: {
imageUrl: "/images/oil_ozone.png",
linkUrl: "/category/1",
title: "Special Offer",
description: "Get 10% off on your first purchase of Oil Ozone collection",
buttonText: "Shop Now"
}
}
});
// Section 5: Text info
await prisma.pageSection.create({
data: {
pageId: page.id,
type: "TEXT",
order: 5,
isActive: true,
payload: {
title: "About HomAroma",
content: "HomAroma is dedicated to sourcing the finest raw materials to formulate high-quality essential oils, reed diffusers, and room sprays. Our goal is to bring nature's purity directly into your life.",
textAlign: "center"
}
}
});
console.log("✅ Seeded 5 default home page sections successfully!");
// 3. Create the Shop Page Layout
const shopPage = await prisma.page.upsert({
where: { slug: "shop-layout" },
update: {},
create: {
slug: "shop-layout",
title: "Shop Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${shopPage.title} (slug: ${shopPage.slug})`);
// Clear existing sections for shop page so we don't duplicate
await prisma.pageSection.deleteMany({
where: { pageId: shopPage.id }
});
// Shop Section 1: Announcement Bar
await prisma.pageSection.create({
data: {
pageId: shopPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["[FREE SHIPPING] on orders over ฿1,500", "New Premium Collection is out now!"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
// Shop Section 2: Hero Banner (Set to active by default to showcase the header capabilities)
await prisma.pageSection.create({
data: {
pageId: shopPage.id,
type: "HERO",
order: 2,
isActive: true,
payload: {
tagline: "CURATED BOTANICALS",
title: "The [Shop] Collection",
description: "Transform your daily space into a luxury escape with our natural aroma range.",
imageUrl: "/images/hero.png",
buttonText: "Learn More",
buttonLink: "/about"
}
}
});
// Shop Section 3: Editorial Tile
await prisma.pageSection.create({
data: {
pageId: shopPage.id,
type: "EDITORIAL_TILE",
order: 3,
isActive: true,
payload: {
title: "Crafted with [Sensory Passion]",
description: "Every formulation at HomAroma is a tribute to pure botanical essences, hand-blended to capture nature’s quiet intelligence.",
imageUrl: "/images/oil_ozone.png",
imagePosition: "right",
buttonText: "Read Our Story",
buttonLink: "/about",
backgroundColor: "#FDFDF9",
textColor: "#1F3D2D"
}
}
});
// Shop Section 4: Newsletter
await prisma.pageSection.create({
data: {
pageId: shopPage.id,
type: "NEWSLETTER",
order: 4,
isActive: true,
payload: {
title: "Begin Your Wellness Journey",
description: "Subscribe to receive 10% off your first purchase and exclusive updates.",
buttonText: "Subscribe",
placeholderText: "Enter your email address",
showPrivacyCheckbox: true,
privacyText: "I agree to the privacy policy."
}
}
});
console.log("✅ Seeded default shop-layout page sections successfully!");
// 4. Create the Scent Guide Page Layout
const scentGuidePage = await prisma.page.upsert({
where: { slug: "scent-guide-layout" },
update: {},
create: {
slug: "scent-guide-layout",
title: "Scent Guide Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${scentGuidePage.title} (slug: ${scentGuidePage.slug})`);
// Clear existing sections for scent guide page so we don't duplicate
await prisma.pageSection.deleteMany({
where: { pageId: scentGuidePage.id }
});
// Scent Guide Section 1: Announcement Bar
await prisma.pageSection.create({
data: {
pageId: scentGuidePage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Explore our Scent Guide to find your signature fragrance", "Read wellness articles crafted by experts"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
// Scent Guide Section 2: Hero Banner
await prisma.pageSection.create({
data: {
pageId: scentGuidePage.id,
type: "HERO",
order: 2,
isActive: true,
payload: {
tagline: "JOURNAL & INSIGHTS",
title: "The [Scent] Guide",
description: "Welcome to the sensory archive of HomAroma. Explore the art and science of botanical aromatherapy.",
imageUrl: "/images/hero.png",
buttonText: "Read Story",
buttonLink: "/about"
}
}
});
// Scent Guide Section 3: Newsletter
await prisma.pageSection.create({
data: {
pageId: scentGuidePage.id,
type: "NEWSLETTER",
order: 3,
isActive: true,
payload: {
title: "Stay Inspired",
description: "Subscribe to our journal and get regular wellness guides, blending tips, and exclusive offers.",
buttonText: "Subscribe",
placeholderText: "Enter your email address",
showPrivacyCheckbox: true,
privacyText: "I agree to the privacy policy."
}
}
});
console.log("✅ Seeded default scent-guide-layout page sections successfully!");
// 5. Create Category Page Layout
const categoryPage = await prisma.page.upsert({
where: { slug: "category-layout" },
update: {},
create: {
slug: "category-layout",
title: "Category Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${categoryPage.title} (slug: ${categoryPage.slug})`);
await prisma.pageSection.deleteMany({
where: { pageId: categoryPage.id }
});
// Announcement Bar for Categories
await prisma.pageSection.create({
data: {
pageId: categoryPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Explore our specialized collections for your sanctuary", "Free premium shipping on orders over ฿1,500"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
// Newsletter at the bottom of Categories
await prisma.pageSection.create({
data: {
pageId: categoryPage.id,
type: "NEWSLETTER",
order: 2,
isActive: true,
payload: {
title: "Join [HomAroma] Circle",
description: "Subscribe to receive announcements of new single-origin botanical releases.",
buttonText: "Subscribe",
placeholderText: "Enter your email address",
showPrivacyCheckbox: true,
privacyText: "I agree to the privacy policy."
}
}
});
// 6. Create Product Detail Page Layout
const productDetailPage = await prisma.page.upsert({
where: { slug: "product-detail-layout" },
update: {},
create: {
slug: "product-detail-layout",
title: "Product Detail Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${productDetailPage.title} (slug: ${productDetailPage.slug})`);
await prisma.pageSection.deleteMany({
where: { pageId: productDetailPage.id }
});
// Announcement Bar for Product Details
await prisma.pageSection.create({
data: {
pageId: productDetailPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Special Offer: Get 10% off your first purchase of single-origin oils", "Hand-formulated with pure botanical extracts"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
// Editorial banner at the bottom of Product Details
await prisma.pageSection.create({
data: {
pageId: productDetailPage.id,
type: "EDITORIAL_TILE",
order: 2,
isActive: true,
payload: {
title: "The [Botanical] Sourcing",
description: "All our raw materials are sustainably harvested at peak potency from verified organic micro-farms worldwide.",
imageUrl: "/images/oil_ozone.png",
imagePosition: "left",
buttonText: "Sourcing Map",
buttonLink: "/about",
backgroundColor: "#FDFDF9",
textColor: "#1F3D2D"
}
}
});
// 7. Create FAQ Page Layout
const faqPage = await prisma.page.upsert({
where: { slug: "faq-layout" },
update: {},
create: {
slug: "faq-layout",
title: "FAQ Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${faqPage.title} (slug: ${faqPage.slug})`);
await prisma.pageSection.deleteMany({
where: { pageId: faqPage.id }
});
// Announcement Bar for FAQ
await prisma.pageSection.create({
data: {
pageId: faqPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Need instant help? Reach out on LINE @homaroma", "FAQ updated for Summer 2026 delivery guidelines"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 4000
}
}
});
// Newsletter at the bottom of FAQ
await prisma.pageSection.create({
data: {
pageId: faqPage.id,
type: "NEWSLETTER",
order: 2,
isActive: true,
payload: {
title: "Stay informed with [HomAroma]",
description: "Sign up to receive shipping updates, care guides, and exclusive collection invites.",
buttonText: "Subscribe",
placeholderText: "Enter your email address",
showPrivacyCheckbox: true,
privacyText: "I agree to the privacy policy."
}
}
});
console.log("✅ Seeded default category, product-detail, and FAQ layout sections successfully!");
// 8. Create Wishlist Page Layout
const wishlistPage = await prisma.page.upsert({
where: { slug: "wishlist-layout" },
update: {},
create: {
slug: "wishlist-layout",
title: "Wishlist Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${wishlistPage.title} (slug: ${wishlistPage.slug})`);
await prisma.pageSection.deleteMany({ where: { pageId: wishlistPage.id } });
await prisma.pageSection.create({
data: {
pageId: wishlistPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Sign up to HomAroma Circle to get 10% off your wishlist items", "Hand-crafted botanicals shipped directly to you"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
await prisma.pageSection.create({
data: {
pageId: wishlistPage.id,
type: "NEWSLETTER",
order: 2,
isActive: true,
payload: {
title: "Don't lose your favorites",
description: "Subscribe to receive price drops, back-in-stock alerts, and exclusive discounts on items in your wishlist.",
buttonText: "Subscribe",
placeholderText: "Enter your email address",
showPrivacyCheckbox: true,
privacyText: "I agree to the privacy policy."
}
}
});
// 9. Create Search Page Layout
const searchPage = await prisma.page.upsert({
where: { slug: "search-layout" },
update: {},
create: {
slug: "search-layout",
title: "Search Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${searchPage.title} (slug: ${searchPage.slug})`);
await prisma.pageSection.deleteMany({ where: { pageId: searchPage.id } });
await prisma.pageSection.create({
data: {
pageId: searchPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Need help finding something? Live Chat with our scent experts on LINE @homaroma"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
await prisma.pageSection.create({
data: {
pageId: searchPage.id,
type: "EDITORIAL_TILE",
order: 2,
isActive: true,
payload: {
title: "Find Your [Signature Scent]",
description: "Aromatherapy is the art of tuning your environment. Discover our curation of room sprays, reed diffusers, and essential oils designed for modern sanctuaries.",
imageUrl: "/images/hero.png",
imagePosition: "right",
buttonText: "Explore Guide",
buttonLink: "/scent-guide",
backgroundColor: "#FDFDF9",
textColor: "#1F3D2D"
}
}
});
// 10. Create Coupons Page Layout
const couponsPage = await prisma.page.upsert({
where: { slug: "coupons-layout" },
update: {},
create: {
slug: "coupons-layout",
title: "Coupons Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${couponsPage.title} (slug: ${couponsPage.slug})`);
await prisma.pageSection.deleteMany({ where: { pageId: couponsPage.id } });
await prisma.pageSection.create({
data: {
pageId: couponsPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Enjoy limited-time discount codes for your sensory sanctuary"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
await prisma.pageSection.create({
data: {
pageId: couponsPage.id,
type: "NEWSLETTER",
order: 2,
isActive: true,
payload: {
title: "Get Exclusive Secret Codes",
description: "Become a subscriber to get weekly private discount codes and early access to new collections.",
buttonText: "Subscribe",
placeholderText: "Enter your email address",
showPrivacyCheckbox: true,
privacyText: "I agree to the privacy policy."
}
}
});
// 11. Create Contact Page Layout
const contactPage = await prisma.page.upsert({
where: { slug: "contact-layout" },
update: {},
create: {
slug: "contact-layout",
title: "Contact Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${contactPage.title} (slug: ${contactPage.slug})`);
await prisma.pageSection.deleteMany({ where: { pageId: contactPage.id } });
await prisma.pageSection.create({
data: {
pageId: contactPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Customer support is available Mon-Sat, 9:00 - 18:00 on LINE @homaroma"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 4000
}
}
});
await prisma.pageSection.create({
data: {
pageId: contactPage.id,
type: "EDITORIAL_TILE",
order: 2,
isActive: true,
payload: {
title: "Our [Bangkok Studio]",
description: "Visit our flagship boutique to experience custom blending sessions and smell our full botanical library in person.",
imageUrl: "/images/hero.png",
imagePosition: "left",
buttonText: "Book Session",
buttonLink: "/about",
backgroundColor: "#FDFDF9",
textColor: "#1F3D2D"
}
}
});
// 12. Create Order Success Page Layout
const orderSuccessPage = await prisma.page.upsert({
where: { slug: "order-success-layout" },
update: {},
create: {
slug: "order-success-layout",
title: "Order Success Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${orderSuccessPage.title} (slug: ${orderSuccessPage.slug})`);
await prisma.pageSection.deleteMany({ where: { pageId: orderSuccessPage.id } });
await prisma.pageSection.create({
data: {
pageId: orderSuccessPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Thank you for shopping with HomAroma! Your package is preparing.", "Your order tracking status will be updated here."],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
await prisma.pageSection.create({
data: {
pageId: orderSuccessPage.id,
type: "EDITORIAL_TILE",
order: 2,
isActive: true,
payload: {
title: "Crafting Your [Sanctuary]",
description: "Every order is carefully packaged by hand using sustainable, biodegradable materials. We ensure your botanicals arrive fresh and ready to enrich your space.",
imageUrl: "/images/oil_ozone.png",
imagePosition: "right",
buttonText: "Our Sustainability Commitments",
buttonLink: "/about",
backgroundColor: "#FDFDF9",
textColor: "#1F3D2D"
}
}
});
// 13. Create Track Order Page Layout
const trackOrderPage = await prisma.page.upsert({
where: { slug: "track-order-layout" },
update: {},
create: {
slug: "track-order-layout",
title: "Track Order Page Layout",
isPublished: true,
}
});
console.log(`✅ Created page: ${trackOrderPage.title} (slug: ${trackOrderPage.slug})`);
await prisma.pageSection.deleteMany({ where: { pageId: trackOrderPage.id } });
await prisma.pageSection.create({
data: {
pageId: trackOrderPage.id,
type: "ANNOUNCEMENT_BAR",
order: 1,
isActive: true,
payload: {
slides: ["Check shipping status live. For any delivery queries, reach LINE @homaroma"],
backgroundColor: "#1F3D2D",
textColor: "#FDFDF9",
speed: 3000
}
}
});
await prisma.pageSection.create({
data: {
pageId: trackOrderPage.id,
type: "EDITORIAL_TILE",
order: 2,
isActive: true,
payload: {
title: "Scenting Your [Daily Rituals]",
description: "While waiting for your order, explore how different botanical notes impact focus, sleep, and emotional balance in our Scent Guide.",
imageUrl: "/images/hero.png",
imagePosition: "left",
buttonText: "Read Scent Guide",
buttonLink: "/scent-guide",
backgroundColor: "#FDFDF9",
textColor: "#1F3D2D"
}
}
});
console.log("✅ Seeded default Category, Product Detail, FAQ, Wishlist, Search, Coupons, Contact, Order Success, and Track Order layouts successfully!");
}
main()
.catch((e) => {
console.error("❌ Error seeding page:", e);
process.exit(1);
})
.finally(async () => {
await prisma.$disconnect();
await pool.end();
});