cloudflare
references/static-assets/api.md
.md 200 lines
Content
# API Reference
## ASSETS Binding
The `ASSETS` binding provides access to static assets via the `Fetcher` interface.
### Type Definition
```typescript
interface Env {
ASSETS: Fetcher;
}
interface Fetcher {
fetch(input: RequestInfo | URL, init?: RequestInit): Promise<Response>;
}
```
### Method Signatures
```typescript
// 1. Forward entire request
await env.ASSETS.fetch(request);
// 2. String path (hostname ignored, only path matters)
await env.ASSETS.fetch("https://any-host/path/to/asset.png");
// 3. URL object
await env.ASSETS.fetch(new URL("/index.html", request.url));
// 4. Constructed Request object
await env.ASSETS.fetch(new Request(new URL("/logo.png", request.url), {
method: "GET",
headers: request.headers
}));
```
**Key behaviors:**
- Host/origin is ignored for string/URL inputs (only path is used)
- Method must be GET (others return 405)
- Request headers pass through (affects response)
- Returns standard `Response` object
## Request Handling
### Path Resolution
```typescript
// All resolve to same asset:
env.ASSETS.fetch("https://example.com/logo.png")
env.ASSETS.fetch("https://ignored.host/logo.png")
env.ASSETS.fetch("/logo.png")
```
Assets are resolved relative to configured `assets.directory`.
### Headers
Request headers that affect response:
| Header | Effect |
|--------|--------|
| `Accept-Encoding` | Controls compression (gzip, brotli) |
| `Range` | Enables partial content (206 responses) |
| `If-None-Match` | Conditional request via ETag |
| `If-Modified-Since` | Conditional request via modification date |
Custom headers pass through but don't affect asset serving.
### Method Support
| Method | Supported | Response |
|--------|-----------|----------|
| `GET` | ✅ Yes | Asset content |
| `HEAD` | ✅ Yes | Headers only, no body |
| `POST`, `PUT`, etc. | ❌ No | 405 Method Not Allowed |
## Response Behavior
### Content-Type Inference
Automatically set based on file extension:
| Extension | Content-Type |
|-----------|--------------|
| `.html` | `text/html; charset=utf-8` |
| `.css` | `text/css` |
| `.js` | `application/javascript` |
| `.json` | `application/json` |
| `.png` | `image/png` |
| `.jpg`, `.jpeg` | `image/jpeg` |
| `.svg` | `image/svg+xml` |
| `.woff2` | `font/woff2` |
### Default Headers
Responses include:
```
Content-Type: <inferred>
ETag: "<hash>"
Cache-Control: public, max-age=3600
Content-Encoding: br (if supported and beneficial)
```
**Cache-Control defaults:**
- 1 hour (`max-age=3600`) for most assets
- Override via Worker response transformation (see patterns.md:27-35)
### Compression
Automatic compression based on `Accept-Encoding`:
- **Brotli** (`br`): Preferred, best compression
- **Gzip** (`gzip`): Fallback
- **None**: If client doesn't support or asset too small
### ETag Generation
ETags are content-based hashes:
```
ETag: "a3b2c1d4e5f6..."
```
Used for conditional requests (`If-None-Match`). Returns `304 Not Modified` if match.
## Error Responses
| Status | Condition | Behavior |
|--------|-----------|----------|
| `404` | Asset not found | Body depends on `not_found_handling` config |
| `405` | Non-GET/HEAD method | `{ "error": "Method not allowed" }` |
| `416` | Invalid Range header | Range not satisfiable |
### 404 Handling
Depends on configuration (see configuration.md:45-52):
```typescript
// not_found_handling: "single-page-application"
// Returns /index.html with 200 status
// not_found_handling: "404-page"
// Returns /404.html if exists, else 404 response
// not_found_handling: "none"
// Returns 404 response
```
## Advanced Usage
### Modifying Responses
```typescript
const response = await env.ASSETS.fetch(request);
// Clone and modify
return new Response(response.body, {
status: response.status,
headers: {
...Object.fromEntries(response.headers),
'Cache-Control': 'public, max-age=31536000',
'X-Custom': 'value'
}
});
```
See patterns.md:27-35 for full example.
### Error Handling
```typescript
const response = await env.ASSETS.fetch(request);
if (!response.ok) {
// Asset not found or error
return new Response('Custom error page', { status: 404 });
}
return response;
```
### Conditional Serving
```typescript
const url = new URL(request.url);
// Serve different assets based on conditions
if (url.pathname === '/') {
return env.ASSETS.fetch('/index.html');
}
return env.ASSETS.fetch(request);
```
See patterns.md for complete patterns.