feat(pricing,types): price list API + price calculations with price lists (#5498)
**what:** **PriceList Service APIs:** - createPriceList - updatePriceList - addPriceListPrices - removePriceListRules - setPriceListRules - deletePriceList - listPriceLists - listAndCountPriceLists **Price Calculations** - Returns prices with price list prices - Returns a new shape with calculated and original prices Co-authored-by: Philip Korsholm <88927411+pKorsholm@users.noreply.github.com>
This commit is contained in:
co-authored by
Philip Korsholm
parent
2947f57db1
commit
1772e80ed1
@@ -146,6 +146,151 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"title": {
|
||||
"name": "title",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"description": {
|
||||
"name": "description",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"status": {
|
||||
"name": "status",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"default": "'draft'",
|
||||
"enumItems": [
|
||||
"active",
|
||||
"draft"
|
||||
],
|
||||
"mappedType": "enum"
|
||||
},
|
||||
"type": {
|
||||
"name": "type",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"default": "'sale'",
|
||||
"enumItems": [
|
||||
"sale",
|
||||
"override"
|
||||
],
|
||||
"mappedType": "enum"
|
||||
},
|
||||
"starts_at": {
|
||||
"name": "starts_at",
|
||||
"type": "timestamptz",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": true,
|
||||
"length": 6,
|
||||
"mappedType": "datetime"
|
||||
},
|
||||
"ends_at": {
|
||||
"name": "ends_at",
|
||||
"type": "timestamptz",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": true,
|
||||
"length": 6,
|
||||
"mappedType": "datetime"
|
||||
},
|
||||
"number_rules": {
|
||||
"name": "number_rules",
|
||||
"type": "integer",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"default": "0",
|
||||
"mappedType": "integer"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamptz",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"length": 6,
|
||||
"default": "now()",
|
||||
"mappedType": "datetime"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamptz",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"length": 6,
|
||||
"default": "now()",
|
||||
"mappedType": "datetime"
|
||||
},
|
||||
"deleted_at": {
|
||||
"name": "deleted_at",
|
||||
"type": "timestamptz",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": true,
|
||||
"length": 6,
|
||||
"mappedType": "datetime"
|
||||
}
|
||||
},
|
||||
"name": "price_list",
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"columnNames": [
|
||||
"deleted_at"
|
||||
],
|
||||
"composite": false,
|
||||
"keyName": "IDX_price_list_deleted_at",
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"keyName": "price_list_pkey",
|
||||
"columnNames": [
|
||||
"id"
|
||||
],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
"id": {
|
||||
@@ -221,6 +366,15 @@
|
||||
"nullable": false,
|
||||
"default": "0",
|
||||
"mappedType": "integer"
|
||||
},
|
||||
"price_list_id": {
|
||||
"name": "price_list_id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": true,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "price_set_money_amount",
|
||||
@@ -244,6 +398,15 @@
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"columnNames": [
|
||||
"price_list_id"
|
||||
],
|
||||
"composite": false,
|
||||
"keyName": "IDX_price_rule_price_list_id",
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"keyName": "price_set_money_amount_pkey",
|
||||
"columnNames": [
|
||||
@@ -281,6 +444,19 @@
|
||||
"referencedTableName": "public.money_amount",
|
||||
"deleteRule": "cascade",
|
||||
"updateRule": "cascade"
|
||||
},
|
||||
"price_set_money_amount_price_list_id_foreign": {
|
||||
"constraintName": "price_set_money_amount_price_list_id_foreign",
|
||||
"columnNames": [
|
||||
"price_list_id"
|
||||
],
|
||||
"localTableName": "public.price_set_money_amount",
|
||||
"referencedColumnNames": [
|
||||
"id"
|
||||
],
|
||||
"referencedTableName": "public.price_list",
|
||||
"deleteRule": "cascade",
|
||||
"updateRule": "cascade"
|
||||
}
|
||||
}
|
||||
},
|
||||
@@ -604,15 +780,6 @@
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"price_list_id": {
|
||||
"name": "price_list_id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "price_rule",
|
||||
@@ -696,6 +863,184 @@
|
||||
"updateRule": "cascade"
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"rule_type_id": {
|
||||
"name": "rule_type_id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"priority": {
|
||||
"name": "priority",
|
||||
"type": "integer",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"default": "0",
|
||||
"mappedType": "integer"
|
||||
},
|
||||
"price_list_id": {
|
||||
"name": "price_list_id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "price_list_rule",
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"columnNames": [
|
||||
"rule_type_id"
|
||||
],
|
||||
"composite": false,
|
||||
"keyName": "IDX_price_list_rule_rule_type_id",
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"columnNames": [
|
||||
"price_list_id"
|
||||
],
|
||||
"composite": false,
|
||||
"keyName": "IDX_price_list_rule_price_list_id",
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"keyName": "IDX_price_list_rule_rule_type_id_price_list_id_unique",
|
||||
"columnNames": [
|
||||
"price_list_id",
|
||||
"rule_type_id"
|
||||
],
|
||||
"composite": true,
|
||||
"primary": false,
|
||||
"unique": true
|
||||
},
|
||||
{
|
||||
"keyName": "price_list_rule_pkey",
|
||||
"columnNames": [
|
||||
"id"
|
||||
],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {
|
||||
"price_list_rule_rule_type_id_foreign": {
|
||||
"constraintName": "price_list_rule_rule_type_id_foreign",
|
||||
"columnNames": [
|
||||
"rule_type_id"
|
||||
],
|
||||
"localTableName": "public.price_list_rule",
|
||||
"referencedColumnNames": [
|
||||
"id"
|
||||
],
|
||||
"referencedTableName": "public.rule_type",
|
||||
"updateRule": "cascade"
|
||||
},
|
||||
"price_list_rule_price_list_id_foreign": {
|
||||
"constraintName": "price_list_rule_price_list_id_foreign",
|
||||
"columnNames": [
|
||||
"price_list_id"
|
||||
],
|
||||
"localTableName": "public.price_list_rule",
|
||||
"referencedColumnNames": [
|
||||
"id"
|
||||
],
|
||||
"referencedTableName": "public.price_list",
|
||||
"updateRule": "cascade"
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"price_list_rule_id": {
|
||||
"name": "price_list_rule_id",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"value": {
|
||||
"name": "value",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "price_list_rule_value",
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"columnNames": [
|
||||
"price_list_rule_id"
|
||||
],
|
||||
"composite": false,
|
||||
"keyName": "IDX_price_list_rule_price_list_rule_value_id",
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"keyName": "price_list_rule_value_pkey",
|
||||
"columnNames": [
|
||||
"id"
|
||||
],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {
|
||||
"price_list_rule_value_price_list_rule_id_foreign": {
|
||||
"constraintName": "price_list_rule_value_price_list_rule_id_foreign",
|
||||
"columnNames": [
|
||||
"price_list_rule_id"
|
||||
],
|
||||
"localTableName": "public.price_list_rule_value",
|
||||
"referencedColumnNames": [
|
||||
"id"
|
||||
],
|
||||
"referencedTableName": "public.price_list_rule",
|
||||
"deleteRule": "cascade",
|
||||
"updateRule": "cascade"
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -101,5 +101,39 @@ export class Migration20230929122253 extends Migration {
|
||||
this.addSql(
|
||||
'alter table "price_rule" add constraint "price_rule_price_set_money_amount_id_foreign" foreign key ("price_set_money_amount_id") references "price_set_money_amount" ("id") on update cascade on delete cascade;'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'create table if not exists "price_list" ("id" text not null, "status" text check ("status" in (\'active\', \'draft\')) not null default \'draft\', "starts_at" timestamptz null, "ends_at" timestamptz null, "number_rules" integer not null default 0, constraint "price_list_pkey" primary key ("id"));'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'create table "price_list_rule" ("id" text not null, "rule_type_id" text not null, "value" text not null, "price_list_id" text not null, constraint "price_list_rule_pkey" primary key ("id"));'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'create index "IDX_price_list_rule_rule_type_id" on "price_list_rule" ("rule_type_id");'
|
||||
)
|
||||
this.addSql(
|
||||
'create index "IDX_price_list_rule_price_list_id" on "price_list_rule" ("price_list_id");'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list_rule" add constraint "price_list_rule_rule_type_id_foreign" foreign key ("rule_type_id") references "rule_type" ("id") on update cascade;'
|
||||
)
|
||||
this.addSql(
|
||||
'alter table "price_list_rule" add constraint "price_list_rule_price_list_id_foreign" foreign key ("price_list_id") references "price_list" ("id") on update cascade;'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" add column "price_list_id" text null;'
|
||||
)
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" add constraint "price_set_money_amount_price_list_id_foreign" foreign key ("price_list_id") references "price_list" ("id") on update cascade on delete set null;'
|
||||
)
|
||||
this.addSql(
|
||||
'create index "IDX_price_rule_price_list_id" on "price_set_money_amount" ("price_list_id");'
|
||||
)
|
||||
|
||||
this.addSql('alter table "price_rule" drop column "price_list_id";')
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
import { Migration } from "@mikro-orm/migrations"
|
||||
|
||||
export class Migration20231101232834 extends Migration {
|
||||
async up(): Promise<void> {
|
||||
this.addSql(
|
||||
'create table "price_list_rule_value" ("id" text not null, "value" text not null, "price_list_rule_id" text not null, constraint "price_list_rule_value_pkey" primary key ("id"));'
|
||||
)
|
||||
this.addSql(
|
||||
'create index "IDX_price_list_rule_price_list_rule_value_id" on "price_list_rule_value" ("price_list_rule_id");'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list_rule_value" add constraint "price_list_rule_value_price_list_rule_id_foreign" foreign key ("price_list_rule_id") references "price_list_rule" ("id") on update cascade on delete cascade;'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
`ALTER TABLE price_list ADD COLUMN IF NOT EXISTS number_rules integer not null default 0`
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list" add column if not exists "title" text not null, add column if not exists "description" text not null, add column if not exists "type" text check ("type" in (\'sale\', \'override\')) not null default \'sale\';'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" drop constraint "price_set_money_amount_price_list_id_foreign";'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" add constraint "price_set_money_amount_price_list_id_foreign" foreign key ("price_list_id") references "price_list" ("id") on update cascade on delete cascade;'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list" add column if not exists "title" text not null, add column if not exists "description" text not null, add column if not exists "type" text check ("type" in (\'sale\', \'override\')) not null default \'sale\', add column if not exists "created_at" timestamptz not null default now(), add column if not exists "updated_at" timestamptz not null default now(), add column if not exists "deleted_at" timestamptz null;'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'create index if not exists "IDX_price_list_deleted_at" on "price_list" ("deleted_at");'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list_rule" drop constraint if exists "IDX_price_list_rule_rule_type_id_price_list_id_unique"'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list_rule" add constraint "IDX_price_list_rule_rule_type_id_price_list_id_unique" unique ("price_list_id", "rule_type_id");'
|
||||
)
|
||||
}
|
||||
|
||||
async down(): Promise<void> {
|
||||
this.addSql('drop table if exists "price_list_rule_value" cascade;')
|
||||
|
||||
this.addSql(`ALTER TABLE price_list DROP COLUMN IF EXISTS number_rules`)
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "title";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "description";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "type";')
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" drop constraint "price_set_money_amount_price_list_id_foreign";'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" add constraint "price_set_money_amount_price_list_id_foreign" foreign key ("price_list_id") references "price_list" ("id") on update cascade on delete set null;'
|
||||
)
|
||||
|
||||
this.addSql('drop index if exists "IDX_price_list_deleted_at";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "title";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "description";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "type";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "created_at";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "updated_at";')
|
||||
|
||||
this.addSql('alter table "price_list" drop column if exists "deleted_at";')
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_list_rule" drop constraint if exists "IDX_price_list_rule_rule_type_id_price_list_id_unique";'
|
||||
)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user