Adds docker-compose.yml (Postgres on host port 5433, to avoid clashing with another project's container already using 5432 on this machine) and .env.example so `docker compose up -d` + `cp .env.example .env.local` gets a working local DB. Adds a db:seed script alongside the existing db:* scripts. Rewrites README's "Adding a Database" section, which still described Better Auth's DB as optional/hypothetical even though this project already requires Postgres for both its own data and Better Auth's tables. Fills in CLAUDE.md's Data layer connection-details placeholder and fixes two more stale pnpm references and a wrong migrations path (src/db/migrations/ instead of the actual drizzle/) found nearby. Also fixes a real bug the new docs surfaced: `npm run db:seed` didn't load .env.local the way drizzle-kit does, so DATABASE_URL was silently unset when run as documented. seed.ts now loads env the same way drizzle.config.ts already does. Verified the full documented flow end-to-end against a fresh container: migrate, better-auth migrate, seed, dev server, real page render. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
100 lines
2.7 KiB
TypeScript
100 lines
2.7 KiB
TypeScript
import type { NodePgDatabase } from 'drizzle-orm/node-postgres'
|
|
|
|
import * as schema from '#/db/schema.ts'
|
|
|
|
// Sample Brand/menu/hardware data for local dev and as the shared fixture
|
|
// tests seed against. Specific menu items are explicitly out of scope for
|
|
// the ordering spec — Pizza/Burger here are illustrative, not final content.
|
|
export const seedGhostKitchen = async (db: NodePgDatabase<typeof schema>) => {
|
|
const [brand] = await db
|
|
.insert(schema.brands)
|
|
.values({ name: 'Ghost Kitchen' })
|
|
.returning()
|
|
|
|
const [ovenTag] = await db
|
|
.insert(schema.machineTags)
|
|
.values({ name: 'oven' })
|
|
.returning()
|
|
const [grillTag] = await db
|
|
.insert(schema.machineTags)
|
|
.values({ name: 'grill' })
|
|
.returning()
|
|
const [assemblyTag] = await db
|
|
.insert(schema.machineTags)
|
|
.values({ name: 'assembly' })
|
|
.returning()
|
|
|
|
const [oven1] = await db
|
|
.insert(schema.machines)
|
|
.values({ name: 'Oven 1', machineTagId: ovenTag.id })
|
|
.returning()
|
|
const [grill1] = await db
|
|
.insert(schema.machines)
|
|
.values({ name: 'Grill 1', machineTagId: grillTag.id })
|
|
.returning()
|
|
const [assembly1] = await db
|
|
.insert(schema.machines)
|
|
.values({ name: 'Assembly Station 1', machineTagId: assemblyTag.id })
|
|
.returning()
|
|
|
|
const [pizza] = await db
|
|
.insert(schema.menuItems)
|
|
.values({
|
|
brandId: brand.id,
|
|
name: 'Pizza',
|
|
description: 'Classic oven-baked pizza.',
|
|
priceCents: 1299,
|
|
})
|
|
.returning()
|
|
|
|
await db.insert(schema.menuItemSteps).values({
|
|
menuItemId: pizza.id,
|
|
sequence: 1,
|
|
machineTagId: ovenTag.id,
|
|
estimatedDurationSeconds: 600,
|
|
})
|
|
|
|
const [burger] = await db
|
|
.insert(schema.menuItems)
|
|
.values({
|
|
brandId: brand.id,
|
|
name: 'Burger',
|
|
description: 'Grilled burger, assembled to order.',
|
|
priceCents: 999,
|
|
})
|
|
.returning()
|
|
|
|
await db.insert(schema.menuItemSteps).values([
|
|
{
|
|
menuItemId: burger.id,
|
|
sequence: 1,
|
|
machineTagId: grillTag.id,
|
|
estimatedDurationSeconds: 240,
|
|
},
|
|
{
|
|
menuItemId: burger.id,
|
|
sequence: 2,
|
|
machineTagId: assemblyTag.id,
|
|
estimatedDurationSeconds: 90,
|
|
},
|
|
])
|
|
|
|
return {
|
|
brand,
|
|
machineTags: { oven: ovenTag, grill: grillTag, assembly: assemblyTag },
|
|
machines: { oven1, grill1, assembly1 },
|
|
menuItems: { pizza, burger },
|
|
}
|
|
}
|
|
|
|
if (import.meta.url === `file://${process.argv[1]}`) {
|
|
const { config } = await import('dotenv')
|
|
config({ path: ['.env.local', '.env'] })
|
|
|
|
const { drizzle } = await import('drizzle-orm/node-postgres')
|
|
const db = drizzle(process.env.DATABASE_URL!, { schema })
|
|
await seedGhostKitchen(db)
|
|
console.log('Seeded Ghost Kitchen sample data.')
|
|
process.exit(0)
|
|
}
|