GithubHelp home page GithubHelp logo

darkmarmot / elixir-hl7 Goto Github PK

View Code? Open in Web Editor NEW

This project forked from hca-healthcare/elixir-hl7

0.0 2.0 0.0 688 KB

An Elixir library for working with HL7 v2.x healthcare data

License: Apache License 2.0

Elixir 100.00%

elixir-hl7's Introduction

Elixir HL7

hex.pm version hex.pm downloads hex.pm license

An Elixir library for working with HL7 v2.x healthcare data

Elixir HL7 provides functions to parse, query and modify healthcare data that conforms to the HL7 v2.x standards. It should be able to reconstruct any HL7 Message without data loss or corruption.

It also provides basic support for reading HL7 file streams with configurable delimiters (MLLP included).

This library has been tested on a fairly wide variety of real-world HL7 messages to ensure correctness and flexibility.

You can learn more about HL7 here:

Please report an issue if something appears to be handled incorrectly.

Getting started

Add this library to your mix.exs file:

defp deps do
  [{:elixir_hl7, "~> 0.3.0"}]
end

Check out the HL7.Examples module for sample data that you can use to explore the API.

Route

HL7 messages can be minimally validated to gather header (MSH segment) information for quick routing and acknowledgements.

iex> hl7_text = HL7.Examples.wikipedia_sample_hl7()
...> raw_msg = HL7.Message.raw(hl7_text)
...> raw_msg.header.message_type
"ADT" 

See the HL7.RawMessage and HL7.Header modules for more information.

Parse

HL7 messages can be fully parsed into lists of lists and strings to provide a compact representation of the message structure.

One could grab the 2nd segment in a message:

iex> HL7.Examples.wikipedia_sample_hl7()
...> |> HL7.Message.to_list()
...> |> Enum.at(1)
["EVN", "", "200605290901", "", "", "", "200605290900"]

Or get the field value of RXA-5.2 (finding the first RXA segment's 5th field, 1st repetition, 2nd component):

iex> HL7.Examples.nist_immunization_hl7()
...> |> HL7.Message.find("RXA")
...> |> HL7.Segment.get_part(5, 1, 2)
"Influenza"

It's also possible to modify the data within a segment (but it is much easier to manipulate messages using the HL7.Query module):

iex> HL7.Examples.wikipedia_sample_hl7()
...> |> HL7.Message.find("EVN")
...> |> HL7.Segment.replace_part("extra data", 5, 2, 1)
[      
  "EVN",
  "",
  "200605290901",
  "",
  "",
  ["", "", ["", "extra data"]],
  "200605290900"
]

See the HL7.Message and HL7.Segment modules for more information.

Query

Advanced manipulation and analysis of HL7 messages can be performed with the HL7.Query module.

It supports a pipeline-friendly API modeled after jQuery and D3, allowing set-based document operations and queries.

Messages can be broken into groups using a segment selector (similar to a CSS selector string) that denotes optional and repeating segments in potentially nested hierarchies.

Individual segments can be decomposed using a field selector to reference specific field, repetition, component and subcomponent indices.

Note that all HL7.Query selections implicitly retain the entire message structure such that elements can be selected, modified and then used to reconstruct a new HL7 message.

The act of selecting something never modifies the content of a message. Applying other methods to a selection, such as delete, filter, append, etc., does modify the actual message content.

For instance, this would select all textual diagnoses (DG1-3.2) associated with a patient visit (PV1):

iex> import HL7.Query
iex> HL7.Examples.nist_syndromic_hl7()
...> |> select("PV1 [{DG1}]")
...> |> select("DG1")
...> |> get_parts("3.2")
["Cryptosporidiosis", "Dehydration", "Diarrhea"]

The statement select("PV1 [{DG1}]") grabs a list of segment groups containing a PV1 segment and any DG1 segments that might follow it. Thus, we would select one group containing a PV1 segment and three DG1 segments.

[ 
  [ # 1 group of 4 segments
    ["PV1", "1", "(data truncated to fit)"],
    ["DG1", "1", "", [["0074", "Cryptosporidiosis", "I9CDX"]], "", "", "F"],
    ["DG1", "2", "", [["27651", "Dehydration", "I9CDX"]], "", "", "F"],
    ["DG1", "3", "", [["78791", "Diarrhea", "I9CDX"]], "", "", "F"]
  ]
]

Then select("DG1") creates three groups of individual DG1 segments by searching within the confines of the prior selection.

[  # 3 groups of 1 segment each
  [["DG1", "1", "", [["0074", "Cryptosporidiosis", "I9CDX"]], "", "", "F"]],
  [["DG1", "2", "", [["27651", "Dehydration", "I9CDX"]], "", "", "F"]],
  [["DG1", "3", "", [["78791", "Diarrhea", "I9CDX"]], "", "", "F"]]
]

Finally, get_parts("3.2") will return a flattened list of data containing the 3rd field, 1st repetition (the default), 2nd component for each selected segment.

["Cryptosporidiosis", "Dehydration", "Diarrhea"]

Alternately, one could select and remove every diagnosis tied to a patient visit and then output a modified HL7 message:

iex> import HL7.Query
iex> HL7.Examples.nist_syndromic_hl7()
...> |> select("PV1 [{DG1}]")
...> |> select("DG1")
...> |> delete()
...> |> to_string()
"MSH|^~\\&||LakeMichMC^9879874000^NPI|||201204020040||ADT^A03^ADT_A03|NIST-SS-003.32|P|2.5.1|||||||||PH_SS-NoAck^SS Sender^2.16.840.1.114222.4.10.3^ISO\rEVN||201204020030|||||LakeMichMC^9879874000^NPI\rPID|1||33333^^^^MR||^^^^^^~^^^^^^S|||F||2106-3^^CDCREC|^^^^53217^^^^55089|||||||||||2186-5^^CDCREC\rPV1|1||||||||||||||||||33333_001^^^^VN|||||||||||||||||09||||||||201204012130\rOBX|1|CWE|SS003^^PHINQUESTION||261QE0002X^Emergency Care^NUCC||||||F\rOBX|2|NM|21612-7^^LN||45|a^^UCUM|||||F\rOBX|3|CWE|8661-1^^LN||^^^^^^^^Diarrhea, stomach pain, dehydration||||||F\r"  

The following query extracts each Common Order (ORC) group's OBX segments and outputs a list of each order's associated vaccine types.

iex> import HL7.Query
iex> HL7.Examples.nist_immunization_hl7()
...> |> select("ORC [RXA] [RXR] {OBX}")
...> |> filter(fn q -> get_part(q, "3.2") == "vaccine type" end)
...> |> map(fn q -> get_parts(q, "5.2") end)
[
    ["Influenza, unspecified formulation"], 
    ["DTaP", "Polio", "Hep B, unspecified formulation"]
]   

See the HL7.Query module for more information.

Create

HL7 messages can be constructed from scratch with the HL7.Message module. Passing an HL7.Header struct to HL7.Message.new/1 will produce a base message upon which you can add additional segments. These can be appended as list data.

The final raw message can be produced by invoking the to_string/1 protocol on either the HL7.Query or HL7.Message structs.

Files

The HL7 module contains utility functions to open file streams of HL7 message content with support for MLLP and standard :line storage. Other formats are somewhat supported by specifying expected prefix and suffix delimiters between messages.

Sockets

A separate library, Elixir-MLLP, exists to manage MLLP connections. MLLP is a simple protocol on top of TCP that is commonly used for sending and receiving HL7 messages.

Status

This project is approaching a v1.0 release. The API is mostly stable at this point.

Also, please be aware of the details of the license (Apache 2.0).

License

Elixir-HL7 source code is released under Apache 2 License. Check LICENSE file for more information.

elixir-hl7's People

Contributors

bryanhunter avatar calvinb avatar darkmarmot avatar thefunc5 avatar

Watchers

 avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.