HL7 Inbound API
The HL7 Inbound API receives inbound HL7 v2.x ADT messages from EHR systems over HTTP and returns standard HL7 acknowledgment responses. It implements the HAPI HL7-over-HTTP convention, accepting raw pipe-delimited ER7 message bodies and processing them against configured parser profiles.
- Validates the MSH segment for required fields (MSH.3, MSH.4, MSH.7, MSH.9, MSH.10, MSH.12) and encoding characters (
^~\&). - Resolves a matching active parser profile using the composite key: Sending Application (MSH.3), Sending Facility (MSH.4), HL7 Version (MSH.12), Message Type (MSH.9), and Message Event (MSH.9).
- Parses configured HL7 fields per the matched profile's segment and field map definitions, storing the result as a JSON blob (
parsed_data) on the message log record. - Creates an
sn_hl7_v2_message_logrecord for only the messages with an active parser configuration. If the parser configuration isn't detected, an ACK is sent back to the sender. - Returns an HL7 v2.x ACK response (MSH + MSA segments in ER7 format) with one of the following ACK codes:
AA: acceptedAR: rejected, no matching profile foundAE: error
- EHR systems sending ADT discharge notifications (ADT^A03) to trigger downstream workflows such as Environmental Services (EVS) case creation in ServiceNow.
- Any HL7 v2.x message type for which a matching active parser profile is configured.
- Integration testing and parser profile validation before go-live.
For more information about these features, see HL7 v2.x Integration.
Requirements
The HL7 Inbound API is supported by the HL7 V2.x Integration application and requires the sn_hl7_v2 plugin.
The sn_hl7_v2.admin role is required to invoke the API.
- Parser configuration (sn_hl7_v2_parser_config table): The top-level profile record. Must be set to active and uniquely identify the sending system using the following fields:
- Sending Application
- Sending Facility
- HL7 Version
- Message Type
- Message Event
These values must match the corresponding MSH segment fields in the incoming message exactly.
- Segment definitions (sn_hl7_v2_parser_segment table): One or more records defining which HL7 segments the API should extract from the message.
- Field mappings (sn_hl7_v2_parser_field_map table): Records that map specific field positions within each segment to output field names stored on the message log record. For setup instructions, see Extending the API.
Downstream processing
This is a standalone endpoint. Downstream processing, such as EVS case creation, is triggered asynchronously by a record insert on sn_hl7_v2_message_log from a separate consumer-scope application
(app-ind-cto-evs) and not by a subsequent API call.
Extending the API
The HL7 Inbound API accepts any HL7 v2.x message type in the base system. Processing behavior is driven entirely by parser profiles; no code changes are required to support a new message type or EHR system. To add support, an administrator creates a new parser configuration.
To add support for a new sending system or message type:
- In the app navigator, open HL7 Parser Configurations.
- Create a new parser profile (
sn_hl7_v2_parser_config) with a composite key that matches the sending system's MSH fields: Sending Application, Sending Facility, HL7 Version, Message Type, and Message Event. - Add segment records (
sn_hl7_v2_parser_segment) for each HL7 segment you want to extract. - Add field map records (
sn_hl7_v2_parser_field_map) to define the field position-to-output field name mappings for each segment. - Use the Parse Sample Payload UI action to validate the profile against a real HL7 message before activating it.
To clone from existing parser configuration, see the instructions in Clone and customize a parser configuration.
HL7 Inbound - POST /api/sn_hl7_v2/hl7/message
Accepts a raw pipe-delimited HL7 v2.x message in ER7 format, validates the MSH segment, resolves a matching parser profile, and creates an sn_hl7_v2_message_log record for downstream processing.
The response is an HL7 ACK message body. Inspect both the HTTP status code and the MSA segment ACK code to determine the outcome.
Call this endpoint whenever an external system, such as an EHR or integration engine, needs to deliver an inbound HL7 v2.x message to ServiceNow.
URL format
Versioned URL: /api/sn_hl7_v2/{api_version}/hl7/message
Default URL: /api/sn_hl7_v2/hl7/message
Supported request parameters
| Name | Description |
|---|---|
| api_version | Optional. Version of the endpoint to access. For example, v1 or v2. Only specify this value to use an endpoint version other than the
latest.
Data type: String |
| Name | Description |
|---|---|
| None |
Request body parameters (ER7 segments)
The following fields are transmitted as segments and field positions within the raw HL7 v2.x pipe-delimited (ER7) message body, not as JSON or XML parameters. Each field is identified by its MSH position number.
| Name | Description |
|---|---|
| MSH.2 | Required. Encoding characters. Must be exactly ^~\& or the message is rejected.Data type: String |
| MSH.3 | Required. Sending Application. Used in the parser profile composite key and to address the ACK response. Data type: String |
| MSH.4 | Required. Sending Facility. Used in the parser profile composite key and to address the ACK response. Data type: String |
| MSH.7 | Required. Date/time of message in YYYYMMDDHHmmss format. Stored on the message log record.Table: Message Log [sn_hl7_v2_message_log] Data type: String |
| MSH.9 | Required. Message type and event. For example, ADT^A03^ADT_A03. Used in the parser profile composite key.Note: Both the message type and message event components are used separately in the lookup, since
MSH.9 is a composite field. Data type: String |
| MSH.10 | Required. Message Control ID. Echoed back in the MSA.2 field of the ACK response.Data type: String |
| MSH.12 | Required. Version ID. For example, 2.5.1. Used in the parser profile composite key.Data type: String |
| Additional segments | Optional. HL7 segments, such as EVN, PID, PV1. Parsed per the matched parser profile's segment and field map configuration. Extracted fields are stored as JSON in the
message log record.Table: Message Log [sn_hl7_v2_message_log], Field: Data type: String |
Headers
The following request and response headers apply to this HTTP action only, or apply to this action in a distinct way. For a list of general headers used in the REST API, see Supported REST API headers.
| Header | Description |
|---|---|
| Content-Type: x-application/hl7-v2+er7 | Required. Identifies the body as a raw HL7 v2.x pipe-delimited (ER7) message. Any other content type returns an error. |
| Authorization: Basic <base64(user:password)> | Required. ServiceNow Basic Auth credentials for the calling user or any ServiceNow supported authentication types, such as OAuth. |
| Header | Description |
|---|---|
| Content-Type: x-application/hl7-v2+er7 | Always set by the endpoint. Indicates the response body is a raw HL7 ACK message in ER7 format. |
Status codes
The following status codes apply to this HTTP action. For a list of possible status codes used in the REST API, see REST API HTTP response codes.
| Status code | Description |
|---|---|
| 200 |
Message was processed. Inspect MSA segment ACK code for outcome:
|
| 422 | MSH structural validation failed. Possible errors:
ACK code in body will be AE. No message log record is created. |
| 500 | Unexpected server-side error. ACK code in body returns AE with "Internal server error" detail. |
Response body parameters (ER7 segments)
The response body is a raw HL7 v2.x ACK message in pipe-delimited ER7 format containing two segments: MSH and MSA.
| Name | Description |
|---|---|
| MSH segment | ACK message header in pipe-delimited ER7 format. Key fields:
Data type: String (pipe-delimited HL7 segment) |
| MSA segment | Message acknowledgment. Possible values:
Data type: String (pipe-delimited HL7 segment) |
cURL request
This example sends an ADT^A03 (patient discharge) message from an EHR system to the HL7 Inbound API. The message originates from the EPIC application at GENERAL_HOSPITAL. The API validates the MSH
segment, resolves a matching active parser profile using the composite key (EPIC + GENERAL_HOSPITAL + 2.5.1 + ADT + A03), parses the configured
fields from the EVN, PID, and PV1 segments, and creates an sn_hl7_v2_message_log record. The response is an HL7 ACK message addressed back to the originating system.
Request:
curl 'https://<instance>.service-now.com/api/sn_hl7_v2/v1/hl7/message' \
--request POST \
--header 'Content-Type: x-application/hl7-v2+er7' \
--user 'username:password' \
--data-binary $'MSH|^~\\&|EPIC|GENERAL_HOSPITAL|sn_hl7_v2||20260421120000||ADT^A03^ADT_A03|CTRL001|P|2.5.1\rEVN|A03|20260421120000\rPID|1||MRN001^^^GENERAL_HOSPITAL||Doe^John\rPV1|1|I|WEST_WING^ROOM1'
Response body: Success (HTTP 200, ACK AA)
MSH|^~\&|sn_hl7_v2||EPIC|GENERAL_HOSPITAL|20260421120005||ACK^A01^ACK|A1B2C3D4E5F6|P|2.5
MSA|AA|CTRL001
The message was accepted and fully parsed. The ACK is addressed back to the originating system (EPIC at GENERAL_HOSPITAL). MSA.1 returns AA and
MSA.2 echoes the original Message Control ID (CTRL001).
Response body: No profile match (HTTP 200, ACK AR)
MSH|^~\&|sn_hl7_v2||EPIC|GENERAL_HOSPITAL|20260421120005||ACK^A01^ACK|G7H8I9J0K1L2|P|2.5
MSA|AR|CTRL001|No active parser profile found for the inbound message.
The MSH segment was valid but no active parser profile matched the composite key. Because no matching parser configuration is found, the record isn't staged on sn_hl7_v2_message_log. MSA.1 returns AR and MSA.3 contains the rejection detail. To resolve this, verify that an active parser profile exists for the sending system and message type. See Requirements.
Response body: MSH validation failure (HTTP 422, ACK AE)
MSH|^~\&|sn_hl7_v2||||20260421120005||ACK^A01^ACK|M3N4O5P6Q7R8|P|2.5
MSA|AE||Request body is empty.
The request failed MSH validation before processing could begin. Note that MSH.5 and MSH.6 are empty in the response — because the sending application and facility could not be read from the
inbound message, the ACK cannot be addressed back to the originator. MSA.1 returns AE and MSA.3 contains the error detail.