WebOrbiton
v1.0.0.0

StocketBase

162 lines · 8.1 KB
  1. <?php
  2. ​
  3. declare(strict_types=1);
  4. ​
  5. require_once __DIR__ . '/includes/config.php';
  6. require_once __DIR__ . '/includes/database.php';
  7. require_once __DIR__ . '/includes/user-auth.php';
  8. require_once __DIR__ . '/includes/language.php';
  9. require_once __DIR__ . '/includes/site-front.php';
  10. require_once __DIR__ . '/includes/cart.php';
  11. require_once __DIR__ . '/includes/currency.php';
  12. ​
  13. UserAuth::boot();
  14. ​
  15. $settings = SiteFront::settings();
  16. $sessionId = trim((string) ($_GET['session_id'] ?? ''));
  17. $orderId = (int) ($_GET['order_id'] ?? 0);
  18. ​
  19. $order = null;
  20. $orderItems = [];
  21. ​
  22. if ($orderId > 0) {
  23. $usersDb = Database::users();
  24. $statement = $usersDb->prepare('SELECT * FROM orders WHERE id = :id LIMIT 1');
  25. $statement->execute(['id' => $orderId]);
  26. $candidateOrder = $statement->fetch();
  27. ​
  28. $currentCustomer = UserAuth::user();
  29. $sessionOwnsOrder = isset($_SESSION['checkout_order_ids']) && is_array($_SESSION['checkout_order_ids'])
  30. && in_array($orderId, $_SESSION['checkout_order_ids'], true);
  31. $accountOwnsOrder = $candidateOrder && $currentCustomer !== null
  32. && $candidateOrder['user_account_id'] !== null
  33. && (int) $candidateOrder['user_account_id'] === (int) $currentCustomer['id'];
  34. ​
  35. if ($candidateOrder && ($sessionOwnsOrder || $accountOwnsOrder)) {
  36. $order = $candidateOrder;
  37. $itemsStatement = $usersDb->prepare('SELECT * FROM order_items WHERE order_id = :id ORDER BY id ASC');
  38. $itemsStatement->execute(['id' => $orderId]);
  39. $orderItems = $itemsStatement->fetchAll();
  40. }
  41. }
  42. ​
  43. if ($sessionId !== '' || $order !== null) {
  44. Cart::clear();
  45. }
  46. ​
  47. require_once __DIR__ . '/includes/digital-files.php';
  48. ​
  49. $orderHasDownloads = false;
  50. $orderDownloads = [];
  51. if ($order !== null) {
  52. $orderIsPaid = in_array($order['status'], DigitalFiles::PAID_ORDER_STATUSES, true);
  53. $orderTokens = $orderIsPaid ? DigitalFiles::tokensForOrder((int) $order['id']) : [];
  54. $viewer = UserAuth::user();
  55. $viewerOwnsAccountOrder = $viewer !== null && $order['user_account_id'] !== null && (int) $order['user_account_id'] === (int) $viewer['id'];
  56. ​
  57. foreach (array_unique(array_map(static fn(array $item): int => (int) $item['product_id'], $orderItems)) as $orderProductId) {
  58. $orderProductFiles = DigitalFiles::filesForProduct($orderProductId);
  59. if (empty($orderProductFiles)) {
  60. continue;
  61. }
  62. $orderHasDownloads = true;
  63. ​
  64. if (!$orderIsPaid) {
  65. continue;
  66. }
  67. ​
  68. $productToken = $viewerOwnsAccountOrder ? null : ($orderTokens[$orderProductId] ?? null);
  69. if (!$viewerOwnsAccountOrder && $productToken === null) {
  70. continue;
  71. }
  72. ​
  73. foreach ($orderProductFiles as $orderProductFile) {
  74. $orderDownloads[] = [
  75. 'name' => DigitalFiles::displayName($orderProductFile),
  76. 'size' => (int) $orderProductFile['size_bytes'],
  77. 'url' => DigitalFiles::downloadUrl((int) $orderProductFile['id'], $productToken),
  78. ];
  79. }
  80. }
  81. }
  82. ​
  83. $pageTitle = Language::get('order_confirmation_title', 'Thank you') . ' - ' . $settings['site_name'];
  84. $pageDescription = '';
  85. ​
  86. require __DIR__ . '/includes/front-header.php';
  87. ​
  88. ?>
  89. <h1 class="article-title"><?= htmlspecialchars(Language::get('order_confirmation_title', 'Thank you')) ?></h1>
  90. ​
  91. <?php if ($order !== null): ?>
  92. <?php if ($order['status'] === 'pending'): ?>
  93. <p><?= htmlspecialchars(Language::get('order_confirmation_processing', 'Your payment is still being processed. This page will show your final order status once confirmed — you will also receive a confirmation email.')) ?></p>
  94. <?php else: ?>
  95. <p><?= htmlspecialchars(Language::get('order_confirmation_success', 'Your order has been placed successfully.')) ?></p>
  96. <?php endif; ?>
  97. ​
  98. <div class="order-summary">
  99. <p><strong><?= htmlspecialchars(Language::get('order_number_label', 'Order number')) ?>:</strong> <?= htmlspecialchars($order['order_number']) ?></p>
  100. <p><strong><?= htmlspecialchars(Language::get('order_status_label', 'Status')) ?>:</strong> <span class="status-pill status-<?= htmlspecialchars($order['status']) ?>"><?= htmlspecialchars(Language::get('order_status_' . $order['status'], ucfirst($order['status']))) ?></span></p>
  101. ​
  102. <table class="dash-table">
  103. <thead>
  104. <tr>
  105. <th><?= htmlspecialchars(Language::get('cart_column_product', 'Product')) ?></th>
  106. <th><?= htmlspecialchars(Language::get('cart_column_quantity', 'Quantity')) ?></th>
  107. <th><?= htmlspecialchars(Language::get('cart_column_total', 'Total')) ?></th>
  108. </tr>
  109. </thead>
  110. <tbody>
  111. <?php foreach ($orderItems as $item): ?>
  112. <tr>
  113. <td><?= htmlspecialchars($item['product_title_snapshot']) ?><?= $item['variant_name_snapshot'] !== null ? ' — ' . htmlspecialchars($item['variant_name_snapshot']) : '' ?></td>
  114. <td><?= (int) $item['quantity'] ?></td>
  115. <td><?= htmlspecialchars(Currency::format((int) $item['total_cents'], $order['currency'])) ?></td>
  116. </tr>
  117. <?php endforeach; ?>
  118. </tbody>
  119. </table>
  120. ​
  121. <div class="cart-summary">
  122. <div class="cart-summary-row"><span><?= htmlspecialchars(Language::get('cart_subtotal', 'Subtotal')) ?></span><span><?= htmlspecialchars(Currency::format((int) $order['subtotal_cents'], $order['currency'])) ?></span></div>
  123. <?php if ((int) $order['discount_cents'] > 0): ?>
  124. <div class="cart-summary-row"><span><?= htmlspecialchars(Language::get('cart_discount', 'Discount')) ?></span><span>-<?= htmlspecialchars(Currency::format((int) $order['discount_cents'], $order['currency'])) ?></span></div>
  125. <?php endif; ?>
  126. <?php if ((int) $order['shipping_cents'] > 0): ?>
  127. <div class="cart-summary-row"><span><?= htmlspecialchars(Language::get('order_shipping_label', 'Shipping')) ?></span><span><?= htmlspecialchars(Currency::format((int) $order['shipping_cents'], $order['currency'])) ?></span></div>
  128. <?php endif; ?>
  129. <div class="cart-summary-row cart-summary-total"><span><?= htmlspecialchars(Language::get('cart_total', 'Total')) ?></span><span><?= htmlspecialchars(Currency::format((int) $order['total_cents'], $order['currency'])) ?></span></div>
  130. </div>
  131. </div>
  132. ​
  133. <?php if ($orderHasDownloads): ?>
  134. <h2><?= htmlspecialchars(Language::get('order_downloads_title', 'Your downloads')) ?></h2>
  135. <?php if (!empty($orderDownloads)): ?>
  136. <ul class="download-list">
  137. <?php foreach ($orderDownloads as $orderDownload): ?>
  138. <li>
  139. <a href="<?= htmlspecialchars($orderDownload['url']) ?>" rel="nofollow"><?= Icons::icon('download', 'icon icon-sm') ?><?= htmlspecialchars($orderDownload['name']) ?></a>
  140. <small><?= htmlspecialchars(DigitalFiles::formatSize($orderDownload['size'])) ?></small>
  141. </li>
  142. <?php endforeach; ?>
  143. </ul>
  144. <?php else: ?>
  145. <p><?= htmlspecialchars(Language::get('order_downloads_pending', 'Your download links will appear here and be emailed to you as soon as the payment is confirmed. Refresh this page in a moment.')) ?></p>
  146. <?php endif; ?>
  147. <?php endif; ?>
  148. ​
  149. <?php if (UserAuth::check()): ?>
  150. <p><a href="account.php?order=<?= (int) $order['id'] ?>"><?= htmlspecialchars(Language::get('order_confirmation_view_account', 'View this order in your account')) ?></a></p>
  151. <?php endif; ?>
  152. <?php else: ?>
  153. <p><?= htmlspecialchars(Language::get('order_confirmation_generic', 'Thank you! Your purchase is being confirmed — you will receive an email shortly.')) ?></p>
  154. <?php if (UserAuth::check()): ?>
  155. <p><a href="account.php"><?= htmlspecialchars(Language::get('order_confirmation_view_account', 'Go to your account')) ?></a></p>
  156. <?php endif; ?>
  157. <?php endif; ?>
  158. ​
  159. <p><a href="index.php"><?= htmlspecialchars(Language::get('order_confirmation_continue_shopping', 'Continue shopping')) ?></a></p>
  160. ​
  161. <?php require __DIR__ . '/includes/front-footer.php'; ?>
  162. ​