diff --git a/src/mikro/benchmark-pg.ts b/src/mikro/benchmark-pg.ts index 27cb005..a16147b 100644 --- a/src/mikro/benchmark-pg.ts +++ b/src/mikro/benchmark-pg.ts @@ -1,34 +1,35 @@ import 'reflect-metadata'; -import { MikroORM, EntitySchema } from '@mikro-orm/core'; +import { exit } from 'node:process'; +import { MikroORM } from '@mikro-orm/core'; import { PostgreSqlDriver } from '@mikro-orm/postgresql'; import dotenv from 'dotenv'; -import { Customer, CustomerSchema } from './schema'; -import { Employee, EmployeeSchema } from './schema'; +import { CustomerSchema } from './schema'; +import { EmployeeSchema } from './schema'; import { Order, OrderSchema } from './schema'; -import { OrderDetail, OrderDetailSchema } from './schema'; -import { Product, ProductSchema } from './schema'; -import { Supplier, SupplierSchema } from './schema'; +import { OrderDetailSchema } from './schema'; +import { ProductSchema } from './schema'; +import { SupplierSchema } from './schema'; dotenv.config(); const ITERATIONS = Number.parseInt(process.env.ITERATIONS); +const ROUNDS = Number.parseInt(process.env.ROUNDS); +const POOLSIZE = Number.parseInt(process.env.POOLSIZE) async function main() { const orm = await MikroORM.init({ - // metadataProvider: TSONMetadataProvider, entities: [CustomerSchema, EmployeeSchema, OrderSchema, OrderDetailSchema, ProductSchema, SupplierSchema], discovery: { warnWhenNoEntities: true, requireEntitiesArray: false, alwaysAnalyseProperties: true, }, - // entities: [Customer, Employee, Order, OrderDetail, Product, Supplier], - dbName: 'your_db_name', + dbName: 'postgres', driver: PostgreSqlDriver, clientUrl: `${process.env.POSTGRES_URL}`, pool: { - min: 1, - max: 1 + min: POOLSIZE, + max: POOLSIZE }, debug: false, }); @@ -37,30 +38,37 @@ async function main() { async function benchmark() { await warmup(); - await getRowsWithRelations(); + console.time(`mikro:pool ${POOLSIZE}`); + for (let i = 0; i < ROUNDS; i++) { + await getRowsWithRelations(); + } + console.timeEnd(`mikro:pool ${POOLSIZE}`) + await orm.close(true); + exit(0); } async function warmup() { const em = orm.em.fork(); - await em.find(Order, {}, { limit: 1 }); + //to initate possible lazy loaded pool + const promises = []; + for (let i = 0; i < ITERATIONS; i++) { + promises.push(em.find(Order, {}, { limit: 1 })); + } + await Promise.all(promises); } async function getRowsWithRelations() { const em = orm.em.fork(); - console.time('mikroORM'); const promises = []; for (let i = 0; i < ITERATIONS; i++) { const p = em.find(Order, {}, { - populate: ['customer', 'employee', 'orderDetails.product.supplier'], + populate: ['customer', 'employee', 'orderDetails.product.supplier'], }).then(JSON.stringify); promises.push(p); } await Promise.all(promises); - console.timeEnd('mikroORM'); } - - await orm.close(true); } diff --git a/src/mikro/schema.ts b/src/mikro/schema.ts index 5e98742..1aaee06 100644 --- a/src/mikro/schema.ts +++ b/src/mikro/schema.ts @@ -1,7 +1,7 @@ import { EntitySchema, Collection, type Rel } from '@mikro-orm/core'; // Customer entity -export class Customer { +export class Customer { id!: string; companyName!: string; contactName!: string; @@ -18,6 +18,7 @@ export class Customer { export const CustomerSchema = new EntitySchema({ name: 'Customer', + tableName: 'customers', properties: { id: { type: 'string', primary: true }, companyName: { type: 'string', fieldName: 'company_name' }, @@ -47,14 +48,15 @@ export class OrderDetail { export const OrderDetailSchema = new EntitySchema({ name: 'OrderDetail', + tableName: 'order_details', properties: { unitPrice: { type: 'number', fieldName: 'unit_price' }, quantity: { type: 'number' }, discount: { type: 'number' }, - orderId: { type: 'string', primary: true, fieldName: 'order_id' }, - productId: { type: 'string', primary: true, fieldName: 'product_id' }, - order: { kind: 'm:1', entity: () => Order }, - product: { kind: 'm:1', entity: () => Product }, + // orderId: { type: 'string', primary: true}, + // productId: { type: 'string', primary: true }, + order: { kind: 'm:1', entity: () => Order, fieldName: 'order_id', primary: true }, + product: { kind: 'm:1', entity: () => Product, fieldName: 'product_id', primary: true }, }, }); @@ -80,6 +82,7 @@ export class Employee { export const EmployeeSchema = new EntitySchema({ name: 'Employee', + tableName: 'employees', properties: { id: { type: 'string', primary: true }, lastName: { type: 'string', fieldName: 'last_name' }, @@ -113,8 +116,8 @@ export class Order { shipRegion?: string; shipPostalCode?: string; shipCountry!: string; - customerId!: string; - employeeId!: string; + // customerId!: string; + // employeeId!: string; customer!: Rel; employee!: Rel; orderDetails = new Collection(this); @@ -122,6 +125,7 @@ export class Order { export const OrderSchema = new EntitySchema({ name: 'Order', + tableName: 'orders', properties: { id: { type: 'string', primary: true }, orderDate: { type: 'Date', fieldName: 'order_date' }, @@ -134,10 +138,10 @@ export const OrderSchema = new EntitySchema({ shipRegion: { type: 'string', nullable: true, fieldName: 'ship_region' }, shipPostalCode: { type: 'string', nullable: true, fieldName: 'ship_postal_code' }, shipCountry: { type: 'string', fieldName: 'ship_country' }, - customerId: { type: 'string', fieldName: 'customer_id' }, - employeeId: { type: 'string', fieldName: 'employee_id' }, - customer: { kind: 'm:1', entity: () => Customer }, - employee: { kind: 'm:1', entity: () => Employee }, + // customerId: { type: 'string', fieldName: 'customer_id' }, + // employeeId: { type: 'string' }, + customer: { kind: 'm:1', entity: () => Customer, fieldName: 'customer_id' }, + employee: { kind: 'm:1', entity: () => Employee, fieldName: 'employee_id' }, orderDetails: { kind: '1:m', entity: () => OrderDetail, mappedBy: 'order' }, }, }); @@ -159,6 +163,7 @@ export class Product { export const ProductSchema = new EntitySchema({ name: 'Product', + tableName: 'products', properties: { id: { type: 'string', primary: true }, name: { type: 'string' }, @@ -168,8 +173,8 @@ export const ProductSchema = new EntitySchema({ unitsOnOrder: { type: 'number', fieldName: 'units_on_order' }, reorderLevel: { type: 'number', fieldName: 'reorder_level' }, discontinued: { type: 'number' }, - supplierId: { type: 'string', fieldName: 'supplier_id' }, - supplier: { kind: 'm:1', entity: () => Supplier }, + // supplierId: { type: 'string', fieldName: 'supplier_id' }, + supplier: { kind: 'm:1', entity: () => Supplier, fieldName: 'supplier_id' }, orderDetails: { kind: '1:m', entity: () => OrderDetail, mappedBy: 'product' }, }, }); @@ -191,6 +196,7 @@ export class Supplier { export const SupplierSchema = new EntitySchema({ name: 'Supplier', + tableName: 'suppliers', properties: { id: { type: 'string', primary: true }, companyName: { type: 'string', fieldName: 'company_name' },