Transforming Messages: HL7 to JSON

In this tutorial, we will cover transforming messages - in this case HL7v2 to JSON - but you can use the same transformation techniques when mapping data between any of the different types of node trees.

This tutorial will follow a simple repeatable pattern for getting started with any interface:

  1. Parsing the inbound HL7v2 messages.

  2. Filtering unwanted messages.

  3. Transforming the messages to JSON.

  4. Queueing messages for the downstream component.

Let’s build an HL7 to JSON component.

using the Custom Component, call it HL7 to JSON.

In the component card, open the Translator by clicking Edit > Make a Copy and Edit.

Add so we can leverage the Translator’s Auto-complete and the Annotations.

  • Iguana automatically passes the sample data to the main() function.

  • The message can be accessed using the Data parameter.

Let’s add this sample HL7 ADT^A01 message:

MSH|^~\&|MESA_ADT|XYZ_ADMITTING|iFW|ZYX_HOSPITAL|||ADT^A01|103102|P|2.4|||||||| EVN||200007010800||||200007010800 PID|||583295^^^ADT1||DOE^JANE||19610615|M-||2106-3|123 MAIN STREET^^GREENSBORO^NC^27401-1020|GL|(919)379-1212|(919)271-3434~(919)277-3114||S||PATID12345001^2^M10|123456789|9-87654^NC NK1|1|BATES^RONALD^L|SPO|||||20011105 PV1||E||||||5101^NELL^FREDERICK^P^^DR|||||||||||V1295^^^ADT1|||||||||||||||||||||||||200007010800|||||||| PV2|||^ABDOMINAL PAIN OBX|1|HD|SR Instance UID||1.123456.2.2000.31.2.1||||||F|||||| AL1|1||^PENICILLIN||PRODUCES HIVES~RASH AL1|2||^CAT DANDER DG1|001|I9|1550|MAL NEO LIVER, PRIMARY|19880501103005|F|| PR1|2234|M11|111^CODE151|COMMON PROCEDURES|198809081123 ROL|45^RECORDER^ROLE MASTER LIST|AD|CP|KATE^SMITH^ELLEN|199505011201 GT1|1122|1519|BILL^GATES^A IN1|001|A357|1234|BCMD|||||132987 IN2|ID1551001|SSN12345678

First, use hl7.parse to parse the HL7 message. In order to parse, we need to pass:

  • A vmd defining our expected inbound HL7 messages.

  • The data to be parsed.

Three values will be returned which we can use later on:

  • The parsed message as an HL7 node tree.

  • The name of the HL7 message type as defined in the VMD - we can use this in our next step to apply filtering rules based on message type.

  • Data integrity warnings for missing message segments or fields expected.

-- 1) Parse the inbound HL7 message local msgIn, msgType, warnings = hl7.parse{vmd="hl7.vmd", data=Data}

If a VMD isn't added to the project, you’ll see an “Unable to find…“ error in the Translator.

We must create a VMD to use for our sample message: See and come back to finish the transformation tutorial.

Now that we have our HL7 message parsed and identified, let’s create a filters.lua file to apply filtering rules on inbound messages.

We are going to

  1. First create a new file, call it filters and make sure it is a .lua file type. Use the technique from to create a rule to filter out messages not identified as an ADTA01.

-- This module contains sample filtering rules. -- Use your own filter conditions and error messages. local filter ={} function filter.filterMessage(msgType) if msgType ~= 'ADTA01' then iguana.logError('Unexpected message type.') return true end return false end return filter
  1. Call your filter.filterMessage function in main:

    • First assign the required filters.lua module to the variable filter so you can call it.

    • Use an if statement and the not operator to check the name of the message type. If the msgType is not equal to ADTA01, the filter function will return false and not continue executing the block of code.

If you add additional sample data to the Translator, you can test to see how your interface reacts to different message types by viewing the annotations.

For the purpose of this tutorial we will perform some example mappings for a simple JSON object.

  1. Paste the following JSON template at the top outside of main to use as the outbound message schema:

Now inside your filter if statement under the comment -- Transform the message to JSON, add the transformation logic:

  1. First, parse the JSON template so its ready to be populated with the HL7 data:

  1. Create a mapADT.lua file to store your mapping functions. Its good practice to modularize mappings into separate functions for readability and future maintenance. Here we are going to split the mapping into functions for each HL7 segment.

In this example, we are using simple assignment mapping, assigning values from the inbound HL7 message to the outbound JSON. There are many different strategies to map messages. Please see for more strategies.

  1. Now call these mapper functions in main:

    • First assign the required mapADT.lua module to the variable mapper so you can call it.

    • Call each mapping function, passing the appropriate HL7 segments.

Use the annotations to see the results of your mappings. You can also use trace(msgOut) to view your JSON in the annotation window at any point during processing.

Â