Usage API Caching TTL in Claude HUD: Success vs Failure Handling

Claude HUD implements two distinct time-to-live (TTL) values for caching Anthropic's usage API responses: a 5-minute TTL for successful requests and a 15-second TTL for failures, balancing rate-limit compliance against data freshness.

Claude HUD, an open-source VS Code extension maintained by jarrodwatts/claude-hud, queries Anthropic's usage endpoint to render real-time "Usage" progress bars in the developer interface. To prevent rate-limit exhaustion while maintaining responsive UI updates, the plugin employs a sophisticated dual-tier caching mechanism defined in src/usage-api.ts that applies different expiration logic depending on request success or failure states.

How the Dual TTL System Works

The caching architecture distinguishes between valid usage data and transient errors. When the plugin retrieves usage statistics, it stores the response in memory with an expiration timestamp determined by the request outcome.

Success Cache TTL

Successful API responses—those returning valid usage statistics—are cached for 5 minutes (300,000 milliseconds). This duration is defined as the constant CACHE_TTL_MS in src/usage-api.ts at line 48. The extended TTL reflects the relatively static nature of usage data during short windows, allowing the UI to display consistent metrics without redundant network calls.

Failure Cache TTL

Failed requests—triggered by network errors, non-2xx HTTP statuses, or API unavailability—receive a much shorter cache duration of 15 seconds (15,000 milliseconds). Defined as CACHE_FAILURE_TTL_MS in src/usage-api.ts at line 49, this brief TTL prevents aggressive retry storms during outages while enabling rapid recovery once the service restores connectivity.

Configuration and Customization

Both TTL values are configurable via user settings, allowing customization based on specific network conditions or usage patterns.

Default Values

Cache Type Constant Name Default Duration Configuration Key
Success CACHE_TTL_MS 5 minutes usage.cacheTtlSeconds
Failure CACHE_FAILURE_TTL_MS 15 seconds usage.failureCacheTtlSeconds

Customizing TTL in config.json

Users override defaults by modifying their config.json file. The plugin reads these values during initialization in src/index.ts (lines 65-66) and converts seconds to milliseconds before passing them to the usage layer:

{
  "usage": {
    "cacheTtlSeconds": 600,
    "failureCacheTtlSeconds": 30
  }
}

This example extends successful data retention to 10 minutes and failure suppression to 30 seconds.

Implementation Details

The caching logic dynamically selects the appropriate TTL by inspecting the apiUnavailable flag within cached data. As implemented in src/usage-api.ts at line 166:

const ttl = cache.data.apiUnavailable
  ? ttls.failureCacheTtlMs   // use short TTL for failures
  : ttls.cacheTtlMs;         // use long TTL for successful data

During plugin initialization, src/index.ts bundles these values into a TTL configuration object:

// src/index.ts (lines 65-66)
cacheTtlMs: config.usage.cacheTtlSeconds * 1000,
failureCacheTtlMs: config.usage.failureCacheTtlSeconds * 1000,

The usage module then exposes these through a ttls object at line 352 of src/usage-api.ts:

ttls: { cacheTtlMs: CACHE_TTL_MS, failureCacheTtlMs: CACHE_FAILURE_TTL_MS },

Practical Code Examples

Adjusting Cache Durations

To modify caching behavior for high-latency environments, update your configuration:

{
  "usage": {
    "cacheTtlSeconds": 300,
    "failureCacheTtlSeconds": 15
  }
}

Accessing Cached Data Internally

When building extensions that consume Claude HUD's usage data, the getUsageData function automatically respects the TTL logic:

import { getUsageData } from './usage-api';

async function showUsage() {
  const usage = await getUsageData();
  console.log(`5-hour usage: ${usage.fiveHourPct}%`);
  console.log(`7-day usage: ${usage.sevenDayPct}%`);
}

Handling Failure Scenarios

The short failure TTL ensures quick recovery from transient errors. When fetchUsage encounters a network failure, it caches the error state briefly:

import { fetchUsage } from './usage-api';

// After a network failure, subsequent calls return cached error for 15s
await fetchUsage(); // fails → cached with failure TTL

Summary

  • Claude HUD uses two distinct TTL values for usage API caching: 5 minutes for successes and 15 seconds for failures.
  • The constants CACHE_TTL_MS and CACHE_FAILURE_TTL_MS are defined in src/usage-api.ts at lines 48 and 49.
  • Configuration occurs through config.json keys usage.cacheTtlSeconds and usage.failureCacheTtlSeconds.
  • The selection logic at line 166 of src/usage-api.ts checks the apiUnavailable flag to determine which TTL to apply.
  • This dual-tier approach optimizes for rate-limit preservation during normal operations and rapid error recovery during outages.

Frequently Asked Questions

What is the default Usage API caching TTL in Claude HUD?

The default TTL for successful usage API responses is 5 minutes (300 seconds), while failed responses receive a 15-second cache duration. These defaults prevent excessive API calls during normal operations while allowing quick retries after network interruptions.

Why does Claude HUD use different TTL values for success and failure?

Successful usage data changes infrequently over 5-minute windows, making long caching safe and rate-limit friendly. Failures are typically transient network issues; a short 15-second TTL prevents "retry storms" that could overwhelm the API while still allowing the plugin to recover quickly once connectivity returns.

How do I modify the Usage API caching duration?

Adjust the usage.cacheTtlSeconds and usage.failureCacheTtlSeconds values in your config.json file. The plugin reads these settings in src/index.ts and applies them throughout the caching layer defined in src/usage-api.ts.

Where is the caching logic implemented in the source code?

The core caching implementation resides in src/usage-api.ts, specifically at lines 48-49 where constants are defined, line 166 where TTL selection occurs, and line 352 where the configuration object is constructed. Initialization logic appears in src/index.ts at lines 65-66.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →