Merge pull request 'fix: link LineItem to Kot' (#73) from link-line-item-to-kot into master
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful

Reviewed-on: #73
This commit is contained in:
Aravinth Manivannan 2024-07-23 21:50:22 +05:30
commit 520036734d
14 changed files with 143 additions and 38 deletions

View file

@ -1,6 +1,6 @@
{
"db_name": "PostgreSQL",
"query": "INSERT INTO cqrs_ordering_line_item_query (\n version,\n product_name,\n product_id,\n line_item_id,\n quantity_minor_unit,\n quantity_minor_number,\n quantity_major_unit,\n quantity_major_number,\n sale_time,\n deleted\n ) VALUES (\n $1, $2, $3, $4, $5, $6, $7, $8, $9, $10\n );",
"query": "INSERT INTO cqrs_ordering_line_item_query (\n version,\n product_name,\n product_id,\n line_item_id,\n quantity_minor_unit,\n quantity_minor_number,\n quantity_major_unit,\n quantity_major_number,\n created_time,\n kot_id,\n deleted\n ) VALUES (\n $1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11\n );",
"describe": {
"columns": [],
"parameters": {
@ -14,10 +14,11 @@
"Text",
"Int4",
"Timestamptz",
"Uuid",
"Bool"
]
},
"nullable": []
},
"hash": "88f519e645dba9eb091d18e8f5c0db127ac0d070fb81e5b157a68638c3688996"
"hash": "34ba93d669697b7080df26bb23e7d27dcb4352041b04fc9d21e7332f0b8b32be"
}

View file

@ -1,6 +1,6 @@
{
"db_name": "PostgreSQL",
"query": "SELECT \n product_name,\n product_id,\n line_item_id,\n quantity_minor_unit,\n quantity_minor_number,\n quantity_major_unit,\n quantity_major_number,\n sale_time,\n deleted\n FROM\n cqrs_ordering_line_item_query\n WHERE\n line_item_id = $1;",
"query": "SELECT \n product_name,\n product_id,\n line_item_id,\n quantity_minor_unit,\n quantity_minor_number,\n quantity_major_unit,\n quantity_major_number,\n created_time,\n kot_id,\n deleted\n FROM\n cqrs_ordering_line_item_query\n WHERE\n line_item_id = $1;",
"describe": {
"columns": [
{
@ -40,11 +40,16 @@
},
{
"ordinal": 7,
"name": "sale_time",
"name": "created_time",
"type_info": "Timestamptz"
},
{
"ordinal": 8,
"name": "kot_id",
"type_info": "Uuid"
},
{
"ordinal": 9,
"name": "deleted",
"type_info": "Bool"
}
@ -63,8 +68,9 @@
false,
false,
false,
false,
false
]
},
"hash": "2d5ff8c368757fc2d390aaaed23d18fe6888ace9e7e2b9d12f02d2c50d80e685"
"hash": "3b9849078c846bc254aca3d56efd44b9a919e77bdfa9074b6c1b335380a0ce6c"
}

View file

@ -1,6 +1,6 @@
{
"db_name": "PostgreSQL",
"query": "UPDATE\n cqrs_ordering_line_item_query\n SET\n version = $1,\n product_name = $2,\n product_id = $3,\n line_item_id = $4,\n quantity_minor_unit = $5,\n quantity_minor_number = $6,\n quantity_major_unit = $7,\n quantity_major_number = $8,\n sale_time = $9,\n deleted = $10;",
"query": "UPDATE\n cqrs_ordering_line_item_query\n SET\n version = $1,\n product_name = $2,\n product_id = $3,\n line_item_id = $4,\n quantity_minor_unit = $5,\n quantity_minor_number = $6,\n quantity_major_unit = $7,\n quantity_major_number = $8,\n created_time = $9,\n kot_id = $10,\n deleted = $11;",
"describe": {
"columns": [],
"parameters": {
@ -14,10 +14,11 @@
"Text",
"Int4",
"Timestamptz",
"Uuid",
"Bool"
]
},
"nullable": []
},
"hash": "724e980a30694acbdc309702e5349ddff36d11757477e5ec130c1f4209e613dc"
"hash": "c348d55dd91acb0d4697c433f61866b288fec93971bf9ab41faec21680e50f71"
}

View file

@ -6,9 +6,11 @@ CREATE TABLE IF NOT EXISTS cqrs_ordering_line_item_query
(
version bigint CHECK (version >= 0) NOT NULL,
sale_time timestamp with time zone DEFAULT (CURRENT_TIMESTAMP) NOT NULL,
created_time timestamp with time zone DEFAULT (CURRENT_TIMESTAMP) NOT NULL,
line_item_id UUID NOT NULL UNIQUE,
kot_id UUID NOT NULL,
product_name TEXT NOT NULL,
product_id UUID NOT NULL,

View file

@ -47,9 +47,10 @@ pub mod tests {
quantity_minor_number,
quantity_major_unit,
quantity_major_number,
kot_id,
deleted
) VALUES (
$1, $2, $3, $4, $5, $6, $7, $8, $9
$1, $2, $3, $4, $5, $6, $7, $8, $9, $10
);",
1,
line_item.product_name(),
@ -59,6 +60,7 @@ pub mod tests {
line_item.quantity().major().number().clone() as i32,
line_item.quantity().minor().unit().to_string(),
line_item.quantity().minor().number().clone() as i32,
line_item.kot_id(),
line_item.deleted().clone(),
)
.execute(&db.pool)

View file

@ -26,7 +26,8 @@ pub const NEW_LINE_ITEM_NON_UUID: &str = "new_line_item_non_uuid-asdfa";
pub struct LineItemView {
product_name: String,
product_id: Uuid,
sale_time: OffsetDateTime,
kot_id: Uuid,
created_time: OffsetDateTime,
line_item_id: Uuid,
@ -41,9 +42,10 @@ pub struct LineItemView {
impl Default for LineItemView {
fn default() -> Self {
Self {
sale_time: OffsetDateTime::now_utc(),
created_time: OffsetDateTime::now_utc(),
product_name: Default::default(),
product_id: Default::default(),
kot_id: Default::default(),
line_item_id: Default::default(),
@ -80,8 +82,9 @@ impl From<LineItemView> for LineItem {
.product_name(v.product_name)
.line_item_id(v.line_item_id)
.quantity(quantity)
.sale_time(v.sale_time)
.created_time(v.created_time)
.product_id(v.product_id)
.kot_id(v.kot_id)
.deleted(v.deleted)
.build()
.unwrap()
@ -104,7 +107,8 @@ impl View<LineItem> for LineItemView {
self.quantity_major_unit = val.line_item().quantity().major().unit().to_string();
self.quantity_minor_unit = val.line_item().quantity().minor().unit().to_string();
self.sale_time = val.line_item().sale_time().clone();
self.created_time = val.line_item().created_time().clone();
self.kot_id = *val.line_item().kot_id();
self.deleted = false;
}
@ -131,7 +135,8 @@ impl ViewRepository<LineItemView, LineItem> for OrderingDBPostgresAdapter {
quantity_minor_number,
quantity_major_unit,
quantity_major_number,
sale_time,
created_time,
kot_id,
deleted
FROM
cqrs_ordering_line_item_query
@ -165,7 +170,8 @@ impl ViewRepository<LineItemView, LineItem> for OrderingDBPostgresAdapter {
quantity_minor_number,
quantity_major_unit,
quantity_major_number,
sale_time,
created_time,
kot_id,
deleted
FROM
cqrs_ordering_line_item_query
@ -218,10 +224,11 @@ impl ViewRepository<LineItemView, LineItem> for OrderingDBPostgresAdapter {
quantity_minor_number,
quantity_major_unit,
quantity_major_number,
sale_time,
created_time,
kot_id,
deleted
) VALUES (
$1, $2, $3, $4, $5, $6, $7, $8, $9, $10
$1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11
);",
version,
view.product_name,
@ -231,7 +238,8 @@ impl ViewRepository<LineItemView, LineItem> for OrderingDBPostgresAdapter {
view.quantity_minor_number,
view.quantity_major_unit,
view.quantity_major_number,
view.sale_time,
view.created_time,
view.kot_id,
view.deleted,
)
.execute(&self.pool)
@ -253,8 +261,9 @@ impl ViewRepository<LineItemView, LineItem> for OrderingDBPostgresAdapter {
quantity_minor_number = $6,
quantity_major_unit = $7,
quantity_major_number = $8,
sale_time = $9,
deleted = $10;",
created_time = $9,
kot_id = $10,
deleted = $11;",
version,
view.product_name,
view.product_id,
@ -263,7 +272,8 @@ impl ViewRepository<LineItemView, LineItem> for OrderingDBPostgresAdapter {
view.quantity_minor_number,
view.quantity_major_unit,
view.quantity_major_number,
view.sale_time,
view.created_time,
view.kot_id,
view.deleted,
)
.execute(&self.pool)

View file

@ -11,6 +11,7 @@ use time::OffsetDateTime;
use super::errors::*;
use crate::ordering::{
application::port::output::db::kot_id_exists::*,
application::port::output::db::line_item_id_exists::*,
domain::{add_line_item_command::*, line_item_added_event::*, line_item_aggregate::*},
};
@ -27,12 +28,17 @@ pub type AddLineItemServiceObj = Arc<dyn AddLineItemUseCase>;
#[derive(Clone, Builder)]
pub struct AddLineItemService {
db_line_item_id_exists: LineItemIDExistsDBPortObj,
db_kot_id_exists: KotIDExistsDBPortObj,
get_uuid: GetUUIDInterfaceObj,
}
#[async_trait::async_trait]
impl AddLineItemUseCase for AddLineItemService {
async fn add_line_item(&self, cmd: AddLineItemCommand) -> OrderingResult<LineItemAddedEvent> {
if !self.db_kot_id_exists.kot_id_exists(cmd.kot_id()).await? {
return Err(OrderingError::KotIDNotFound);
}
let mut line_item_id = self.get_uuid.get_uuid();
loop {
@ -49,9 +55,10 @@ impl AddLineItemUseCase for AddLineItemService {
}
let line_item = LineItemBuilder::default()
.sale_time(OffsetDateTime::now_utc())
.created_time(cmd.created_time().clone())
.product_name(cmd.product_name().into())
.product_id(*cmd.product_id())
.kot_id(*cmd.kot_id())
.line_item_id(line_item_id)
.quantity(cmd.quantity().clone())
.deleted(false)
@ -98,6 +105,7 @@ pub mod tests {
let s = AddLineItemServiceBuilder::default()
.db_line_item_id_exists(mock_line_item_id_exists_db_port_false(IS_CALLED_ONLY_ONCE))
.db_kot_id_exists(mock_kot_id_exists_db_port_true(IS_CALLED_ONLY_ONCE))
.get_uuid(mock_get_uuid(IS_CALLED_ONLY_ONCE))
.build()
.unwrap();
@ -105,9 +113,28 @@ pub mod tests {
let res = s.add_line_item(cmd.clone()).await.unwrap();
assert_eq!(res.line_item().product_name(), cmd.product_name());
assert_eq!(res.line_item().product_id(), cmd.product_id());
assert_eq!(res.line_item().kot_id(), cmd.kot_id());
assert_eq!(res.line_item().quantity(), cmd.quantity());
assert_eq!(res.line_item().quantity(), cmd.quantity());
assert_eq!(res.line_item().created_time(), cmd.created_time());
assert!(!res.line_item().deleted());
assert_eq!(res.added_by_user(), cmd.adding_by());
}
#[actix_rt::test]
async fn test_service_kot_id_doesnt_exist() {
let cmd = AddLineItemCommand::get_cmd();
let s = AddLineItemServiceBuilder::default()
.db_line_item_id_exists(mock_line_item_id_exists_db_port_false(IS_NEVER_CALLED))
.db_kot_id_exists(mock_kot_id_exists_db_port_false(IS_CALLED_ONLY_ONCE))
.get_uuid(mock_get_uuid(IS_NEVER_CALLED))
.build()
.unwrap();
assert_eq!(
s.add_line_item(cmd.clone()).await,
Err(OrderingError::KotIDNotFound)
);
}
}

View file

@ -47,10 +47,11 @@ impl DeleteLineItemUseCase for DeleteLineItemService {
}
let deleted_line_item = LineItemBuilder::default()
.sale_time(cmd.line_item().sale_time().clone())
.created_time(cmd.line_item().created_time().clone())
.product_name(cmd.line_item().product_name().into())
.product_id(*cmd.line_item().product_id())
.line_item_id(*cmd.line_item().line_item_id())
.kot_id(*cmd.line_item().kot_id())
.quantity(cmd.line_item().quantity().clone())
.deleted(true)
.build()
@ -110,6 +111,7 @@ pub mod tests {
res.line_item().line_item_id(),
cmd.line_item().line_item_id()
);
assert_eq!(res.line_item().kot_id(), cmd.line_item().kot_id());
assert!(res.line_item().deleted());
assert_eq!(res.added_by_user(), cmd.adding_by());

View file

@ -11,6 +11,7 @@ use time::OffsetDateTime;
use super::errors::*;
use crate::ordering::{
application::port::output::db::kot_id_exists::*,
application::port::output::db::line_item_id_exists::*,
domain::{line_item_aggregate::*, line_item_updated_event::*, update_line_item_command::*},
};
@ -30,6 +31,7 @@ pub type UpdateLineItemServiceObj = Arc<dyn UpdateLineItemUseCase>;
#[derive(Clone, Builder)]
pub struct UpdateLineItemService {
db_line_item_id_exists: LineItemIDExistsDBPortObj,
db_kot_id_exists: KotIDExistsDBPortObj,
}
#[async_trait::async_trait]
@ -46,11 +48,16 @@ impl UpdateLineItemUseCase for UpdateLineItemService {
return Err(OrderingError::LineItemIDNotFound);
}
if !self.db_kot_id_exists.kot_id_exists(cmd.kot_id()).await? {
return Err(OrderingError::KotIDNotFound);
}
let new_line_item = LineItemBuilder::default()
.sale_time(cmd.sale_time().clone())
.created_time(cmd.created_time().clone())
.product_name(cmd.product_name().into())
.product_id(*cmd.product_id())
.line_item_id(*cmd.old_line_item().line_item_id())
.kot_id(*cmd.kot_id())
.quantity(cmd.quantity().clone())
.deleted(false)
.build()
@ -98,6 +105,7 @@ pub mod tests {
let s = UpdateLineItemServiceBuilder::default()
.db_line_item_id_exists(mock_line_item_id_exists_db_port_true(IS_CALLED_ONLY_ONCE))
.db_kot_id_exists(mock_kot_id_exists_db_port_true(IS_CALLED_ONLY_ONCE))
.build()
.unwrap();
@ -105,11 +113,12 @@ pub mod tests {
assert_eq!(res.new_line_item().product_name(), cmd.product_name());
assert_eq!(res.new_line_item().product_id(), cmd.product_id());
assert_eq!(res.new_line_item().quantity(), cmd.quantity());
assert_eq!(res.new_line_item().quantity(), cmd.quantity());
assert_eq!(
res.new_line_item().line_item_id(),
cmd.old_line_item().line_item_id()
);
assert_eq!(res.new_line_item().kot_id(), cmd.old_line_item().kot_id());
assert!(!res.new_line_item().deleted());
assert_eq!(res.old_line_item(), cmd.old_line_item());
@ -123,6 +132,7 @@ pub mod tests {
let s = UpdateLineItemServiceBuilder::default()
.db_line_item_id_exists(mock_line_item_id_exists_db_port_false(IS_CALLED_ONLY_ONCE))
.db_kot_id_exists(mock_kot_id_exists_db_port_true(IS_NEVER_CALLED))
.build()
.unwrap();
@ -131,4 +141,20 @@ pub mod tests {
Err(OrderingError::LineItemIDNotFound)
);
}
#[actix_rt::test]
async fn test_service_kot_id_doesnt_exist() {
let cmd = UpdateLineItemCommand::get_cmd();
let s = UpdateLineItemServiceBuilder::default()
.db_line_item_id_exists(mock_line_item_id_exists_db_port_true(IS_CALLED_ONLY_ONCE))
.db_kot_id_exists(mock_kot_id_exists_db_port_false(IS_CALLED_ONLY_ONCE))
.build()
.unwrap();
assert_eq!(
s.update_line_item(cmd.clone()).await,
Err(OrderingError::KotIDNotFound)
);
}
}

View file

@ -25,9 +25,10 @@ pub struct UnvalidatedAddLineItemCommand {
adding_by: Uuid,
#[builder(default = "OffsetDateTime::now_utc()")]
sale_time: OffsetDateTime,
created_time: OffsetDateTime,
product_name: String,
product_id: Uuid,
kot_id: Uuid,
quantity: Quantity,
}
@ -43,9 +44,10 @@ impl UnvalidatedAddLineItemCommand {
}
Ok(AddLineItemCommand {
sale_time: self.sale_time,
created_time: self.created_time,
product_name,
product_id: self.product_id,
kot_id: self.kot_id,
quantity: self.quantity,
adding_by: self.adding_by,
})
@ -54,9 +56,10 @@ impl UnvalidatedAddLineItemCommand {
#[derive(Clone, Debug, Serialize, Deserialize, Eq, PartialEq, Ord, PartialOrd, Getters)]
pub struct AddLineItemCommand {
sale_time: OffsetDateTime,
created_time: OffsetDateTime,
product_name: String,
product_id: Uuid,
kot_id: Uuid,
quantity: Quantity,
adding_by: Uuid,
@ -74,15 +77,17 @@ mod tests {
pub fn get_cmd() -> Self {
let product_name = "foo";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
let quantity = Quantity::get_quantity();
UnvalidatedAddLineItemCommandBuilder::default()
.product_name(product_name.into())
.adding_by(adding_by)
.sale_time(datetime!(1970-01-01 0:00 UTC))
.created_time(datetime!(1970-01-01 0:00 UTC))
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.build()
.unwrap()
.validate()
@ -94,6 +99,7 @@ mod tests {
fn test_cmd() {
let product_name = "foo";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
let quantity = Quantity::get_quantity();
@ -102,6 +108,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.build()
.unwrap()
.validate()
@ -117,6 +124,7 @@ mod tests {
fn test_cmd_product_name_empty() {
let product_name = "";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
let quantity = Quantity::get_quantity();
@ -126,6 +134,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.build()
.unwrap()
.validate(),
@ -137,6 +146,7 @@ mod tests {
fn test_cmd_quantity_empty() {
let product_name = "foo";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
// minor = 0; major = 0;
let quantity = Quantity::default();
@ -147,6 +157,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.build()
.unwrap()
.validate(),

View file

@ -21,9 +21,10 @@ use crate::types::quantity::Quantity;
)]
pub struct LineItem {
#[builder(default = "OffsetDateTime::now_utc()")]
sale_time: OffsetDateTime,
created_time: OffsetDateTime,
product_name: String,
product_id: Uuid,
kot_id: Uuid,
line_item_id: Uuid,
// TODO: add kot_id
quantity: Quantity,
@ -34,10 +35,11 @@ pub struct LineItem {
impl Default for LineItem {
fn default() -> Self {
Self {
sale_time: OffsetDateTime::now_utc(),
created_time: OffsetDateTime::now_utc(),
product_name: String::default(),
product_id: Default::default(),
line_item_id: Default::default(),
kot_id: Default::default(),
quantity: Default::default(),
deleted: false,
}
@ -57,10 +59,11 @@ mod tests {
let cmd = AddLineItemCommand::get_cmd();
LineItemBuilder::default()
.sale_time(cmd.sale_time().clone())
.created_time(cmd.created_time().clone())
.product_name("test_product".into())
.product_id(*cmd.product_id())
.quantity(cmd.quantity().clone())
.kot_id(*cmd.kot_id())
.line_item_id(UUID)
.build()
.unwrap()

View file

@ -28,9 +28,10 @@ pub mod tests {
cmd: &DeleteLineItemCommand,
) -> LineItemDeletedEvent {
let deleted_line_item = LineItemBuilder::default()
.sale_time(cmd.line_item().sale_time().clone())
.created_time(cmd.line_item().created_time().clone())
.product_name(cmd.line_item().product_name().into())
.product_id(*cmd.line_item().product_id())
.kot_id(*cmd.line_item().kot_id())
.line_item_id(*cmd.line_item().line_item_id())
.quantity(cmd.line_item().quantity().clone())
.deleted(true)

View file

@ -29,9 +29,10 @@ pub mod tests {
cmd: &UpdateLineItemCommand,
) -> LineItemUpdatedEvent {
let new_line_item = LineItemBuilder::default()
.sale_time(cmd.sale_time().clone())
.created_time(cmd.created_time().clone())
.product_name(cmd.product_name().clone())
.product_id(*cmd.product_id())
.kot_id(*cmd.kot_id())
.quantity(cmd.quantity().clone())
.line_item_id(*cmd.old_line_item().line_item_id())
.build()

View file

@ -27,9 +27,10 @@ pub struct UnvalidatedUpdateLineItemCommand {
adding_by: Uuid,
#[builder(default = "OffsetDateTime::now_utc()")]
sale_time: OffsetDateTime,
created_time: OffsetDateTime,
product_name: String,
product_id: Uuid,
kot_id: Uuid,
quantity: Quantity,
old_line_item: LineItem,
@ -47,9 +48,10 @@ impl UnvalidatedUpdateLineItemCommand {
}
Ok(UpdateLineItemCommand {
sale_time: self.sale_time,
created_time: self.created_time,
product_name,
product_id: self.product_id,
kot_id: self.kot_id,
quantity: self.quantity,
adding_by: self.adding_by,
old_line_item: self.old_line_item,
@ -59,9 +61,10 @@ impl UnvalidatedUpdateLineItemCommand {
#[derive(Clone, Debug, Serialize, Deserialize, Eq, PartialEq, Ord, PartialOrd, Getters)]
pub struct UpdateLineItemCommand {
sale_time: OffsetDateTime,
created_time: OffsetDateTime,
product_name: String,
product_id: Uuid,
kot_id: Uuid,
quantity: Quantity,
old_line_item: LineItem,
@ -71,7 +74,7 @@ pub struct UpdateLineItemCommand {
#[cfg(test)]
mod tests {
use crate::utils::uuid::tests::UUID;
use crate::{ordering::domain::order_aggregate::Order, utils::uuid::tests::UUID};
use super::*;
@ -79,6 +82,7 @@ mod tests {
pub fn get_cmd() -> Self {
let product_name = "foo";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
let quantity = Quantity::get_quantity();
@ -87,6 +91,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(product_id)
.old_line_item(LineItem::get_line_item())
.build()
.unwrap()
@ -99,6 +104,7 @@ mod tests {
fn test_cmd() {
let product_name = "foo";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
let quantity = Quantity::get_quantity();
let old_line_item = LineItem::get_line_item();
@ -108,6 +114,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.old_line_item(old_line_item.clone())
.build()
.unwrap()
@ -116,6 +123,7 @@ mod tests {
assert_eq!(cmd.quantity(), &quantity);
assert_eq!(*cmd.product_id(), product_id);
assert_eq!(*cmd.kot_id(), kot_id);
assert_eq!(*cmd.adding_by(), adding_by);
assert_eq!(cmd.product_name(), product_name);
assert_eq!(cmd.old_line_item(), &old_line_item);
@ -125,6 +133,7 @@ mod tests {
fn test_cmd_product_name_empty() {
let product_name = "";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
let quantity = Quantity::get_quantity();
@ -134,6 +143,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.old_line_item(LineItem::get_line_item())
.build()
.unwrap()
@ -146,6 +156,7 @@ mod tests {
fn test_cmd_quantity_empty() {
let product_name = "foo";
let product_id = UUID;
let kot_id = UUID;
let adding_by = UUID;
// minor = 0; major = 0;
let quantity = Quantity::default();
@ -156,6 +167,7 @@ mod tests {
.adding_by(adding_by)
.quantity(quantity.clone())
.product_id(product_id)
.kot_id(kot_id)
.old_line_item(LineItem::get_line_item())
.build()
.unwrap()