=== OrderUnstick ===
Contributors: flexpoint
Tags: woocommerce, orders, stripe, pending payment, webhook
Requires at least: 6.4
Tested up to: 7.0
Requires PHP: 7.4
Stable tag: 0.1.0
License: GPLv2 or later
License URI: https://www.gnu.org/licenses/gpl-2.0.html

Read-only detector for WooCommerce orders stuck in Pending payment or On-hold that may carry stored payment metadata. Detects and reports only.

== Description ==

When a payment gateway webhook never reaches your store (after a site migration, a security plugin blocking the callback URL, a CDN rewrite, or a dead endpoint), a customer can pay while the order stays stuck in **Pending payment** or **On-hold**. The customer paid, but nothing ships.

OrderUnstick scans for those orders and reports **possible stuck paid orders**: stuck orders older than a configurable age threshold that carry stored Stripe or generic payment metadata.

**Version 0.1 is strictly read-only.** It detects and reports only.

What it does:

* Adds a report page under **WooCommerce → OrderUnstick** (administrators and shop managers only).
* Scans orders in Pending payment and/or On-hold that are older than your age threshold (default 2 hours).
* Looks for payment identifiers already stored on the order by your gateway plugin: Stripe intent, charge, and source ids, and the standard WooCommerce transaction id.
* Shows a report with the order, age, status, customer, total, gateway, the masked payment id found, a conservative risk level, the reason flagged, and the total value across flagged orders.
* Keeps a local scan history with summary counts only.

What it does NOT do, by design, in this version:

* It does not call Stripe, PayPal, Mollie, or any payment gateway or external API.
* It does not change order status, stock, notes, refunds, or payment data.
* It does not send any email.
* It does not auto-fix or recover anything. There is no "mark as paid" button.
* It does not guarantee that any payment succeeded. **Payment metadata found is not proof of payment.**
* It does not connect to any external service and sends no telemetry. Everything runs inside your site.

**Important: gateway confirmation required.** A flagged order means only that a stuck order carries stored payment metadata. Always confirm the payment in your gateway dashboard (for example the Stripe dashboard) before acting. Do not fulfill based only on this report.

A later version is planned that can re-check candidates against the gateway using a merchant-supplied restricted key, still flag-only. That functionality is not available now and nothing in this version contacts any gateway.

OrderUnstick requires WooCommerce. It supports both High-Performance Order Storage (HPOS) and legacy order storage, and reads orders only through the WooCommerce order API.

== Installation ==

1. Install and activate the plugin. WooCommerce must be installed and active.
2. Go to **WooCommerce → OrderUnstick**.
3. Set the age threshold, statuses, and maximum orders per scan, then click **Run Scan**.
4. Review the candidates and confirm each one in your payment gateway dashboard before taking any action.

== Frequently Asked Questions ==

= Does this plugin change my orders? =

No. Version 0.1 never modifies orders, statuses, stock, emails, notes, refunds, or payment data. It only reads and reports.

= Does it contact Stripe or any other gateway? =

No. It only reads payment identifiers that your gateway plugin already stored on the order. It makes no external requests of any kind and sends no telemetry.

= A scan flagged an order. Is that order paid? =

Not necessarily. A flag means a stuck order carries stored payment metadata, nothing more. This version cannot verify payment. Confirm in your gateway dashboard before fulfilling.

= Which gateways are detected? =

Version 0.1 looks for stored Stripe identifiers and the standard WooCommerce transaction id that most gateways set. Live verification and further gateways are planned for later versions.

= Does it store customer or payment data? =

No. The scan report is shown on screen only. The saved scan history contains summary counts only (time, orders scanned, flagged, no evidence, flagged value). Payment ids are always shown partially masked, never in full.

= Does it work with HPOS (High-Performance Order Storage)? =

Yes. It declares HPOS compatibility and reads orders only through the WooCommerce order API, so both HPOS and legacy storage work.

= What happens if WooCommerce is not active? =

OrderUnstick stays inactive and shows an admin notice. It does not cause errors.

== Screenshots ==

1. The OrderUnstick report page with the read-only notice and scan settings: age threshold, statuses, and max orders per scan.
2. Scan results with flagged possible stuck paid orders: masked payment ids, risk level, reason flagged, and the total value across flagged orders.
3. The safety notice: results are candidates only, gateway confirmation is required, and this version never modifies orders.
4. Recent scan history with summary counts only.
5. A flagged order opened in WooCommerce afterwards: still untouched, exactly as it was.

== Changelog ==

= 0.1.0 =
* Initial release: read-only detector for stuck WooCommerce orders carrying stored payment metadata.
* Scan settings: age threshold, statuses (Pending payment, On-hold), max orders per scan.
* Report with masked payment ids, conservative risk rating, and flagged total value.
* Local scan history with summary counts only.
* No gateway calls, no order changes, no emails, no external services, no telemetry.

== Upgrade Notice ==

= 0.1.0 =
First release. Read-only detector: it reports possible stuck paid orders and never modifies anything.
