Beispiel #1
0
    def _create_response(self, ack_code, query_ack_code, patients):
        res = Message('RSP_K21', reference=self.RES_MP)
        res.msh.msh_5 = self.incoming_message.msh.msh_3
        res.msh.msh_6 = self.incoming_message.msh.msh_4
        res.msh.msh_7.ts_1 = DTM(datetime.datetime.now())
        res.msh.msh_9 = 'RSP^K22^RSP_K21'
        res.msh.msh_10 = uuid.uuid4().hex

        # MSA creation
        res.msa.msa_1 = ack_code
        res.msa.msa_2 = self.incoming_message.msh.msh_10.msh_10_1

        # QAK creation
        res.qak.qak_1 = self.incoming_message.qpd.qpd_2
        res.qak.qak_2 = 'OK' if len(patients) > 0 else 'NF'
        res.qak.qak_4 = str(len(patients))

        # QPD creation
        res.qpd = self.incoming_message.qpd

        # RSP_K21_QUERY_RESPONSE creation
        res.add_group('rsp_k21_query_response')
        g = res.rsp_k21_query_response
        for i, p in enumerate(patients):
            # add a pid segment for every patient
            g.add_segment('PID')
            g.pid[i].pid_3.cx_1, g.pid[i].pid_5.xpn_1, g.pid[i].pid_5.xpn_2 = p[:]

        return res.to_mllp()
Beispiel #2
0
 def ack(self, resp_type='AA'):
     """
     Build ACK response for incoming message.
     :type resp_type: str
     :param resp_type: 'AA' for ACK, 'AR' for Reject, 'AE' for Application Error
     :rtype: HL7apy.core.Message
     :return: ACK ('AA') or NAK ('AE', 'AR') message
     """
     resp_types = ('AA', 'AR', 'AE')
     if resp_type not in resp_types:
         raise ValueError(
             "Invalid ACK type. Expected one of: {}".format(resp_types))
     resp = Message('ACK', version='2.5.1')
     resp.msh.msh_3 = 'LIS'
     resp.msh.msh_4 = 'LIS Facility'
     resp.msh.msh_5 = self.msg.msh.msh_3
     resp.msh.msh_6 = Config.LABNAME
     resp.msh.msh_9 = 'ACK^R22^ACK'
     resp.msh.msh_10 = self.run_info.msg_guid
     resp.msh.msh_11 = 'P'
     resp.msh.msh_12 = '2.5.1'
     resp.msh.msh_18 = 'UNICODE UTF-8'
     resp.msh.msh_21 = 'LAB-29^IHE'
     resp.add_segment('MSA')
     resp.msa.msa_1 = resp_type
     resp.msa.msa_2 = self.run_info.msg_guid
     if resp_type != 'AA':
         pass
     end_resp = add_mllp_frame(resp.to_er7())
     assert isinstance(end_resp, bytes)
     return end_resp
Beispiel #3
0
def responder(m):
    # cria uma mensagem de resposta RSP_K11
    response = Message("RSP_K11")
    response.MSH.MSH_9 = "RSP^K11^RSP_K11"
    response.MSA = "MSA|AA"
    response.MSA.MSA_2 = m.MSH.MSH_10
    qak = Segment("QAK")
    qak.qak_1 = m.QPD.QPD_2
    qak.qak_2 = "OK"
    qak.qak_3 = "Q22^Specimen Labeling Instructions^IHE_LABTF"
    qak.qak_4 = "1"
    response.add(qak)
    response.QPD = m.QPD
    response.PID.PID_1 = '1'
    response.PID.PID_5.PID_5_1 = 'CUNHA'
    response.PID.PID_5.PID_5_2 = 'JOSE'
    response.PID.PID_6 = "19800101"
    response.PID.PID_7 = "F"
    response.PID.PID_23 = "Brasil"
    spm = Segment("SPM")
    obr = Segment("OBR")
    spm.SPM_1 = '1'
    spm.SPM_2 = "12345"
    obr.OBR_4 = "ORDER^DESCRIPTION"
    response.add(spm)
    response.add(obr)
    return response.to_mllp()
Beispiel #4
0
 def _create_test_message(self, msh_values):
     """
     Create a test message - RSP_K11 - with only the msh segment.
     The msh is filled with the sent in input
     """
     msg = Message('RSP_K11')
     msg.msh = self._get_msh(msh_values)
     return msg
Beispiel #5
0
    def test_msg_to_string_empty(self):
        """
        It tests the to_er7 message for an empty message
        """
        from datetime import datetime

        msg = Message('RSP_K11')
        self.assertRegexpMatches(msg.to_er7(), 'MSH|^~\\&|||||d+|||||2.5')
Beispiel #6
0
def readExampleHL7():
    m = Message()
    fl = ""
    with open(fileorig, 'r') as fd:
        for line in fd.readlines():
            fl = fl + "\r" + line
    m = pm(fl)
    return m
Beispiel #7
0
 def test_to_string_msh_field(self):
     m = Message('OML_O33')
     msh = m.msh
     self.assertEqual(msh.msh_1.to_er7(), '|')
     self.assertEqual(msh.msh_2.to_er7(), '^~\\&')
     msh_1 = Field('MSH_1')
     msh_2 = Field('MSH_2')
     self.assertRaises(IndexError, msh_1.to_er7)
     self.assertRaises(IndexError, msh_2.to_er7)
Beispiel #8
0
 def test_to_string_msh_field_v27(self):
     for v in ('2.7', '2.8', '2.8.1', '2.8.2'):
         m = Message('OML_O33', version=v)
         msh = m.msh
         self.assertEqual(msh.msh_1.to_er7(), '|')
         self.assertEqual(msh.msh_2.to_er7(), '^~\\&#')
         msh_1 = Field('MSH_1')
         msh_2 = Field('MSH_2')
         self.assertRaises(IndexError, msh_1.to_er7)
         self.assertRaises(IndexError, msh_2.to_er7)
Beispiel #9
0
def genACK(msg, encoding):
    try:
        m = pm(msg.decode(encoding))
        res = Message('RSP_K11')
        res.MSH.MSH_9 = 'RSP^K11^RSP_K11'
        res.MSA = "MSA|AA"
        res.MSA.MSA_2 = m.MSH.MSH_10
    except AttributeError as e:
        print("Impossible to generate ACK: {0}".format(e))
        res = Message('RSP_K11')
        res.MSH.MSH_9 = 'RSP^K11^RSP_K11'
        res.MSA = "MSA|AA"
    except:
        print("Error trying to generate ACK: ", sys.exc_info()[0])
        res = Message('RSP_K11')
        res.MSH.MSH_9 = 'RSP^K11^RSP_K11'
        res.MSA = "MSA|AA"
    finally:
        return res.to_mllp()
def _create_hl7_message(message_name: str, message_type: str) -> Message:
    hl7_set_version("2.5.1")
    m = Message(message_name)
    msg_datetime = datetime.now().strftime("%Y%m%d%H%M%S")
    m.MSH.MSH_7 = msg_datetime
    m.MSH.MSH_9 = message_type
    m.MSH.MSH_10 = uuid4().hex
    m.MSH.MSH_11 = "T"
    m.MSH.MSH_16 = "AL"

    return m
Beispiel #11
0
    def reply(message):
        """
        Parse the incoming message and return the ER7 encoded response

        :param message: incoming message
        :return: response encoded to ER7 - it can be a NAK or RSP_K11 message
        """
        print("Received by LIP", repr(message))

        try:
            # parse the incoming message
            m = parse_message(message, find_groups=False)
        except:
            print('parsing failed', repr(message))
            response = LIP.nak()
        else:
            print("Message type:", m.MSH.message_type.to_er7())
            print("Message content:", repr(m.to_er7()))
            if m.MSH.MSH_9.MSH_9_3.to_er7() == 'QBP_Q11':
                # create a new RSP_K11 message
                response = Message("RSP_K11")
                response.MSH.MSH_9 = "RSP^K11^RSP_K11"
                # add MSA segment
                response.MSA = "MSA|AA"
                response.MSA.MSA_2 = m.MSH.MSH_10
                # create a QAK segment
                qak = Segment("QAK")
                qak.qak_1 = m.QPD.QPD_2
                qak.qak_2 = "OK"
                qak.qak_3 = "Q22^Specimen Labeling Instructions^IHE_LABTF"
                qak.qak_4 = "1"
                # add the QAK segment to the RSP_K11 message
                response.add(qak)
                # copy the QPD segment from the incoming message
                response.QPD = m.QPD
                # create a PID segment
                response.PID.PID_1 = '1'
                response.PID.PID_5.PID_5_1 = 'PATIENT_SURNAME'
                response.PID.PID_5.PID_5_2 = 'PATIENT_NAME'
                response.PID.PID_6 = "19800101"
                response.PID.PID_7 = "F"
                # create a SPM segment
                spm = Segment("SPM")
                # create an OBR segment
                obr = Segment("OBR")
                spm.SPM_1 = '1'
                spm.SPM_2 = "12345"
                obr.OBR_4 = "ORDER^DESCRIPTION"
                # add spm and obr to the RSP_K11 response
                response.add(spm)
                response.add(obr)
            else:
                response = LIP.nak(m)
        return response.to_mllp()  # encode to ER7
Beispiel #12
0
def enviar(patient_id):
    # cria uma mensagem de consulta QBP_Q11 de acordo com o id do paciente
    m = Message("QBP_Q11")
    m.MSH.sending_application = "Cliente"
    m.MSH.receiving_application = "Servidor"
    m.MSH.MSH_9 = "QBP^SLI^QBP_Q11"
    m.MSH.MSH_10 = uuid.uuid4().hex
    m.QPD.QPD_1 = "SLI^Specimen Labeling Instructions^IHE_LABTF"
    m.QPD.query_tag = uuid.uuid4().hex
    m.QPD.QPD_3 = patient_id
    m.RCP = "RCP|I||R"
    return m.to_mllp()
Beispiel #13
0
 def send(patient_id):
     # create a QBP_Q11 query message for the given patient_id
     m = Message("QBP_Q11")
     m.MSH.sending_application = "LB module"  # same as m.msh.msh_3
     m.MSH.receiving_application = "LIP module"  # same as m.msh.msh_5
     m.MSH.MSH_9 = "QBP^SLI^QBP_Q11"
     m.MSH.MSH_10 = uuid.uuid4().hex
     m.QPD.QPD_1 = "SLI^Specimen Labeling Instructions^IHE_LABTF"
     m.QPD.query_tag = uuid.uuid4().hex
     m.QPD.QPD_3 = patient_id
     m.RCP = "RCP|I||R"
     return m.to_mllp()
Beispiel #14
0
 def test_to_string_msh_field_v27_no_truncation(self):
     for v in ('2.7', '2.8', '2.8.1', '2.8.2'):
         m = Message('OML_O33',
                     encoding_chars=DEFAULT_ENCODING_CHARS,
                     version=v)
         msh = m.msh
         self.assertEqual(msh.msh_1.to_er7(), '|')
         self.assertEqual(msh.msh_2.to_er7(), '^~\\&')
         msh_1 = Field('MSH_1')
         msh_2 = Field('MSH_2')
         self.assertRaises(IndexError, msh_1.to_er7)
         self.assertRaises(IndexError, msh_2.to_er7)
Beispiel #15
0
    def nak(message):
        """
        Build a NAK response for the incoming message

        :param message: incoming message
        :return: a NAK message
        """
        response = Message("ACK")
        response.MSH.MSH_9 = "ACK"
        response.MSA.MSA_1 = "AE"
        response.MSA.MSA_2 = message.MSH.MSH_10
        response.MSA.MSA_3 = "Message type not supported"
        return response
Beispiel #16
0
def make_hl7(filename):
    messages = []
    with open(filename, newline='', encoding='utf-8-sig') as f:
        reader = csv.reader(f, delimiter=',', quotechar='|')
        for row in reader:
            m = Message("ADT_A01", version='2.7')
            m.msh.msh_3 = row[0]
            m.pid.pid_3.pid_3_1 = row[1]
            m.pid.pid_3.pid_3_2 = row[2]
            m.pid.pid_3.pid_3_3 = row[3]
            m.pid.pid_3.pid_3_4 = row[4]
            m.pid.pid_5.pid_5_1 = row[5]
            m.pid.pid_5.pid_5_2 = row[6]
            m.pid.pid_5.pid_5_3 = row[7]
            messages.append(m)
    return messages
Beispiel #17
0
    def reply(self):

        if isinstance(self.exc, UnsupportedMessageType):
            err_code, err_msg = 101, 'Unsupported message'
        elif isinstance(self.exc, InvalidHL7Message):
            err_code, err_msg = 102, 'Incoming message is not an HL7 valid message'
        else:
            err_code, err_msg = 100, 'Unknown error occurred'

        parsed_message = parse_message(self.incoming_message)

        m = Message("ACK")
        m.MSH.MSH_9 = "ACK^ACK"
        m.MSA.MSA_1 = "AR"
        m.MSA.MSA_2 = parsed_message.MSH.MSH_10
        m.ERR.ERR_1 = "%s" % err_code
        m.ERR.ERR_2 = "%s" % err_msg

        return m.to_mllp()
 listenerSocket.listen(1)
 inSock, addr = listenerSocket.accept()
 #inSock.settimeout(5.0)
 print("Got inbound connection from {}".format(addr))
 while True:
     oneMsg = receiveOneMsg(inSock)
     try:
         m = parse_message(oneMsg)
         try:
             msgType = m.children.get("MSH").children.get("MSH_9").value
             if msgType == "ACK^R41":
                 print("Got ACK {}".format(pretty(m)))
             elif msgType == "ORU^R40^ORU_R40":
                 seg1 = _getObxSegment(m, 1)
                 alarmTypeTxt = seg1.children.get("OBX_3").value
                 answer = Message(version="2.7")
                 if alarmTypeTxt == "196614^MDC_EVT_ACTIVE^MDC":
                     # answer with ack
                     print("************ Got Heartbeat ************")
                     print("Full message {}: \n{}".format(
                         datetime.now(), pretty(m)))
                     answer.msh.children.get("MSH_9").value = "ACK^R40"
                     answer.msa.children.get("MSA_1").value = "CA"
                     corId = m.msh.children.get("MSH_10").value
                     answer.msa.children.get("MSA_2").value = corId
                 else:
                     # answer with pcd-05 message
                     print("************ Got Alarm {} ************".format(
                         alarmTypeTxt))
                     print("Full message {}: \n{}".format(
                         datetime.now(), pretty(m)))
Beispiel #19
0
def parse_message(message, validation_level=None, find_groups=True, message_profile=None, report_file=None,
                  force_validation=False):
    """
    Parse the given ER7-encoded message and return an instance of :class:`Message <hl7apy.core.Message>`.

    :type message: ``str``
    :param message: the ER7-encoded message to be parsed

    :type validation_level: ``int``
    :param validation_level: the validation level. Possible values are those defined in
        :class:`VALIDATION_LEVEL <hl7apy.consts.VALIDATION_LEVEL>` class or ``None`` to use the default
        validation level (see :func:`set_default_validation_level <hl7apy.set_default_validation_level>`)

    :type find_groups: ``bool``
    :param find_groups: if ``True``, automatically assign the segments found to the appropriate
        :class:`Groups <hl7apy.core.Group>` instances. If ``False``, the segments found are assigned as
        children of the :class:`Message <hl7apy.core.Message>` instance
        
    :type force_validation: ``bool``
    :type force_validation: if ``True``, automatically forces the message validation after the end of the parsing

    :return: an instance of :class:`Message <hl7apy.core.Message>`

    >>> message = "MSH|^~\&|GHH_ADT||||20080115153000||OML^O33^OML_O33|0123456789|P|2.5||||AL\\rPID|1||" \
    "566-554-3423^^^GHH^MR||EVERYMAN^ADAM^A|||M|||2222 HOME STREET^^ANN ARBOR^MI^^USA||555-555-2004|||M\\r"
    >>> m = parse_message(message)
    >>> print(m)
    <Message OML_O33>
    >>> print(m.msh.sending_application.to_er7())
    GHH_ADT
    >>> print(m.children)
    [<Segment MSH>, <Group OML_O33_PATIENT>]
    """
    message = message.lstrip()
    encoding_chars, message_structure, version = get_message_info(message)

    validation_level = _get_validation_level(validation_level)

    try:
        reference = message_profile[message_structure] if message_profile else None
    except KeyError:
        raise MessageProfileNotFound()

    try:
        m = Message(name=message_structure, reference=reference, version=version,
                    validation_level=validation_level, encoding_chars=encoding_chars)
    except InvalidName:
        m = Message(version=version, validation_level=validation_level,
                    encoding_chars=encoding_chars)
    children = parse_segments(message, m.version, encoding_chars, validation_level,
                              m.structure_by_name)
    if m.name is not None and find_groups:
        m.children = []
        create_groups(m, children, validation_level)
    else:
        m.children = children

    if force_validation:
        if message_profile is None:
            Validator.validate(m, report_file=report_file)
        else:
            Validator.validate(m, message_profile[message_structure], report_file=report_file)

    return m
Beispiel #20
0
 def __init__(self):
     self.m = Message()
 def __init__(self):
     self._myMsgControlIdIter = 0
     self._ORU_R40 = Message(version="2.6")