chore: import upstream snapshot with attribution
This commit is contained in:
@@ -0,0 +1,253 @@
|
||||
import BetterSqlite3 from 'better-sqlite3';
|
||||
import { sql } from 'drizzle-orm';
|
||||
import type { BetterSQLite3Database } from 'drizzle-orm/better-sqlite3';
|
||||
import { drizzle } from 'drizzle-orm/better-sqlite3';
|
||||
import { afterAll, afterEach, beforeAll, expect, test } from 'vitest';
|
||||
import { reset, seed } from '../../../src/index.ts';
|
||||
import * as schema from './sqliteSchema.ts';
|
||||
|
||||
let client: BetterSqlite3.Database;
|
||||
let db: BetterSQLite3Database;
|
||||
|
||||
beforeAll(async () => {
|
||||
client = new BetterSqlite3(':memory:');
|
||||
|
||||
db = drizzle(client);
|
||||
|
||||
db.run(
|
||||
sql.raw(`
|
||||
CREATE TABLE \`customer\` (
|
||||
\`id\` text PRIMARY KEY NOT NULL,
|
||||
\`company_name\` text NOT NULL,
|
||||
\`contact_name\` text NOT NULL,
|
||||
\`contact_title\` text NOT NULL,
|
||||
\`address\` text NOT NULL,
|
||||
\`city\` text NOT NULL,
|
||||
\`postal_code\` text,
|
||||
\`region\` text,
|
||||
\`country\` text NOT NULL,
|
||||
\`phone\` text NOT NULL,
|
||||
\`fax\` text
|
||||
);
|
||||
`),
|
||||
);
|
||||
|
||||
db.run(
|
||||
sql.raw(`
|
||||
CREATE TABLE \`order_detail\` (
|
||||
\`unit_price\` numeric NOT NULL,
|
||||
\`quantity\` integer NOT NULL,
|
||||
\`discount\` numeric NOT NULL,
|
||||
\`order_id\` integer NOT NULL,
|
||||
\`product_id\` integer NOT NULL
|
||||
);
|
||||
`),
|
||||
);
|
||||
|
||||
db.run(
|
||||
sql.raw(`
|
||||
CREATE TABLE \`employee\` (
|
||||
\`id\` integer PRIMARY KEY NOT NULL,
|
||||
\`last_name\` text NOT NULL,
|
||||
\`first_name\` text,
|
||||
\`title\` text NOT NULL,
|
||||
\`title_of_courtesy\` text NOT NULL,
|
||||
\`birth_date\` integer NOT NULL,
|
||||
\`hire_date\` integer NOT NULL,
|
||||
\`address\` text NOT NULL,
|
||||
\`city\` text NOT NULL,
|
||||
\`postal_code\` text NOT NULL,
|
||||
\`country\` text NOT NULL,
|
||||
\`home_phone\` text NOT NULL,
|
||||
\`extension\` integer NOT NULL,
|
||||
\`notes\` text NOT NULL,
|
||||
\`reports_to\` integer,
|
||||
\`photo_path\` text
|
||||
);
|
||||
`),
|
||||
);
|
||||
|
||||
db.run(
|
||||
sql.raw(`
|
||||
CREATE TABLE \`order\` (
|
||||
\`id\` integer PRIMARY KEY NOT NULL,
|
||||
\`order_date\` integer NOT NULL,
|
||||
\`required_date\` integer NOT NULL,
|
||||
\`shipped_date\` integer,
|
||||
\`ship_via\` integer NOT NULL,
|
||||
\`freight\` numeric NOT NULL,
|
||||
\`ship_name\` text NOT NULL,
|
||||
\`ship_city\` text NOT NULL,
|
||||
\`ship_region\` text,
|
||||
\`ship_postal_code\` text,
|
||||
\`ship_country\` text NOT NULL,
|
||||
\`customer_id\` text NOT NULL,
|
||||
\`employee_id\` integer NOT NULL
|
||||
);
|
||||
`),
|
||||
);
|
||||
|
||||
db.run(
|
||||
sql.raw(`
|
||||
CREATE TABLE \`product\` (
|
||||
\`id\` integer PRIMARY KEY AUTOINCREMENT NOT NULL,
|
||||
\`name\` text NOT NULL,
|
||||
\`quantity_per_unit\` text NOT NULL,
|
||||
\`unit_price\` numeric NOT NULL,
|
||||
\`units_in_stock\` integer NOT NULL,
|
||||
\`units_on_order\` integer NOT NULL,
|
||||
\`reorder_level\` integer NOT NULL,
|
||||
\`discontinued\` integer NOT NULL,
|
||||
\`supplier_id\` integer NOT NULL
|
||||
);
|
||||
`),
|
||||
);
|
||||
|
||||
db.run(
|
||||
sql.raw(`
|
||||
CREATE TABLE \`supplier\` (
|
||||
\`id\` integer PRIMARY KEY AUTOINCREMENT NOT NULL,
|
||||
\`company_name\` text NOT NULL,
|
||||
\`contact_name\` text NOT NULL,
|
||||
\`contact_title\` text NOT NULL,
|
||||
\`address\` text NOT NULL,
|
||||
\`city\` text NOT NULL,
|
||||
\`region\` text,
|
||||
\`postal_code\` text NOT NULL,
|
||||
\`country\` text NOT NULL,
|
||||
\`phone\` text NOT NULL
|
||||
);
|
||||
`),
|
||||
);
|
||||
});
|
||||
|
||||
afterAll(async () => {
|
||||
client.close();
|
||||
});
|
||||
|
||||
afterEach(async () => {
|
||||
await reset(db, schema);
|
||||
});
|
||||
|
||||
const checkSoftRelations = (
|
||||
customers: (typeof schema.customers.$inferSelect)[],
|
||||
details: (typeof schema.details.$inferSelect)[],
|
||||
employees: (typeof schema.employees.$inferSelect)[],
|
||||
orders: (typeof schema.orders.$inferSelect)[],
|
||||
products: (typeof schema.products.$inferSelect)[],
|
||||
suppliers: (typeof schema.suppliers.$inferSelect)[],
|
||||
) => {
|
||||
// employees soft relations check
|
||||
const employeeIds = new Set(employees.map((employee) => employee.id));
|
||||
const employeesPredicate = employees.every((employee) =>
|
||||
employee.reportsTo !== null && employeeIds.has(employee.reportsTo)
|
||||
);
|
||||
expect(employeesPredicate).toBe(true);
|
||||
|
||||
// orders soft relations check
|
||||
const customerIds = new Set(customers.map((customer) => customer.id));
|
||||
const ordersPredicate1 = orders.every((order) => order.customerId !== null && customerIds.has(order.customerId));
|
||||
expect(ordersPredicate1).toBe(true);
|
||||
|
||||
const ordersPredicate2 = orders.every((order) => order.employeeId !== null && employeeIds.has(order.employeeId));
|
||||
expect(ordersPredicate2).toBe(true);
|
||||
|
||||
// product soft relations check
|
||||
const supplierIds = new Set(suppliers.map((supplier) => supplier.id));
|
||||
const productsPredicate = products.every((product) =>
|
||||
product.supplierId !== null && supplierIds.has(product.supplierId)
|
||||
);
|
||||
expect(productsPredicate).toBe(true);
|
||||
|
||||
// details soft relations check
|
||||
const orderIds = new Set(orders.map((order) => order.id));
|
||||
const detailsPredicate1 = details.every((detail) => detail.orderId !== null && orderIds.has(detail.orderId));
|
||||
expect(detailsPredicate1).toBe(true);
|
||||
|
||||
const productIds = new Set(products.map((product) => product.id));
|
||||
const detailsPredicate2 = details.every((detail) => detail.productId !== null && productIds.has(detail.productId));
|
||||
expect(detailsPredicate2).toBe(true);
|
||||
};
|
||||
|
||||
test('basic seed, soft relations test', async () => {
|
||||
await seed(db, schema);
|
||||
|
||||
const customers = await db.select().from(schema.customers);
|
||||
const details = await db.select().from(schema.details);
|
||||
const employees = await db.select().from(schema.employees);
|
||||
const orders = await db.select().from(schema.orders);
|
||||
const products = await db.select().from(schema.products);
|
||||
const suppliers = await db.select().from(schema.suppliers);
|
||||
|
||||
expect(customers.length).toBe(10);
|
||||
expect(details.length).toBe(10);
|
||||
expect(employees.length).toBe(10);
|
||||
expect(orders.length).toBe(10);
|
||||
expect(products.length).toBe(10);
|
||||
expect(suppliers.length).toBe(10);
|
||||
|
||||
checkSoftRelations(customers, details, employees, orders, products, suppliers);
|
||||
});
|
||||
|
||||
test("redefine(refine) orders count using 'with' in customers, soft relations test", async () => {
|
||||
await seed(db, schema, { count: 11 }).refine(() => ({
|
||||
customers: {
|
||||
count: 4,
|
||||
with: {
|
||||
orders: 2,
|
||||
},
|
||||
},
|
||||
orders: {
|
||||
count: 13,
|
||||
},
|
||||
}));
|
||||
|
||||
const customers = await db.select().from(schema.customers);
|
||||
const details = await db.select().from(schema.details);
|
||||
const employees = await db.select().from(schema.employees);
|
||||
const orders = await db.select().from(schema.orders);
|
||||
const products = await db.select().from(schema.products);
|
||||
const suppliers = await db.select().from(schema.suppliers);
|
||||
|
||||
expect(customers.length).toBe(4);
|
||||
expect(details.length).toBe(11);
|
||||
expect(employees.length).toBe(11);
|
||||
expect(orders.length).toBe(8);
|
||||
expect(products.length).toBe(11);
|
||||
expect(suppliers.length).toBe(11);
|
||||
|
||||
checkSoftRelations(customers, details, employees, orders, products, suppliers);
|
||||
});
|
||||
|
||||
test("sequential using of 'with', soft relations test", async () => {
|
||||
await seed(db, schema, { count: 11 }).refine(() => ({
|
||||
customers: {
|
||||
count: 4,
|
||||
with: {
|
||||
orders: 2,
|
||||
},
|
||||
},
|
||||
orders: {
|
||||
count: 12,
|
||||
with: {
|
||||
details: 3,
|
||||
},
|
||||
},
|
||||
}));
|
||||
|
||||
const customers = await db.select().from(schema.customers);
|
||||
const details = await db.select().from(schema.details);
|
||||
const employees = await db.select().from(schema.employees);
|
||||
const orders = await db.select().from(schema.orders);
|
||||
const products = await db.select().from(schema.products);
|
||||
const suppliers = await db.select().from(schema.suppliers);
|
||||
|
||||
expect(customers.length).toBe(4);
|
||||
expect(details.length).toBe(24);
|
||||
expect(employees.length).toBe(11);
|
||||
expect(orders.length).toBe(8);
|
||||
expect(products.length).toBe(11);
|
||||
expect(suppliers.length).toBe(11);
|
||||
|
||||
checkSoftRelations(customers, details, employees, orders, products, suppliers);
|
||||
});
|
||||
@@ -0,0 +1,128 @@
|
||||
import { relations } from 'drizzle-orm';
|
||||
import { integer, numeric, sqliteTable, text } from 'drizzle-orm/sqlite-core';
|
||||
|
||||
export const customers = sqliteTable('customer', {
|
||||
id: text('id').primaryKey(),
|
||||
companyName: text('company_name').notNull(),
|
||||
contactName: text('contact_name').notNull(),
|
||||
contactTitle: text('contact_title').notNull(),
|
||||
address: text('address').notNull(),
|
||||
city: text('city').notNull(),
|
||||
postalCode: text('postal_code'),
|
||||
region: text('region'),
|
||||
country: text('country').notNull(),
|
||||
phone: text('phone').notNull(),
|
||||
fax: text('fax'),
|
||||
});
|
||||
|
||||
export const employees = sqliteTable(
|
||||
'employee',
|
||||
{
|
||||
id: integer('id').primaryKey(),
|
||||
lastName: text('last_name').notNull(),
|
||||
firstName: text('first_name'),
|
||||
title: text('title').notNull(),
|
||||
titleOfCourtesy: text('title_of_courtesy').notNull(),
|
||||
birthDate: integer('birth_date', { mode: 'timestamp' }).notNull(),
|
||||
hireDate: integer('hire_date', { mode: 'timestamp' }).notNull(),
|
||||
address: text('address').notNull(),
|
||||
city: text('city').notNull(),
|
||||
postalCode: text('postal_code').notNull(),
|
||||
country: text('country').notNull(),
|
||||
homePhone: text('home_phone').notNull(),
|
||||
extension: integer('extension').notNull(),
|
||||
notes: text('notes').notNull(),
|
||||
reportsTo: integer('reports_to'),
|
||||
photoPath: text('photo_path'),
|
||||
},
|
||||
);
|
||||
|
||||
export const employeesRelations = relations(employees, ({ one }) => ({
|
||||
employee: one(employees, {
|
||||
fields: [employees.reportsTo],
|
||||
references: [employees.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export const orders = sqliteTable('order', {
|
||||
id: integer('id').primaryKey(),
|
||||
orderDate: integer('order_date', { mode: 'timestamp' }).notNull(),
|
||||
requiredDate: integer('required_date', { mode: 'timestamp' }).notNull(),
|
||||
shippedDate: integer('shipped_date', { mode: 'timestamp' }),
|
||||
shipVia: integer('ship_via').notNull(),
|
||||
freight: numeric('freight').notNull(),
|
||||
shipName: text('ship_name').notNull(),
|
||||
shipCity: text('ship_city').notNull(),
|
||||
shipRegion: text('ship_region'),
|
||||
shipPostalCode: text('ship_postal_code'),
|
||||
shipCountry: text('ship_country').notNull(),
|
||||
|
||||
customerId: text('customer_id').notNull(),
|
||||
|
||||
employeeId: integer('employee_id').notNull(),
|
||||
});
|
||||
|
||||
export const ordersRelations = relations(orders, ({ one }) => ({
|
||||
customer: one(customers, {
|
||||
fields: [orders.customerId],
|
||||
references: [customers.id],
|
||||
}),
|
||||
employee: one(employees, {
|
||||
fields: [orders.employeeId],
|
||||
references: [employees.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export const suppliers = sqliteTable('supplier', {
|
||||
id: integer('id').primaryKey({ autoIncrement: true }),
|
||||
companyName: text('company_name').notNull(),
|
||||
contactName: text('contact_name').notNull(),
|
||||
contactTitle: text('contact_title').notNull(),
|
||||
address: text('address').notNull(),
|
||||
city: text('city').notNull(),
|
||||
region: text('region'),
|
||||
postalCode: text('postal_code').notNull(),
|
||||
country: text('country').notNull(),
|
||||
phone: text('phone').notNull(),
|
||||
});
|
||||
|
||||
export const products = sqliteTable('product', {
|
||||
id: integer('id').primaryKey({ autoIncrement: true }),
|
||||
name: text('name').notNull(),
|
||||
quantityPerUnit: text('quantity_per_unit').notNull(),
|
||||
unitPrice: numeric('unit_price').notNull(),
|
||||
unitsInStock: integer('units_in_stock').notNull(),
|
||||
unitsOnOrder: integer('units_on_order').notNull(),
|
||||
reorderLevel: integer('reorder_level').notNull(),
|
||||
discontinued: integer('discontinued').notNull(),
|
||||
|
||||
supplierId: integer('supplier_id').notNull(),
|
||||
});
|
||||
|
||||
export const productsRelations = relations(products, ({ one }) => ({
|
||||
supplier: one(suppliers, {
|
||||
fields: [products.supplierId],
|
||||
references: [suppliers.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export const details = sqliteTable('order_detail', {
|
||||
unitPrice: numeric('unit_price').notNull(),
|
||||
quantity: integer('quantity').notNull(),
|
||||
discount: numeric('discount').notNull(),
|
||||
|
||||
orderId: integer('order_id').notNull(),
|
||||
|
||||
productId: integer('product_id').notNull(),
|
||||
});
|
||||
|
||||
export const detailsRelations = relations(details, ({ one }) => ({
|
||||
order: one(orders, {
|
||||
fields: [details.orderId],
|
||||
references: [orders.id],
|
||||
}),
|
||||
product: one(products, {
|
||||
fields: [details.productId],
|
||||
references: [products.id],
|
||||
}),
|
||||
}));
|
||||
Reference in New Issue
Block a user