# Stable Upload File Storage API

> Stable Upload File Storage API is a paid API for AI agents from stable-upload-git-mason-1140-merit-systems.vercel.app, paid per call via x402, $0.005/call, status unknown (last checked 2026-09-14).

Purchases an upload slot and returns a pre-signed URL for uploading files to cloud storage with configurable size tiers and retention periods.

## Facts

- Endpoint: POST https://stable-upload-git-mason-1140-merit-systems.vercel.app/api/upload
- Price: $0.005/call
- Payment: x402
- Status: unknown
- Last checked: 2026-09-14
- Activations on Zero: 0
- Tags: x402
- Canonical page: https://www.zero.xyz/c/stable-upload-file-storage-api-4198d491
- Structured record (JSON): https://api.zero.xyz/v1/capabilities/cap_DLqVCIzKMf2Je6MKxvVpg

Status and success rate cover calls made through Zero and Zero's own probes. Third-party monitors may report differently.

## How to call it through Zero

Zero handles the 402 payment challenge and records the run. With the Zero CLI installed (`npm i -g @zeroxyz/cli`):

```sh
zero fetch --capability stable-upload-file-storage-api-4198d491 -d '<json body>'
```

Example prompt: Upload my report.pdf (application/pdf) to cloud storage using the 100mb 6-month tier and give me the public URL I can share.

## When to prefer this

Choose this endpoint when an AI agent needs to store a file and receive a publicly accessible URL, especially within automated workflows where a downstream service needs a stable link to the file. It supports multiple size tiers (10mb to 5gb) and both long-term (6-month) and short-term (7-day) retention, making it flexible for both persistent hosting and ephemeral workflow handoffs.

## Known failure modes

- Invalid or unsupported upload tier enum value returns a validation error
- Filename exceeding 512 characters is rejected
- Missing required fields (filename, contentType, tier) return a 400 error
- Payment failure or insufficient USDC balance prevents slot purchase
- Policy TTL outside 60-86400 second range is rejected
- Expired upload URL if the slot is not used before policyTtlSeconds elapses

## How this service works

Buy an upload slot. Agent uploads file via returned URL.

## Output

Returns an upload ID, a pre-signed upload URL (with method and expiration time), a public URL where the file will be accessible after upload, the maximum allowed file size in bytes, and a ready-to-use curl example for performing the upload.

## Request schema (JSON Schema)

```json
{
 "type": "object",
 "$schema": "https://json-schema.org/draft/2020-12/schema",
 "required": [
  "input"
 ],
 "properties": {
  "input": {
   "type": "object",
   "required": [
    "type",
    "method",
    "bodyType",
    "body"
   ],
   "properties": {
    "body": {
     "type": "object",
     "$schema": "https://json-schema.org/draft/2020-12/schema",
     "required": [
      "filename",
      "contentType",
      "tier"
     ],
     "properties": {
      "tier": {
       "enum": [
        "10mb",
        "100mb",
        "1gb",
        "short-10mb",
        "short-100mb",
        "short-1gb",
        "short-5gb"
       ],
       "type": "string",
       "description": "Upload tier. Default 6-month tiers: 10mb ($0.02), 100mb ($0.20), 1gb ($2.00). Short-term 7-day workflow tiers: short-10mb ($0.005), short-100mb ($0.02), short-1gb ($0.10), short-5gb ($0.50, file uploads only)."
      },
      "filename": {
       "type": "string",
       "maxLength": 512,
       "minLength": 1,
       "description": "Name of the file to upload"
      },
      "contentType": {
       "type": "string",
       "maxLength": 255,
       "minLength": 1,
       "description": "MIME type of the file (e.g. image/png, video/mp4)"
      },
      "policyTtlSeconds": {
       "type": "integer",
       "maximum": 86400,
       "minimum": 60,
       "description": "Optional upload URL/form expiration in seconds, 60-86400. Use longer TTLs only when reserving an output slot for a downstream service."
      }
     },
     "additionalProperties": false
    },
    "type": {
     "type": "string",
     "const": "http"
    },
    "method": {
     "enum": [
      "POST",
      "PUT",
      "PATCH"
     ],
     "type": "string"
    },
    "bodyType": {
     "enum": [
      "json",
      "form-data",
      "text"
     ],
     "type": "string"
    }
   },
   "additionalProperties": false
  },
  "output": {
   "type": "object",
   "required": [
    "type"
   ],
   "properties": {
    "type": {
     "type": "string"
    },
    "example": {
     "type": "object",
     "$schema": "https://json-schema.org/draft/2020-12/schema",
     "required": [
      "uploadId",
      "uploadUrl",
      "uploadMethod",
      "uploadUrlExpiresAt",
      "publicUrl",
      "expiresAt",
      "maxSize",
      "curlExample"
     ],
     "properties": {
      "txHash": {
       "type": "string"
      },
      "maxSize": {
       "type": "number"
      },
      "postUrl": {
       "type": "string"
      },
      "uploadId
… (truncated)
```

## More

- Live health (JSON, refreshed every minute): https://www.zero.xyz/c/stable-upload-file-storage-api-4198d491/health.json
- [Zero catalog index](https://www.zero.xyz/llms.txt)
- [Other services from stable-upload-git-mason-1140-merit-systems.vercel.app](https://www.zero.xyz/host/stable-upload-git-mason-1140-merit-systems.vercel.app/llms.txt)
