Grist attachments API
Documents may include attached files. Data records can refer to these using a column of type `Attachments`.
Documents may include attached files. Data records can refer to these using a column of type `Attachments`.
Every API here is available over the APIs.io API and to AI agents over MCP.
One button, every client — Claude, Cursor, VS Code and the rest.
https://apis.io/mcp
find_apisBrowse and filter every API in the catalog.get_api_artifactsOne API's artifacts, grouped by type.get_openapiThe primary OpenAPI for this API.find_similar_apisAPIs that look like this one.apis_io_searchSTART HERE — APIs, providers and tags for one query, each with its total.resolveTurn a domain, URL or GitHub org into the provider it belongs to.find_cohortsEvery scored population of providers in the catalog.curl "https://apis.io/api/v1/apis/grist-attachments-api"
curl "https://apis.io/api/v1/apis?limit=25"
Discovery needs no key. Ratings and market analysis are Pro.
Free tier, no form to fill in. Signing in shares your email address with us — we store it to create your key and to recognise you if you sign in with another provider. See our Privacy Policy and Terms.
A second provider on the same verified email joins the account you already have.
openapi: 3.2.0
info:
description: 'An API for manipulating Grist sites, workspaces, and documents.
# Authentication
<SecurityDefinitions />
'
version: 1.0.1
title: Grist Attachments API
servers:
- url: https://{gristhost}/api
variables:
subdomain:
description: The team name, or `docs` for personal areas
default: docs
security:
- ApiKey: []
tags:
- name: attachments
description: Documents may include attached files. Data records can refer to these using a column of type `Attachments`.
paths:
/docs/{docId}/attachments:
get:
operationId: listAttachments
tags:
- attachments
summary: List metadata of all attachments in a doc
parameters:
- $ref: '#/components/parameters/docIdPathParam'
- $ref: '#/components/parameters/filterQueryParam'
- $ref: '#/components/parameters/sortQueryParam'
- $ref: '#/components/parameters/limitQueryParam'
- $ref: '#/components/parameters/sortHeaderParam'
- $ref: '#/components/parameters/limitHeaderParam'
responses:
200:
description: List of attachment metadata records. Note that the list may temporarily include records for attachments that are stored in the document but not referenced by any Attachments type cell.
content:
application/json:
schema:
$ref: '#/components/schemas/AttachmentMetadataList'
post:
operationId: uploadAttachments
tags:
- attachments
summary: Upload attachments to a doc
parameters:
- $ref: '#/components/parameters/docIdPathParam'
requestBody:
description: the files to add to the doc
content:
multipart/form-data:
schema:
$ref: '#/components/schemas/AttachmentUpload'
required: true
responses:
200:
description: IDs of attachments added, one per file.
content:
application/json:
schema:
$ref: '#/components/schemas/RowIds'
/docs/{docId}/attachments/{attachmentId}:
get:
operationId: getAttachmentMetadata
tags:
- attachments
summary: Get the metadata for an attachment
parameters:
- $ref: '#/components/parameters/docIdPathParam'
- in: path
name: attachmentId
schema:
$ref: '#/components/schemas/AttachmentId'
required: true
responses:
200:
description: Attachment metadata
content:
application/json:
schema:
$ref: '#/components/schemas/AttachmentMetadata'
/docs/{docId}/attachments/{attachmentId}/download:
get:
operationId: downloadAttachment
tags:
- attachments
summary: Download the contents of an attachment
parameters:
- $ref: '#/components/parameters/docIdPathParam'
- in: path
name: attachmentId
schema:
$ref: '#/components/schemas/AttachmentId'
required: true
responses:
200:
description: Attachment contents, with suitable Content-Type.
/docs/{docId}/attachments/archive:
get:
operationId: downloadAttachments
tags:
- attachments
summary: Download all attachments
parameters:
- $ref: '#/components/parameters/docIdPathParam'
- in: query
name: format
schema:
type: string
enum:
- zip
- tar
responses:
200:
description: Archive of all attachments, in either .zip or .tar format.
post:
operationId: uploadMissingAttachments
tags:
- attachments
summary: Upload missing attachments
description: Restores attachments which are missing from external storage.
parameters:
- $ref: '#/components/parameters/docIdPathParam'
requestBody:
description: A .tar file downloaded from Grist, containing all the document's attachments.
content:
multipart/form-data:
schema:
type: object
properties:
file:
type: string
format: binary
description: The .tar file. Must have `Content-Type=application/x-tar` set.
responses:
200:
description: Summary of attachments used
content:
application/json:
schema:
type: object
properties:
added:
type: integer
description: Total files added to external storage.
errored:
type: integer
description: Total files that errored when attempting to process them.
unused:
type: integer
description: Total files that aren't needed, or don't match an existing attachment.
/docs/{docId}/attachments/store:
get:
operationId: getDocumentAttachmentStore
tags:
- attachments
summary: Get external store
parameters:
- $ref: '#/components/parameters/docIdPathParam'
responses:
200:
description: Document's current external storage setting
content:
application/json:
schema:
$ref: '#/components/schemas/DocumentStoreSetting'
post:
operationId: setDocumentAttachmentStore
tags:
- attachments
summary: Set external store
parameters:
- $ref: '#/components/parameters/docIdPathParam'
requestBody:
content:
application/json:
schema:
$ref: '#/components/schemas/DocumentStoreSetting'
responses:
200:
description: The ID of the store the document's store
content:
application/json:
schema:
type: object
properties:
store:
$ref: '#/components/schemas/DocumentStoreId'
/docs/{docId}/attachments/stores:
get:
operationId: listAttachmentStores
tags:
- attachments
summary: List external attachment stores
parameters:
- $ref: '#/components/parameters/docIdPathParam'
responses:
200:
description: Document's current external storage setting
content:
application/json:
schema:
$ref: '#/components/schemas/DocumentStoreSetting'
/docs/{docId}/attachments/transferAll:
post:
operationId: startAttachmentTransfer
tags:
- attachments
summary: Start transferring attachments
parameters:
- $ref: '#/components/parameters/docIdPathParam'
responses:
200:
description: Transfer status
content:
application/json:
schema:
$ref: '#/components/schemas/AttachmentsTransferStatus'
/docs/{docId}/attachments/transferStatus:
get:
operationId: getAttachmentTransferStatus
tags:
- attachments
summary: Get attachment transfer status
parameters:
- $ref: '#/components/parameters/docIdPathParam'
responses:
200:
description: Transfer status
content:
application/json:
schema:
$ref: '#/components/schemas/AttachmentsTransferStatus'
/docs/{docId}/attachments/removeUnused:
post:
operationId: removeUnusedAttachments
tags:
- attachments
summary: Delete unused attachments from the document
description: 'When an uploaded attachment is no longer used in a Grist document, it''s retained for a period of time in case it''s needed again (e.g. to facilitate an "undo").
This removes all of these retained attachments, reducing the amount of storage used. This is particularly useful if a document has hit its attachment storage limit.
'
parameters:
- $ref: '#/components/parameters/docIdPathParam'
- in: query
name: expiredOnly
schema:
type: boolean
description: Only remove attachments that haven't been used for a period of time. This duration is set by host of the Grist instance.
responses:
200:
description: Success
/docs/{docId}/attachments/updateUsed:
post:
operationId: updateUsedAttachments
tags:
- attachments
summary: Update attachment usage tracking
description: 'Recalculate which attachments are in use by scanning the document.
This is mostly used for testing and maintenance.
'
parameters:
- $ref: '#/components/parameters/docIdPathParam'
responses:
200:
description: Success
/docs/{docId}/attachments/verifyFiles:
post:
operationId: verifyAttachmentFiles
tags:
- attachments
summary: Verify attachment file integrity
description: 'Verify that attachment records match the actual stored files.
This is a maintenance endpoint to check for data consistency.
Only document owners can call this endpoint.
'
parameters:
- $ref: '#/components/parameters/docIdPathParam'
responses:
200:
description: Verification passed
components:
schemas:
AttachmentMetadata:
type: object
properties:
fileName:
type: string
example: logo.png
fileSize:
type: number
example: 12345
timeUploaded:
type: string
example: '2020-02-13T12:17:19.000Z'
DocumentStoreSetting:
type: object
properties:
type:
type: string
enum:
- external
- internal
RowIds:
type: array
example:
- 101
- 102
- 103
items:
type: integer
AttachmentId:
type: number
description: An integer ID
DocumentStoreId:
type:
- string
- 'null'
example: 83395209-fc3b-4d02-8934-b2619efec712-filesystem
DocumentAttachmentsLocation:
type: string
description: The current location of attachment files in the document
enum:
- none
- internal
- mixed
- external
example: mixed
AttachmentMetadataList:
type: object
required:
- records
properties:
records:
type: array
items:
type: object
required:
- id
- fields
properties:
id:
type: number
example: 1
fields:
$ref: '#/components/schemas/AttachmentMetadata'
AttachmentsTransferStatus:
type: object
properties:
status:
type: object
properties:
pendingTransferCount:
type: integer
description: Remaining transfers be performed
example: 19
isRunning:
type: boolean
description: Are files actively being transferred?
example: true
locationSummary:
$ref: '#/components/schemas/DocumentAttachmentsLocation'
AttachmentUpload:
type: object
properties:
upload:
type: array
items:
type: string
format: binary
parameters:
docIdPathParam:
in: path
name: docId
schema:
type: string
description: A string id (UUID)
required: true
sortHeaderParam:
in: header
name: X-Sort
schema:
type: string
description: Same as `sort` query parameter.
example: pet,-age
required: false
limitQueryParam:
in: query
name: limit
schema:
type: number
description: Return at most this number of rows. A value of 0 is equivalent to having no limit.
example: '5'
required: false
sortQueryParam:
in: query
name: sort
schema:
type: string
description: 'Order in which to return results. If a single column name is given (e.g. `pet`), results are placed in ascending order of values in that column. To get results in an order that was previously prepared manually in Grist, use the special `manualSort` column name. Multiple columns can be specified, separated by commas (e.g. `pet,age`). For descending order, prefix a column name with a `-` character (e.g. `pet,-age`). To include additional sorting options append them after a colon (e.g. `pet,-age:naturalSort;emptyLast,owner`). Available options are: `orderByChoice`, `naturalSort`, `emptyLast`. Without the `sort` parameter, the order of results is unspecified.'
example: pet,-age
required: false
limitHeaderParam:
in: header
name: X-Limit
schema:
type: number
description: Same as `limit` query parameter.
example: '5'
required: false
filterQueryParam:
in: query
name: filter
schema:
type: string
description: 'This is a JSON object mapping column names to arrays of allowed values. For example, to filter column `pet` for values `cat` and `dog`, the filter would be `{"pet": ["cat", "dog"]}`. JSON contains characters that are not safe to place in a URL, so it is important to url-encode them. For this example, the url-encoding is `%7B%22pet%22%3A%20%5B%22cat%22%2C%20%22dog%22%5D%7D`. See https://rosettacode.org/wiki/URL_encoding for how to url-encode a string, or https://www.urlencoder.org/ to try some examples. Multiple columns can be filtered. For example the filter for `pet` being either `cat` or `dog`, AND `size` being either `tiny` or `outrageously small`, would be `{"pet": ["cat", "dog"], "size": ["tiny", "outrageously small"]}`.'
example: '{"pet": ["cat", "dog"]}'
required: false
securitySchemes:
ApiKey:
type: http
scheme: bearer
bearerFormat: 'Authorization: Bearer XXXXXXXXXXX'
description: Access to the Grist API is controlled by an Authorization header, which should contain the word 'Bearer', followed by a space, followed by your API key.