This topic contains 0 replies, has 1 voice, and was last updated by  lev 3 years, 8 months ago.

How to split long report into fields of limited length

  • Quite often we have long report text in single field and have to split it to lines shorter than field length limit, to match limits of field length in say OBX-5 field.

    Having said that, the function splitText() below is universally good to split any type of ASCII text to lines shorter than length limit.

    In this example we take complete report from original single OBX-5 field as bulk text, and split it into chunks shorter than length limit, without changing the text, not even original ‘new lines’.

    Sometimes ‘new line’ in original text is indicated by tilde character, which is interpreted as repetitions of OBX-5 field.

    Sometimes ‘new line’ in original text is indicated by or or combination of both.

    We preserve all and any of above four cases for original text content.

    In this example, for each, less than N characters of length chunk of original text, we add another OBX segment to outbound HL7 message. Each such chunk of text is placed into OBX-5 field of next respective segment.

    Here is function splitText():

    function splitText(s, RS, max)
       -- split text into chunks of MAX length
       local function _g(s, i, c, RS) 
          -- recursively split text 
          local function _f(s , i, c)      
             -- recursively find words and add each word to a chunk     
             local w, i = findWord(s, i)                
             if i == #s then return c..w end
             if  #(c..w) < max  then
                c = c..w 
                s = s:sub(i + 1,#s,true)
                return _f(s, 1, c)
                return c
          RS[#RS + 1] = _f(s,1,'')
          i = i + #RS[#RS]      
          if i < #s then 
             local s = s:sub(i, #s, true)
             return _g(s, 1, '', RS)    
             return RS          
       return _g(s, 1, '', RS)

    Function splitText() is using helper function findWord()

    local function findWord(s, i)
       -- find first word in given text
       local j = i + 1
       while not _isWhite(s:byte(j)) and j < #s do
          j = j + 1
       return s:sub(i,j), j

    And here is complete example how we call it from main() to add OBX segments to our sample HL7 message

    function main(Data)
       local MAX = 81 -- we wish to have maximum of 80 characters per line
       local In,Name = hl7.parse{vmd='Untitled.vmd', data=Data}
       local Out = hl7.message{vmd='Untitled.vmd', name=Name}
       -- in this example we have only 1st repetition of Observation, with very long OBX-5
       local RS = {} 
       RS = splitText(In.Observation[1].OBX[1][5]:S(), RS, MAX)
       for i = 1,#RS do   
          Out.Observation[1].OBX[i][1] = i
          Out.Observation[1].OBX[i][2] = 'TX'
          Out.Observation[1].OBX[i][3][1] = In.Observation[1].OBX[1][3][1]
          Out.Observation[1].OBX[i][5][1] = RS[i]
       return Out

    And a complete Project file for impatient 🙂

    You must be logged in to view attached files.

You must be logged in to reply to this topic.