Tier 0 Product1
Runbook

Troubleshooting

Common API errors and debugging


Objective

Use this runbook to diagnose and resolve common HTTP API errors returned by pycli when creating, listing, viewing, or canceling orders.


Scope

This runbook covers HTTP 4xx and 5xx error responses from the pycli API endpoints (POST /orders, GET /orders, GET /orders/{order_id}, DELETE /orders/{order_id}), how to interpret error shapes, and steps to recover from common failure states.

This runbook does not cover:

  • CLI (pycli deploy, pycli config set) errors or exit codes
  • Network-layer issues (DNS, TLS, firewall)
  • Server-side infrastructure failures beyond what the API surface exposes
  • Authentication and authorization configuration (covered separately)

Prerequisites

Before working through this runbook, confirm you have the following:

  • curl or an equivalent HTTP client installed and accessible on your PATH
  • The pycli API base URL (https://api.example.com) confirmed reachable from your environment
  • A valid Content-Type: application/json header available for any POST requests you need to replay
  • Basic familiarity with reading JSON response bodies
  • Any order_id values relevant to the request you are debugging

Steps

Work through these steps in order, stopping when you identify and resolve your error.


1. Reproduce the error and capture the full response

Run the failing request with -i so curl prints both headers and body. For example, to replay a failed order creation:

curl -i -X POST https://api.example.com/orders \
  -H 'Content-Type: application/json' \
  -d '{"amount": 1500, "currency": "USD"}'

For a failing fetch:

curl -i https://api.example.com/orders/42

Success looks like an HTTP 200 or 201 status line at the top of the response. If you see a 4xx or 5xx status, continue to the next step.


2. Check for HTTP 422 — Invalid request body (POST /orders only)

A 422 Unprocessable Entity means the JSON body you sent failed schema validation. The POST /orders endpoint expects a body matching the CreateOrderBody shape:

{
  "amount": 1500,
  "currency": "USD"
}

Common causes:

  • Missing amount or currency field
  • amount sent as a string instead of a number
  • Malformed JSON (unquoted keys, trailing commas)
  • Wrong or missing Content-Type: application/json header

Verify your request body is valid JSON before resending:

echo '{"amount": 1500, "currency": "USD"}' | python3 -m json.tool

If the command prints the formatted object without errors, the JSON is valid. Correct any fields flagged in the API error response body and retry step 1.


3. Check for HTTP 404 — Order not found (GET or DELETE /orders/{order_id})

A 404 Not Found on GET /orders/42 or DELETE /orders/42 means the order ID does not exist or has already been deleted.

  • Confirm the order_id value by listing orders and scanning the results:
curl 'https://api.example.com/orders?limit=10'
  • If you are trying to cancel an order, it may have already been canceled. A previous DELETE is non-reversible; confirm the order is absent from the list before escalating.
  • If the ID came from a previous POST /orders response, check that you copied it without truncation or extra whitespace.

4. Check for HTTP 400 — Bad query parameters (GET /orders)

A 400 Bad Request on the list endpoint usually means a query parameter has an unexpected value. The status filter accepts specific values (for example, paid); passing an unrecognized status string may trigger this error.

Retry with known-good parameters to isolate the problem:

curl 'https://api.example.com/orders?limit=10'

If this succeeds, reintroduce your original query parameters one at a time to identify the offending value.


5. Check for HTTP 5xx — Server-side errors

A 500 Internal Server Error or other 5xx response indicates a problem on the server, not in your request. Steps you can take:

  • Wait 30–60 seconds and retry the identical request. Transient errors often resolve on retry.
  • Simplify your request to the minimal valid payload to rule out an edge case in your data.
  • Check whether the issue affects all endpoints or only one (e.g., POST works but GET /orders/{id} consistently returns 500).

If retries do not resolve the error within a few minutes, proceed to the Escalation section.


6. Verify connectivity if all requests fail

If every endpoint returns an error or times out, confirm basic reachability:

curl -i https://api.example.com/orders?limit=1

A connection timeout or 000 curl exit code (rather than an HTTP status code) indicates a network or infrastructure issue outside the API itself, which is out of scope for this runbook.


Verification

After applying a fix, confirm resolution with the following checks:

  • Order creation: A successful POST /orders returns HTTP 201 (or 200) with a JSON body containing the new order's ID and details. No error fields should be present.
  • Order listing: GET /orders?limit=10 returns HTTP 200 with a JSON array. The order you just created (if applicable) should appear in the list.
  • Single order fetch: GET /orders/{order_id} with the correct ID returns HTTP 200 and the expected order object.
  • Order cancellation: DELETE /orders/{order_id} returns a 200 or 204 success status. A subsequent GET /orders/{order_id} should return 404, confirming the order no longer exists.

If all targeted endpoints return 2xx responses with well-formed JSON bodies, the issue is resolved.


Rollback

Most read operations (GET /orders, GET /orders/{order_id}) are safe to retry without side effects.

For write operations:

  • Accidentally created an order (POST /orders): Cancel it immediately using the order_id returned in the creation response:

    curl -X DELETE https://api.example.com/orders/{order_id}
    

    Confirm cancellation by verifying the subsequent GET /orders/{order_id} returns 404.

  • Accidentally canceled an order (DELETE /orders/{order_id}): Deletion is permanent based on the current API surface. There is no restore endpoint. If the order must be recreated, issue a new POST /orders with the original parameters and treat it as a new order.


Escalation

If you have completed all steps above and the error persists, escalate with the following information to reduce back-and-forth:

  1. The full curl command you ran (redact any sensitive values)
  2. The complete HTTP response including status line, headers, and body (captured with -i)
  3. The endpoint and method affected (e.g., POST /orders)
  4. Whether the issue is consistent or intermittent — include how many retries you attempted and over what time window
  5. Any order_id values relevant to the failing request
  6. The timestamp(s) of the failing requests in UTC