Skip to content

Error Codes Reference

Complete guide to Claude API error codes, their meanings, and solutions.

HTTP Status Codes

4xx Client Errors

400 - Bad Request

Meaning: The request is malformed or contains invalid parameters.

Common Causes:

  • Invalid JSON format
  • Missing required fields
  • Invalid parameter values
  • Incorrect content type

Solutions:

python
# ❌ Bad Request Example
{
    "model": "invalid-model-name",
    "max_tokens": "not-a-number",  # Should be integer
    "messages": "not-an-array"     # Should be array
}

# ✅ Correct Format
{
    "model": "claude-3-5-sonnet-20241022",
    "max_tokens": 1024,
    "messages": [
        {"role": "user", "content": "Hello"}
    ]
}

401 - Unauthorized

Meaning: Authentication failed or API key is invalid.

Common Causes:

  • Missing API key
  • Invalid API key format
  • Expired API key
  • Incorrect header format

Solutions:

bash
# Check API key format
echo $ANTHROPIC_API_KEY | cut -c1-10  # Should start with sk-ant-api03

# Verify headers
curl -H "x-api-key: $ANTHROPIC_API_KEY" \
     -H "anthropic-version: 2024-10-22" \
     https://api.anthropic.com/v1/messages

403 - Forbidden

Meaning: Authentication successful but access denied.

Common Causes:

  • Insufficient permissions
  • Account suspended
  • Rate limits exceeded (soft limit)
  • Model access restricted

Solutions:

python
# Check account status
response = requests.get(
    "https://api.anthropic.com/v1/messages",
    headers={
        "x-api-key": api_key,
        "anthropic-version": "2024-10-22"
    }
)
print(response.status_code, response.json())

404 - Not Found

Meaning: Requested resource doesn't exist.

Common Causes:

  • Incorrect API endpoint
  • Invalid model name
  • Resource ID doesn't exist

Solutions:

python
# ❌ Wrong endpoint
url = "https://api.anthropic.com/v1/message"  # Missing 's'

# ✅ Correct endpoint  
url = "https://api.anthropic.com/v1/messages"

# ❌ Invalid model
model = "claude-3-5-sonnet-latest"

# ✅ Valid model
model = "claude-3-5-sonnet-20241022"

413 - Payload Too Large

Meaning: Request exceeds size limits.

Common Causes:

  • Message content too long
  • Too many messages in conversation
  • Large file attachments

Solutions:

python
# Check content length
def check_token_count(text):
    # Rough estimation: ~4 characters per token
    estimated_tokens = len(text) // 4
    if estimated_tokens > 200000:
        print(f"Content might be too large: ~{estimated_tokens} tokens")
    return estimated_tokens

# Chunk large content
def chunk_content(text, max_chunk_size=100000):
    chunks = []
    for i in range(0, len(text), max_chunk_size):
        chunks.append(text[i:i+max_chunk_size])
    return chunks

422 - Unprocessable Entity

Meaning: Request is well-formed but contains semantic errors.

Common Causes:

  • Invalid parameter combinations
  • Conflicting settings
  • Unsupported features for model

Solutions:

python
# Check parameter compatibility
def validate_request(model, max_tokens, temperature):
    if model.startswith("claude-3-5-haiku") and max_tokens > 4096:
        print("Warning: Haiku models work best with max_tokens <= 4096")
    
    if temperature < 0 or temperature > 1:
        raise ValueError("Temperature must be between 0 and 1")

429 - Too Many Requests

Meaning: Rate limit exceeded.

Common Causes:

  • Too many requests per minute
  • Too many tokens per minute
  • Too many requests per day

Solutions:

python
import time
import random
from anthropic import RateLimitError

def exponential_backoff(func, max_retries=5, base_delay=1):
    """Implement exponential backoff for rate limits"""
    for attempt in range(max_retries):
        try:
            return func()
        except RateLimitError as e:
            if attempt == max_retries - 1:
                raise e
            
            # Exponential backoff with jitter
            delay = base_delay * (2 ** attempt) + random.uniform(0, 1)
            print(f"Rate limited. Waiting {delay:.2f}s before retry {attempt + 1}/{max_retries}")
            time.sleep(delay)

# Usage
response = exponential_backoff(
    lambda: client.messages.create(
        model="claude-3-5-sonnet-20241022",
        max_tokens=1024,
        messages=[{"role": "user", "content": "Hello"}]
    )
)

5xx Server Errors

500 - Internal Server Error

Meaning: Unexpected server error.

Common Causes:

  • Temporary service issues
  • Server overload
  • Model processing errors

Solutions:

python
def robust_api_call(client, **kwargs):
    """Make API call with automatic retry for server errors"""
    max_retries = 3
    
    for attempt in range(max_retries):
        try:
            return client.messages.create(**kwargs)
        except Exception as e:
            if hasattr(e, 'status_code') and e.status_code >= 500:
                if attempt < max_retries - 1:
                    wait_time = 2 ** attempt
                    print(f"Server error, retrying in {wait_time}s...")
                    time.sleep(wait_time)
                    continue
            raise e

502 - Bad Gateway

Meaning: Gateway or proxy error.

Solutions:

python
# Check service status
import requests

def check_anthropic_status():
    """Check if Anthropic API is operational"""
    try:
        response = requests.get("https://status.anthropic.com", timeout=10)
        print(f"Status page: {response.status_code}")
    except requests.RequestException:
        print("Cannot reach status page")
        
# Implement circuit breaker
class CircuitBreaker:
    def __init__(self, threshold=5, reset_timeout=60):
        self.threshold = threshold
        self.reset_timeout = reset_timeout
        self.failure_count = 0
        self.last_failure_time = None
        self.state = "closed"  # closed, open, half-open
    
    def call(self, func, *args, **kwargs):
        if self.state == "open":
            if time.time() - self.last_failure_time > self.reset_timeout:
                self.state = "half-open"
            else:
                raise Exception("Circuit breaker is open")
        
        try:
            result = func(*args, **kwargs)
            if self.state == "half-open":
                self.state = "closed"
                self.failure_count = 0
            return result
        except Exception as e:
            self.failure_count += 1
            self.last_failure_time = time.time()
            
            if self.failure_count >= self.threshold:
                self.state = "open"
            
            raise e

503 - Service Unavailable

Meaning: Service temporarily unavailable.

Solutions:

python
# Check service availability
def wait_for_service(max_wait=300):
    """Wait for service to become available"""
    start_time = time.time()
    
    while time.time() - start_time < max_wait:
        try:
            # Quick health check
            client.messages.create(
                model="claude-3-5-haiku-20241022",
                max_tokens=10,
                messages=[{"role": "user", "content": "Hi"}]
            )
            print("Service is available!")
            return True
        except Exception as e:
            if "503" in str(e):
                print("Service unavailable, waiting...")
                time.sleep(30)
            else:
                raise e
    
    print("Service not available after maximum wait time")
    return False

Claude Code Specific Errors

Permission Denied

Error: Permission denied when accessing file

Solutions:

bash
# Check file permissions
ls -la filename

# Fix permissions
chmod 644 filename  # For files
chmod 755 dirname   # For directories

# Check Claude Code permissions
claude-code permissions list
claude-code permissions add bash

Context Window Exceeded

Error: Context window exceeded

Solutions:

bash
# Clear context
/clear

# Compact context
/compact

# Check context usage
# Look for indicator in bottom-right of Claude Code UI

Tool Execution Failed

Error: Tool execution failed: command not found

Solutions:

bash
# Check if tool is installed
which git
which docker
which npm

# Install missing tools
# Ubuntu/Debian
sudo apt install git

# macOS
brew install git

# Add to Claude Code allowlist
claude-code config tools.allowlist add git

Model Access Denied

Error: Model access denied or not available

Solutions:

bash
# Check available models
claude-code --list-models

# Use fallback model
claude-code --model claude-3-5-sonnet-20241022

# Check account tier
# Some models require higher tier access

API Response Error Codes

Anthropic-Specific Error Types

python
from anthropic import (
    APIError,
    APIConnectionError,
    APITimeoutError,
    RateLimitError,
    AuthenticationError,
    BadRequestError,
    ConflictError,
    InternalServerError,
    NotFoundError,
    PermissionDeniedError
)

# Comprehensive error handling
def handle_anthropic_errors(func):
    """Decorator for comprehensive error handling"""
    def wrapper(*args, **kwargs):
        try:
            return func(*args, **kwargs)
        except AuthenticationError:
            print("❌ Authentication failed. Check your API key.")
        except RateLimitError as e:
            print(f"❌ Rate limit exceeded: {e}")
        except BadRequestError as e:
            print(f"❌ Bad request: {e}")
        except NotFoundError:
            print("❌ Resource not found. Check model name/endpoint.")
        except APIConnectionError:
            print("❌ Connection error. Check internet/proxy settings.")
        except APITimeoutError:
            print("❌ Request timed out. Try again or increase timeout.")
        except InternalServerError:
            print("❌ Server error. Try again later.")
        except APIError as e:
            print(f"❌ API error: {e}")
        except Exception as e:
            print(f"❌ Unexpected error: {e}")
    
    return wrapper

Debugging Guide

Enable Debug Logging

python
import logging

# Enable debug logging
logging.basicConfig(level=logging.DEBUG)

# For requests debugging
import httpx
client = Anthropic(
    http_client=httpx.Client(
        event_hooks={
            'request': [lambda r: print(f"Request: {r.method} {r.url}")],
            'response': [lambda r: print(f"Response: {r.status_code}")]
        }
    )
)

Error Information Collection

python
def collect_error_info(error):
    """Collect comprehensive error information"""
    info = {
        "error_type": type(error).__name__,
        "error_message": str(error),
        "timestamp": datetime.now().isoformat(),
    }
    
    # Add HTTP-specific info if available
    if hasattr(error, 'status_code'):
        info["status_code"] = error.status_code
    if hasattr(error, 'response'):
        info["response_headers"] = dict(error.response.headers)
    if hasattr(error, 'request'):
        info["request_method"] = error.request.method
        info["request_url"] = str(error.request.url)
    
    return info

Health Check Script

python
#!/usr/bin/env python3
"""Claude API Health Check Script"""

import sys
from anthropic import Anthropic

def health_check():
    """Comprehensive health check for Claude API"""
    checks = []
    
    # 1. API Key Check
    try:
        api_key = os.getenv('ANTHROPIC_API_KEY')
        if not api_key:
            checks.append(("API Key", "❌", "ANTHROPIC_API_KEY not set"))
        elif not api_key.startswith('sk-ant-'):
            checks.append(("API Key", "❌", "Invalid API key format"))
        else:
            checks.append(("API Key", "✅", "Valid format"))
    except Exception as e:
        checks.append(("API Key", "❌", str(e)))
    
    # 2. Connection Test
    try:
        client = Anthropic()
        response = client.messages.create(
            model="claude-3-5-haiku-20241022",
            max_tokens=10,
            messages=[{"role": "user", "content": "Hi"}]
        )
        checks.append(("Connection", "✅", "API accessible"))
    except Exception as e:
        checks.append(("Connection", "❌", str(e)))
    
    # 3. Model Access Test
    models_to_test = [
        "claude-3-5-haiku-20241022",
        "claude-3-5-sonnet-20241022",
        "claude-3-opus-20240229"
    ]
    
    for model in models_to_test:
        try:
            response = client.messages.create(
                model=model,
                max_tokens=10,
                messages=[{"role": "user", "content": "test"}]
            )
            checks.append((f"Model {model}", "✅", "Accessible"))
        except Exception as e:
            checks.append((f"Model {model}", "❌", str(e)))
    
    # Print results
    print("\n=== Claude API Health Check ===")
    for check_name, status, message in checks:
        print(f"{status} {check_name}: {message}")
    
    # Return overall status
    failed_checks = [c for c in checks if c[1] == "❌"]
    return len(failed_checks) == 0

if __name__ == "__main__":
    success = health_check()
    sys.exit(0 if success else 1)

Quick Reference

Most Common Errors

ErrorQuick FixCommand
401 UnauthorizedCheck API keyecho $ANTHROPIC_API_KEY
429 Rate LimitedWait and retrysleep 60
400 Bad RequestCheck JSON formatValidate with JSON linter
500 Server ErrorRetry requestUse exponential backoff
Context Too LargeClear context/clear or /compact

Emergency Commands

bash
# Reset everything
export ANTHROPIC_API_KEY="your-key"
claude-code /clear
claude-code config reset

# Test basic functionality
claude-code "Hello, are you working?"

# Check service status
curl -s https://status.anthropic.com | grep -i "operational"

When reporting bugs: Include error code, full error message, request details, and steps to reproduce.

Claude Code Documentation Hub