Guides
SFTP for batch partners
Drop 837D claim files on a private SFTP account and read the acknowledgments, statuses and remittances back as files. How to connect, the folders, the file rules, what comes back and when, and how replacements and voids work.
If your system already speaks X12, you can send claims as files instead of calling the API. You drop 837D files on a private SFTP account. Claim House reads each claim out of the file and makes it a claim, the same as one made with POST /claims: validated, queued, sent to the network, followed on its timeline, with events, webhooks and remittance matching. Claim House sends its own 837D to the network, never your file. What comes back, the acknowledgment, the statuses and the remittances, is written to a folder you read.
Every claim from a file is also a claim in the dashboard and the API. Read it with GET /claims. On its timeline, the entries your SFTP account caused name it as the actor: actor.kind is sftp.
Live mode is not open yet. Use the test folders with the sandbox network. A file dropped in IN is read and answered, but every claim in it is refused: Live claims are not available yet: nothing was sent. Drop test files in TEST/IN.
Set up the account#
An organization has one SFTP account, for test and live files. Set it up with POST /sftp-account (or the set_up_sftp_account tool of the MCP server), with a key that has the submit permission:
curl -X POST "https://sandbox.myclaimhouse.com/api/v1/sftp-account" \
-H "Authorization: Bearer $CLAIMHOUSE_KEY" \
-H "Idempotency-Key: $(uuidgen)" \
-H "Content-Type: application/json" \
-d '{}'The reply has the account's username, its host, port and host_key_fingerprint, and a generated password. The password is shown once, in this reply and in the reply to rotating it, and nowhere else: store it now. The copy kept for an Idempotency-Key replay has no password and says "password_available": false. Setting up a second time is refused with 409 CONFLICT: rotate the password instead.
GET /sftp-account shows the account again without the password: its status, the connection facts, the folders, its keys, when it last logged in and when it last had a file taken.
Connect#
| Host | sftp.sandbox.myclaimhouse.com |
| Port | 22 |
| Host key fingerprint (SHA256) | SHA256:Y28qHRaWLMyRfJfHvRuw9p2L/6EmZkF9tP179UmwPCo |
| User name | The username of your account |
Check the fingerprint the first time you connect: your client shows the server's host key, and it must be the one above. Then log in with the password or with a key:
sftp -P 22 <username>@sftp.sandbox.myclaimhouse.comOnly SFTP is offered. There is no FTP, FTPS or web upload. An account can have 10 connections open at once.
Password. The generated password is a long random string. Rotate it with POST /sftp-account/rotate-password: the new password is shown once and the old one stops working for every new login at once; rotating also ends a lock. 5 wrong passwords within 15 minutes lock the account for 15 minutes; while it is locked, the right password is refused too, but a key that is on the account still logs in. Disabling the account refuses every new login at once, with the password or a key (POST /sftp-account/disable); enable allows them again. While the account is disabled, its files stay where they are and nothing dropped in IN or TEST/IN is taken; it is taken once the account is enabled. A session already open stays open until the client disconnects or has been idle 15 minutes. That holds after a rotation, a disable or a key's removal too.
Keys. Add a public key with POST /sftp-account/keys, a label and the key as one OpenSSH line: ssh-ed25519, ecdsa-sha2-nistp256, -nistp384, -nistp521, or ssh-rsa of at least 2048 bits. An account takes at most 5 keys, and a key once; either refusal is 409 CONFLICT. Remove one with DELETE /sftp-account/keys/{id}. A key that is not on the account is refused, and that never counts toward the lock: a client that offers every key it holds cannot lock you out.
Folders and modes#
When you log in you see only your own account's folders, all four from the start. The folder is the mode. A name that starts with a dot is Claim House's (each folder holds an empty one, so the folder shows): you do not see it, and it is never taken as a file.
| Folder | Mode | What it is for |
|---|---|---|
IN | Live | Drop your 837D files here. |
OUT | Live | Claim House writes what comes back here. |
TEST/IN | Test | Drop your 837D files here. |
TEST/OUT | Test | Claim House writes what comes back here. |
A file dropped in TEST/IN makes test claims, which go to the sandbox network: see Sandbox and scenarios. A file dropped in IN makes live claims. Responses are written to the OUT folder of the mode the file came from.
After a file is taken, it is moved to processed/ under the folder it was dropped in (TEST/IN/processed for a test file), so you can see it was taken. Files in OUT and in processed/ are removed after 60 days; Claim House keeps its own copy of each dropped file.
File rules#
- An 837D, implementation
005010X224A2(the GS08 and ST03 of the file say so), in one interchange. A second interchange in the file, or any other kind of file, refuses the whole file. - The usage indicator (
ISA15) is the folder's:TinTEST/IN,PinIN. A file whose indicator is the other is refused whole. - Up to 25,000 claims and 25 MB in a file. Split larger batches into several files.
- Give every file its own name. The responses are named after the file, so a file with the name of an earlier one writes over that file's responses. Dropping the very same file again changes nothing.
- A file is read after its upload has finished, never part-way, and is taken about every 60 seconds.
- The payer ID in each claim (
NM1*PR) must be in the payer directory, and the payer must take claims. A claim for a payer that is not is refused. - Your billing provider (
2010AA) is matched to one of your offices by NPI; by tax ID only when the file gives no NPI. An NPI that none of your offices has is a new location: an office is made from the file, never billed under another office's NPI. A rendering provider (2310B) is matched by NPI and made from the file when there is none; its license state is taken to be the billing office's (the file carries the number only). Offices and providers made from a file sayorigin: "sftp". - Primary claims only: a claim whose payer responsibility (
SBR01) is notPis refused (unsupported). Coordination of benefits (loops2320and2330),HIdiagnosis codes,DN2tooth status and line-level providers (2420) are not carried to the claim: they are left out, and the claim is made without them. A claim-level service date (DTP*472in2300) is used for every line that gives none.
A claim that cannot be made is refused on its own: the other claims in the file are still made. Its report line gives every reason found, not only the first. A file that is not a valid 837D, is too large, holds too many claims, or has the wrong usage indicator is refused whole, and nothing in it is made.
What comes back and when#
For every file it takes, Claim House writes three files to OUT (or TEST/OUT) once it has read the whole file, named after your file. A file of a few claims is answered within a minute or two; a large one is read at most about 500 claims a minute, so it is answered after several minutes, and every claim in it is answered then:
| File | What it is |
|---|---|
<name>.997 | A 997: your file's envelope was accepted, or rejected with the reasons. |
<name>.277 | A 277 with one status for each claim, in the order of the file. TRN02 is your CLM01 and REF*D9 is the Claim House claim ID (clm_...). |
<name>.report.txt | A plain-text report for people: the counts, then one line for each claim: CLM01 | result | claim ID or - | message. |
A claim that was made is A1 20 (accepted for processing). A claim that was made but needs attention, because its validation found a problem, is A1 20 with the first finding in the status text; the claim waits in the dashboard until it is corrected (see Claims). A refused claim is A3, with the reason in the status text and in the report:
| Reason | 277 status | What it means |
|---|---|---|
payer_unknown | A3 33 | No payer in the payer directory has the payer ID in the claim (NM1*PR). Use a payer ID from the directory. |
payer_no_claims | A3 21 | The payer is in the directory but does not take claims through Claim House. |
control_number | A3 21 | The claim's control number (CLM01) is not one a claim can have, or CLM05 says the claim replaces or voids one and no claim of that mode has this number. |
duplicate | A3 88 | A claim with this control number (CLM01) exists already. Send CLM05 7 to replace it or 8 to void it. |
attachment_unknown | A3 21 | A PWK names a Claim House attachment (att_...) that does not exist in this organization and mode. |
attachment_open | A3 21 | A PWK names a Claim House attachment that is not closed yet: close it, then send the claim again. |
claims_unavailable | A3 21 | Live claims are not available yet: nothing was sent. Drop test files in TEST/IN. |
unreadable | A3 21 | The claim could not be read from the file (a required segment is missing or a value cannot be used), or its billing provider or rendering provider could not be added from the file. The report says which. |
unsupported | A3 21 | A secondary or tertiary claim (SBR01 other than P): coordination of benefits (loops 2320 and 2330) is not carried yet, so only primary claims are sent. |
invalid | A3 21 | The claim was read, but sending it is refused: the API would refuse the same claim (a claim that cannot be replaced or voided in its state, for example). The report gives the reason. |
A file refused whole gets a 997 that rejects it and a report that says why, and no 277. The reason is one of:
| Reason | What it means |
|---|---|
too_large | The file is larger than 25 MB: it was not read. Split it into smaller files. |
too_many_claims | The file holds more than 25,000 claims: it was not read. Split it into smaller files. |
not_837d | The file is not an 837D (005010X224A2) this service reads: its envelope is not valid. See the 997. |
wrong_usage | The file's usage indicator (ISA15) is not its folder's: TEST/IN takes test files (T), IN takes production files (P). Nothing in it was read. |
Then, as the claims move, Claim House writes more files to the same OUT folder. In the sandbox these arrive on the compressed clock of Claims: the status about 60 seconds after the claims are sent and, for a claim of the CH-PAID-ERA scenario, an 835 about 2 minutes after that. The member ID in the claim chooses the scenario.
ClaimHouse-277.<YYYYMMDD>.<HHMMSS>.277: a 277 with the statuses the network gave your claims, the category and status codes as it gave them,TRN02your control number,REF*1Kthe payer's claim number when it has given one. It holds only claims your files made. The network's own 997 of Claim House's file is not passed on: when it rejects the file your claims went out in, Claim House writes aClaimHouse-277.<YYYYMMDD>.<HHMMSS>.277withA3 21for each of them, saying: The network rejected the file Claim House sent this claim in (its 997): the claim goes out again in the next batch.ClaimHouse-835.<YYYYMMDD>.<HHMMSS>.835: an 835 when a remittance pays or denies one of your claims. It is your organization's whole remittance as stored, with bank account numbers cut to their last four digits. If the same remittance also pays a claim you made with the API, that payment is in it too: it is your organization's own.
Claims made with the API or in the dashboard never produce files in OUT, so a partner that uses both never sees duplicates. If a file could not be written when the network's answer arrived, it is written on a later pass; it is never written twice. Each file taken, and each refusal of a whole file, also sends an event: see File events.
GET /sftp-account/files lists the files taken from your IN folders, newest first: how many claims each made and refused, and the names of the responses written. A key lists the files of its own mode: a test key lists TEST/IN files.
Control numbers, replacements and voids#
CLM01 is the claim's patient control number: 1 to 20 letters, digits and hyphens. It is the one identifier that comes back on the 277 and on the 835 (CLP01), so use one your system can look up. A control number is unique in your organization, in test and live mode together.
CLM05 carries the claim frequency in its third part, and Claim House reads it:
CLM05-3 | Meaning | What Claim House does |
|---|---|---|
1 | An original claim | A claim is made. If a claim with this control number exists, the claim is refused as a duplicate (A3 88). |
7 | A replacement | The claim with this control number is corrected with this content and sent again as a replacement, by the same rules as correcting a claim. |
8 | A void | The claim with this control number is voided, by the same rules as voiding a claim. |
A 7 or an 8 whose control number is not the number of a claim in that mode is refused. A replacement or a void that the claim's state does not allow, such as a claim that is queued and not yet sent, is refused with the reason in the report.
Attachments#
A PWK segment whose control number (PWK06) is the ID of one of your own attachments (att_...), in the same mode and closed, is swapped for the attachment's number on the claim Claim House sends, and linked to the claim. An att_ ID that does not exist is refused, and so is one that is not closed yet: close it, then drop the claim again.
Any other PWK and its NTE, such as a control number from your own attachment account with the network, passes through to the claim unchanged.
What the endpoints are#
| Endpoint | Permission |
|---|---|
GET /sftp-account | read |
POST /sftp-account | submit |
POST /sftp-account/rotate-password | submit |
POST /sftp-account/keys | submit |
DELETE /sftp-account/keys/{id} | submit |
POST /sftp-account/disable | submit |
POST /sftp-account/enable | submit |
GET /sftp-account/files | read |
A key sees its own organization's account, and the files of its own mode. Every POST needs an Idempotency-Key: see Errors, retries and idempotency.