Most Content Version work is API or Apex driven. The UI handles version uploads transparently, but for developers integrating files into custom flows, knowing the insert patterns matters.
- Upload a new file through Apex
Create a ContentVersion record with Title, PathOnClient, and VersionData fields. Insert it. Salesforce creates the Content Document and the initial Content Document Link automatically.
- Link the file to a parent record
After insert, query ContentDocumentId from the inserted ContentVersion. Create a ContentDocumentLink with ContentDocumentId, LinkedEntityId (the parent record), and ShareType (V for Viewer, C for Collaborator, I for Inferred from sharing rules).
- Upload a new version of an existing file
Insert a new ContentVersion with ContentDocumentId set to the existing Content Document Id. Optionally set ReasonForChange to explain what changed.
- Read a specific version
SELECT Id, Title, VersionData FROM ContentVersion WHERE Id = :versionId. The VersionData blob can be passed to a webhook or written to disk in a callout.
- List all versions of a document
SELECT VersionNumber, Title, ContentSize, CreatedDate, ReasonForChange FROM ContentVersion WHERE ContentDocumentId = :docId ORDER BY VersionNumber DESC. Useful for building a version-history component.
- Delete a specific version
Delete the ContentVersion record. Salesforce updates IsLatest and LatestPublishedVersionId on the parent automatically if the latest version is deleted. Do not delete the only version; that orphans the Content Document.
- VersionData over the API is base64-encoded. Apex Blob fields are decoded automatically, but raw REST callers need to handle encoding.
- Inserting a Content Version without ContentDocumentId creates a new Content Document, not a new version. Forgetting to set the parent Id is a common source of unintended Content Document proliferation.
- Single-record file size cap is 2 GB through the chunked API, with lower limits for standard insert (38 MB pre-2026, larger in modern releases). Check the latest limits in the Files REST API docs.
- Deleting the only Content Version on a Content Document leaves an orphan Content Document with no payload. Salesforce does not auto-clean this; delete the parent Content Document instead.
- Content Version size is counted against your org file storage. Frequent versioning of large files can exhaust storage quickly; have a retention policy.