Overview
POST/storage/uploadsstorage

Begin an upload: reserve an attachment + presigned PUT URL

Create a record in uploads.

Auth: bearerAuth — calls run as the authenticated user.

Request body

application/json · optional

  • filenamestring
  • contentTypestring
  • ownerTypeoptionalstring

    Polymorphic owner kind (defaults to 'standalone').

  • ecosystemIdoptionalstring?
  • sizeBytesoptionalinteger

    Declared size; enforced against the storage quota at init.

  • contentHashoptionalstring

    When it matches an existing ready object, the upload is deduplicated.

Example
{
  "filename": "string",
  "contentType": "string",
  "ownerType": "string",
  "ecosystemId": "string",
  "sizeBytes": 0,
  "contentHash": "string"
}
Responses
200

Deduplicated — an identical object already exists; no new upload

  • attachmentStorageAttachment
  • deduplicatedtrue
Example
{
  "attachment": {
    "id": "string",
    "ecosystemId": "string",
    "customerId": "string",
    "ownerType": "string",
    "ownerId": "string",
    "objectKey": "string",
    "storageKind": "string",
    "filename": "string",
    "contentType": "string",
    "sizeBytes": 0,
    "contentHash": "string",
    "width": 0,
    "height": 0,
    "durationMs": 0,
    "status": "pending",
    "metadata": {},
    "createdAt": "string",
    "updatedAt": "string",
    "deletedAt": "string"
  },
  "deduplicated": true
}
201

Pending attachment + presigned PUT URL

  • attachmentStorageAttachment
  • uploadUrlstring

    Presigned PUT URL — upload the bytes directly to R2.

Example
{
  "attachment": {
    "id": "string",
    "ecosystemId": "string",
    "customerId": "string",
    "ownerType": "string",
    "ownerId": "string",
    "objectKey": "string",
    "storageKind": "string",
    "filename": "string",
    "contentType": "string",
    "sizeBytes": 0,
    "contentHash": "string",
    "width": 0,
    "height": 0,
    "durationMs": 0,
    "status": "pending",
    "metadata": {},
    "createdAt": "string",
    "updatedAt": "string",
    "deletedAt": "string"
  },
  "uploadUrl": "string"
}
400

Error

  • erroroptionalobject
Example
{
  "error": {
    "message": "string",
    "code": "string"
  }
}
401

Error

  • erroroptionalobject
Example
{
  "error": {
    "message": "string",
    "code": "string"
  }
}
413

Storage quota exceeded

  • errorError
  • usedinteger

    Bytes currently used by ready attachments.

  • quotainteger

    The caller’s total quota in bytes.

  • requestedinteger

    Declared size of the rejected upload.

Example
{
  "error": {
    "error": {
      "message": "string",
      "code": "string"
    }
  },
  "used": 0,
  "quota": 0,
  "requested": 0
}
Code examples
cURL
curl -X POST "https://api.agenticdeveloperhub.com/storage/uploads" \
  -H "Authorization: Bearer YOUR_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
  "filename": "string",
  "contentType": "string",
  "ownerType": "string",
  "ecosystemId": "string",
  "sizeBytes": 0,
  "contentHash": "string"
}'
JavaScript
const res = await fetch("https://api.agenticdeveloperhub.com/storage/uploads", {
  method: "POST",
  headers: {
    "Authorization": "Bearer YOUR_TOKEN",
    "Content-Type": "application/json"
  },
  body: "{\n  \"filename\": \"string\",\n  \"contentType\": \"string\",\n  \"ownerType\": \"string\",\n  \"ecosystemId\": \"string\",\n  \"sizeBytes\": 0,\n  \"contentHash\": \"string\"\n}",
});
const data = await res.json();