Copyright © infotec016 . Powered by Blogger.

Tuesday, February 26, 2019

HL7 - Intro


HL-7 is an international standard used to exchange medical records between healthcare systems. It is introduced by Health level 7 international which is an non profit organization.

Health Level Seven refers to the seventh level(Application Layer) of OSI Model(Open System Interconnection). It specifies communication contents and exchange formats on the 7th layer on OSI.

Application layer addresses the definition of data to be exchanged, the timing of the interchange and communication of certain errors to the application.

Application layer function supports security check, availability check, exchange mechanism negotiation and data exchanging structuring.

Monday, February 25, 2019

HL-7 Version 2 Message Structure


Message

Message is the smallest transferable unit in hl7 and is composed of segments. It begins with the message header Segment(MSH) and is identified by the message type and the initiating event (trigger event).


Segments 

Segments are a way of grouping of items in a logical way. Segments are clearly identified by three letters located at the beginning(Segment Identifier) and are separated by segment separators.
Here, all segments beginning with Z are reserved for locally defined messages.


Fields

The information are contained in the fields of the segments. These fields are in variable length and are separated by field separators.
For each field. a data type is defined.
Field contents can be required or optional and individual fields can be repeated.
Multi component fields are used for further sub division of a field and facilitate the transmission of logically related contents.


Abstract Message Syntax



Hl7 Messages are structured using Abstract Message Syntax to enable straight forward exchange. This describes the frequency of occurrence (cardinality) and definition (required/optional/repeatable) of control and data segments in a message.
Required segments are identified by the segment identifiers, optional segments enclosed in [], repeatable in {}.


Encoding Rules

HL7 provides a specification for the presentation of data. The separating are as follows:

Every message begins with the information about the message itself.
|   => Field Separator
^ => Component Separator
~ = Repetition Separator
\  => Escape Character
& => Subcomponent Separator 


Message Segments 

MSH => Message header
PID => patient identity
PV1 => patient visit information
NK1 => patient’s Next of Kin
EVN => event type
OBX => observation/result
AL1  => Allergy information 
DG1 => Diagnosis information 
DRG => Diagnosis related group 
PR1 => procedures
ROL => Role
IN1 => Insurance
ACC => Accident information
ROL => Role
PDA => Patient death and autopsy


Message Types

ADT => Admission Transfer Discharge
ORM => Order (Pharmacy/ Treatment)
ORU => Observation Result
BAR => (Add/ Change) Billing Account
ACK=> General Acknowledgement
DFT => Detailed Financial Transaction
MDM  => Medical Document Management 
MFN => Master Files Notification
RAS => Pharmacy/ Treatment Administration
RDE => Pharmacy/ Treatment Encoded Order
RGV => Pharmacy/ Treatment Give

Message Structure




Sunday, February 24, 2019

Handling HAPI Test Panel


What is HAPI Test Panel


HAPI Test Panel is a full featured HL7 message editor, used to send and receive HL7 messages.

Install TestPanel

  • Download hapi-testpanel-2.0.1-linux.tar.bz2 from here
  • Extract the download to your perfect location
  • In Ubuntu, run the testpanel.sh file which is at the Home of the Hapi Test Panel extraction
  • In Windows, run the testpanel Application which is at the Home of the Hapi Test Panel extraction

Sending HL7 messages using Testpanel





Creating Sample HL7 Message


  • Go to Test menu and click Populate TestPanel with sample message and connections
  • You can send the message by clicking the send button 






Sending HL7 messages

  • You can click the plus button which is in the Sending Connections panel in the left menu
  • You can give your appropriate Port number, encoding schemes and etc under the Setting menu 
  • You can see the activities through the selected port under the Activity



Receiving HL7 messages

  • You can click the plus button which is in the Receiving Connections panel in the left menu
  • You can give your appropriate Port number, encoding schemes and etc under the Setting menu 
  • You can see the activities through the selected port under the Activity




Creating different type of HL7 messages

  • Go to File which is in the main menu and click the New Message 
  • Select the appropriate message version and message type


Saturday, February 23, 2019

Hl7 Simple Java Client


HL7 Sender Java Code


package hl7sender;
import ca.uhn.hl7v2.DefaultHapiContext;
import ca.uhn.hl7v2.HapiContext;
import ca.uhn.hl7v2.app.Connection;
import ca.uhn.hl7v2.app.Initiator;
import ca.uhn.hl7v2.model.Message;
import ca.uhn.hl7v2.parser.Parser;

public class hl7sender {

   public static void main(String[] args) {

final int PORT_NUMBER = 9014;
// In HAPI, almost all things revolve around a context object.
HapiContext context = new DefaultHapiContext();

      try {
        String adtMessage = "MSH|^~\\&|NES|NINTENDO|TESTSYSTEM|TESTFACILITY|" + "20010101000000||ADT^A01|Q123456789T123456789X123456|P|2.3\r" + "EVN|A01|20010101000000|||^KOOPA^BOWSER\r" + "PID|1||123456789|0123456789^AA^^JP|BROS^MARIO||19850101000000|" + "M|||123 FAKE STREET^MARIO \\T\\ LUIGI BROS PLACE^TOADSTOOL" + "KINGDOM^NES^A1B2C3^JP^HOME^^1234|1234|(555)555-0123^HOME^JP:" + "1234567|||S|MSH|12345678|||||||0|||||N\r" + "NK1|1|PEACH^PRINCESS|SO|ANOTHER CASTLE^^TOADSTOOL KINGDOM" + "^NES^^JP|(123)555-1234|(123)555-2345|NOK\r" + "NK1|2|TOADSTOOL^PRINCESS|SO|YET ANOTHER CASTLE^^TOADSTOOL" + "KINGDOM^NES^^JP|(123)555-3456|(123)555-4567|EMC\r" + "PV1|1|O|ABCD^EFGH||||123456^DINO^YOSHI^^^^^^MSRM^CURRENT" + "^^^NEIGHBOURHOOD DR NBR|^DOG^DUCKHUNT^^^^^^^CURRENT||CRD||" + "|||||123456^DINO^YOSHI^^^^^^MSRM^CURRENT^^^NEIGHBOURHOOD DR" + " NBR|AO|0123456789|1|||||||||||||||||||MSH||A|||20010101000000\r" + "IN1|1|PAR^PARENT||||LUIGI\r";

// create a new MLLP client over the specified port.
Connection connection = context.newClient("localhost", PORT_NUMBER, false);

// The initiator which will be used to transmit our message.
Initiator initiator = connection.getInitiator();

// send the created HL7 message over the connection established
Parser parser = context.getPipeParser();

System.out.println("Sending message:" + "\n" + adtMessage);
Message response = initiator.sendAndReceive(parser.parse(adtMessage));

// display the message response received from the remote party
String responseString = parser.encode(response);
System.out.println("Received response:\n" + responseString.replaceAll("\r", "\n"));
        }
        catch (Exception e) {
           e.printStackTrace();
        }
   }
}


HL7 Receiver Java Code

This main class is used to


package hl7receiver;

import ca.uhn.hl7v2.DefaultHapiContext;

import ca.uhn.hl7v2.HapiContext;
import ca.uhn.hl7v2.app.HL7Service;
import ca.uhn.hl7v2.parser.Parser;
import ca.uhn.hl7v2.parser.PipeParser;

public class hl7receiver {

    public static void main(String args[]) {

        final int PORT_NUMBER = 9014;
        //In HAPI,almost all things revolve around a context object
        HapiContext context = new DefaultHapiContext();
        try {
            Parser parser = new PipeParser();
            HL7Service ourHl7Server =                   context.newServer(PORT_NUMBER, false);
            // You can set up routing rules for your HL7 listener by extending the AppRoutingData class
            ourHl7Server.registerApplication(new     RegisterEventRouter(), new ourSimpleApplication());
            ourHl7Server.setShutdownTimeout(10000);
            ourHl7Server.startAndWait();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}


Simple Application class that is used to receive the message and create and send the acknowledgement

package hl7receiver;

import ca.uhn.hl7v2.HL7Exception;

import ca.uhn.hl7v2.model.Message;
import ca.uhn.hl7v2.parser.PipeParser;
import ca.uhn.hl7v2.protocol.ReceivingApplication;
import ca.uhn.hl7v2.protocol.ReceivingApplicationException;

import java.io.IOException;
import java.util.Map;

public class ourSimpleApplication implements ReceivingApplication {

    PipeParser pipeParser = new PipeParser();

    public Message processMessage(Message message, Map map) throws
 ReceivingApplicationException, HL7Exception {

        System.out.println("Received Message\n" + pipeParser.encode(message));
        Message response = null;
        try {
            response = message.generateACK();
            System.out.println("Sent Response\n" + pipeParser.encode(response));
        } catch (IOException e) {
            e.printStackTrace();
        }
        return response;
    }

    public boolean canProcess(Message message) {

        return true;
    }
}



Event Router class that is used to rout the message to the appropriate versions and types.


package hl7receiver;

import ca.uhn.hl7v2.protocol.ApplicationRouter;


public class RegisterEventRouter implements ApplicationRouter.AppRoutingData {

    public String getMessageType() {

        return "*";
    }

    public String getTriggerEvent() {

        return "*";
    }

    public String getProcessingId() {

        return "*";
    }

    public String getVersion() {

        return "*";
    }

}

Friday, February 22, 2019

Hl7 Java Client with Tls


HL7 Sender Java Code


package hl7senderwithTls;

import ca.uhn.hl7v2.DefaultHapiContext;
import ca.uhn.hl7v2.HL7Exception;
import ca.uhn.hl7v2.HapiContext;
import ca.uhn.hl7v2.app.Connection;
import ca.uhn.hl7v2.app.Initiator;
import ca.uhn.hl7v2.hoh.sockets.CustomCertificateTlsSocketFactory;
import ca.uhn.hl7v2.hoh.util.HapiSocketTlsFactoryWrapper;
import ca.uhn.hl7v2.hoh.util.KeystoreUtils;
import ca.uhn.hl7v2.llp.LLPException;
import ca.uhn.hl7v2.model.Message;
import ca.uhn.hl7v2.parser.Parser;

import java.io.IOException;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;

public class hl7senderwithTls {

    public static void main(String[] args) throws HL7Exception, 
     LLPException, IOException {

        final int PORT_NUMBER = 9014;
        final String tlsKeystoreFilepath = "src/main/resources/keystore.jks";
        final String tlsKeystorePassphrase = "changeit";
        final String tlsKeystoreType = "JKS";

        // InHAPI almost all things revolve around a context object
        HapiContext context = new DefaultHapiContext();

        String adtMessage = "MSH|^~\\&|NES|NINTENDO|TESTSYSTEM|TESTFACILITY" + 
                "|20010101000000||ADT^A01|Q123456789T123456789X123456|P|2.3\r" +
                "EVN|A01|20010101000000|||^KOOPA^BOWSER\r";
        try {
            //To validate the keystore
            KeyStore keyStore = KeystoreUtils.loadKeystore(tlsKeystoreFilepath, 
             tlsKeystorePassphrase);
            KeyStore.getInstance(tlsKeystoreType);
            KeystoreUtils.validateKeystoreForTlsSending(keyStore);
            CustomCertificateTlsSocketFactory tlsFac = new 
             CustomCertificateTlsSocketFactory(tlsKeystoreType,
                    tlsKeystoreFilepath, tlsKeystorePassphrase);
            context.setSocketFactory(new HapiSocketTlsFactoryWrapper(tlsFac));
        } catch (IOException e) {
            e.printStackTrace();
        } catch (CertificateException e) {
            e.printStackTrace();
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        } catch (KeyStoreException e) {
            e.printStackTrace();
        }
        // create a new MLLP client over the specified port
        Connection connection = context.newClient("localhost", PORT_NUMBER, true);

        // The initiator which will be used to transmit our message
        Initiator initiator = connection.getInitiator();

        // send the created HL7 message over the connection established
        Parser parser = context.getPipeParser();
        System.out.println("Sending message:" + "\n" + adtMessage);
        Message response = initiator.sendAndReceive(parser.parse(adtMessage));

        // display the message response received from the remote party
        String responseString = parser.encode(response);
        System.out.println("Received response:\n" + responseString.replaceAll("\r", "\n"));

    }
}

HL7 Receiver Java Code

This main class is used to


package hl7receiverwithTls;

import ca.uhn.hl7v2.DefaultHapiContext;
import ca.uhn.hl7v2.HapiContext;
import ca.uhn.hl7v2.app.HL7Service;
import ca.uhn.hl7v2.hoh.sockets.CustomCertificateTlsSocketFactory;
import ca.uhn.hl7v2.hoh.util.HapiSocketTlsFactoryWrapper;
import ca.uhn.hl7v2.hoh.util.KeystoreUtils;
import ca.uhn.hl7v2.parser.Parser;
import ca.uhn.hl7v2.parser.PipeParser;

import java.io.IOException;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;

public class hl7receiverwithTls {
    public static void main(String[] args) throws InterruptedException {

        final int PORT_NUMBER = 9014;
        final String tlsKeystoreFilepath = "src/main/resources/keystore.jks";
        final String tlsKeystorePassphrase = "changeit";
        final String tlsKeystoreType = "JKS";
        // In HAPI, almost all things revolve around a context object
        HapiContext context = new DefaultHapiContext();
        try {
            //To validate the keystore
            KeyStore keyStore = KeystoreUtils.loadKeystore(tlsKeystoreFilepath, tlsKeystorePassphrase);
            KeyStore.getInstance(tlsKeystoreType);
            KeystoreUtils.validateKeystoreForTlsSending(keyStore);
            CustomCertificateTlsSocketFactory tlsFac = new CustomCertificateTlsSocketFactory(tlsKeystoreType,
                    tlsKeystoreFilepath, tlsKeystorePassphrase);
            context.setSocketFactory(new HapiSocketTlsFactoryWrapper(tlsFac));
        } catch (IOException e) {
            e.printStackTrace();
        } catch (CertificateException e) {
            e.printStackTrace();
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        } catch (KeyStoreException e) {
            e.printStackTrace();
        }
            Parser parser = new PipeParser();
            HL7Service ourHl7Server = context.newServer(PORT_NUMBER, true);
            // You can set up routing rules for your HL7 listener by extending the AppRoutingData class
            ourHl7Server.registerApplication(new RegisterEventRouter(), new ourSimpleApplication());
            ourHl7Server.setShutdownTimeout(10000);
            ourHl7Server.startAndWait(); 
    }
}


Simple Application class that is used to receive the message and create and send the acknowledgement

package hl7receiverwithTls;

import ca.uhn.hl7v2.HL7Exception;
import ca.uhn.hl7v2.model.Message;
import ca.uhn.hl7v2.parser.PipeParser;
import ca.uhn.hl7v2.protocol.ReceivingApplication;
import ca.uhn.hl7v2.protocol.ReceivingApplicationException;

import java.io.IOException;
import java.util.Map;

public class ourSimpleApplication implements ReceivingApplication {

    PipeParser pipeParser = new PipeParser();

    public Message processMessage(Message message, Map map) throws ReceivingApplicationException, HL7Exception {

        System.out.println("Received Message\n" + pipeParser.encode(message));
        Message response = null;
        try {
            response = message.generateACK();
            System.out.println("Sent Response\n" + pipeParser.encode(response));
        } catch (IOException e) {
            e.printStackTrace();
        }
        return response;
    }

    public boolean canProcess(Message message) {

        return true;
    }
}


Event Router class that is used to rout the message to the appropriate versions and types.


package hl7receiverwithTls;

import ca.uhn.hl7v2.protocol.ApplicationRouter;

public class RegisterEventRouter implements ApplicationRouter.AppRoutingData {

    public String getMessageType() {

        return "*";
    }

    public String getTriggerEvent() {

        return "*";
    }

    public String getProcessingId() {

        return "*";
    }

    public String getVersion() {

        return "*";
    }

}


Thursday, February 21, 2019