Skip to content

Docs: by job

Claim status

Ask where a claim stands, read the payer’s answer as a next step, and know when to ask again.

Read as markdown

Payerworks writes and explains files; it sends nothing to a payer. Every file a route writes says transmitted: false, and is yours to send on your own connection. A test key is for invented data only, never a real patient.

Write the claim status question as a 276 from JSON (POST /v1/claim-status/276), send it on your own connection, and give Payerworks the 277 that comes back (POST /v1/claim-status/explain). Each question is answered with where the claim stands, whether money is coming and how much, the next step, and when to ask again.

POST /v1/claims/follow-up works the other way round: send your open claims with the day each was sent, and your own history of when each payer paid, and each claim comes back with when its remittance is expected and whether it is late. Each payer’s days to pay are learned from your history alone, with how many paid claims they rest on, and only from five up.

Routes

Each route shows its call with curl and with the two clients, then its real answer, shortened, and the fields it holds. The client calls assume one client made once, const pw = new Payerworks() in JavaScript or pw = payerworks.Payerworks() in Python, each reading PAYERWORKS_API_KEY and PAYERWORKS_BASE_URL, and body is the request.json shown.

POST/v1/claim-status/276

Write a 276

Up to one hundred claim status questions, from the JSON shape most clearinghouse APIs take, written as one 005010X212 interchange for you to send on your own connection. Each question is checked field by field first, and nothing is written if any would be refused. A test key writes test files only.

Request

curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/claim-status/276" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
request.jsonJSON
{
  "sender_id": "SAMPLEBILLER",
  "receiver_id": "99999",
  "control_number": 21,
  "payer_name": "SAMPLE HEALTH PLAN",
  "inquiry": {
    "tradingPartnerServiceId": "99999",
    "providers": [
      {
        "providerType": "BillingProvider",
        "npi": "1234567893",
        "organizationName": "SAMPLE FAMILY MEDICINE"
      }
    ],
    "subscriber": {
      "memberId": "W123456789",
      "firstName": "SAMPLE",
      "lastName": "PATIENT",
      "dateOfBirth": "19800214"
    },
    "encounter": {
      "trackingNumber": "STATUS-0001",
      "beginningDateOfService": "20261001",
      "endDateOfService": "20261001",
      "submittedAmount": "215.00",
      "patientControlNumber": "PW-2001"
    }
  }
}
The answer (200)JSON
{
  "version": "005010X212",
  "usage": "T",
  "x12": "ISA*00*          *00*          *ZZ*SAMPLEBILLER   *ZZ*99999          *261019*1500*^*00501*000000021*0*T*:~GS*HR*SAMPLEBILLER*99999*20261019*1500*21*X*005010X212~ST*276*0001*005010X212~BHT*0010*13*STATUS-0001*20261019*1500~HL*1**20*1~NM1*PR*…",
  "interchange_control_number": "000000021",
  "group_control_number": "21",
  "transaction_set_control_numbers": [
    "0001"
  ],
  "inquiries": [
    {
      "index": 0,
      "trace": "STATUS-0001",
      "transaction_set_control_number": "0001",
      "warnings": []
    }
  ],
  "transmitted": false
}

Shortened here: lists show their first two items and long strings are cut. The whole answer is this route’s example in /openapi.json.

Field, Type, What it is
FieldTypeWhat it is
versionstringThe implementation guide written.
usageone of "T", "P"T or P.
x12stringThe whole interchange.
interchange_control_numberstring
group_control_numberstring
transaction_set_control_numberslist of string
segmentsinteger
transmittedthe value falsePayerworks wrote the file and sent it nowhere.
inquirieslist of object

POST/v1/claim-status/explain

Explain a claim status answer

A 277 claim status answer, as X12 or as the JSON most clearinghouse APIs return, said per question: where the claim stands, whether money is coming and how much, what to do next and when to ask again. A claim the payer cannot find yet is never called a rejection, and a question the payer refused because of its own data is never asked again unchanged. A claim the payer’s search did not find comes back with the next questions to ask, in order, each built from the question you sent (asked.request) and what you hold (asked.known), never from a value you did not give; a payer whose system did not answer, with a retry schedule for the same day.

Request

curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/claim-status/explain" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
request.jsonJSON
{
  "x12": "ISA*00*          *00*          *ZZ*SAMPLEPAYER    *ZZ*SAMPLEBILLER   *261018*0900*^*00501*000000092*0*T*:~\nGS*HN*SAMPLEPAYER*SAMPLEBILLER*20261018*0900*92*X*005010X212~\nST*277*0001*005010X212~\nBHT*0010*08*STATUS-0001*20261018*0900*DG~\nHL*1**20*1~\nNM1*PR*2*SAMPLE HEALTH PLAN*****PI*99999~\nHL*2*1*21*1~\nNM1*41*2*SAMPLE FAMILY MEDICINE*****46*SAMPLEBILLER~\nHL*3*2*19*1~\nNM1*1P*2*SAMPLE FAMILY MEDICINE*****XX*1234567893~\nHL*4*3*22*0~\nNM1*IL*1*PATIENT*SAMPLE****MI*W123456789~\nTRN*2*STATUS-0001~\nSTC*F1:65*20261015**215*103.2*20261015*CHK*20261016*CHK10021~\nREF*1K*PAYER-CN-21~\nREF*EJ*PW-2001~\nDTP*472*RD8*20261001-20261001~\nHL*5*3*22*0~\nNM1*IL*1*PATIENT*SECOND****MI*W987654321~\nTRN*2*STATUS-0002~\nSTC*P3:123:1P*20261015**350*0*****P3:297:1P~\nREF*1K*PAYER-CN-22~\nREF*EJ*PW-2002~\nDTP*472*RD8*20261002-20261002~\nSE*23*0001~\nGE*1*92~\nIEA*1*000000092~",
  "asked": {
    "submitted_on": "2026-10-05",
    "today": "2026-10-19"
  }
}
The answer (200)JSON
{
  "kind": "277",
  "label_source": "paraphrase",
  "business_days": "Business days are Monday to Friday. Holidays are not counted, so a payer closed on a holiday may need one day more.",
  "today": "2026-10-19",
  "inquiries": [
    {
      "trace": "STATUS-0001",
      "claims": [
        0
      ],
      "answered_by": 0,
      "state": "paid",
      "meaning": "The claim was finalized and paid: the claim or line has been paid (STC F1:65).",
      "money": {
        "coming": "yes",
        "amount": 103.2,
        "check_number": "CHK10021",
        "check_date": "2026-10-16",
        "adjudicated_on": "2026-10-15",
        "why": "The payer reports $103.20 paid on check or payment CHK10021 dated 10/16/2026. The remittance (835) carries the allowed amount, the adjustments and the patient's share; this answer does not."
      },
      "next_step": {
        "action": "post_remittance",
        "words": "Nothing to send again. Post the remittance (835) when it arrives: it says what was allowed and what the patient owes."
      },
      "ask_again": {
        "after_business_days": null,
        "not_before": null,
        "never": true,
        "why": "The payer has paid it: the remittance (835) is the rest of the answer, and asking again returns the same."
      },
      "asks": [],
      "next_inquiries": [],
      "retry_schedule": null
    },
    {
      "trace": "STATUS-0002",
      "claims": [
        1
      ],
      "answered_by": 1,
      "state": "info_requested",
      "meaning": "The claim was pending for provider information: more information was asked of the provider (STC P3:123:1P).",
      "money": {
        "coming": "not_yet",
        "amount": 0,
        "check_number": "",
        "check_date": "",
        "adjudicated_on": "",
        "why": "Nothing is paid until the payer receives what it asked for."
      },
      "next_step": {
        "action": "send_records",
        "words": "Send the payer the records it asked for: medical notes or a report. The claim does not move until they arrive."
      },
      "ask_again": {
        "after_business_days": 5,
        "not_before": "2026-10-26",
        "never": false,
        "why": "After what was asked is sent. The usual schedule: 3, 5 and 7 business days apart, then every 10, counted from this answer."
      },
      "asks": [
        {
          "status_code": "297",
          "procedure_code": "",
          "words": "medical notes or a report"
        }
      ],
      "next_inquiries": [],
      "retry_schedule": null
    }
  ],
  "claims": [
    {
      "index": 0,
      "trace": "STATUS-0001",
      "payer_claim_number": "PAYER-CN-21",
      "clearinghouse_claim_number": "",
      "patient_control_number": "PW-2001",
      "service_date": {
        "from": "2026-10-01",
        "to": "2026-10-01"
      },
      "charge": 215,
      "status": {
        "category_code": "F1",
        "status_code": "65",
        "entity_code": ""
      },
      "state": "paid",
      "meaning": "The claim was finalized and paid: the claim or line has been paid (STC F1:65).",
      "money": {
        "coming": "yes",
        "amount": 103.2,
        "check_number": "CHK10021",
        "check_date": "2026-10-16",
        "adjudicated_on": "2026-10-15",
        "why": "The payer reports $103.20 paid on check or payment CHK10021 dated 10/16/2026. The remittance (835) carries the allowed amount, the adjustments and the patient's share; this answer does not."
      },
      "next_step": {
        "action": "post_remittance",
        "words": "Nothing to send again. Post the remittance (835) when it arrives: it says what was allowed and what the patient owes."
      },
      "ask_again": {
        "after_business_days": null,
        "not_before": null,
        "never": true,
        "why": "The payer has paid it: the remittance (835) is the rest of the answer, and asking again returns the same."
      },
      "asks": [],
      "next_inquiries": [],
      "retry_schedule": null,
      "lines": [],
      "matches_requested": null,
      "describes_replaced_claim": false
    },
    {
      "index": 1,
      "trace": "STATUS-0002",
      "payer_claim_number": "PAYER-CN-22",
      "clearinghouse_claim_number": "",
      "patient_control_number": "PW-2002",
      "service_date": {
        "from": "2026-10-02",
        "to": "2026-10-02"
      },
      "charge": 350,
      "status": {
        "category_code": "P3",
        "status_code": "123",
        "entity_code": "1P"
      },
      "state": "info_requested",
      "meaning": "The claim was pending for provider information: more information was asked of the provider (STC P3:123:1P).",
      "money": {
        "coming": "not_yet",
        "amount": 0,
        "check_number": "",
        "check_date": "",
        "adjudicated_on": "",
        "why": "Nothing is paid until the payer receives what it asked for."
      },
      "next_step": {
        "action": "send_records",
        "words": "Send the payer the records it asked for: medical notes or a report. The claim does not move until they arrive."
      },
      "ask_again": {
        "after_business_days": 5,
        "not_before": "2026-10-26",
        "never": false,
        "why": "After what was asked is sent. The usual schedule: 3, 5 and 7 business days apart, then every 10, counted from this answer."
      },
      "asks": [
        {
          "status_code": "297",
          "procedure_code": "",
          "words": "medical notes or a report"
        }
      ],
      "next_inquiries": [],
      "retry_schedule": null,
      "lines": [],
      "matches_requested": null,
      "describes_replaced_claim": false
    }
  ],
  "notices": [],
  "errors": []
}
Field, Type, What it is
FieldTypeWhat it is
kindone of "277", "json"
label_sourcethe value "paraphrase"
business_daysstring
todaystring
inquirieslist of ClaimStatusReading
claimslist of ClaimStatusClaim
noticeslist of object
errorslist of object

POST/v1/sandbox/claim-status

Run the claim status sandbox

Your claim status questions, as JSON or a 276, answered by the sandbox payer with a 277 in the same call and explained. It agrees with the claims sandbox: the same payer claim number and, for each claim, the same paid amount. How the member ID ends decides the answer.

Request

curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/sandbox/claim-status" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
request.jsonJSON
{
  "inquiry": {
    "tradingPartnerServiceId": "99999",
    "providers": [
      {
        "providerType": "BillingProvider",
        "npi": "1234567893",
        "organizationName": "SAMPLE FAMILY MEDICINE"
      }
    ],
    "subscriber": {
      "memberId": "W12345INFO",
      "firstName": "SAMPLE",
      "lastName": "PATIENT",
      "dateOfBirth": "19800214"
    },
    "encounter": {
      "trackingNumber": "STATUS-0001",
      "beginningDateOfService": "20261001",
      "endDateOfService": "20261001",
      "submittedAmount": "215.00",
      "patientControlNumber": "PW-2001"
    }
  }
}
The answer (200)JSON
{
  "usage": "T",
  "transmitted": false,
  "control": {
    "inquiry": "000000001",
    "answer": "000000002"
  },
  "files": {
    "claim_status_inquiry_276": "ISA*00*          *00*          *ZZ*SUBMITTER      *ZZ*PWSANDBOX      *261019*1500*^*00501*000000001*0*T*:~GS*HR*SUBMITTER*PWSANDBOX*20261019*1500*1*X*005010X212~ST*276*0001*005010X212~BHT*0010*13*STATUS-0001*20261019*1500~HL*1**20*1~NM1*PR*…",
    "claim_status_277": "ISA*00*          *00*          *ZZ*PWSANDBOX      *ZZ*SUBMITTER      *261019*1500*^*00501*000000002*0*T*:~GS*HN*PWSANDBOX*SUBMITTER*20261019*1500*2*X*005010X212~ST*277*0001*005010X212~BHT*0010*08*STATUS-0001*20261019*1500*DG~HL*1**20*1~NM1*…"
  },
  "outcomes": [
    {
      "trace": "STATUS-0001",
      "reference": "PW-2001",
      "rule": "INFO",
      "outcome": "info_requested",
      "category": "P3",
      "status": "123",
      "entity": "1P",
      "payer_claim_number": "PWS0120638906",
      "charge": 215,
      "paid": 0
    }
  ],
  "explained": {
    "label_source": "paraphrase",
    "business_days": "Business days are Monday to Friday. Holidays are not counted, so a payer closed on a holiday may need one day more.",
    "today": "2026-10-19",
    "inquiries": [
      {
        "trace": "STATUS-0001",
        "claims": [
          0
        ],
        "answered_by": 0,
        "state": "info_requested",
        "meaning": "The claim was pending for provider information: more information was asked of the provider (STC P3:123:1P).",
        "money": {
          "coming": "not_yet",
          "amount": 0,
          "check_number": "",
          "check_date": "",
          "adjudicated_on": "",
          "why": "Nothing is paid until the payer receives what it asked for."
        },
        "next_step": {
          "action": "send_records",
          "words": "Send the payer the records it asked for: medical notes or a report. The claim does not move until they arrive."
        },
        "ask_again": {
          "after_business_days": 5,
          "not_before": "2026-10-26",
          "never": false,
          "why": "After what was asked is sent. The usual schedule: 3, 5 and 7 business days apart, then every 10, counted from this answer."
        },
        "asks": [
          {
            "status_code": "297",
            "procedure_code": "",
            "words": "medical notes or a report"
          }
        ],
        "next_inquiries": [],
        "retry_schedule": null
      }
    ],
    "claims": [
      {
        "index": 0,
        "trace": "STATUS-0001",
        "payer_claim_number": "PWS0120638906",
        "clearinghouse_claim_number": "",
        "patient_control_number": "PW-2001",
        "service_date": {
          "from": "2026-10-01",
          "to": "2026-10-01"
        },
        "charge": 215,
        "status": {
          "category_code": "P3",
          "status_code": "123",
          "entity_code": "1P"
        },
        "state": "info_requested",
        "meaning": "The claim was pending for provider information: more information was asked of the provider (STC P3:123:1P).",
        "money": {
          "coming": "not_yet",
          "amount": 0,
          "check_number": "",
          "check_date": "",
          "adjudicated_on": "",
          "why": "Nothing is paid until the payer receives what it asked for."
        },
        "next_step": {
          "action": "send_records",
          "words": "Send the payer the records it asked for: medical notes or a report. The claim does not move until they arrive."
        },
        "ask_again": {
          "after_business_days": 5,
          "not_before": "2026-10-26",
          "never": false,
          "why": "After what was asked is sent. The usual schedule: 3, 5 and 7 business days apart, then every 10, counted from this answer."
        },
        "asks": [
          {
            "status_code": "297",
            "procedure_code": "",
            "words": "medical notes or a report"
          }
        ],
        "next_inquiries": [],
        "retry_schedule": null,
        "lines": [],
        "matches_requested": null,
        "describes_replaced_claim": false
      }
    ],
    "notices": [],
    "errors": []
  }
}

Shortened here: lists show their first two items and long strings are cut. The whole answer is this route’s example in /openapi.json.

Field, Type, What it is
FieldTypeWhat it is
usagethe value "T"
transmittedthe value false
controlobject
filesobject
outcomeslist of object
explainedClaimStatusAnswer

GET/v1/codes/claim-status/{category}

A claim status category

A claim status category code in words, read both ways: on a claim acknowledgment (277CA), whether it means accepted, rejected or denied, and in a claim status answer, the state the explainer gives it.

Request

curl -sS -X GET "$PAYERWORKS_BASE_URL/v1/codes/claim-status/P3" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY"
The answer (200)JSON
{
  "category": "P3",
  "words": "pending for provider information",
  "verdict": "A",
  "known": true,
  "acknowledgment_verdict": {
    "verdict": "A",
    "words": "Not a refusal: read on a claim acknowledgment (277CA), the claim was received, accepted, pended or finalized without a denial."
  },
  "status_answer": {
    "state": "info_requested",
    "meaning": "Pending for provider information."
  }
}
Field, Type, What it is
FieldTypeWhat it is
categorystring
wordsstring
verdictstringAs read on a 277CA: A, R, D or empty.
knownboolean
acknowledgment_verdictobject
status_answerobject

GET/v1/codes/claim-status-code/{code}

A claim status code

A claim status code in words, and whether it names an entity.

Request

curl -sS -X GET "$PAYERWORKS_BASE_URL/v1/codes/claim-status-code/297" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY"
The answer (200)JSON
{
  "code": "297",
  "words": "medical notes or a report",
  "names_an_entity": false,
  "known": true,
  "label_source": "paraphrase"
}
Field, Type, What it is
FieldTypeWhat it is
codestring
wordsstring
names_an_entityboolean
knownboolean
label_sourcethe value "paraphrase"

POST/v1/claims/follow-up

Follow up on open claims

Your open claims (up to 200) with the day each was sent, and your history of when each payer paid (up to 20,000 rows), or the 837Ps, 277CAs and 835s themselves. Each payer’s days to pay are learned from your history alone, with how many paid claims they rest on, and only from five up; below that the answer says there is not enough history. Each claim comes back with when its remittance is expected, whether it is late, and the next step: ask its status now, wait until a day, the next questions after a not found, or retries for a payer whose system did not answer. Your own follow-up codes come back as you sent them, never read. Nothing is stored, nothing is sent, and no payer is asked.

Request

curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/claims/follow-up" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
request.jsonJSON
{
  "claims": [
    {
      "reference": "PW-3001",
      "payer_id": "99999",
      "sent_on": "2026-10-01",
      "service_date": "2026-09-29",
      "charge_amount": 215
    },
    {
      "reference": "PW-3002",
      "payer_id": "99999",
      "sent_on": "2026-08-31",
      "service_date": "2026-08-27",
      "charge_amount": 150,
      "last_status": {
        "state": "not_found",
        "asked_on": "2026-10-02",
        "checks_made": 1
      }
    }
  ],
  "history": [
    {
      "payer_id": "99999",
      "sent_on": "2026-06-01",
      "remitted_on": "2026-06-19"
    },
    {
      "payer_id": "99999",
      "sent_on": "2026-06-15",
      "remitted_on": "2026-07-08"
    },
    {
      "payer_id": "99999",
      "sent_on": "2026-07-01",
      "remitted_on": "2026-07-17"
    },
    {
      "payer_id": "99999",
      "sent_on": "2026-07-20",
      "remitted_on": "2026-08-14"
    },
    {
      "payer_id": "99999",
      "sent_on": "2026-08-03",
      "remitted_on": "2026-08-21"
    },
    {
      "payer_id": "99999",
      "sent_on": "2026-08-17",
      "remitted_on": "2026-09-11"
    }
  ],
  "today": "2026-10-19"
}
The answer (200)JSON
{
  "today": "2026-10-19",
  "business_days": "Business days are Monday to Friday. Holidays are not counted, so a payer closed on a holiday may need one day more.",
  "floor": 5,
  "method": "Days to pay are calendar days from the day a claim was sent to the day its remittance (835) came, learned per payer from the history you sent. A payer's window runs from the 25th to the 90th percentile of its own days, with the median as th…",
  "payers": [
    {
      "payer_id": "99999",
      "history": {
        "n": 6,
        "median_days": 20.5,
        "p25_days": 18,
        "p90_days": 25,
        "min_days": 16,
        "max_days": 25,
        "remitted_from": "2026-06-19",
        "remitted_to": "2026-09-11"
      },
      "basis": "your_history",
      "words": "Your history: 6 paid claims from this payer, paid in 20.5 days at the median, and in 18 to 25 days from the 25th to the 90th percentile."
    }
  ],
  "claims": [
    {
      "index": 0,
      "reference": "PW-3001",
      "payer_id": "99999",
      "sent_on": "2026-10-01",
      "disposition": null,
      "open": true,
      "expected_by": {
        "from": "2026-10-19",
        "likely": "2026-10-22",
        "to": "2026-10-26",
        "basis": "your_history",
        "n": 6
      },
      "overdue": false,
      "days_since_sent": 18,
      "next_step": {
        "action": "wait_until",
        "on": "2026-10-27",
        "words": "Nothing to do yet: the remittance is expected by 10/26/2026, most likely around 10/22/2026. If none has come by then, ask the payer's status on 10/27/2026."
      },
      "inquiry_window": null,
      "next_inquiries": [],
      "retry_schedule": null
    },
    {
      "index": 1,
      "reference": "PW-3002",
      "payer_id": "99999",
      "sent_on": "2026-08-31",
      "disposition": null,
      "open": true,
      "expected_by": {
        "from": "2026-09-18",
        "likely": "2026-09-21",
        "to": "2026-09-25",
        "basis": "your_history",
        "n": 6
      },
      "overdue": true,
      "days_since_sent": 49,
      "next_step": {
        "action": "follow_not_found_plan",
        "on": "2026-10-19",
        "words": "The payer's search found no claim. A search can miss a claim the payer has: ask again with the next questions, in order (next_inquiries), before sending the claim again, since a claim the payer has, sent again, is a duplicate."
      },
      "inquiry_window": null,
      "next_inquiries": [
        {
          "step": 1,
          "kind": "add_charge_amount",
          "route": "POST /v1/claim-status/276",
          "builds_on": null,
          "status": "needs_value",
          "changes": [],
          "inquiry": null,
          "warnings": [],
          "errors": [],
          "needs": [
            "the question that found nothing (asked.request)"
          ],
          "why": "Add the claim's total charge: some payers search by it, and a question without it can miss the claim."
        },
        {
          "step": 2,
          "kind": "add_payer_claim_number",
          "route": "POST /v1/claim-status/276",
          "builds_on": null,
          "status": "needs_value",
          "changes": [],
          "inquiry": null,
          "warnings": [],
          "errors": [],
          "needs": [
            "the question that found nothing (asked.request)",
            "known.payer_claim_number"
          ],
          "why": "Add the payer's own claim number, from its claim acknowledgment (the 277CA's REF*1K): a payer finds its own number first. With no 277CA from the payer, there is no number to add: the payer may never have accepted the claim."
        }
      ],
      "retry_schedule": null
    }
  ],
  "counts": {
    "claims": 2,
    "open": 2,
    "overdue": 1,
    "not_overdue": 1,
    "cannot_say": 0
  },
  "history_used": {
    "rows": 6,
    "from_files": 0
  },
  "reads": "Reads only what you send. Nothing is stored, nothing is sent, and no payer is asked."
}

Shortened here: lists show their first two items and long strings are cut. The whole answer is this route’s example in /openapi.json.

Field, Type, What it is
FieldTypeWhat it is
todaystring
business_daysstring
floorintegerThe fewest paid claims a payer’s days to pay are read from.
methodstring
payerslist of object
claimslist of object
countsobject
history_usedobject
readsstring

Reading the answer

  • A claim the payer cannot find (A4 or D0) is not_found, never a rejection. The answer gives the next questions to ask, in order, built only from what you sent.
  • E1, E2 and 689 are the payer’s own system: ask again later, with the retry schedule the answer gives. E0, E3 and E4 are the question’s own error: correct it before asking again.
  • Only F1 says paid. F0, F3, F3F and F3N wait for the amount, and a figure the payer did not state is null.
  • The claims sandbox and the status sandbox agree: a status question about a sandbox claim answers the same payer claim number and paid amount as that claim’s 277CA and 835.

Troubleshooting

  • invalid_inquiries (422): One question would be refused, so nothing was written. Each question’s errors are listed with the field.
  • not_a_claim_status_answer (422): The explain route reads a 277 claim status answer (005010X212). A 277CA is an acknowledgment: send it to POST /v1/acknowledgments/explain.
  • ambiguous_answer (400): Send the answer once, as x12 or as json, never both.
  • A claim the payer did not find yet is often a claim it has not loaded: the answer says when to ask again rather than calling it lost.

Every refusal these routes may answer, with its status. Any route may also answer the codes every route shares, on Every error.

Code, Status, What it means
CodeStatusWhat it means
ambiguous_answer400Send the answer once: as x12 or as json, not both.
ambiguous_follow_up400Send the claims once: as claims or as files, not both.
ambiguous_question400Send the claim status questions once: as inquiry or inquiries, or as x12 (a 276), not both.
invalid_category400A claim status category is a letter and up to two letters or digits, such as A1 or F2.
invalid_claim_status_json400json is the JSON claim status answer, an object with its claims list (or its errors).
invalid_follow_up_request400A field of the request is not in the shape it takes; each problem is listed with its field.
invalid_payer_name400payer_name is the payer's name as the 276 writes it (2100A NM103): text of at most 60 characters.
invalid_status_asked400asked describes the question you asked; one of its fields is not in the form it takes.
invalid_status_code400A claim status code is one to five digits, such as 65 or 689.
invalid_submitter_name400submitter_name is your organization's name as the 276 writes it (2100B NM103): text of at most 60 characters.
no_claim_status_answer400Send the payer's claim status answer as x12 (a 277) or json (the JSON answer).
no_claims_to_follow400Send the open claims as claims (each with its reference, payer_id and sent_on), or the files as files (x12_837, acknowledgments, remittances).
no_inquiry400Send the claim status question as inquiry (or inquiries), in the JSON claim status shape.
too_many_inquiries400At most 100 claim status questions a call.
test_key_production_file403A test key writes test interchanges only (ISA15 = T). Use a live key for a production file.
answer_too_large413This answer is larger than one response can carry: send less in each call (split the file, or send fewer claims or requests).
file_too_large413This file holds more than one call can read: the error names what was counted (unit) and the most one call reads (limit). Split it and send each part in its own call.
too_much_to_follow413More was sent than one call takes: the error names what was counted (unit) and the most one call takes (limit).
duplicate_inquiry_trace422Two questions in one file carry the same trace (encounter.trackingNumber); each must be unique so its answer matches back.
invalid_inquiries422One or more claim status questions would be refused; nothing was written. Each question's errors are listed.
not_a_claim_status_answer422This is not a claim status answer Payerworks reads: send a 277 (005010X212) or the JSON answer.
not_a_claim_status_question422This is not a claim status question: send a 276 (005010X212) as x12, or the questions as inquiry or inquiries.

Code lists

Any one code in words: GET /v1/codes/claim-status/{category}, GET /v1/codes/claim-status-code/{code}.

The claim status sandbox’s member ID endings

A claim status question follows the claims list, so it agrees with that claim’s 277CA and 835: the same payer claim number and the same paid amount. These endings are the status sandbox’s own, the answers a status question alone can get:

Ending, Outcome, What it answers
EndingOutcomeWhat it answers
NOFILEnot_foundA member ID ending in NOFILE is not found: the payer has no claim on file for the question (A4:35). It is never a rejection.
SLOWpayer_errorA member ID ending in SLOW gets no answer in time: the payer’s system did not respond (E2:689:PR), so there is nothing to record and the question is asked again on the next business day.
INFOinfo_requestedA member ID ending in INFO is pended for information the payer already asked the provider for (P3:123:1P), and the answer names it: medical notes or a report (P3:297:1P).
NOPAYno_paymentA member ID ending in NOPAY is finalized with no further payment forthcoming (F4:1). The claims sandbox pays the same claim, and the answer states what it paid: nothing more is coming.

One exception: when a claim’s payment depends on its service lines (member IDs ending in D97), the status answer says the claim is finalized and leaves what was paid to the remittance, because a status question carries no lines.

Where a claim stands (state)

paid, denied, rejected, pending, info_requested, not_found, member_not_found, no_payment, finalized_unpaid, payer_error, request_error, review

The next step (action)

post_remittance, work_denial, correct_and_resubmit, wait, confirm_receipt, check_coverage, ask_again, fix_request, send_records, send_information, read_remittance, read_answer, ask_other_entity

Example

claim-status.mjs runs every step below against the API with a test key. It needs payerworks.mjs and sample-data.mjs beside it.

claim-status.mjsJavaScript
// Payerworks example: claim status, a 276 written and a 277 explained. Docs: https://payerworks.com/docs/claim-status
//
// Run it with Node 18 or later, with the JavaScript client (https://payerworks.com/sdk/payerworks.mjs)
// and sample-data.mjs beside this file:
//   PAYERWORKS_API_KEY=pw_test_... PAYERWORKS_BASE_URL=<the base URL shown with your key> node claim-status.mjs
// A test key and invented data only. Payerworks sends nothing to a payer: every file it writes is yours.
import { pathToFileURL } from 'node:url';
import { Payerworks, PayerworksError } from './payerworks.mjs';
import { STATUS_QUESTION, SENDER_ID, PAYER_ID, copy, endingIn, refusalOf } from './sample-data.mjs';

/** @param {Payerworks} pw */
export async function run(pw) {
  // 1. Write the question as a 276, to send on your own connection.
  const written = await pw.postClaimStatus276({ sender_id: SENDER_ID, receiver_id: PAYER_ID, control_number: 21, payer_name: 'SAMPLE HEALTH PLAN', inquiry: copy(STATUS_QUESTION) });

  // 2. The status sandbox answers it as a 277, already explained.
  const sandbox = await pw.postSandboxClaimStatus({ inquiry: copy(STATUS_QUESTION) });

  // 3. Explain a 277 you hold: the same reading, from the file alone.
  const explained = await pw.postClaimStatusExplain({ x12: sandbox.files.claim_status_277 });
  const claim = explained.claims[0];

  // 4. A member ID ending in NOFILE: the payer has no claim on file. That is not found, never rejected.
  const notFound = await pw.postSandboxClaimStatus({ inquiry: endingIn(STATUS_QUESTION, 'NOFILE') });

  // 5. The failure path: the answer sent twice, as X12 and as JSON, is refused.
  const refused = await refusalOf(() => pw.postClaimStatusExplain({ x12: sandbox.files.claim_status_277, json: { claims: [] } }), { PayerworksError });

  return {
    written: { transmitted: written.transmitted },
    state: claim.state,
    next_step: Boolean(claim.next_step),
    not_found: notFound.explained.claims[0]?.state ?? notFound.explained.inquiries[0]?.state,
    refused,
  };
}

// Run as a script: node <this file>, with PAYERWORKS_API_KEY and PAYERWORKS_BASE_URL set.
if (process.argv[1] && import.meta.url === pathToFileURL(process.argv[1]).href) {
  console.log(JSON.stringify(await run(new Payerworks()), null, 2));
}
What it answered, run against the API in Payerworks’ own tests (your request ids will differ)JSON
{
  "written": {
    "transmitted": false
  },
  "state": "paid",
  "next_step": true,
  "not_found": "not_found",
  "refused": {
    "status": 400,
    "code": "ambiguous_answer",
    "request_id": "req_5"
  }
}

Talk to us

What happens next

  1. 1

    A person at Payerworks reads what you sent, usually within a business day.

  2. 2

    One reply by email names the next step: our trading partner details, where each of your payers stands, or a key for the API.

  3. 3

    Nothing follows unless you answer. There is no sequence behind this form.

Or write to hello@payerworks.com.

Talk to Payerworks

Who you are and what you want to connect. A person replies by email, usually within a business day, and there is no follow-up sequence.

Used to reply to you and for nothing else.