{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "$id": "https://artifacts.apis.io/sendraven-ai/json-schema/sendraven-ai-usage-schema.json",
  "title": "Usage",
  "x-generated": "2026-10-31",
  "x-method": "derived",
  "x-generator": "derive-json-schema.py",
  "x-source": "openapi/sendraven-ai-api-openapi.json#/components/schemas/Usage",
  "type": "object",
  "required": [
    "object",
    "plan",
    "plan_name",
    "pricing_version",
    "unlimited",
    "included_emails",
    "emails_used",
    "emails_remaining",
    "period_start",
    "period_end",
    "estimated_cents",
    "estimated",
    "next_price_point",
    "payment_method",
    "budget",
    "sending_locked",
    "lock_reason",
    "enterprise_suggested",
    "enterprise_from_emails",
    "estimated_at_period_end_cents"
  ],
  "properties": {
    "object": {
      "type": "string",
      "enum": [
        "usage"
      ]
    },
    "plan": {
      "type": "string",
      "enum": [
        "free",
        "standard",
        "enterprise",
        "pro",
        "scale"
      ],
      "description": "No subscription means free. pro and scale are the retired v1 plans, still reported for the workspaces that are on them."
    },
    "plan_name": {
      "type": "string",
      "description": "Free, Standard or Enterprise."
    },
    "pricing_version": {
      "type": "string",
      "enum": [
        "v1",
        "v2"
      ],
      "description": "Which pricing generation this workspace is billed on. New workspaces are v2."
    },
    "unlimited": {
      "type": "boolean",
      "description": "True for a staff-owned workspace: included_emails and emails_remaining are null and sending_locked is false."
    },
    "included_emails": {
      "type": [
        "integer",
        "null"
      ],
      "description": "Free's monthly allowance (3,000), or the emails the Standard monthly minimum covers (50,000). On Standard it is not a ceiling — sending past it is priced, never refused. null when unlimited."
    },
    "emails_used": {
      "type": "integer",
      "minimum": 0,
      "description": "Recipients sent in the current billing period, from a rollup that trails by at least a minute and longer during large sends. Leave headroom."
    },
    "emails_remaining": {
      "type": [
        "integer",
        "null"
      ],
      "description": "included_emails - emails_used; negative once past it on a metered plan, where it means nothing is blocked. null when unlimited."
    },
    "period_start": {
      "type": "string",
      "format": "date-time",
      "description": "Start of the window emails_used and estimated_cents cover: the calendar month on Free, the Stripe subscription period on a paid plan, or the moment of an upgrade for the period it started."
    },
    "period_end": {
      "type": "string",
      "format": "date-time"
    },
    "estimated_cents": {
      "type": "integer",
      "minimum": 0,
      "description": "What this period costs so far, in US cents, on the same curve Stripe bills: the monthly minimum plus usage. Not projected to the end of the period."
    },
    "estimated": {
      "type": "string",
      "description": "estimated_cents as dollars, e.g. $48.71."
    },
    "next_price_point": {
      "type": [
        "object",
        "null"
      ],
      "required": [
        "emails",
        "cents"
      ],
      "description": "The next published volume and what the month costs there, so a client can show the shape of the curve. null past the last published point.",
      "properties": {
        "emails": {
          "type": "integer"
        },
        "cents": {
          "type": "integer"
        }
      }
    },
    "payment_method": {
      "type": "object",
      "required": [
        "present",
        "required",
        "brand",
        "last4",
        "verified_at"
      ],
      "description": "The saved payment method. No outbound email leaves a workspace where required is true and present is false, including on Free and including a test send. Only a person can add one, in the dashboard.",
      "properties": {
        "present": {
          "type": "boolean"
        },
        "required": {
          "type": "boolean",
          "description": "False for a staff workspace and for an enterprise account on invoice terms."
        },
        "brand": {
          "type": [
            "string",
            "null"
          ]
        },
        "last4": {
          "type": [
            "string",
            "null"
          ]
        },
        "verified_at": {
          "type": [
            "string",
            "null"
          ],
          "format": "date-time"
        }
      }
    },
    "budget": {
      "type": [
        "object",
        "null"
      ],
      "required": [
        "cents",
        "action",
        "reached"
      ],
      "description": "The workspace's own monthly spend ceiling, when it has set one.",
      "properties": {
        "cents": {
          "type": "integer"
        },
        "action": {
          "type": "string",
          "enum": [
            "pause_marketing",
            "pause_all"
          ],
          "description": "pause_marketing, the default, lets transactional mail through: a budget that stops password resets is an outage rather than a saving."
        },
        "reached": {
          "type": "boolean"
        }
      }
    },
    "sending_locked": {
      "type": "boolean",
      "description": "True when every outbound send is refused for a billing reason. False while a reached budget pauses marketing only (lock_reason is then budget_exceeded and transactional mail still sends). Inbound is never affected."
    },
    "lock_reason": {
      "type": [
        "string",
        "null"
      ],
      "enum": [
        "payment_method_required",
        "plan_limit_reached",
        "billing_past_due",
        "budget_exceeded",
        null
      ],
      "description": "Why, named as the error type a send would answer with, so a caller branches on one vocabulary. null when sending works. budget_exceeded may apply to marketing only."
    },
    "enterprise_suggested": {
      "type": "boolean",
      "description": "True as the workspace approaches the volume where a negotiated rate usually beats self-service."
    },
    "enterprise_from_emails": {
      "type": "integer",
      "description": "The volume from which a negotiated rate usually beats self-service, and where enterprise_suggested turns true. Not a sending wall and not a plan change: the published curve keeps applying at every volume above it."
    },
    "estimated_at_period_end_cents": {
      "type": "integer",
      "description": "This period's volume priced on the public self-service curve, for comparison with a quote."
    }
  }
}