Systems and records
Exporting Salesforce case history with feeds, emails and comments
By SourceX Editorial · Updated
Short answer
A complete Salesforce case history export pulls several objects, not just Case: CaseComment, EmailMessage, FeedItem with FeedComment, and CaseHistory, plus files linked through ContentDocumentLink. Each child record points back to the case through a parent or case ID field, so join on that key, sort by timestamp and remove feed entries that duplicate emails or comments.
Key takeaways
- The Case object holds only the header; the conversation lives in CaseComment, EmailMessage and FeedItem records.
- Child objects point back to the case: ParentId on comments, emails and feed items, and CaseId on CaseHistory.
- Case Feed can repeat emails and comments as feed entries, so deduplicate before counting interactions.
- Use query-all options to include deleted and archived records, and export User and Contact tables to resolve IDs into roles.
- Reconcile record counts per object against the org before treating an export as complete.
Which objects hold a case's full history?#
A Salesforce case's full history is spread across several standard objects, and the Case record itself holds only the header: subject, status, priority, owner, account, contact and timestamps. The back-and-forth with the customer and the internal discussion live in child objects, each exported as its own file.
Calls and tasks logged against the case sit in the Task object, linked through WhatId, and chat or messaging transcripts live in their own objects. Include them if your team handled cases by phone or chat as well as email.
| Object | What it holds | Link to the case | Watch for |
|---|---|---|---|
| Case | Header fields, status, origin, owner, description | Id | Record types and picklist values need label mapping |
| CaseComment | Comments added by agents or portal users | ParentId | IsPublished separates customer-visible comments from internal notes |
| EmailMessage | Inbound and outbound emails with subject, body, addresses and dates | ParentId | Incoming marks direction; HTML and text bodies are separate fields |
| FeedItem | Case Feed posts, text updates and system entries | ParentId | Some entries mirror emails or comments you already exported |
| FeedComment | Replies to feed posts | FeedItemId, then the feed item's ParentId | Keep FeedItemId so each reply nests under the right post, not just the right case |
| CaseHistory | Changes to tracked fields such as status and owner | CaseId | Only fields with history tracking switched on are recorded |
| ContentDocumentLink and ContentVersion | Files attached to the case or its emails | LinkedEntityId | Download file versions separately from the link metadata |
How the keys rejoin one case thread#
The case ID rejoins a Salesforce case thread: CaseComment, EmailMessage and FeedItem carry it in ParentId, CaseHistory carries it in CaseId, and file links carry it in LinkedEntityId. Feed comments join one step further out, through their feed item, and files attached to emails link to the EmailMessage rather than the case.
Keep timestamps in UTC as Salesforce returns them and convert only for display. Mixed time zones are a common reason a rebuilt thread shows the answer before the question.
- Step 1: export Case with Id, CaseNumber, AccountId, ContactId, status fields, CreatedDate and ClosedDate.
- Step 2: export each child object filtered to the cases in scope, keeping its ID, parent key, author and timestamp fields.
- Step 3: tag every row with its source and direction: inbound email, outbound email, public comment, internal note, feed post or field change.
- Step 4: sort each case's rows by time, using MessageDate for emails and CreatedDate elsewhere.
- Step 5: drop feed entries whose content duplicates an email or comment already in the thread; check the FeedItem Type values in your org to find them.
- Step 6: replace user, contact and account IDs with roles such as agent, engineer or customer before anyone outside support reviews the output.
- 01Your work records
- 02Personal details removed
- 03You approve the release
- 04Licensed to AI developers
Which export method fits your org?#
The right Salesforce export method for case history depends on volume, how often you need a copy and whether deleted or archived records must be included. Reports are the wrong tool here, because they are built for summaries, not full text bodies and every related record.
Whatever the method, write down the exact queries, the date of the pull and the user who ran it. A future reviewer needs to know whether the export covered every case or only open ones, and whether it included records sitting in the recycle bin.
| Method | Good for | Check before relying on it |
|---|---|---|
| Data Export service in Setup | A scheduled full copy of all objects as CSV files | How often your edition allows it, and whether attachments and files are included |
| Data Loader with Export All | Targeted pulls by object with SOQL, including deleted and archived rows | Large text fields and date-range filters |
| Bulk API 2.0 scripts | Large orgs and repeatable pulls | API limits, job monitoring and retries |
| Existing third-party backup | Companies that already back up the org | Whether its export keeps parent keys and full bodies |
What gets lost in a careless export#
A careless Salesforce case export usually loses email bodies, internal-note labels, older field history, deleted records and files, because it assumes the Case object holds more than it does. These gaps show up again and again when support teams first try to rebuild threads outside Salesforce.
- Email bodies left out because only EmailMessage header fields were selected.
- Internal notes mixed with customer-visible comments because IsPublished was not exported.
- Field history older than your org's retention, unless Field Audit Trail or an earlier backup kept it.
- Archived activities and deleted records, which ordinary queries skip.
- Inline images and attachments referenced in email or feed bodies but never downloaded.
- Email attachments in older orgs stored as classic Attachment records whose ParentId points at the EmailMessage, not the case.
- Chat and messaging transcripts stored in objects such as LiveChatTranscript or MessagingSession.
- User, Contact and Account tables, without which IDs cannot be turned into roles.
Illustrative: a scheduling software company rebuilds its support history#
Illustrative: a fictional maker of crew scheduling software for commercial cleaning companies has run support in Service Cloud for many years, with Email-to-Case, Case Feed and a customer portal. The CTO wants a full export before a planned move to another help desk and before any review of whether the history could be licensed.
The first pass uses the scheduled Data Export files and looks complete, but rebuilt threads show many emails twice: once as an EmailMessage and once as a Case Feed entry. The team filters feed items that mirror emails, labels internal notes using IsPublished, and pulls deleted and archived records with Data Loader.
Reconciliation then shows that field history reaches back only part of the way, so the team records that limit instead of implying a full audit trail. The final package links each case to the customer's product tier and to the Jira issue keys that engineers mentioned in internal notes.
How to prove the export is complete#
A Salesforce case export is proven complete with counts, samples and a written record of how it was produced. Run each check per object, not only for the Case file, and keep the results with the export itself.
| Check | How | Pass condition |
|---|---|---|
| Record counts | Compare exported rows with a SOQL COUNT() in the org using the same filters | Counts match, or each difference is explained |
| Parent integrity | Look for child rows whose case ID is missing from the Case export | No orphans, or orphans traced to deleted cases |
| Thread samples | Rebuild a sample of cases and compare them with the Salesforce UI | Same messages, order and visibility |
| Files | Compare ContentDocumentLink rows with downloaded files | Every linked file is present or listed as missing |
| Integrity | Record hashes of every export file | Hashes stored with the export log |
Preparing case history for review or licensing#
Case history prepared for review needs three things beyond a complete export: clear labels for who wrote each entry, a record of what was removed, and a decision on which customers' cases are in scope. Threads that connect a customer's problem to the diagnosis and the fix are the kind of customer support record AI developers look for, which is why the labeling work in the rebuild steps pays off later.
Customer contracts and privacy obligations decide what can be used, and names, email addresses, phone numbers and signatures are removed during preparation. That redaction belongs to the Preparation step of the SourceX five-step transaction, which runs Supply, Rights, Preparation, Approval, Delivery in that order. Its fit check needs only metadata, such as case volumes by year and which objects are populated, and a SourceX Evidence Packet records the privacy work and permitted use for any package that proceeds.
Frequently asked questions
Does the Data Export service include email bodies?
The EmailMessage file includes body fields when that object is part of the export, but check a sample: very long bodies, HTML formatting and inline images can behave differently from plain text. Attachments and files are included only if you select those options, so confirm the settings before the export runs.
How do I include deleted or archived cases?
Use an export option that queries all rows, such as Export All in Data Loader or queryAll through the API. Deleted records stay in the recycle bin only for a limited time, so anything purged earlier is gone unless a backup kept it.
Do I need to export users and contacts if names will be removed anyway?
Yes. The User and Contact tables let you label each message as coming from an agent, an engineer or a customer before names are removed. Keep those tables out of any shared package once the labels are applied.
Can we include cases from a customer portal or community?
Yes. Portal comments and posts are stored in the same objects, with the portal user as the author. Label them as customer-authored, and check the portal terms of use as well as the customer contract before any use beyond support.
How large will the export be?
It depends on case volume, email length and attachments, and files usually dominate the total. Estimate it from object row counts and the Storage Usage page in Setup before you schedule the pull, and plan storage for the files separately from the CSVs.
Related resources
See if your company qualifies
A short company assessment. No data uploads are needed.