fix: billing checkout — auto-provisioning, zero-dollar flow, duplicate prevention, paid-invoice cart fix
Agent-Logs-Url: https://github.com/GameServerPanel/GSP/sessions/d18a8f6c-0715-46c4-9c97-94ec7e2a22fc Co-authored-by: iaretechnician <2749183+iaretechnician@users.noreply.github.com>
This commit is contained in:
parent
a7a8dd791a
commit
73f125ea21
7 changed files with 429 additions and 21 deletions
|
|
@ -1,6 +1,12 @@
|
|||
# Changelog
|
||||
|
||||
## 2026-05-05
|
||||
- **Billing checkout — automatic server provisioning after payment:** Fixed the core provisioning gap where `capture_order.php` never populated `$newOrderIds`, so the auto-provisioner was always skipped. After a successful PayPal capture (or zero-dollar checkout), a `billing_orders` row is now created for each paid invoice and passed to `billing_invoke_provision()` so the game server is created/installed immediately without manual admin action.
|
||||
- **Billing checkout — duplicate provisioning prevention:** Invoice→Order linkage is written atomically (`billing_invoices.order_id` updated after order creation). Because `getUnpaidInvoicesForUser()` filters on `payment_status NOT IN ('paid',…)`, a retried PayPal capture will find no invoices and skip all processing — preventing duplicate servers.
|
||||
- **Billing checkout — paid invoices no longer reappear in cart:** `markInvoicePaid()` now sets both `payment_status='paid'` and `status='paid'`. The cart query was also tightened to exclude any invoice where `payment_status` is paid/cancelled/refunded.
|
||||
- **Billing checkout — zero-dollar checkout:** New `checkout_free.php` handles orders where a coupon reduces the total to $0. The cart now shows a "Complete Free Order" button instead of the PayPal button when `$final_amount <= 0`. Free checkout marks invoices paid (method=coupon), creates orders, increments the coupon use counter, and triggers provisioning — identical flow to a PayPal capture.
|
||||
- **Billing checkout — payment_success.php JOIN fix:** Fixed a broken `SELECT … s.game_name` JOIN that referenced a non-existent column; corrected to `s.service_name`.
|
||||
- **Billing checkout — SQL migration:** Added `sql/002_billing_checkout_fixes.sql` — idempotent migration that adds `coupon_id`, `discount_amount`, `payment_status`, `subtotal`, and `total_due` columns to `gsp_billing_invoices`, and `coupon_id`/`discount_amount` to `gsp_billing_orders` for older installations missing these columns.
|
||||
- **Billing order status standardization:** Canonical `billing_orders.status` values are now `Active`, `Invoiced`, and `Expired` only. All old writes of `installed`, `paid` (as order status), and `suspended` have been replaced. A SQL migration script `modules/billing/sql/normalize_billing_order_status.sql` converts any existing legacy rows. Backward-compatibility read paths (e.g. renewable-status checks in `my_account.php`) are preserved until the migration runs.
|
||||
- **Expiration display date-only:** The billing expiration shown on the game server monitor (`server_monitor.php`) now displays as `YYYY-MM-DD` only instead of `YYYY-MM-DD HH:MM`.
|
||||
- **Full-day expiration grace rule:** A server whose `end_date` falls on today is treated as active for the entire calendar day. Expiration is only processed starting the next calendar day. This rule is applied consistently in: billing cron (`cron-shop.php` Steps B and C), the server monitor expiration helper (`home_handling_functions.php::get_server_billing_expiration_html`), and the OGP user/group assignment expiration processor (`user_games/check_expire.php`). All comparisons now use `DATE(end_date) < CURDATE()` (SQL) or `< strtotime(date('Y-m-d'))` (PHP) — never `<= NOW()` or `<= time()`.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue