Skip to main content
Endpoints for uploading and managing identity profile images stored in Cloudflare R2.

Upload avatar

POST /api/upload/avatar
endpoint
Upload an avatar image for an identity
Upload an avatar image that will be stored in Cloudflare R2 and associated with the specified identity. Authentication: Required (session token) Content-Type: multipart/form-data

Request Parameters

file
File
required
Image file to uploadAccepted formats: JPEG, PNG, GIF, WebP
Maximum size: 5MB
identityId
string
required
ID of the identity to update

Response

avatarUrl
string
Public URL of the uploaded avatar image

Example

const formData = new FormData();
formData.append('file', avatarFile);
formData.append('identityId', 'identity_abc123');

const response = await fetch('https://api.aveid.net/api/upload/avatar', {
  method: 'POST',
  body: formData,
  credentials: 'include'
});

const { avatarUrl } = await response.json();
console.log('Avatar URL:', avatarUrl);
Response:
{
  "avatarUrl": "https://cdn.aveid.net/avatars/1234567890-abc123.png"
}

Behavior

  • Automatically deletes the previous avatar if one exists
  • Generates a unique filename with timestamp and random string
  • Stores in R2 bucket under avatars/ prefix
  • Sets 1-year cache control header
  • Logs avatar_updated activity

Error Responses

{
  "error": "No file provided"
}

Upload banner

POST /api/upload/banner
endpoint
Upload a banner image for an identity
Upload a banner image that will be stored in Cloudflare R2 and associated with the specified identity. Authentication: Required (session token) Content-Type: multipart/form-data

Request Parameters

file
File
required
Image file to uploadAccepted formats: JPEG, PNG, GIF, WebP
Maximum size: 10MB
identityId
string
required
ID of the identity to update

Response

bannerUrl
string
Public URL of the uploaded banner image

Example

const formData = new FormData();
formData.append('file', bannerFile);
formData.append('identityId', 'identity_abc123');

const response = await fetch('https://api.aveid.net/api/upload/banner', {
  method: 'POST',
  body: formData,
  credentials: 'include'
});

const { bannerUrl } = await response.json();
console.log('Banner URL:', bannerUrl);
Response:
{
  "bannerUrl": "https://cdn.aveid.net/banners/1234567890-xyz789.jpg"
}

Behavior

  • Automatically deletes the previous banner if it’s an image URL (not a color code)
  • Generates a unique filename with timestamp and random string
  • Stores in R2 bucket under banners/ prefix
  • Sets 1-year cache control header
  • Logs banner_updated activity

Delete avatar

DELETE /api/upload/avatar/:identityId
endpoint
Remove the avatar from an identity
Delete the avatar image from R2 storage and remove the URL from the identity record. Authentication: Required (session token)

Path Parameters

identityId
string
required
ID of the identity

Response

success
boolean
Always true if deletion succeeds

Example

curl -X DELETE https://api.aveid.net/api/upload/avatar/identity_abc123 \
  -H "Cookie: ave_session=YOUR_SESSION_TOKEN"
Response:
{
  "success": true
}

Delete banner

DELETE /api/upload/banner/:identityId
endpoint
Remove the banner from an identity
Delete the banner image from R2 storage and remove the URL from the identity record. Only deletes image files, not color codes. Authentication: Required (session token)

Path Parameters

identityId
string
required
ID of the identity

Response

success
boolean
Always true if deletion succeeds

Example

curl -X DELETE https://api.aveid.net/api/upload/banner/identity_abc123 \
  -H "Cookie: ave_session=YOUR_SESSION_TOKEN"
Response:
{
  "success": true
}

Configuration

The upload endpoints require the following environment variables to be configured:
R2_ACCOUNT_ID
string
required
Cloudflare R2 account ID
R2_ACCESS_KEY_ID
string
required
R2 access key ID
R2_SECRET_ACCESS_KEY
string
required
R2 secret access key
R2_BUCKET_NAME
string
R2 bucket name (defaults to “ave-uploads”)
R2_PUBLIC_URL
string
required
Public URL for accessing uploaded files

File Specifications

Avatar Images

  • Formats: JPEG, PNG, GIF, WebP
  • Maximum size: 5MB
  • Storage path: avatars/{timestamp}-{random}.{ext}
  • Cache: 1 year (max-age=31536000)
  • Formats: JPEG, PNG, GIF, WebP
  • Maximum size: 10MB
  • Storage path: banners/{timestamp}-{random}.{ext}
  • Cache: 1 year (max-age=31536000)
Banner URLs can also be color codes (starting with #) instead of image URLs. The delete endpoint only removes actual image files, not color codes.

Security

  • Authentication required: All endpoints require valid session authentication
  • Identity ownership: Users can only upload to identities they own
  • File type validation: Only allows JPEG, PNG, GIF, and WebP images
  • Size limits: 5MB for avatars, 10MB for banners
  • Automatic cleanup: Old images are deleted when replaced
  • Activity logging: All uploads and deletions are logged

Next Steps

Identities

Manage identity information

Activity log

View upload activity

Build docs developers (and LLMs) love