Skip to content

Storage endpoints

26 endpoints at https://api.vaif.studio, generated from the API's OpenAPI document. The REST API page covers authentication, and All endpoints lists every group.

POST /storage/upload-base64

Request body (application/json, required)
{
  projectId: string (uuid);
  bucket: string;
  path: string;
  data: string;
  contentType?: string;
}
Response 200 (application/json)
{
  ok: true;
  key: string;
  sizeBytes: number;
}

Errors: 400, 403, 404, 500, with the error body.

POST /storage/upload-url

Request body (application/json, required)
{
  bucket?: string;
  key: string;
  sizeBytes: number;
  contentType?: string;
}
Response 200 (application/json)
{
  ok: true;
  url: string;
}

Errors: 400, 403, with the error body.

POST /storage/upload

ParameterInTypeRequired
bucketquerystringNo
keyquerystringYes
Response 200 (application/json)
{
  ok: boolean;
  key: string;
  bucket: string;
  sizeBytes: number;
}

POST /storage/download-url

Request body (application/json, required)
{
  bucket?: string;
  key: string;
  expiresIn?: number;
}
Response 200 (application/json)
{
  ok: true;
  url: string;
  expiresIn: number;
}

Errors: 400, 403, with the error body.

GET /storage/download

ParameterInTypeRequired
bucketquerystringNo
keyquerystringYes
expiresInquerynumberNo
Response 200 (application/octet-stream)
string (binary)
Response 307

No body.

GET /storage/buckets

ParameterInTypeRequired
projectIdquerystringNo
envIdquerystringNo
limitquerystringNo
offsetquerystringNo
Response 200 (application/json)
{
  ok: boolean;
  buckets: {
    id: string;
    projectId: string;
    envId: null | string;
    storageEnvironment: string;
    name: string;
    public: boolean;
    fileSizeLimit: null | number;
    allowedMimeTypes: any;
    corsOrigins: any;
    sizeBytes: number;
    createdAt: string (date-time);
    updatedAt: string (date-time);
  }[];
}

POST /storage/buckets

Request body (application/json, required)
{
  projectId: string (uuid);
  envId?: string (uuid);
  name: string;
  public?: boolean;
  fileSizeLimit?: number;
  allowedMimeTypes?: string[];
  corsOrigins?: string[];
  allowProduction?: boolean;
}
Response 201 (application/json)
{
  ok: true;
  bucket?: any;
}

Errors: 400, 401, 403, 404, 409, with the error body.

POST /storage/multipart/create

Initiate a multipart upload

Request body (application/json, required)
{
  bucketId: string;
  key: string;
  contentType?: string;
  sizeBytes?: number;
  allowProduction?: boolean;
}
Response 200 (application/json)
{
  ok: true;
  uploadId: string;
  key: string;
  resumeToken: string;
  partSize: number;
}

Errors: 400, 401, 403, 404, 500, with the error body.

POST /storage/multipart/{uploadId}/part-url

Get a signed URL for uploading a part

ParameterInTypeRequired
uploadIdpathstringYes
Request body (application/json, required)
{
  bucketId: string;
  key: string;
  partNumber: number;
}
Response 200 (application/json)
{
  ok: true;
  url: string;
  partNumber: number;
}

Errors: 400, 401, 403, 404, 500, with the error body.

POST /storage/multipart/{uploadId}/complete

Complete a multipart upload

ParameterInTypeRequired
uploadIdpathstringYes
Request body (application/json, required)
{
  bucketId: string;
  key: string;
  parts: {
    PartNumber: number;
    ETag: string;
    sizeBytes?: number;
  }[];
  allowProduction?: boolean;
}
Response 200 (application/json)
{
  ok: true;
  key: string;
}

Errors: 400, 401, 403, 404, 409, 500, with the error body.

POST /storage/multipart/{uploadId}/abort

Abort a multipart upload

ParameterInTypeRequired
uploadIdpathstringYes
Request body (application/json, required)
{
  bucketId: string;
  key: string;
  allowProduction?: boolean;
}
Response 200 (application/json)
{
  ok: true;
}

Errors: 400, 401, 403, 404, 500, with the error body.

POST /storage/multipart/resume

Resume an in-progress multipart upload by token

Request body (application/json, required)
{
  resumeToken: string;
}
Response 200 (application/json)
{
  uploadId: string;
  bucketId: string;
  key: string;
  sizeBytes: number | null;
  parts: {
    partNumber: number;
    etag: string;
    sizeBytes: number;
  }[];
  expiresAt: string;
}

Errors: 403, 404, 410, with the error body.

GET /storage/multipart/list-pending

List the current user's in-progress multipart uploads

Response 200 (application/json)
{
  uploads: {
    uploadId: string;
    bucketId: string;
    key: string;
    sizeBytes: number | null;
    partCount: number;
    resumeTokenPrefix: string;
    expiresAt: string;
    createdAt: string;
  }[];
}

POST /storage/files/copy

Request body (application/json)
{
  bucketId: string;
  sourceKey: string;
  destinationKey: string;
}
Response 200 (application/json)
{
  ok: boolean;
  key: string;
}

POST /storage/files/move

Request body (application/json)
{
  bucketId: string;
  sourceKey: string;
  destinationKey: string;
}
Response 200 (application/json)
{
  ok: boolean;
  key: string;
}

POST /storage/files/delete-batch

Request body (application/json)
{
  bucketId: string;
  keys: string[];
}
Response 200 (application/json)
{
  ok: boolean;
  deletedCount: number;
}

GET /storage/files/{bucketId}/metadata

ParameterInTypeRequired
bucketIdpathstringYes
keyquerystringYes
Response 200 (application/json)
{
  ok: boolean;
  metadata: {
    size: number;
    contentType?: string;
    lastModified?: string (date-time);
    etag?: string;
    cacheControl: null | string;
    metadata: {
      [key: string]: string;
    };
  };
}

PATCH /storage/files/{bucketId}/metadata

ParameterInTypeRequired
bucketIdpathstringYes
Request body (application/json)
{
  key: string;
  metadata: {
    [key: string]: string;
  };
  contentType?: string;
}
Response 200 (application/json)
{
  ok: boolean;
}

POST /storage/upload-from-url

Request body (application/json)
{
  bucketId: string;
  key: string;
  url: string;
  contentType?: string;
}
Response 200 (application/json)
{
  ok: boolean;
  key: string;
  sizeBytes: number;
}

GET /storage/usage/project/{projectId}

ParameterInTypeRequired
projectIdpathstringYes
envIdquerystringNo
Response 200 (application/json)
{
  ok: boolean;
  envId: string;
  storedBytes: number;
  pendingBytes: number;
  usedBytes: number;
  bucketCount: number;
  listCap: number;
  buckets: {
    id: string;
    name: string;
    public: boolean;
    objectCount: null | number;
    bytes: null | number;
    truncated: boolean;
  }[];
}

GET /storage/buckets/{bucketId}/policies

ParameterInTypeRequired
bucketIdpathstringYes
Response 200 (application/json)
{
  policies: {
    id: string;
    bucketId: string;
    name: string;
    operation: string;
    definition: string;
    checkExpression: null | string;
    enabled: boolean;
    ruleJson: null | {
      operation: any;
      who: any;
      pathPrefix?: any;
      mimePattern?: any;
      maxSizeBytes?: any;
    };
    createdAt: string (date-time);
    updatedAt: string (date-time);
  }[];
}

POST /storage/buckets/{bucketId}/policies

ParameterInTypeRequired
bucketIdpathstringYes
Request body (application/json)
{
  name: string;
  operation: "ALL" | "DELETE" | "INSERT" | "SELECT" | "UPDATE";
  definition?: string;
  checkExpression?: string;
  rule?: {
    operation: "DELETE" | "INSERT" | "SELECT" | "UPDATE";
    who: {
      kind: "anonymous";
    } | {
      kind: "authenticated";
    } | {
      kind: "owner";
    } | {
      kind: "role";
      role: string;
    };
    pathPrefix?: string;
    mimePattern?: string;
    maxSizeBytes?: number;
  };
  enabled?: boolean;
  allowProduction?: boolean;
}
Response 200

No body.

Response 201 (application/json)
{
  policy: {
    bucketId: string;
    checkExpression: null | string;
    createdAt: string (date-time);
    definition: string;
    enabled: boolean;
    id: string;
    name: string;
    operation: string;
    ruleJson: null | {
      operation: "DELETE" | "INSERT" | "SELECT" | "UPDATE";
      who: {
        kind: any;
        role: any;
      } | {
        kind: any;
      };
      pathPrefix?: string;
      mimePattern?: string;
      maxSizeBytes?: number;
    };
    updatedAt: string (date-time);
  };
  policies: {
    bucketId: string;
    checkExpression: null | string;
    createdAt: string (date-time);
    definition: string;
    enabled: boolean;
    id: string;
    name: string;
    operation: string;
    ruleJson: null | {
      operation: any;
      who: any;
      pathPrefix?: any;
      mimePattern?: any;
      maxSizeBytes?: any;
    };
    updatedAt: string (date-time);
  }[];
}

PUT /storage/buckets/{bucketId}/policies/{policyId}

ParameterInTypeRequired
bucketIdpathstringYes
policyIdpathstringYes
Request body (application/json)
{
  name?: string;
  operation?: "ALL" | "DELETE" | "INSERT" | "SELECT" | "UPDATE";
  definition?: string;
  checkExpression?: null | string;
  rule?: null | {
    operation: "DELETE" | "INSERT" | "SELECT" | "UPDATE";
    who: {
      kind: "anonymous";
    } | {
      kind: "authenticated";
    } | {
      kind: "owner";
    } | {
      kind: "role";
      role: string;
    };
    pathPrefix?: string;
    mimePattern?: string;
    maxSizeBytes?: number;
  };
  enabled?: boolean;
  allowProduction?: boolean;
}
Response 200 (application/json)
{
  policy: {
    id: string;
    bucketId: string;
    name: string;
    operation: string;
    definition: string;
    checkExpression: null | string;
    enabled: boolean;
    ruleJson: null | {
      operation: "DELETE" | "INSERT" | "SELECT" | "UPDATE";
      who: {
        kind: any;
        role: any;
      } | {
        kind: any;
      };
      pathPrefix?: string;
      mimePattern?: string;
      maxSizeBytes?: number;
    };
    createdAt: string (date-time);
    updatedAt: string (date-time);
  };
}

DELETE /storage/buckets/{bucketId}/policies/{policyId}

ParameterInTypeRequired
bucketIdpathstringYes
policyIdpathstringYes
Response 200 (application/json)
{
  success: boolean;
}

POST /storage/buckets/{bucketId}/policies/{policyId}/toggle

ParameterInTypeRequired
bucketIdpathstringYes
policyIdpathstringYes
Response 200 (application/json)
{
  policy: {
    id: string;
    bucketId: string;
    name: string;
    operation: string;
    definition: string;
    checkExpression: null | string;
    enabled: boolean;
    ruleJson: null | {
      operation: "DELETE" | "INSERT" | "SELECT" | "UPDATE";
      who: {
        kind: any;
        role: any;
      } | {
        kind: any;
      };
      pathPrefix?: string;
      mimePattern?: string;
      maxSizeBytes?: number;
    };
    createdAt: string (date-time);
    updatedAt: string (date-time);
  };
}

POST /storage/buckets/{bucketId}/policies/simulate

ParameterInTypeRequired
bucketIdpathstringYes
Request body (application/json)
{
  operation: "DELETE" | "INSERT" | "SELECT" | "UPDATE";
  path: string;
  mimeType?: string;
  sizeBytes?: number;
  as: {
    kind: "anonymous";
  } | {
    kind: "authenticated";
    userId: string;
    role?: string;
  };
}
Response 200 (application/json)
{
  allowed: boolean;
  matchedPolicyId: null;
  reason: string;
} | {
  allowed: boolean;
  matchedPolicyId: null | string;
  reason: string;
}