Skip to content

Commit

Permalink
Limit number of unpaid orders per user (#540)
Browse files Browse the repository at this point in the history
* Limit max number of unpaid orders per buyer

* Increase max unpaid orders limit to 100

* Fix flash error message on fail to insert new order
  • Loading branch information
yzernik authored Jul 30, 2022
1 parent dfd7776 commit b171d8c
Show file tree
Hide file tree
Showing 3 changed files with 64 additions and 5 deletions.
18 changes: 18 additions & 0 deletions sqlx-data.json
Original file line number Diff line number Diff line change
Expand Up @@ -982,6 +982,24 @@
},
"query": "UPDATE usersettings SET squeaknode_address = ? WHERE user_id = ?;"
},
"506a715d6ca6157c9b48f0892946fd827423ba20b679c814ea5b8a3824f28f49": {
"describe": {
"columns": [
{
"name": "num_unpaid_orders",
"ordinal": 0,
"type_info": "Int"
}
],
"nullable": [
false
],
"parameters": {
"Right": 1
}
},
"query": "\nselect\n COUNT(orders.id) as num_unpaid_orders\nfrom\n orders\nWHERE\n orders.buyer_user_id = ?\nAND\n NOT orders.paid\n;"
},
"5a24f9c5cf60ff7f2dc4ce2cf145931a81121bd7854c8b958625bd8ead17c0f8": {
"describe": {
"columns": [],
Expand Down
45 changes: 42 additions & 3 deletions src/models.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1943,13 +1943,22 @@ WHERE NOT EXISTS(SELECT 1 FROM usersettings WHERE user_id = ?)

impl Order {
/// Returns the id of the inserted row.
pub async fn insert(order: Order, db: &mut Connection<Db>) -> Result<i32, sqlx::Error> {
pub async fn insert(
order: Order,
max_unpaid_orders: u32,
db: &mut Connection<Db>,
) -> Result<i32, String> {
let amount_owed_sat: i64 = order.amount_owed_sat.try_into().unwrap();
let seller_credit_sat: i64 = order.seller_credit_sat.try_into().unwrap();
let created_time_ms: i64 = order.created_time_ms.try_into().unwrap();
let payment_time_ms: i64 = order.payment_time_ms.try_into().unwrap();
let review_time_ms: i64 = order.review_time_ms.try_into().unwrap();

let mut tx = db
.begin()
.await
.map_err(|_| "failed to begin transaction.")?;

let insert_result = sqlx::query!(
"INSERT INTO orders (public_id, buyer_user_id, seller_user_id, quantity, listing_id, shipping_option_id, shipping_instructions, amount_owed_sat, seller_credit_sat, paid, shipped, canceled_by_seller, canceled_by_buyer, reviewed, review_text, review_rating, invoice_hash, invoice_payment_request, created_time_ms, payment_time_ms, review_time_ms) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
order.public_id,
Expand All @@ -1974,8 +1983,38 @@ impl Order {
payment_time_ms,
review_time_ms,
)
.execute(&mut **db)
.await?;
.execute(&mut *tx)
.await
.map_err(|_| "failed to insert order.")?;

let num_unpaid_orders = sqlx::query!(
"
select
COUNT(orders.id) as num_unpaid_orders
from
orders
WHERE
orders.buyer_user_id = ?
AND
NOT orders.paid
;",
order.buyer_user_id,
)
.fetch_one(&mut *tx)
.map_ok(|r| r.num_unpaid_orders as u32)
.await
.map_err(|_| "failed to get count of unpaid orders for buyer.")?;

if num_unpaid_orders > max_unpaid_orders {
return Err(format!(
"more than {:?} unpaid orders not allowed.",
max_unpaid_orders,
));
}

tx.commit()
.await
.map_err(|_| "failed to commit transaction.")?;

Ok(insert_result.last_insert_rowid() as _)
}
Expand Down
6 changes: 4 additions & 2 deletions src/prepare_order.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ use rocket_auth::User;
use rocket_db_pools::Connection;
use rocket_dyn_templates::Template;

const MAX_UNPAID_ORDERS: u32 = 100;

#[derive(Debug, Serialize)]
#[serde(crate = "rocket::serde")]
struct Context {
Expand Down Expand Up @@ -196,7 +198,7 @@ async fn create_order(
review_time_ms: 0,
};

match Order::insert(order, db).await {
match Order::insert(order, MAX_UNPAID_ORDERS, db).await {
Ok(order_id) => match Order::single(db, order_id).await {
Ok(new_order) => Ok(new_order.public_id),
Err(e) => {
Expand All @@ -206,7 +208,7 @@ async fn create_order(
},
Err(e) => {
error_!("DB insertion error: {}", e);
Err("Order could not be inserted due an internal error.".to_string())
Err(e)
}
}
}
Expand Down

0 comments on commit b171d8c

Please sign in to comment.