Class: HL7::Message::Segment

Inherits:
Object
  • Object
show all
Extended by:
SegmentListStorage, TimeFormatterHelper
Includes:
SegmentFields
Defined in:
lib/segment.rb

Overview

Ruby Object representation of an hl7 2.x message segment The segments can be setup to provide aliases to specific fields with optional validation code that is run when the field is modified The segment field data is also accessible via the e<number> method.

Defining a New Segment

class HL7::Message::Segment::NK1 < HL7::Message::Segment
  weight 100 # segments are sorted ascendingly
  add_field :something_you_want       # assumes :idx=>1
  add_field :something_else, :idx=>6  # :idx=>6 and field count=6
  add_field :something_more           # :idx=>7
  add_field :block_example do |value|
     raise HL7::InvalidDataError.new
                                unless value.to_i < 100 && value.to_i > 10
    return value
  end
  # this block will be executed when seg.block_example= is called
  # and when seg.block_example is called

Direct Known Subclasses

AIG, AIL, AIP, AIS, DG1, Default, ERR, EVN, FT1, FTS, GT1, IN1, MFE, MFI, MRG, MSA, MSH, NK1, NTE, OBR, OBX, ORC, ORU, PID, PRD, PRT, PV1, PV2, QRD, QRF, RF1, RGS, ROL, SCH, SFT, SPM, TQ1, TXA

Defined Under Namespace

Classes: AIG, AIL, AIP, AIS, DG1, Default, ERR, EVN, FT1, FTS, GT1, IN1, MFE, MFI, MRG, MSA, MSH, NK1, NTE, OBR, OBX, ORC, ORU, PID, PRD, PRT, PV1, PV2, QRD, QRF, RF1, RGS, ROL, SCH, SFT, SPM, TQ1, TXA

Constant Summary collapse

METHOD_MISSING_FOR_INITIALIZER =
<<-END
  def method_missing( sym, *args, &blk )
    __seg__.send( sym, args, blk )
  end
END

Instance Attribute Summary collapse

Attributes included from SegmentListStorage

#child_types

Instance Method Summary collapse

Methods included from SegmentListStorage

add_child_type

Methods included from TimeFormatterHelper

hl7_formatted_date, hl7_formatted_timestamp

Methods included from SegmentFields

#[], #[]=, #field_info, included, #read_field, #write_field

Constructor Details

#initialize(raw_segment = "", delims = []) {|_self| ... } ⇒ Segment

setup a new HL7::Message::Segment

raw_segment

is an optional String or Array which will be used as the segment’s field data

delims

an optional array of delimiters, where

delims[0] = element delimiter
delims[1] = item delimiter

Yields:

  • (_self)

Yield Parameters:



43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
# File 'lib/segment.rb', line 43

def initialize(raw_segment = "", delims = [], &blk)
  @segments_by_name = {}
  @field_total = 0
  @is_child = false

  setup_delimiters delims

  @elements = elements_from_segment(raw_segment)

  return unless block_given?

  callctx = eval("self", blk.binding, __FILE__, __LINE__)
  def callctx.__seg__(val = nil)
    @__seg_val__ ||= val
  end
  callctx.__seg__(self)
  # TODO: find out if this pollutes the calling namespace permanently...

  eval(METHOD_MISSING_FOR_INITIALIZER, blk.binding)
  yield self
  eval("class << self; remove_method :method_missing;end", blk.binding, __FILE__, __LINE__)
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(sym, *args, &blk) ⇒ Object

handle the e<number> field accessor and any aliases that didn’t get added to the system automatically



97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
# File 'lib/segment.rb', line 97

def method_missing(sym, *args, &blk)
  base_str = sym.to_s.delete("=")
  base_sym = base_str.to_sym

  if self.class.fields.include?(base_sym)
    # base_sym is ok, let's move on
  elsif /e([0-9]+)/ =~ base_str
    # base_sym should actually be $1, since we're going by
    # element id number
    base_sym = $1.to_i
  else
    super
  end

  if sym.to_s.include?("=")
    write_field(base_sym, args)
  elsif args.length.positive?
    write_field(base_sym, args.flatten.select {|arg| arg })
  else
    read_field(base_sym)
  end
end

Instance Attribute Details

#element_delimObject (readonly)

Returns the value of attribute element_delim.



29
30
31
# File 'lib/segment.rb', line 29

def element_delim
  @element_delim
end

#item_delimObject (readonly)

Returns the value of attribute item_delim.



29
30
31
# File 'lib/segment.rb', line 29

def item_delim
  @item_delim
end

#segment_parentObject

Returns the value of attribute segment_parent.



28
29
30
# File 'lib/segment.rb', line 28

def segment_parent
  @segment_parent
end

#segment_weightObject (readonly)

Returns the value of attribute segment_weight.



29
30
31
# File 'lib/segment.rb', line 29

def segment_weight
  @segment_weight
end

Instance Method Details

#<=>(other) ⇒ Object

sort-compare two Segments, 0 indicates equality



121
122
123
124
125
126
127
128
129
130
# File 'lib/segment.rb', line 121

def <=>(other)
  return nil unless other.is_a?(HL7::Message::Segment)

  # per Comparable docs: http://www.ruby-doc.org/core/classes/Comparable.html
  diff = weight - other.weight
  return -1 if diff.positive?
  return 1 if diff.negative?

  0
end

#eachObject

yield each element in the segment



149
150
151
152
153
# File 'lib/segment.rb', line 149

def each # :yields: element
  return unless @elements

  @elements.each { |e| yield e }
end

#elements_from_segment(raw_segment) ⇒ Object

Breaks the raw segment into elements

raw_segment

is an optional String or Array which will be used as the segment’s field data



69
70
71
72
73
74
75
76
77
78
79
80
81
# File 'lib/segment.rb', line 69

def elements_from_segment(raw_segment)
  if raw_segment.is_a? Array
    elements = raw_segment
  else
    elements = HL7::MessageParser.split_by_delimiter(raw_segment,
      @element_delim)
    if raw_segment == ""
      elements[0] = self.class.to_s.split("::").last
      elements << ""
    end
  end
  elements
end

#has_children?Boolean

Returns:

  • (Boolean)


161
162
163
# File 'lib/segment.rb', line 161

def has_children?
  respond_to?(:children)
end

#is_child_segment=(val) ⇒ Object

indicate whether or not the segment has a parent



144
145
146
# File 'lib/segment.rb', line 144

def is_child_segment=(val)
  @is_child_segment = val
end

#is_child_segment?Boolean

return true if the segment has a parent

Returns:

  • (Boolean)


139
140
141
# File 'lib/segment.rb', line 139

def is_child_segment?
  (@is_child_segment ||= false)
end

#lengthObject

get the length of the segment (number of fields it contains)



156
157
158
159
# File 'lib/segment.rb', line 156

def length
  0 unless @elements
  @elements.length
end

#to_infoObject



83
84
85
# File 'lib/segment.rb', line 83

def to_info
  format("%s: empty segment >> %s", self.class.to_s, @elements.inspect)
end

#to_sObject Also known as: to_hl7

output the HL7 spec version of the segment



88
89
90
# File 'lib/segment.rb', line 88

def to_s
  @elements.join(@element_delim)
end

#weightObject

get the defined sort-weight of this segment class an alias for self.weight



134
135
136
# File 'lib/segment.rb', line 134

def weight
  self.class.weight
end