{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "$id": "https://artifacts.apis.io/immersivecommons-com/json-schema/immersivecommons-com-credits-request-response-schema.json",
  "title": "CreditsRequestResponse",
  "description": "Discriminated on `mode`. minted: the key exists now and `agent_token` + `bundle` are surfaced ONCE, here. queued: an operator approves; poll /api/credits/status?request_id and then POST /api/credits/pickup. existing: the member already holds a live member key (one per person); `usage` is its spend and POST /api/credits/regenerate is how to get a fresh key.",
  "x-generated": "2026-11-12",
  "x-method": "derived",
  "x-generator": "derive-json-schema.py",
  "x-source": "openapi/immersivecommons-com-openapi.json#/components/schemas/CreditsRequestResponse",
  "type": "object",
  "required": [
    "ok",
    "mode"
  ],
  "properties": {
    "ok": {
      "type": "boolean"
    },
    "mode": {
      "type": "string",
      "enum": [
        "minted",
        "queued",
        "existing"
      ]
    },
    "request_id": {
      "type": "string",
      "description": "The request that minted or queued (absent on some `existing` answers)."
    },
    "token_prefix": {
      "type": "string",
      "description": "The key's prefix (minted / existing). Never the plaintext except in agent_token on a mint."
    },
    "agent_token": {
      "type": "string",
      "description": "minted only: the plaintext key, surfaced EXACTLY ONCE."
    },
    "bundle": {
      "type": "object",
      "additionalProperties": true,
      "description": "minted only: ready-to-paste Claude Code (copy_paste) and OpenAI-compatible (copy_paste_openai) configuration."
    },
    "proxy": {
      "type": "object",
      "additionalProperties": true,
      "description": "minted only: the key's limits block (kind, models, default_model, budget, expiry). No secret."
    },
    "status": {
      "type": "string",
      "enum": [
        "pending"
      ],
      "description": "queued only."
    },
    "budget_usd": {
      "type": "number",
      "description": "queued only: the budget the request asks for."
    },
    "usage": {
      "$ref": "#/$defs/CreditsStatus"
    }
  },
  "$defs": {
    "CreditsStatus": {
      "type": "object",
      "required": [
        "has_key"
      ],
      "description": "The member's IC Credits console state.",
      "properties": {
        "has_key": {
          "type": "boolean",
          "description": "Whether a live member key exists."
        },
        "token_prefix": {
          "type": "string"
        },
        "kind": {
          "type": "string"
        },
        "budget_usd": {
          "type": [
            "number",
            "null"
          ]
        },
        "budget_used_usd": {
          "type": "number"
        },
        "budget_remaining_usd": {
          "type": [
            "number",
            "null"
          ]
        },
        "budget_period": {
          "type": [
            "string",
            "null"
          ],
          "enum": [
            "month",
            "lifetime",
            null
          ]
        },
        "budget_resets": {
          "type": [
            "string",
            "null"
          ]
        },
        "by_model": {
          "type": "array",
          "items": {
            "type": "object",
            "properties": {
              "model": {
                "type": "string"
              },
              "provider": {
                "type": "string"
              },
              "tokens": {
                "type": "integer"
              }
            }
          }
        },
        "default_model": {
          "type": "string"
        },
        "pending_request": {
          "type": "object",
          "description": "A member request waiting for an operator, when one exists.",
          "properties": {
            "request_id": {
              "type": "string"
            },
            "budget_usd": {
              "type": "number"
            },
            "created_at": {
              "type": "string",
              "format": "date-time"
            }
          }
        }
      }
    }
  }
}