Upload Attachments
This guide will showcase two ways to upload files into Cake Slice as Attachments.
With a Source URL
The first and easiest way to create an Attachment with a file is to pass a source_url
to the create attachment endpoint. Cake Slice will automatically download and ingest the file at the given url upon creation.
source_url
is not persisted or used beyond initial ingestion. Cake Slice will copy the raw file at the given URL to
our private storage locations to be used indefinitely.
Request
const response = await fetch(
"https://api.cakeslice.com/v1/libraries/:library_id/attachments",
{
method: "POST",
headers: {
"Authorization": `Bearer ${token}`
},
body: JSON.stringify({
data: {
attributes: {
filename: "cake.png",
source_url: "https:example.com/cake.png"
}
}
})
}
)
await response.json()
Response
{
"id": "abc-def-123",
"type": "attachment",
"attributes": {
"filename": "cake.png",
"height": null,
"width": null,
"size": null,
"mimetype": null,
"tags": [],
"caption": null,
"description": null,
"state": "created",
"library_id": "abc-def-123",
"created_at": "2025-02-09T21:20:58.501Z",
"updated_at": "2025-02-09T21:20:58.501Z"
},
"relationships": {}
}
Fields related to the source file such as height
, width
, size
, etc. will fill in automatically as the attachment progresses through our various states of ingestion.
With an Upload URL
Alternatively, if you don't already have a valid source_url
for Cake Slice to ingest the file from you can create the attachment, upload the file, and mark the attachment as ready for further ingestion manually in three steps:
Step 1: create an attachment
Request
const response = await fetch(
"https://api.cakeslice.com/v1/libraries/:library_id/attachments?fields[attachments]=upload_url",
{
method: "POST",
headers: {
"Authorization": `Bearer ${token}`
},
body: JSON.stringify({
data: {
attributes: {
filename: "cake.png",
mimetype: "image/png"
}
}
})
}
)
await response.json()
Response
{
"id": "abc-def-123",
"type": "attachment",
"attributes": {
"filename": "cake.png",
"height": null,
"width": null,
"size": null,
"mimetype": "image/png",
"tags": [],
"caption": null,
"description": null,
"state": "created",
"library_id": "abc-def-123",
"created_at": "2025-02-09T21:20:58.501Z",
"updated_at": "2025-02-09T21:20:58.501Z",
"upload_url": "https://storage.googleapis.com/...."
},
"relationships": {}
}
Grab the id
and upload_url
from the response, you'll need them in the next steps.
Upload URLs are signed and only valid for a short period of time and will expire after 60 minutes. You must finish the upload in step 2 within that timeframe.
Step 2: upload the file to the upload_url
The mechanism you use to upload a file's bytes to a signed URL can differ based on language / framework / environment.
There are two headers you must supply when uploading the file to the signed url:
Content-Type: image/png # the mimetype of your file
Content-Disposition: Attachment
Step 3: mark the attachment as ready
Once the upload in step 2 has finished your ready for the final step. Mark the attachment as uploaded and it will continue on with the ingestion process.
Request
const response = await fetch(
"https://api.cakeslice.com/v1/attachments/:id",
{
method: "PUT",
headers: {
"Authorization": `Bearer ${token}`
},
body: JSON.stringify({
data: {
attributes: {
state: "uploaded"
}
}
})
}
)
await response.json()
Response
{
"id": "abc-def-123",
"type": "attachment",
"attributes": {
"filename": "cake.png",
"height": null,
"width": null,
"size": null,
"mimetype": "image/png",
"tags": [],
"caption": null,
"description": null,
"state": "uploaded",
"library_id": "abc-def-123",
"created_at": "2025-02-09T21:20:58.501Z",
"updated_at": "2025-02-09T21:20:58.501Z"
},
"relationships": {}
}
Fields related to the source file such as height
, width
, size
, etc. will fill in automatically as the attachment progresses through the various states of ingestion.