Skip to content

Commit

Permalink
Merge pull request #205 from creme332/order-bug
Browse files Browse the repository at this point in the history
Fix order bug
  • Loading branch information
creme332 authored May 22, 2024
2 parents db062cc + 48b2d7c commit 4daf1fa
Show file tree
Hide file tree
Showing 3 changed files with 64 additions and 29 deletions.
34 changes: 21 additions & 13 deletions src/controllers/Cart.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
use Exception;
use Steamy\Core\Controller;
use Steamy\Core\Utility;
use Steamy\Model\Mailer;
use Steamy\Model\Order;
use Steamy\Model\OrderProduct;
use Steamy\Model\Product;
Expand Down Expand Up @@ -71,8 +70,6 @@ private function handleInvalidURL(): void

private function handleCheckout(): void
{
// TODO: write appropriate errors to Cart view instead of sending response code

// check if user is logged in
$signed_client = $this->getSignedInClient();
if (!$signed_client) {
Expand Down Expand Up @@ -110,24 +107,35 @@ private function handleCheckout(): void
$new_order->addLineItem($line_item);
}

// save order
$success_order = false;
// attempt to save order. An exception will be generated in case of any errors.
try {
$success_order = $new_order->save();
http_response_code($success_order ? 201 : 400);
} catch (Exception $e) {
error_log($e->getMessage());
http_response_code(500);
echo json_encode(['error' => $e->getMessage()]);
return;
}

// send confirmation email if order was successfully saved
if ($success_order) {
try {
$signed_client->sendOrderConfirmationEmail($new_order);
} catch (Exception $e) {
error_log($e->getMessage());
}
// if order was unsuccessfully saved without any exceptions generated
if (!$success_order) {
http_response_code(500);
echo json_encode(['error' => "Order could not be saved for an unknown reason."]);
return;
}

// send confirmation email
try {
$success_mail = $signed_client->sendOrderConfirmationEmail($new_order);
} catch (Exception $e) {
http_response_code(503);
echo json_encode(['error' => "Order was saved but email could not be sent: " . $e->getMessage()]);
return;
}

if (!$success_mail) {
http_response_code(503);
echo json_encode(['error' => "Order was saved but email could not be sent for an unknown reason."]);
}
}

Expand Down
50 changes: 34 additions & 16 deletions src/models/Order.php
Original file line number Diff line number Diff line change
Expand Up @@ -122,12 +122,8 @@ public function save(): bool
$update_stock_stm = $conn->prepare($query);

foreach ($this->line_items as $line_item) {
if (!empty($line_item->validate())) {
// line item contains invalid attributes
$conn->rollBack();
$conn = null;
throw new Exception("Invalid line item:" . json_encode($line_item));
}
// set order ID of line item
$line_item->setOrderID($new_order_id);

// fetch product corresponding to line item
$product = Product::getByID($line_item->getProductID());
Expand All @@ -139,22 +135,49 @@ public function save(): bool
throw new Exception("Product with ID " . $line_item->getProductID() . " does not exist");
}

// set true unit price of line item
$line_item->setUnitPrice($product->getPrice());

// get stock level for current product
$stock_level = $store->getProductStock($product->getProductID());

if ($line_item->getQuantity() > $stock_level) {
// store does not have enough stock
$conn->rollBack();
$conn = null;

$error_message = <<< EOL
Store with ID $this->store_id has insufficient stock ($stock_level) for the following line item:
Product ID = {$line_item->getProductID()} and quantity = {$line_item->getQuantity()}.
EOL;

throw new Exception($error_message);
}

// validate line item
$line_item_errors = $line_item->validate();
if (!empty($line_item_errors)) {
// line item contains invalid attributes
$conn->rollBack();
$conn = null;

$line_item_info = json_encode($line_item->toArray());
$line_item_errors = json_encode($line_item_errors);

$error_message = <<< EOL
Invalid line item:
$line_item_info
Errors:
$line_item_errors
EOL;

throw new Exception(
"Store with ID " . $this->store_id
. " has insufficient stock for product " . $line_item->getProductID()
$error_message
);
}

// insert into order_product table
$line_item->setOrderID($new_order_id);
$line_item->setUnitPrice($product->getPrice());
// insert line item into order_product table

$success = $insert_line_item_stm->execute($line_item->toArray());
if (!$success) {
Expand Down Expand Up @@ -192,14 +215,9 @@ public function save(): bool
*
* @param OrderProduct $orderProduct
* @return void
* @throws Exception
*/
public function addLineItem(OrderProduct $orderProduct): void
{
$errors = $orderProduct->validate();
if (!empty($errors)) {
throw new Exception("Invalid line item: " . json_encode($errors));
}
$this->line_items[] = $orderProduct;
}

Expand Down
9 changes: 9 additions & 0 deletions src/models/OrderProduct.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,15 @@ class OrderProduct
private int $quantity;
private float $unit_price;

/**
* Create a new OrderProduct object
* @param int $product_id
* @param string $cup_size
* @param string $milk_type
* @param int $quantity
* @param float|null $unit_price If not set, the default $unit_price is -1.
* @param int|null $order_id If not set, the default $order_id is -1.
*/
public function __construct(
int $product_id,
string $cup_size,
Expand Down

0 comments on commit 4daf1fa

Please sign in to comment.