{
  "openapi": "3.1.0",
  "info": {
    "title": "SatStacker Engine Partner API",
    "description": "Embed Smart Timing using partner-scoped test/live API keys. Plan and instruction USD amounts limit total customer debit INCLUDING exchange fees. Confirm actual all-in USD debit and net BTC credited; partner_fee_usd is the fee breakdown already inside that debit. SatStacker does not execute exchange orders. Only final exchange outcomes may be confirmed. Lease redelivery retains identity. See /execution-contract, /sandbox-testing and /operations in the partner docs.",
    "version": "1.0.0",
    "contact": {
      "name": "SatStacker Support",
      "email": "support@satstacker.app"
    },
    "x-documentation-revision": "2026-10-05-partner-v2-all-in"
  },
  "paths": {
    "/partner/v1/health": {
      "get": {
        "tags": [
          "Partner API"
        ],
        "summary": "Partner Health",
        "description": "Public health check. No authentication required.",
        "operationId": "health",
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerHealthOut"
                }
              }
            }
          }
        },
        "security": []
      }
    },
    "/partner/v1/me": {
      "get": {
        "tags": [
          "Partner API"
        ],
        "summary": "Verify Credentials",
        "description": "Returns the authenticated partner and API key environment. Useful for integration testing.",
        "operationId": "me",
        "parameters": [],
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerIdentityOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/users/{partner_user_id}": {
      "patch": {
        "tags": [
          "Partner API"
        ],
        "summary": "Update Partner User Status",
        "description": "Enable or disable a partner user. Disable pauses active plans and cancels/refunds never-delivered instructions. Delivered instructions remain settleable and can be redelivered until final confirmation.",
        "operationId": "update-user-status",
        "parameters": [
          {
            "name": "partner_user_id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "title": "Partner User Id"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/PartnerUserStatusUpdate"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerUserOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/webhooks": {
      "post": {
        "tags": [
          "Partner API"
        ],
        "summary": "Register Webhook",
        "description": "Register/reactivate a webhook and generate a new secret EVERY time, including unchanged URLs. Secret appears only in this response. Exclude from generic automatic retries; a lost response requires coordinated re-registration and verifier update.",
        "operationId": "register-webhook",
        "parameters": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/WebhookRegisterIn"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookRegisterOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      },
      "get": {
        "tags": [
          "Partner API"
        ],
        "summary": "Get Webhook",
        "description": "Returns the current webhook registration for this API key environment.",
        "operationId": "get-webhook",
        "parameters": [],
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      },
      "delete": {
        "tags": [
          "Partner API"
        ],
        "summary": "Delete Webhook",
        "description": "Deletes the current webhook registration for this API key environment.",
        "operationId": "delete-webhook",
        "parameters": [],
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookDeleteOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/users": {
      "post": {
        "tags": [
          "Partner API"
        ],
        "summary": "Create or Link Partner User",
        "description": "Creates or updates a partner user after they opt in to Smart Timing.",
        "operationId": "users",
        "parameters": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/PartnerUserCreate"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerUserOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/plans": {
      "post": {
        "tags": [
          "Partner API"
        ],
        "summary": "Create Partner Plan",
        "description": "Create or update a full plan representation. amount_usd is the all-in window budget including exchange fees. Cancelled plans are terminal. start_date is create-only. Resets return 409 while a delivered instruction is unresolved. Omitted status/smart_timing_enabled default to active/true.",
        "operationId": "plans",
        "parameters": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/PartnerPlanCreate"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerPlanOut"
                }
              }
            }
          },
          "400": {
            "description": "Request violates a financial rule",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "404": {
            "description": "Record not found in this partner/environment",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "409": {
            "description": "Conflicting ownership, lifecycle or confirmation",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/executions/due": {
      "get": {
        "tags": [
          "Partner API"
        ],
        "summary": "Get Due Executions",
        "description": "Lease pending or expired-lease instructions for the authenticated environment. Default lease is five minutes. Redelivery keeps execution_id and idempotency_key. Treat keys as opaque. amount_usd is the maximum total customer debit including exchange fees. Delivered instructions remain settleable after pause/cancel/off. No exchange order is placed by this API call.",
        "operationId": "executions-due",
        "parameters": [
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "maximum": 500,
              "minimum": 1,
              "default": 50,
              "title": "Limit"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/ExecutionInstructionOut"
                  },
                  "title": "Response Executions-Due"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/executions/{execution_id}/confirm": {
      "post": {
        "tags": [
          "Partner API"
        ],
        "summary": "Confirm Execution",
        "description": "Record a definitive exchange outcome. Filled/partial require executed_at, all-in usd_amount, net credited btc_amount and fill execution_price. Fees are already included in usd_amount. Partial is terminal: remaining exchange orders must not still be able to fill. Failed/cancelled require failure_reason and represent zero debit/BTC. Identical final payload replay succeeds; changed outcomes conflict. Never place another buy to retry confirmation.",
        "operationId": "confirm-execution",
        "parameters": [
          {
            "name": "execution_id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "title": "Execution Id"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/TradeConfirmIn"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ExecutionConfirmationOut"
                }
              }
            }
          },
          "400": {
            "description": "Request violates a financial rule",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "404": {
            "description": "Record not found in this partner/environment",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "409": {
            "description": "Conflicting ownership, lifecycle or confirmation",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/billing/monthly": {
      "get": {
        "tags": [
          "Partner API"
        ],
        "summary": "Monthly Billing Report",
        "description": "Monthly aggregates based on executed_at. executed_volume_usd includes the all-in customer debit, including exchange fees; partner fees are separate. closed means the calendar period ended, not an immutable snapshot. Late confirmations can change results. Funded-user count uses plans' current Smart Timing enabled status; headline volume does not apply that plan filter.",
        "operationId": "billing-monthly",
        "parameters": [
          {
            "name": "month",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "examples": [
                "2026-05"
              ],
              "title": "Month"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/MonthlyBillingOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/billing/monthly/users": {
      "get": {
        "tags": [
          "Partner API"
        ],
        "summary": "Monthly Billing User Breakdown",
        "description": "Offset-paginated per-user totals based on executed_at. Current smart_timing_enabled status filters plan eligibility, so disabling can affect historical views. Not an order-level audit export. Preserve partner-side month-end snapshots.",
        "operationId": "billing-monthly-users",
        "parameters": [
          {
            "name": "month",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "examples": [
                "2026-05"
              ],
              "title": "Month"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "maximum": 10000,
              "minimum": 1,
              "default": 1000,
              "title": "Limit"
            }
          },
          {
            "name": "offset",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 0,
              "default": 0,
              "title": "Offset"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/MonthlyBillingUsersOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    },
    "/partner/v1/users/{partner_user_id}/claim-link": {
      "post": {
        "tags": [
          "Partner API"
        ],
        "summary": "Send User Claim Link",
        "description": "Emails a passwordless SatStacker partner-dashboard claim link to a linked partner user.",
        "operationId": "send-user-claim-link",
        "parameters": [
          {
            "name": "partner_user_id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "title": "Partner User Id"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Successful Response",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerClaimLinkOut"
                }
              }
            }
          },
          "401": {
            "description": "Missing, malformed, revoked or invalid API key",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "403": {
            "description": "Partner or user not active",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerErrorOut"
                }
              }
            }
          },
          "422": {
            "description": "Validation Error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/HTTPValidationError"
                }
              }
            }
          }
        },
        "security": [
          {
            "PartnerApiKey": []
          }
        ]
      }
    }
  },
  "components": {
    "schemas": {
      "HTTPValidationError": {
        "properties": {
          "detail": {
            "items": {
              "$ref": "#/components/schemas/ValidationError"
            },
            "type": "array",
            "title": "Detail"
          }
        },
        "type": "object",
        "title": "HTTPValidationError"
      },
      "ValidationError": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          },
          "input": {
            "title": "Input"
          },
          "ctx": {
            "type": "object",
            "title": "Context"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "PartnerClaimLinkOut": {
        "properties": {
          "ok": {
            "type": "boolean",
            "title": "Ok"
          },
          "partner_slug": {
            "type": "string",
            "title": "Partner Slug"
          },
          "partner_user_id": {
            "type": "string",
            "title": "Partner User Id"
          },
          "email": {
            "type": "string",
            "format": "email",
            "title": "Email"
          },
          "message": {
            "type": "string",
            "title": "Message"
          },
          "expires_in_minutes": {
            "type": "integer",
            "title": "Expires In Minutes"
          }
        },
        "type": "object",
        "required": [
          "ok",
          "partner_slug",
          "partner_user_id",
          "email",
          "message",
          "expires_in_minutes"
        ],
        "title": "PartnerClaimLinkOut"
      },
      "TradeConfirmIn": {
        "properties": {
          "partner_order_id": {
            "type": "string",
            "maxLength": 255,
            "minLength": 1,
            "title": "Partner Order Id",
            "description": "Unique exchange order ID, or a unique local attempt ID if no order was placed. Reuse on confirmation replay."
          },
          "status": {
            "type": "string",
            "enum": [
              "filled",
              "failed",
              "cancelled",
              "partial"
            ],
            "title": "Status"
          },
          "executed_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Executed At",
            "description": "UTC definitive exchange outcome time, required for filled/partial. Optional for failed/cancelled; omitted value uses confirmation time."
          },
          "usd_amount": {
            "anyOf": [
              {
                "type": "number"
              },
              {
                "type": "string",
                "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
              },
              {
                "type": "null"
              }
            ],
            "title": "Usd Amount",
            "description": "Actual total customer debit INCLUDING exchange fees. Positive, at most 2 decimal places; must not exceed reserved amount."
          },
          "btc_amount": {
            "anyOf": [
              {
                "type": "number"
              },
              {
                "type": "string",
                "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
              },
              {
                "type": "null"
              }
            ],
            "title": "Btc Amount",
            "description": "Net BTC actually credited, at most 8 decimal places; excludes unrelated subsequent withdrawals."
          },
          "execution_price": {
            "anyOf": [
              {
                "type": "number"
              },
              {
                "type": "string",
                "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
              },
              {
                "type": "null"
              }
            ],
            "title": "Execution Price",
            "description": "Exchange fill price or VWAP before separate fees; stored to cents and positive after rounding."
          },
          "partner_fee_usd": {
            "anyOf": [
              {
                "type": "number"
              },
              {
                "type": "string",
                "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
              },
              {
                "type": "null"
              }
            ],
            "title": "Partner Fee Usd",
            "default": "0.00",
            "description": "Exchange fee already INCLUDED in usd_amount; not an additional debit. Nonnegative for filled/partial; stored to cents. Failed/cancelled record zero."
          },
          "failure_reason": {
            "anyOf": [
              {
                "type": "string",
                "maxLength": 512
              },
              {
                "type": "null"
              }
            ],
            "title": "Failure Reason",
            "description": "Required for failed/cancelled. Omit for filled/partial."
          }
        },
        "type": "object",
        "required": [
          "partner_order_id",
          "status"
        ],
        "title": "TradeConfirmIn",
        "description": "Final outcomes only. Conditional required fields are encoded here; the API also enforces decimal precision, positivity, reserved-amount and lifecycle rules. See /execution-contract and /errors.",
        "allOf": [
          {
            "if": {
              "properties": {
                "status": {
                  "enum": [
                    "filled",
                    "partial"
                  ]
                }
              },
              "required": [
                "status"
              ]
            },
            "then": {
              "required": [
                "executed_at",
                "usd_amount",
                "btc_amount",
                "execution_price"
              ],
              "properties": {
                "executed_at": {
                  "title": "Executed At",
                  "description": "UTC definitive exchange outcome time, required for filled/partial. Optional for failed/cancelled; omitted value uses confirmation time.",
                  "type": "string",
                  "format": "date-time"
                },
                "usd_amount": {
                  "title": "Usd Amount",
                  "description": "Actual total customer debit INCLUDING exchange fees. Positive, at most 2 decimal places; must not exceed reserved amount.",
                  "anyOf": [
                    {
                      "type": "number"
                    },
                    {
                      "type": "string",
                      "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
                    }
                  ]
                },
                "btc_amount": {
                  "title": "Btc Amount",
                  "description": "Net BTC actually credited, at most 8 decimal places; excludes unrelated subsequent withdrawals.",
                  "anyOf": [
                    {
                      "type": "number"
                    },
                    {
                      "type": "string",
                      "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
                    }
                  ]
                },
                "execution_price": {
                  "title": "Execution Price",
                  "description": "Exchange fill price or VWAP before separate fees; stored to cents and positive after rounding.",
                  "anyOf": [
                    {
                      "type": "number"
                    },
                    {
                      "type": "string",
                      "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
                    }
                  ]
                }
              }
            }
          },
          {
            "if": {
              "properties": {
                "status": {
                  "enum": [
                    "failed",
                    "cancelled"
                  ]
                }
              },
              "required": [
                "status"
              ]
            },
            "then": {
              "required": [
                "failure_reason"
              ],
              "properties": {
                "failure_reason": {
                  "type": "string",
                  "minLength": 1,
                  "maxLength": 512
                }
              }
            }
          }
        ]
      },
      "ExecutionInstructionOut": {
        "properties": {
          "execution_id": {
            "type": "string",
            "title": "Execution Id"
          },
          "window_id": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Window Id",
            "description": "Original budget generation ID; newly generated instructions populate it."
          },
          "window_start": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Window Start",
            "description": "Original UTC window anchor for this instruction."
          },
          "tranche_key": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Tranche Key",
            "description": "Zero-based normal tranche index or failsafe; informational, not a deduplication key."
          },
          "partner_slug": {
            "type": "string",
            "title": "Partner Slug"
          },
          "partner_user_id": {
            "type": "string",
            "title": "Partner User Id"
          },
          "partner_plan_id": {
            "type": "string",
            "title": "Partner Plan Id"
          },
          "side": {
            "type": "string",
            "const": "buy",
            "title": "Side",
            "default": "buy"
          },
          "asset": {
            "type": "string",
            "const": "BTC",
            "title": "Asset",
            "default": "BTC"
          },
          "spend_currency": {
            "type": "string",
            "const": "USD",
            "title": "Spend Currency",
            "default": "USD"
          },
          "amount_usd": {
            "type": "string",
            "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$",
            "title": "Amount Usd",
            "description": "Maximum total customer debit including exchange fees for this instruction."
          },
          "reason": {
            "type": "string",
            "title": "Reason"
          },
          "idempotency_key": {
            "type": "string",
            "title": "Idempotency Key",
            "description": "Opaque attempt deduplication key; unchanged on lease redelivery. Do not construct or parse."
          },
          "created_at": {
            "type": "string",
            "format": "date-time",
            "title": "Created At"
          },
          "lease_expires_at": {
            "type": "string",
            "format": "date-time",
            "title": "Lease Expires At"
          },
          "delivered_count": {
            "type": "integer",
            "title": "Delivered Count"
          }
        },
        "type": "object",
        "required": [
          "execution_id",
          "partner_slug",
          "partner_user_id",
          "partner_plan_id",
          "amount_usd",
          "reason",
          "idempotency_key",
          "created_at",
          "lease_expires_at",
          "delivered_count"
        ],
        "title": "ExecutionInstructionOut"
      },
      "PartnerPlanOut": {
        "properties": {
          "ok": {
            "type": "boolean",
            "title": "Ok"
          },
          "partner_slug": {
            "type": "string",
            "title": "Partner Slug"
          },
          "partner_user_id": {
            "type": "string",
            "title": "Partner User Id"
          },
          "partner_plan_id": {
            "type": "string",
            "title": "Partner Plan Id"
          },
          "status": {
            "type": "string",
            "title": "Status"
          },
          "amount_usd": {
            "type": "string",
            "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$",
            "title": "Amount Usd",
            "description": "All-in USD spending budget including exchange fees."
          },
          "frequency": {
            "type": "string",
            "title": "Frequency"
          },
          "smart_timing_enabled": {
            "type": "boolean",
            "title": "Smart Timing Enabled"
          },
          "window_start": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Window Start"
          },
          "next_run": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Next Run"
          },
          "unspent_fiat_usd": {
            "anyOf": [
              {
                "type": "string",
                "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
              },
              {
                "type": "null"
              }
            ],
            "title": "Unspent Fiat Usd",
            "description": "Available current-window budget after confirmed all-in debits and open reservations. This is a logical budget, not custody of funds."
          }
        },
        "type": "object",
        "required": [
          "ok",
          "partner_slug",
          "partner_user_id",
          "partner_plan_id",
          "status",
          "amount_usd",
          "frequency",
          "smart_timing_enabled",
          "window_start",
          "next_run",
          "unspent_fiat_usd"
        ],
        "title": "PartnerPlanOut"
      },
      "PartnerPlanCreate": {
        "properties": {
          "partner_user_id": {
            "type": "string",
            "maxLength": 255,
            "minLength": 1,
            "title": "Partner User Id"
          },
          "partner_plan_id": {
            "type": "string",
            "maxLength": 255,
            "minLength": 1,
            "title": "Partner Plan Id"
          },
          "amount_usd": {
            "anyOf": [
              {
                "type": "number",
                "exclusiveMinimum": 0
              },
              {
                "type": "string",
                "pattern": "^(?!^[-+.]*$)[+-]?0*\\d*\\.?\\d*$"
              }
            ],
            "title": "Amount Usd",
            "description": "All-in total customer debit budget per window, including exchange fees."
          },
          "frequency": {
            "type": "string",
            "enum": [
              "daily",
              "weekly",
              "bi-weekly"
            ],
            "title": "Frequency"
          },
          "smart_timing_enabled": {
            "type": "boolean",
            "title": "Smart Timing Enabled",
            "default": true
          },
          "start_date": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Start Date",
            "description": "Create-only UTC anchor; omit for updates. Changing the existing anchor conflicts."
          },
          "status": {
            "type": "string",
            "enum": [
              "active",
              "paused",
              "cancelled"
            ],
            "title": "Status",
            "default": "active"
          }
        },
        "type": "object",
        "required": [
          "partner_user_id",
          "partner_plan_id",
          "amount_usd",
          "frequency"
        ],
        "title": "PartnerPlanCreate"
      },
      "PartnerUserOut": {
        "properties": {
          "ok": {
            "type": "boolean",
            "title": "Ok"
          },
          "partner_slug": {
            "type": "string",
            "title": "Partner Slug"
          },
          "partner_user_id": {
            "type": "string",
            "title": "Partner User Id"
          },
          "satstacker_partner_user_id": {
            "type": "string",
            "title": "Satstacker Partner User Id"
          },
          "email": {
            "anyOf": [
              {
                "type": "string",
                "format": "email"
              },
              {
                "type": "null"
              }
            ],
            "title": "Email"
          },
          "status": {
            "type": "string",
            "title": "Status"
          }
        },
        "type": "object",
        "required": [
          "ok",
          "partner_slug",
          "partner_user_id",
          "satstacker_partner_user_id",
          "status"
        ],
        "title": "PartnerUserOut"
      },
      "PartnerUserCreate": {
        "properties": {
          "partner_user_id": {
            "type": "string",
            "maxLength": 255,
            "minLength": 1,
            "title": "Partner User Id",
            "examples": [
              "rhino_user_123"
            ]
          },
          "email": {
            "anyOf": [
              {
                "type": "string",
                "format": "email"
              },
              {
                "type": "null"
              }
            ],
            "title": "Email"
          },
          "auth_provider": {
            "anyOf": [
              {
                "type": "string",
                "maxLength": 64
              },
              {
                "type": "null"
              }
            ],
            "title": "Auth Provider",
            "examples": [
              "apple",
              "google",
              "email"
            ]
          },
          "consent_accepted": {
            "type": "boolean",
            "title": "Consent Accepted"
          },
          "consent_version": {
            "type": "string",
            "maxLength": 128,
            "minLength": 1,
            "title": "Consent Version",
            "examples": [
              "satstacker-smart-timing-v1"
            ]
          },
          "consent_timestamp": {
            "type": "string",
            "format": "date-time",
            "title": "Consent Timestamp"
          }
        },
        "type": "object",
        "required": [
          "partner_user_id",
          "consent_accepted",
          "consent_version",
          "consent_timestamp"
        ],
        "title": "PartnerUserCreate"
      },
      "WebhookOut": {
        "properties": {
          "partner_slug": {
            "type": "string",
            "title": "Partner Slug"
          },
          "environment": {
            "type": "string",
            "title": "Environment"
          },
          "url": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Url"
          },
          "status": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Status"
          },
          "created_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Created At"
          },
          "updated_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Updated At"
          },
          "last_delivered_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Last Delivered At"
          },
          "last_status_code": {
            "anyOf": [
              {
                "type": "integer"
              },
              {
                "type": "null"
              }
            ],
            "title": "Last Status Code"
          },
          "consecutive_failures": {
            "anyOf": [
              {
                "type": "integer"
              },
              {
                "type": "null"
              }
            ],
            "title": "Consecutive Failures"
          }
        },
        "type": "object",
        "required": [
          "partner_slug",
          "environment"
        ],
        "title": "WebhookOut"
      },
      "WebhookRegisterOut": {
        "properties": {
          "partner_slug": {
            "type": "string",
            "title": "Partner Slug"
          },
          "environment": {
            "type": "string",
            "title": "Environment"
          },
          "url": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Url"
          },
          "status": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Status"
          },
          "created_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Created At"
          },
          "updated_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Updated At"
          },
          "last_delivered_at": {
            "anyOf": [
              {
                "type": "string",
                "format": "date-time"
              },
              {
                "type": "null"
              }
            ],
            "title": "Last Delivered At"
          },
          "last_status_code": {
            "anyOf": [
              {
                "type": "integer"
              },
              {
                "type": "null"
              }
            ],
            "title": "Last Status Code"
          },
          "consecutive_failures": {
            "anyOf": [
              {
                "type": "integer"
              },
              {
                "type": "null"
              }
            ],
            "title": "Consecutive Failures"
          },
          "secret": {
            "type": "string",
            "title": "Secret"
          }
        },
        "type": "object",
        "required": [
          "partner_slug",
          "environment",
          "secret"
        ],
        "title": "WebhookRegisterOut"
      },
      "WebhookRegisterIn": {
        "properties": {
          "url": {
            "type": "string",
            "minLength": 1,
            "format": "uri",
            "title": "Url"
          }
        },
        "type": "object",
        "required": [
          "url"
        ],
        "title": "WebhookRegisterIn"
      },
      "PartnerUserStatusUpdate": {
        "properties": {
          "status": {
            "type": "string",
            "enum": [
              "linked",
              "disabled"
            ],
            "title": "Status"
          }
        },
        "type": "object",
        "required": [
          "status"
        ],
        "title": "PartnerUserStatusUpdate"
      },
      "PartnerHealthOut": {
        "type": "object",
        "properties": {
          "status": {
            "type": "string"
          },
          "service": {
            "type": "string"
          },
          "time": {
            "type": "string",
            "format": "date-time"
          }
        },
        "required": [
          "status",
          "service",
          "time"
        ]
      },
      "PartnerIdentityOut": {
        "type": "object",
        "properties": {
          "partner_slug": {
            "type": "string"
          },
          "partner_name": {
            "type": "string"
          },
          "status": {
            "type": "string"
          },
          "environment": {
            "type": "string",
            "enum": [
              "test",
              "live"
            ]
          }
        },
        "required": [
          "partner_slug",
          "partner_name",
          "status",
          "environment"
        ]
      },
      "ExecutionConfirmationOut": {
        "type": "object",
        "properties": {
          "ok": {
            "type": "boolean"
          },
          "execution_id": {
            "type": "string"
          },
          "status": {
            "type": "string",
            "enum": [
              "filled",
              "partial",
              "failed",
              "cancelled"
            ]
          },
          "partner_order_id": {
            "type": "string"
          },
          "replayed": {
            "type": "boolean"
          }
        },
        "required": [
          "ok",
          "execution_id",
          "status",
          "partner_order_id"
        ]
      },
      "WebhookDeleteOut": {
        "type": "object",
        "properties": {
          "ok": {
            "type": "boolean"
          },
          "partner_slug": {
            "type": "string"
          },
          "environment": {
            "type": "string"
          },
          "deleted": {
            "type": "boolean"
          }
        },
        "required": [
          "ok",
          "partner_slug",
          "environment",
          "deleted"
        ]
      },
      "PartnerPricingOut": {
        "type": "object",
        "properties": {
          "tier": {
            "type": "string"
          },
          "subscription_rate_usd_per_user": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          },
          "volume_rate_bps": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          },
          "tier_overridden": {
            "type": "boolean"
          },
          "subscription_overridden": {
            "type": "boolean"
          },
          "volume_overridden": {
            "type": "boolean"
          }
        },
        "required": [
          "tier",
          "subscription_rate_usd_per_user",
          "volume_rate_bps",
          "tier_overridden",
          "subscription_overridden",
          "volume_overridden"
        ]
      },
      "MonthlyBillingOut": {
        "type": "object",
        "properties": {
          "partner_slug": {
            "type": "string"
          },
          "month": {
            "type": "string"
          },
          "period_start": {
            "type": "string",
            "format": "date-time"
          },
          "period_end": {
            "type": "string",
            "format": "date-time"
          },
          "period_status": {
            "type": "string",
            "enum": [
              "closed",
              "in_progress"
            ]
          },
          "active_funded_users": {
            "type": "integer"
          },
          "executed_volume_usd": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          },
          "executed_trade_count": {
            "type": "integer"
          },
          "pricing": {
            "$ref": "#/components/schemas/PartnerPricingOut"
          },
          "subscription_fee_total": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          },
          "volume_fee_total": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          },
          "total_due": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          }
        },
        "required": [
          "partner_slug",
          "month",
          "period_start",
          "period_end",
          "period_status",
          "active_funded_users",
          "executed_volume_usd",
          "executed_trade_count",
          "pricing",
          "subscription_fee_total",
          "volume_fee_total",
          "total_due"
        ]
      },
      "MonthlyBillingUserOut": {
        "type": "object",
        "properties": {
          "partner_user_id": {
            "type": "string"
          },
          "executed_volume_usd": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{2}$",
            "description": "USD decimal string with two places"
          },
          "executed_btc": {
            "type": "string",
            "pattern": "^-?\\d+\\.\\d{8}$"
          },
          "trade_count": {
            "type": "integer"
          }
        },
        "required": [
          "partner_user_id",
          "executed_volume_usd",
          "executed_btc",
          "trade_count"
        ]
      },
      "MonthlyBillingUsersOut": {
        "type": "object",
        "properties": {
          "partner_slug": {
            "type": "string"
          },
          "month": {
            "type": "string"
          },
          "period_status": {
            "type": "string",
            "enum": [
              "closed",
              "in_progress"
            ]
          },
          "limit": {
            "type": "integer"
          },
          "offset": {
            "type": "integer"
          },
          "count": {
            "type": "integer"
          },
          "users": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MonthlyBillingUserOut"
            }
          }
        },
        "required": [
          "partner_slug",
          "month",
          "period_status",
          "limit",
          "offset",
          "count",
          "users"
        ]
      },
      "PartnerErrorOut": {
        "type": "object",
        "properties": {
          "detail": {
            "oneOf": [
              {
                "type": "string"
              },
              {
                "type": "array",
                "items": {
                  "type": "object",
                  "additionalProperties": true
                }
              }
            ]
          }
        },
        "required": [
          "detail"
        ]
      }
    },
    "securitySchemes": {
      "PartnerApiKey": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "SatStacker API key",
        "description": "Use the complete sse_test_* or sse_live_* key. Never send credentials to browser/client-side code."
      }
    }
  },
  "externalDocs": {
    "url": "https://docs.satstacker.app",
    "description": "Partner integration documentation"
  },
  "servers": [
    {
      "url": "https://api.satstacker.app",
      "description": "Environment selected by sse_test_* or sse_live_* key"
    }
  ]
}
