# Prior authorization

> Ask for an authorization from JSON, and read the payer’s response as what was certified and what to do next.

Page: https://payerworks.com/docs/prior-authorization · Markdown: https://payerworks.com/docs/prior-authorization.md

> 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 review request as a 278 from JSON, send it the way the payer takes it, and give Payerworks the response that comes back to read. The authorization sandbox answers from the same payer as the eligibility sandbox. POST /v1/authorizations/required checks codes against Medicare’s published prior authorization lists.

## Routes

- [POST /v1/authorizations/278](#post-v1-authorizations-278): Write a 278
- [POST /v1/authorizations/explain](#post-v1-authorizations-explain): Explain a 278 response
- [POST /v1/sandbox/authorizations](#post-v1-sandbox-authorizations): Run the prior authorization sandbox
- [POST /v1/authorizations/required](#post-v1-authorizations-required): Does Medicare require it

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/authorizations/278

**Write a 278.** Up to one hundred prior authorization or referral requests, from JSON (the kind of review, the service type, each procedure code with its units and dates, the requester, the servicing provider, the patient and the diagnoses), written as one 005010X217 interchange for you to send on your own connection, or built in the shape of the Da Vinci PAS request bundle with output set to fhir. Each request is checked field by field first, and nothing is written if any would be refused. A test key writes test files only. Whether a payer takes a 278 at all is the payer’s choice: many take prior authorizations only on a portal, by fax or by phone.

Request

```bash
curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/authorizations/278" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
```

With the JavaScript client

```js
const answer = await pw.postAuthorizations278(body);
```

With the Python client

```python
answer = pw.post_authorizations_278(body)
```

request.json

```json
{
  "sender_id": "SAMPLEBILLER",
  "receiver_id": "99999",
  "control_number": 31,
  "request": {
    "controlNumber": "AUTH-0001",
    "tradingPartnerServiceId": "99999",
    "requester": {
      "organizationName": "Sample Family Medicine",
      "npi": "1234567893"
    },
    "subscriber": {
      "memberId": "W123456789",
      "firstName": "SAMPLE",
      "lastName": "PATIENT",
      "dateOfBirth": "1980-02-14",
      "gender": "F"
    },
    "review": {
      "serviceTypeCode": "12",
      "placeOfServiceCode": "12",
      "diagnoses": [
        "M17.11"
      ]
    },
    "services": [
      {
        "procedureCode": "L1833",
        "units": 4,
        "serviceDate": "2026-11-02"
      }
    ]
  }
}
```

The answer (200)

```json
{
  "version": "005010X217",
  "usage": "T",
  "x12": "ISA*00*          *00*          *ZZ*SAMPLEBILLER   *ZZ*99999          *261019*1500*^*00501*000000031*0*T*:~GS*HI*SAMPLEBILLER*99999*20261019*1500*31*X*005010X217~ST*278*0001*005010X217~BHT*0007*13*AUTH-0001*20261019*1500~HL*1**20*1~NM1*X3*2*…",
  "interchange_control_number": "000000031",
  "group_control_number": "31",
  "transaction_set_control_numbers": [
    "0001"
  ],
  "segments": 22,
  "requests": [
    {
      "index": 0,
      "trace": "AUTH-0001",
      "transaction_set_control_number": "0001",
      "warnings": []
    }
  ],
  "payer_choice": "Payerworks sends nothing. Whether a payer accepts an X12 278 or a FHIR prior authorization request at all is the payer's choice: many take them only on a portal, by fax or by phone, and its companion guide says what it requires.",
  "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](https://payerworks.com/openapi.json).

| Field | Type | What it is |
| --- | --- | --- |
| `version` | string |  |
| `usage` | one of "T", "P" |  |
| `x12` | string |  |
| `interchange_control_number` | string |  |
| `group_control_number` | string |  |
| `transaction_set_control_numbers` | list of string |  |
| `segments` | integer |  |
| `fhir` | object | With output fhir or both: the implementation guide named, a note that the shape is not validated, and each request’s bundle. |
| `requests` | list of object |  |
| `payer_choice` | string | That Payerworks sends nothing, and whether a payer takes a 278 at all is the payer’s choice. |
| `transmitted` | the value false |  |

### POST /v1/authorizations/explain

**Explain a 278 response.** A payer’s 278 response, as X12, as Payerworks’ own JSON read of one, or as a PAS response, said per review: approved, approved in part, approved with changes, not approved, pended, waiting on more information, canceled, no review needed, or not reviewed at all, with the reason in words, the certification and reference numbers, the approved dates and units against what you asked, the claim field the number goes in, and the next step. A request the payer never reviewed is never called a denial.

Request

```bash
curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/authorizations/explain" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
```

With the JavaScript client

```js
const answer = await pw.postAuthorizationsExplain(body);
```

With the Python client

```python
answer = pw.post_authorizations_explain(body)
```

request.json

```json
{
  "x12": "ISA*00*          *00*          *ZZ*PWSANDBOX      *ZZ*SUBMITTER      *261019*1500*^*00501*000000002*0*T*:~GS*HI*PWSANDBOX*SUBMITTER*20261019*1500*2*X*005010X217~ST*278*0001*005010X217~BHT*0007*11*AUTH-0001*20261019*1500*18~HL*1**20*1~NM1*X3*2*PAYERWORKS SANDBOX PAYER*****PI*PWSANDBOX~HL*2*1*21*1~NM1*1P*2*Sample Family Medicine*****XX*1234567893~HL*3*2*22*1~NM1*IL*1*PATIENT*SAMPLE****MI*W12345PARTIAL~DMG*D8*19800214*F~HL*4*3*EV*1~TRN*2*AUTH-0001*9SUBMITTER~UM*HS*I*12*12:B~HCR*A2*PWA033425780*10~REF*NT*PWR951115437~DTP*AAH*RD8*20261102-20270130~DTP*102*D8*20261019~DTP*007*RD8*20261102-20270130~DTP*036*D8*20270130~HI*ABK:M1711~HL*5*4*SS*0~TRN*2*852346626*9SUBMITTER~HCR*A2*PWA033425780*10~DTP*472*D8*20261102~SV1*HC:L1833**UN*2~SE*25*0001~GE*1*2~IEA*1*000000002~",
  "asked": {
    "controlNumber": "AUTH-0001",
    "tradingPartnerServiceId": "PWSANDBOX",
    "requester": {
      "organizationName": "Sample Family Medicine",
      "npi": "1234567893"
    },
    "subscriber": {
      "memberId": "W12345PARTIAL",
      "firstName": "SAMPLE",
      "lastName": "PATIENT",
      "dateOfBirth": "1980-02-14",
      "gender": "F"
    },
    "review": {
      "serviceTypeCode": "12",
      "placeOfServiceCode": "12",
      "diagnoses": [
        "M17.11"
      ]
    },
    "services": [
      {
        "procedureCode": "L1833",
        "units": 4,
        "serviceDate": "2026-11-02"
      }
    ]
  }
}
```

The answer (200)

```json
{
  "kind": "278",
  "source": "x12",
  "envelope": {
    "sender_qualifier": "ZZ",
    "sender": "PWSANDBOX",
    "receiver_qualifier": "ZZ",
    "receiver": "SUBMITTER",
    "date": "261019",
    "time": "1500",
    "control_number": "000000002",
    "usage": "T",
    "functional_group": "HI",
    "version": "005010X217",
    "transaction_sets": {
      "278": 1
    },
    "segments": 28
  },
  "reviews": [
    {
      "index": 0,
      "trace": "AUTH-0001",
      "purpose": "response",
      "payer": {
        "name": "PAYERWORKS SANDBOX PAYER",
        "id": "PWSANDBOX",
        "entity": "X3"
      },
      "requester": {
        "name": "Sample Family Medicine",
        "id_qualifier": "XX",
        "id": "1234567893",
        "entity": "1P"
      },
      "subscriber": {
        "name": "SAMPLE PATIENT",
        "member_id": "W12345PARTIAL",
        "birth_date": "1980-02-14",
        "gender": "F"
      },
      "dependent": null,
      "request_category": {
        "code": "HS",
        "words": "health services review: outpatient services",
        "known": true
      },
      "service_type": {
        "code": "12",
        "words": "durable medical equipment, purchased",
        "known": true,
        "verified_in_005010": true,
        "later_words": ""
      },
      "verdict": "partially_approved",
      "words": "Approved in part, certification number PWA033425780: fewer units than asked on one service.",
      "next_step": "Bill only what was approved, with PWA033425780 as priorAuthorizationNumber (2300 REF*G1). For what was not, ask the payer to reconsider (a 278 with certificationType N and the administrative reference number, where the payer takes one) or f…",
      "certification_number": "PWA033425780",
      "administrative_reference_number": "PWR951115437",
      "previous_authorization_number": "",
      "decision": {
        "code": "A2",
        "words": "certified in part",
        "verdict": "partially_approved",
        "known": true,
        "certification_number": "PWA033425780",
        "second_surgical_opinion": ""
      },
      "reason": {
        "code": "10",
        "words": "the delivery pattern asked (units, days, visits, weeks, hours or months)",
        "kind": "denial",
        "known": true
      },
      "rejections": [],
      "dates": {
        "event": {
          "begin": "2026-11-02",
          "end": "2027-01-30"
        },
        "admission": "",
        "certification": {
          "issued": "2026-10-19",
          "effective": {
            "begin": "2026-11-02",
            "end": "2027-01-30"
          },
          "expires": "2027-01-30"
        }
      },
      "services": [
        {
          "index": 0,
          "trace": "852346626",
          "procedure": {
            "qualifier": "HC",
            "code": "L1833",
            "modifiers": []
          },
          "verdict": "partially_approved",
          "decision": {
            "code": "A2",
            "words": "certified in part",
            "verdict": "partially_approved",
            "known": true,
            "certification_number": "PWA033425780"
          },
          "reason": {
            "code": "10",
            "words": "the delivery pattern asked (units, days, visits, weeks, hours or months)",
            "known": true
          },
          "units": 2,
          "units_asked": 4,
          "units_cut": 2,
          "dates": {
            "begin": "2026-11-02",
            "end": "2026-11-02"
          },
          "dates_asked": {
            "begin": "2026-11-02",
            "end": "2026-11-02"
          },
          "dates_changed": false,
          "quantities": [],
          "administrative_reference_number": "",
          "messages": []
        }
      ],
      "quantities": [],
      "messages": [],
      "claim": {
        "prior_authorization_number": "PWA033425780",
        "field": "claimInformation.claimSupplementalInformation.priorAuthorizationNumber",
        "segment": "2300 REF*G1",
        "route": "POST /v1/claims/837p"
      },
      "notes": [
        "From 01/01/2026, CMS-0057-F (89 FR 8758, 02/08/2024) requires Medicare Advantage organizations, Medicaid and CHIP programs and plans, and QHP issuers on the federal exchanges to give a specific reason for a denied prior authorization (drugs…"
      ],
      "label_source": "paraphrase"
    }
  ],
  "label_source": "paraphrase"
}
```

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

| Field | Type | What it is |
| --- | --- | --- |
| `kind` | the value "278" |  |
| `source` | one of "x12", "json", "fhir" |  |
| `envelope` | Envelope or null |  |
| `reviews` | list of AuthorizationReview |  |
| `answer` | object | Only with ?include=answer: the 278 read to JSON. |
| `label_source` | the value "paraphrase" |  |

### POST /v1/sandbox/authorizations

**Run the prior authorization sandbox.** The round trip on invented data: your requests written as a 278 and the sandbox payer’s 278 response, chosen by how each member ID ends, read back and explained in the same call. Any key may call it, every file is a test file, and nothing reaches a payer.

Request

```bash
curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/sandbox/authorizations" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
```

With the JavaScript client

```js
const answer = await pw.postSandboxAuthorizations(body);
```

With the Python client

```python
answer = pw.post_sandbox_authorizations(body)
```

request.json

```json
{
  "request": {
    "controlNumber": "AUTH-0001",
    "tradingPartnerServiceId": "PWSANDBOX",
    "requester": {
      "organizationName": "Sample Family Medicine",
      "npi": "1234567893"
    },
    "subscriber": {
      "memberId": "W12345PARTIAL",
      "firstName": "SAMPLE",
      "lastName": "PATIENT",
      "dateOfBirth": "1980-02-14",
      "gender": "F"
    },
    "review": {
      "serviceTypeCode": "12",
      "placeOfServiceCode": "12",
      "diagnoses": [
        "M17.11"
      ]
    },
    "services": [
      {
        "procedureCode": "L1833",
        "units": 4,
        "serviceDate": "2026-11-02"
      }
    ]
  }
}
```

The answer (200)

```json
{
  "usage": "T",
  "transmitted": false,
  "control": {
    "interchange_request": "000000001",
    "interchange_response": "000000002",
    "sets": [
      "0001"
    ]
  },
  "files": {
    "authorization_request_278": "ISA*00*          *00*          *ZZ*SUBMITTER      *ZZ*PWSANDBOX      *261019*1500*^*00501*000000001*0*T*:~GS*HI*SUBMITTER*PWSANDBOX*20261019*1500*1*X*005010X217~ST*278*0001*005010X217~BHT*0007*13*AUTH-0001*20261019*1500~HL*1**20*1~NM1*X3*2*…",
    "authorization_response_278": "ISA*00*          *00*          *ZZ*PWSANDBOX      *ZZ*SUBMITTER      *261019*1500*^*00501*000000002*0*T*:~GS*HI*PWSANDBOX*SUBMITTER*20261019*1500*2*X*005010X217~ST*278*0001*005010X217~BHT*0007*11*AUTH-0001*20261019*1500*18~HL*1**20*1~NM1*X3…"
  },
  "outcomes": [
    {
      "index": 0,
      "trace": "AUTH-0001",
      "outcome": "partially_approved",
      "trigger": "PARTIAL"
    }
  ],
  "requests": [
    {
      "index": 0,
      "trace": "AUTH-0001",
      "warnings": []
    }
  ],
  "explained": [
    {
      "index": 0,
      "trace": "AUTH-0001",
      "purpose": "response",
      "payer": {
        "name": "PAYERWORKS SANDBOX PAYER",
        "id": "PWSANDBOX",
        "entity": "X3"
      },
      "requester": {
        "name": "Sample Family Medicine",
        "id_qualifier": "XX",
        "id": "1234567893",
        "entity": "1P"
      },
      "subscriber": {
        "name": "SAMPLE PATIENT",
        "member_id": "W12345PARTIAL",
        "birth_date": "1980-02-14",
        "gender": "F"
      },
      "dependent": null,
      "request_category": {
        "code": "HS",
        "words": "health services review: outpatient services",
        "known": true
      },
      "service_type": {
        "code": "12",
        "words": "durable medical equipment, purchased",
        "known": true,
        "verified_in_005010": true,
        "later_words": ""
      },
      "verdict": "partially_approved",
      "words": "Approved in part, certification number PWA033425780: fewer units than asked on one service.",
      "next_step": "Bill only what was approved, with PWA033425780 as priorAuthorizationNumber (2300 REF*G1). For what was not, ask the payer to reconsider (a 278 with certificationType N and the administrative reference number, where the payer takes one) or f…",
      "certification_number": "PWA033425780",
      "administrative_reference_number": "PWR951115437",
      "previous_authorization_number": "",
      "decision": {
        "code": "A2",
        "words": "certified in part",
        "verdict": "partially_approved",
        "known": true,
        "certification_number": "PWA033425780",
        "second_surgical_opinion": ""
      },
      "reason": {
        "code": "10",
        "words": "the delivery pattern asked (units, days, visits, weeks, hours or months)",
        "kind": "denial",
        "known": true
      },
      "rejections": [],
      "dates": {
        "event": {
          "begin": "2026-11-02",
          "end": "2027-01-30"
        },
        "admission": "",
        "certification": {
          "issued": "2026-10-19",
          "effective": {
            "begin": "2026-11-02",
            "end": "2027-01-30"
          },
          "expires": "2027-01-30"
        }
      },
      "services": [
        {
          "index": 0,
          "trace": "852346626",
          "procedure": {
            "qualifier": "HC",
            "code": "L1833",
            "modifiers": []
          },
          "verdict": "partially_approved",
          "decision": {
            "code": "A2",
            "words": "certified in part",
            "verdict": "partially_approved",
            "known": true,
            "certification_number": "PWA033425780"
          },
          "reason": {
            "code": "10",
            "words": "the delivery pattern asked (units, days, visits, weeks, hours or months)",
            "known": true
          },
          "units": 2,
          "units_asked": 4,
          "units_cut": 2,
          "dates": {
            "begin": "2026-11-02",
            "end": "2026-11-02"
          },
          "dates_asked": {
            "begin": "2026-11-02",
            "end": "2026-11-02"
          },
          "dates_changed": false,
          "quantities": [],
          "administrative_reference_number": "",
          "messages": []
        }
      ],
      "quantities": [],
      "messages": [],
      "claim": {
        "prior_authorization_number": "PWA033425780",
        "field": "claimInformation.claimSupplementalInformation.priorAuthorizationNumber",
        "segment": "2300 REF*G1",
        "route": "POST /v1/claims/837p"
      },
      "notes": [
        "From 01/01/2026, CMS-0057-F (89 FR 8758, 02/08/2024) requires Medicare Advantage organizations, Medicaid and CHIP programs and plans, and QHP issuers on the federal exchanges to give a specific reason for a denied prior authorization (drugs…"
      ],
      "label_source": "paraphrase"
    }
  ],
  "payer_choice": "Payerworks sends nothing. Whether a payer accepts an X12 278 or a FHIR prior authorization request at all is the payer's choice: many take them only on a portal, by fax or by phone, and its companion guide says what it requires."
}
```

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

| Field | Type | What it is |
| --- | --- | --- |
| `usage` | the value "T" |  |
| `transmitted` | the value false |  |
| `control` | object |  |
| `files` | object |  |
| `outcomes` | list of object |  |
| `requests` | list of object |  |
| `explained` | list of AuthorizationReview |  |
| `payer_choice` | string |  |

### POST /v1/authorizations/required

**Does Medicare require it.** Up to one hundred procedure codes checked against CMS’s published Medicare fee-for-service lists on a date of service: the DMEPOS Required Prior Authorization List and the hospital outpatient department list, each named and dated, with the state or the setting asked for where the list depends on it. A code on neither list is said as not on the lists held, never as not required, and for any other payer the answer is that no published list is held.

Request

```bash
curl -sS -X POST "$PAYERWORKS_BASE_URL/v1/authorizations/required" \
  -H "Authorization: Bearer $PAYERWORKS_API_KEY" \
  -H "Content-Type: application/json" \
  -d @request.json
```

With the JavaScript client

```js
const answer = await pw.postAuthorizationsRequired(body);
```

With the Python client

```python
answer = pw.post_authorizations_required(body)
```

request.json

```json
{
  "procedure_codes": [
    "L1833",
    "L3761",
    "E0601"
  ],
  "date_of_service": "2026-11-02",
  "payer_type": "medicare_fee_for_service"
}
```

The answer (200)

```json
{
  "date_of_service": "2026-11-02",
  "payer_type": "medicare_fee_for_service",
  "state": null,
  "setting": null,
  "payer_choice": "Payerworks sends nothing. Whether a payer accepts an X12 278 or a FHIR prior authorization request at all is the payer's choice: many take them only on a portal, by fax or by phone, and its companion guide says what it requires.",
  "codes": [
    {
      "code": "L1833",
      "kind": "hcpcs",
      "required": true,
      "lists": [
        {
          "list": "dmepos",
          "name": "CMS DMEPOS Required Prior Authorization List",
          "url": "https://www.cms.gov/research-statistics-data-and-systems/monitoring-programs/medicare-ffs-compliance-programs/dmepos/downloads/dmepos_pa_required-prior-authorization-list.pdf",
          "updated": "07/29/2026",
          "read": "10/19/2026",
          "group": "Orthoses",
          "words": "knee orthosis, adjustable joints, positional, off the shelf",
          "required": true,
          "from": "2026-10-28",
          "why": "nationwide"
        }
      ],
      "words": "L1833 needs prior authorization for Medicare fee-for-service on 11/02/2026: it is on the DMEPOS Required Prior Authorization List, required from 10/28/2026."
    },
    {
      "code": "L3761",
      "kind": "hcpcs",
      "required": "depends_on_state",
      "lists": [
        {
          "list": "dmepos",
          "name": "CMS DMEPOS Required Prior Authorization List",
          "url": "https://www.cms.gov/research-statistics-data-and-systems/monitoring-programs/medicare-ffs-compliance-programs/dmepos/downloads/dmepos_pa_required-prior-authorization-list.pdf",
          "updated": "07/29/2026",
          "read": "10/19/2026",
          "group": "Orthoses",
          "words": "elbow orthosis, adjustable locking joint, off the shelf",
          "required": "depends_on_state",
          "from": "2026-10-28",
          "states": [
            "NY",
            "MI"
          ],
          "nationwide_from": "2027-04-26",
          "why": "phased"
        }
      ],
      "words": "L3761 is on the DMEPOS Required Prior Authorization List, phased in by state: on 11/02/2026 it is required where the beneficiary lives in NY, MI, FL, CA, and nationwide from 04/26/2027. Send the state the beneficiary lives in to settle it."
    }
  ],
  "sources": [
    {
      "name": "CMS DMEPOS Required Prior Authorization List",
      "url": "https://www.cms.gov/research-statistics-data-and-systems/monitoring-programs/medicare-ffs-compliance-programs/dmepos/downloads/dmepos_pa_required-prior-authorization-list.pdf",
      "updated": "07/29/2026",
      "read": "10/19/2026"
    },
    {
      "name": "CMS Hospital Outpatient Department Services That Require Prior Authorization",
      "url": "https://www.cms.gov/files/document/opd-services-require-prior-authorization.pdf",
      "updated": "09/25/2026",
      "read": "10/19/2026"
    }
  ],
  "note": "Medicare fee-for-service claims for these items, by the date of delivery (for a rental, of the initial rental claim). It does not apply to Medicare Advantage plans. Medicare fee-for-service services furnished in a hospital outpatient depart…"
}
```

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

| Field | Type | What it is |
| --- | --- | --- |
| `date_of_service` | string |  |
| `payer_type` | string |  |
| `state` | string or null |  |
| `setting` | string or null |  |
| `payer_choice` | string |  |
| `codes` | list of object |  |
| `sources` | list of object |  |
| `note` | string |  |

## Reading the answer

- Each review in an explain answer has a `verdict` and its `words`, the `decision` and `reason` codes in words, the `certification_number` when the payer gave one, and the `next_step`.
- A request to the sandbox with a member ID the eligibility sandbox cannot find is not found here either, and a claim the claims sandbox denies is not certified here.

## Troubleshooting

- `invalid_authorization_requests` (422): One request would be refused, so nothing was written; each request’s errors are listed.
- `not_a_278_response` (422): This 278 holds requests only: send the payer’s response.

Every refusal these routes may answer, with its status. Any route may also answer the codes every route shares, on [Every error](https://payerworks.com/docs/errors).

| Code | Status | What it means |
| --- | --- | --- |
| `invalid_asked_requests` | 400 | asked is the review request, or the list of them, that the response answers. |
| `invalid_date_of_service` | 400 | date_of_service is a day, YYYY-MM-DD. |
| `invalid_explain_include` | 400 | include names what to add to the answer: answer (the read of the 278). |
| `invalid_output` | 400 | output is "x12" (the default), "fhir" (the Da Vinci PAS bundle shape) or "both". |
| `invalid_payer_type` | 400 | payer_type is medicare_fee_for_service, medicare_advantage, medicaid, commercial or other. |
| `invalid_procedure_codes` | 400 | Each procedure code is a HCPCS Level II code (a letter and four digits) or a five-character CPT code. |
| `invalid_sender_id` | 400 | sender_id is your submitter id at the receiver: 2 to 15 letters, digits or spaces. |
| `invalid_setting` | 400 | setting is hospital_outpatient or other (where the service is furnished), or left out. |
| `invalid_state` | 400 | state is the two-letter state the patient lives in, such as CA. |
| `no_authorization_answer` | 400 | Send the 278 response as `x12` (the file's text), as `json` (Payerworks' own read of one) or as `fhir` (a Da Vinci PAS response Bundle or ClaimResponse). |
| `no_authorization_request` | 400 | The body has no review request: send `requests` (a list), `request`, or the request itself in the JSON shape the docs describe. |
| `no_procedure_codes` | 400 | Send `procedure_codes`: a list of HCPCS or CPT codes, such as L1833 or 64490. |
| `too_many_authorization_requests` | 400 | At most 100 review requests a call. |
| `too_many_procedure_codes` | 400 | At most 100 procedure codes a call. |
| `test_key_production_file` | 403 | A test key writes test interchanges only (ISA15 = T). Use a live key for a production file. |
| `answer_too_large` | 413 | This answer is larger than one response can carry: send less in each call (split the file, or send fewer claims or requests). |
| `file_too_large` | 413 | This 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. |
| `duplicate_authorization_trace` | 422 | Two review requests in one file carry the same trace (controlNumber); each must be unique so its response matches back. |
| `invalid_authorization_requests` | 422 | One or more review requests would be refused; nothing was written. Each request's errors are listed. |
| `not_a_278` | 422 | This is not an X12 278 request for review and response (005010X217): send the 278 with its ISA envelope. |
| `not_a_278_json` | 422 | This JSON is not a read 278: it holds no `reviews` with a decision or a rejection. |
| `not_a_278_response` | 422 | This 278 holds requests only (BHT02 13): send the payer's response (BHT02 11). |
| `not_a_pas_response` | 422 | This FHIR resource is not a PAS response: send a Bundle holding a ClaimResponse, or the ClaimResponse, with a reviewAction or an error. |

## Code lists

### The prior authorization sandbox’s member ID endings

It answers from the same payer as the eligibility sandbox, and the endings the two share answer alike: a member the eligibility sandbox cannot find is not found here either, and a claim the claims sandbox denies is not certified here. These are its endings:

| Ending | Outcome | What it answers |
| --- | --- | --- |
| `NOTFOUND` | `subscriber_not_found` | A member ID ending in NOTFOUND is not found: the response refuses in the subscriber’s loop with AAA 75 and reviews nothing. |
| `BADDOB` | `birth_date_mismatch` | A member ID ending in BADDOB is found, but the birth date does not match: AAA 71 in the patient’s loop, and nothing reviewed. |
| `DOWN` | `payer_unavailable` | A member ID ending in DOWN reaches a payer that cannot answer: AAA 42 in the payer’s loop, follow-up R. Send it again later, unchanged. |
| `REJ` | `member_id_invalid` | A member ID ending in REJ is refused as a member ID the payer does not accept: AAA 72 in the subscriber’s loop, the same refusal the claims sandbox gives. |
| `INACTIVE` | `not_eligible` | A member ID ending in INACTIVE is not certified because the patient was not covered on the date of service: HCR A3 with reason 53, as the eligibility sandbox ends that coverage last year. |
| `NOTREQ` | `not_required` | A member ID ending in NOTREQ needs no authorization: HCR NA with reason 0H, and no certification number. |
| `PARTIAL` | `partially_approved` | A member ID ending in PARTIAL is certified in part: each service asked for two or more units is approved for half of them, rounded down (HCR A2, reason 10); a service of one unit is approved in full. |
| `MODDATE` | `modified_dates` | A member ID ending in MODDATE is certified with changes (HCR A6): the dates approved start two weeks after the dates asked and run for thirty days. |
| `DENY` | `denied` | A member ID ending in DENY is not certified as not medically necessary (HCR A3, reason 0F), as the claims sandbox denies the claim. |
| `INFO` | `more_information_needed` | A member ID ending in INFO is pended until the payer has more patient information (HCR A4, reason 0U), and a message names the visit notes it needs. |
| `PEND` | `pended` | A member ID ending in PEND is pended while the first utilization review runs (HCR A4, reason 30), with an administrative reference number to follow it by. |
| `` | `approved` | Any other member ID is certified in total (HCR A1) with a certification number, every service approved for the units asked, effective from the first date asked for at least ninety days. |

## Example

[prior-authorization.mjs](https://payerworks.com/docs/examples/prior-authorization.mjs) runs every step below against the API with a test key. It needs [payerworks.mjs](https://payerworks.com/sdk/payerworks.mjs) and [sample-data.mjs](https://payerworks.com/docs/examples/sample-data.mjs) beside it.

prior-authorization.mjs

```js
// Payerworks example: prior authorization, a 278 written and its response read. Docs: https://payerworks.com/docs/prior-authorization
//
// 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 prior-authorization.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 { AUTHORIZATION_REQUEST, SENDER_ID, PAYER_ID, copy, refusalOf } from './sample-data.mjs';

/** @param {Payerworks} pw */
export async function run(pw) {
  // 1. The request written as a 278, to send the way the payer takes it.
  const written = await pw.postAuthorizations278({ sender_id: SENDER_ID, receiver_id: PAYER_ID, control_number: 31, request: copy(AUTHORIZATION_REQUEST) });

  // 2. The authorization sandbox answers it with a 278 response, already explained.
  const request = { ...copy(AUTHORIZATION_REQUEST), tradingPartnerServiceId: 'PWSANDBOX' };
  const sandbox = await pw.postSandboxAuthorizations({ request });

  // 3. Explain a response you hold: the same reading, from the file alone.
  const explained = await pw.postAuthorizationsExplain({ x12: sandbox.files.authorization_response_278 });

  // 4. The failure path: the request you sent is not the payer's response, and the route says so.
  const refused = await refusalOf(() => pw.postAuthorizationsExplain({ x12: written.x12 }), { PayerworksError });

  return {
    written: { transmitted: written.transmitted },
    verdict: explained.reviews[0].verdict,
    next_step: Boolean(explained.reviews[0].next_step),
    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
  },
  "verdict": "approved",
  "next_step": true,
  "refused": {
    "status": 422,
    "code": "not_a_278_response",
    "request_id": "req_4"
  }
}
```
