{"name":"BoltProof","description":"Formally verifies billing, pricing, and subscription logic as Z3 constraints. Returns a proof or a concrete counterexample. Deterministic, not AI.","supportedInterfaces":[{"url":"https://api.boltproof.dev/a2a","protocolBinding":"JSONRPC","protocolVersion":"1.0"}],"provider":{"organization":"BoltProof","url":"https://boltproof.dev"},"iconUrl":"https://api.boltproof.dev/icons/icon-512.png","version":"0.1.0","documentationUrl":"https://api.boltproof.dev/docs","capabilities":{"streaming":true,"pushNotifications":false,"extendedAgentCard":false},"securitySchemes":{"boltproofKey":{"apiKeySecurityScheme":{"description":"BoltProof API key (see https://boltproof.dev)","location":"header","name":"X-API-Key"}}},"securityRequirements":[{"schemes":{"boltproofKey":{"list":[]}}}],"defaultInputModes":["application/json","text/plain"],"defaultOutputModes":["application/json"],"skills":[{"id":"scan_billing_logic","name":"Scan billing logic","description":"Run every approved BoltProof rule against one bundle of billing parameters and return every violation.","tags":["billing","verification","z3","formal","scan"],"examples":["{\"bundle\": {\"charge_amount\": 100, \"refund_request\": 150}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_cloudflare_epoch_zero_invoice","name":"An invoice's date must always lie within the billing period it covers (period_start <= invoice_date <= period_end). A missing or unset timestamp must never serialize as epoch zero (1970-01-01); it must resolve to a real date inside the period. Source: HN 39558132 -- Cloudflare sent an invoice whose PDF was titled cloudflare-invoice-1970-01-01.pdf; an unset timestamp (a Feb 29 leap-day edge in the billing date logic) rendered as 0 instead of a date inside the period. Billing periods start at epoch day >= 1 (epoch day 0 is not a real period start); the invoice_date != 0 guard is entailed by the range clause but kept explicitly to pin the incident.","description":"An invoice's date must always lie within the billing period it covers (period_start <= invoice_date <= period_end). A missing or unset timestamp must never serialize as epoch zero (1970-01-01); it must resolve to a real date inside the period. Source: HN 39558132 -- Cloudflare sent an invoice whose PDF was titled cloudflare-invoice-1970-01-01.pdf; an unset timestamp (a Feb 29 leap-day edge in the billing date logic) rendered as 0 instead of a date inside the period. Billing periods start at epoch day >= 1 (epoch day 0 is not a real period start); the invoice_date != 0 guard is entailed by the range clause but kept explicitly to pin the incident.","tags":["billing","verification","billing","cloudflare_epoch_zero_invoice"],"examples":["{\"rule\": \"cloudflare_epoch_zero_invoice\", \"inputs\": {\"period_start\": 0, \"period_end\": 0, \"invoice_date\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_killbill_cba_adj_date","name":"When a credit is created on a Kill Bill account with an explicit requestedDate, the system generates two paired invoice items — a CREDIT_ADJ (the credit) and a CBA_ADJ (the account-balance adjustment). Both items must carry start_date = end_date = requestedDate. A bug that dates the CBA_ADJ item \"today\" instead of the requested date breaks the pairing. Source: killbill/killbill#2202 — requestedDate=2026-04-01 yields CREDIT_ADJ dated 2026-04-01 but CBA_ADJ dated 2026-04-17 (today). This is a GUARD rule: the computation models the correct system's pairing work (the CBA_ADJ inherits the CREDIT_ADJ's date); the invariant enforces that both items sit on the requested date. Global SAT is expected.","description":"When a credit is created on a Kill Bill account with an explicit requestedDate, the system generates two paired invoice items — a CREDIT_ADJ (the credit) and a CBA_ADJ (the account-balance adjustment). Both items must carry start_date = end_date = requestedDate. A bug that dates the CBA_ADJ item \"today\" instead of the requested date breaks the pairing. Source: killbill/killbill#2202 — requestedDate=2026-04-01 yields CREDIT_ADJ dated 2026-04-01 but CBA_ADJ dated 2026-04-17 (today). This is a GUARD rule: the computation models the correct system's pairing work (the CBA_ADJ inherits the CREDIT_ADJ's date); the invariant enforces that both items sit on the requested date. Global SAT is expected.","tags":["billing","verification","billing","killbill_cba_adj_date"],"examples":["{\"rule\": \"killbill_cba_adj_date\", \"inputs\": {\"requested_date\": 0, \"credit_adj_date\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_lago_subscription_start_date","name":"A subscription's true start (its trial start) and the start of its current billing period are distinct concepts and must never be conflated. The backend stores the true start on the subscription record; every UI/API surface must report that true start (the trial start), never the billing-period anchor. Source: getlago/lago#772.","description":"A subscription's true start (its trial start) and the start of its current billing period are distinct concepts and must never be conflated. The backend stores the true start on the subscription record; every UI/API surface must report that true start (the trial start), never the billing-period anchor. Source: getlago/lago#772.","tags":["billing","verification","billing","lago_subscription_start_date"],"examples":["{\"rule\": \"lago_subscription_start_date\", \"inputs\": {\"trial_start\": 0, \"billing_start\": 0, \"subscription_start\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_paddle_deferred_proration_min_charge","name":"When a subscription update uses prorationBillingMode = prorated_next_billing_period","description":"When a subscription update uses prorationBillingMode = prorated_next_billing_period","tags":["billing","verification","proration","paddle_deferred_proration_min_charge"],"examples":["{\"rule\": \"paddle_deferred_proration_min_charge\", \"inputs\": {\"prorated_amount\": 0, \"minimum_charge\": 0, \"deferred\": 0, \"accepted\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_paddle_preview_commit_consistency","name":"The previewUpdate endpoint must return the same prorated credit and next payment as the committed subscription change. When credits exist on a subscription, both paths must derive the prorated credit from credit_balance and the next payment from base_amount - credit_balance. A preview that shows different numbers than the real change misleads callers. Source: paddle-node-sdk#106 — previewUpdate returns wrong values when credits exist; the \"Next payment\" preview differs from the committed change.","description":"The previewUpdate endpoint must return the same prorated credit and next payment as the committed subscription change. When credits exist on a subscription, both paths must derive the prorated credit from credit_balance and the next payment from base_amount - credit_balance. A preview that shows different numbers than the real change misleads callers. Source: paddle-node-sdk#106 — previewUpdate returns wrong values when credits exist; the \"Next payment\" preview differs from the committed change.","tags":["billing","verification","proration","paddle_preview_commit_consistency"],"examples":["{\"rule\": \"paddle_preview_commit_consistency\", \"inputs\": {\"base_amount\": 0, \"credit_balance\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_proration_cap","name":"A mid-cycle plan change must never produce a prorated charge that exceeds the full-period price of the new plan, and proration must credit the amount the customer actually paid (not assume a zero payment when a full discount applied). Proration for increasing quantity is the added units priced at the new unit price, never more.","description":"A mid-cycle plan change must never produce a prorated charge that exceeds the full-period price of the new plan, and proration must credit the amount the customer actually paid (not assume a zero payment when a full discount applied). Proration for increasing quantity is the added units priced at the new unit price, never more.","tags":["billing","verification","billing","proration_cap"],"examples":["{\"rule\": \"proration_cap\", \"inputs\": {\"new_quantity\": 0, \"old_quantity\": 0, \"unit_price\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_proration_on_actual_paid","name":"A mid-cycle quantity increase must charge exactly the added units at the full unit price. The prorated charge is (new_quantity - old_quantity) * unit_price, and the basis actually applied must be the full price — never the discounted basis the customer actually paid for the old units. Guard rule: the computation models the system's derivation from whatever basis it applied; the invariant enforces that basis is the full unit price. Source: stripe/stripe-dotnet#3103 (over-charge 144 from discounting the old credit; symmetric under-charge from pricing added units at the discounted basis).","description":"A mid-cycle quantity increase must charge exactly the added units at the full unit price. The prorated charge is (new_quantity - old_quantity) * unit_price, and the basis actually applied must be the full price — never the discounted basis the customer actually paid for the old units. Guard rule: the computation models the system's derivation from whatever basis it applied; the invariant enforces that basis is the full unit price. Source: stripe/stripe-dotnet#3103 (over-charge 144 from discounting the old credit; symmetric under-charge from pricing added units at the discounted basis).","tags":["billing","verification","billing","proration_on_actual_paid"],"examples":["{\"rule\": \"proration_on_actual_paid\", \"inputs\": {\"old_quantity\": 0, \"new_quantity\": 0, \"unit_price\": 0, \"actual_paid_per_unit\": 0, \"applied_basis\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_refund_cap","name":"A refund must never exceed the original charge amount, and repeated refund requests against the same charge must never cumulatively exceed the original charge. The computation models a correct system that rejects duplicate (replayed) refund requests; the invariant caps the running total at the charge amount.","description":"A refund must never exceed the original charge amount, and repeated refund requests against the same charge must never cumulatively exceed the original charge. The computation models a correct system that rejects duplicate (replayed) refund requests; the invariant caps the running total at the charge amount.","tags":["billing","verification","billing","refund_cap"],"examples":["{\"rule\": \"refund_cap\", \"inputs\": {\"already_refunded\": 0, \"charge_amount\": 0, \"is_duplicate\": 0, \"refund_request\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_trial_extension_boundary","name":"When a trial end date is extended, the first invoice must be re-derived from the extended trial end. The first invoice must occur on or after the extended trial end and within one billing cycle of it. It must never be anchored to the original trial end.","description":"When a trial end date is extended, the first invoice must be re-derived from the extended trial end. The first invoice must occur on or after the extended trial end and within one billing cycle of it. It must never be anchored to the original trial end.","tags":["billing","verification","billing","trial_extension_boundary"],"examples":["{\"rule\": \"trial_extension_boundary\", \"inputs\": {\"cycle_period_days\": 0, \"trial_end_extended\": 0, \"trial_end_original\": 0, \"trial_start\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]},{"id":"check_trial_extension_fresh","name":"Extending a free trial must never cause an invoice billing cycle to be","description":"Extending a free trial must never cause an invoice billing cycle to be","tags":["billing","verification","billing","trial_extension_fresh"],"examples":["{\"rule\": \"trial_extension_fresh\", \"inputs\": {\"trial_start\": 0, \"trial_end_original\": 0, \"trial_end_extended\": 0, \"cycle_period_days\": 0}}"],"inputModes":["application/json"],"outputModes":["application/json"]}]}