Skip to main content

Overview

The usage endpoint provides real-time information about your current rate limit status, quota usage, and credit balance. This endpoint uses ChatGPT session authentication instead of API keys.

Endpoint

GET /api/codex/usage

Retrieves usage statistics and rate limit information for the authenticated account. Base URL: https://your-codex-lb-instance.com

Query Parameters

None.

Headers

Authorization
string
required
Bearer token from ChatGPT session (e.g., Bearer chatgpt-access-token)
chatgpt-account-id
string
required
ChatGPT workspace/account ID

Response

plan_type
string
Account plan type (e.g., plus, team, enterprise)
rate_limit
object
Rate limit status information
credits
object
Credit balance information (if applicable)

Example Response

{
  "plan_type": "plus",
  "rate_limit": {
    "allowed": true,
    "limit_reached": false,
    "primary_window": {
      "used_percent": 20,
      "limit_window_seconds": 18000,
      "reset_after_seconds": 14400,
      "reset_at": 1704081600
    },
    "secondary_window": {
      "used_percent": 50,
      "limit_window_seconds": 604800,
      "reset_after_seconds": 432000,
      "reset_at": 1704499200
    }
  },
  "credits": {
    "has_credits": true,
    "unlimited": false,
    "balance": "15.0",
    "approx_local_messages": null,
    "approx_cloud_messages": null
  }
}

Example Request

curl -X GET https://your-codex-lb-instance.com/api/codex/usage \
  -H "Authorization: Bearer chatgpt-access-token" \
  -H "chatgpt-account-id: workspace_abc123"

Authentication

This endpoint uses ChatGPT session authentication, not API keys. You must provide:
  1. An Authorization header with a valid ChatGPT access token
  2. A chatgpt-account-id header with your workspace/account ID
These credentials can be obtained from your ChatGPT web session.

Rate Limit Windows

Primary Window

Typically a 5-hour rolling window (18000 seconds). This is the main rate limit that applies to most API usage.

Secondary Window

Typically a 7-day rolling window (604800 seconds). This provides additional capacity for burst usage while maintaining weekly limits.

Window Selection

The API returns both windows when available. If only one window is active (e.g., weekly-only limits), the other will be null.

Usage Monitoring

Interpreting Usage Percentages

  • 0-50% - Normal usage, plenty of capacity
  • 51-80% - Moderate usage, monitor if making many requests
  • 81-99% - High usage, consider throttling requests
  • 100% - Limit reached, requests will be rejected until reset

Planning Based on Reset Times

import time

def wait_for_reset(usage_data):
    """Wait until the rate limit resets"""
    if usage_data['rate_limit']['primary_window']:
        reset_seconds = usage_data['rate_limit']['primary_window']['reset_after_seconds']
        reset_time = time.time() + reset_seconds
        
        print(f"Rate limit resets in {reset_seconds} seconds")
        print(f"Reset time: {time.ctime(reset_time)}")
        
        return reset_seconds
    return 0

Credits

For accounts with credit-based billing:
  • has_credits: true - Account can make requests
  • has_credits: false - Account is out of credits
  • unlimited: true - Account has unlimited credits (enterprise plans)
  • balance - Current credit balance in USD

Error Handling

401 Unauthorized

Invalid or expired access token:
{
  "error": {
    "message": "Invalid authentication credentials",
    "type": "authentication_error",
    "code": "invalid_credentials"
  }
}

403 Forbidden

Missing or invalid chatgpt-account-id header:
{
  "error": {
    "message": "Account ID is required",
    "type": "invalid_request_error",
    "code": "missing_account_id"
  }
}

Use Cases

Pre-Request Validation

Check usage before making requests to avoid hitting rate limits:
def can_make_request(api_base, access_token, account_id, threshold=90):
    """Check if we're below the rate limit threshold"""
    response = requests.get(
        f"{api_base}/api/codex/usage",
        headers={
            "Authorization": f"Bearer {access_token}",
            "chatgpt-account-id": account_id
        }
    )
    usage = response.json()
    
    if not usage['rate_limit']['allowed']:
        return False
    
    # Check primary window
    if usage['rate_limit']['primary_window']:
        if usage['rate_limit']['primary_window']['used_percent'] >= threshold:
            return False
    
    return True

if can_make_request("https://your-instance.com", token, account_id):
    # Make your API request
    pass
else:
    print("Rate limit too high, waiting...")

Dashboard Display

Display usage information in your application:
async function displayUsageStats(apiBase, accessToken, accountId) {
  const response = await fetch(`${apiBase}/api/codex/usage`, {
    headers: {
      'Authorization': `Bearer ${accessToken}`,
      'chatgpt-account-id': accountId
    }
  });
  
  const usage = await response.json();
  
  return {
    plan: usage.plan_type,
    primaryUsage: usage.rate_limit.primary_window?.used_percent || 0,
    secondaryUsage: usage.rate_limit.secondary_window?.used_percent || 0,
    creditsAvailable: usage.credits?.has_credits || false,
    balance: usage.credits?.balance || '0'
  };
}

Notes

  • Usage data is aggregated across all accounts in your Codex-LB pool
  • The endpoint returns the most recent usage data from the last refresh cycle
  • Both primary and secondary windows may not always be present
  • For weekly-only plans, primary_window will be null and secondary_window contains the weekly limit
  • Usage percentages are calculated based on the upstream provider’s limits
  • This endpoint does not count against your rate limit

Build docs developers (and LLMs) love