Module: Yamlr::Reader::Builder

Defined in:
lib/yamlr/reader/builder.rb

Defined Under Namespace

Classes: RootNodeError

Class Method Summary collapse

Class Method Details

.add_to_list(lst, adr) ⇒ Object

list stores hsh addresses of lines, comments, etc.



222
223
224
225
226
227
228
# File 'lib/yamlr/reader/builder.rb', line 222

def self.add_to_list(lst, adr)
  case adr.class.to_s
  when "String" then x = adr
  when "Array" then  x = adr.join(",")
  end
  lst[lst.length + 1] = x
end

.adr_obj(hsh, adr) ⇒ Object

returns the actual object at an address in tree



104
105
106
107
# File 'lib/yamlr/reader/builder.rb', line 104

def self.adr_obj(hsh, adr)
  m = self.to_adr(adr)
  eval("hsh#{m.to_s}")
end

.adr_obj_to_array(hsh, adr) ⇒ Object

converts an object in tree to empty array



111
112
113
114
# File 'lib/yamlr/reader/builder.rb', line 111

def self.adr_obj_to_array(hsh, adr)
  m = self.to_adr(adr)
  eval("hsh#{m.to_s} = []")
end

.arr_parse(las, adr, val, upd) ⇒ Object

sub-parses array message, and logic from update-method



74
75
76
77
78
79
80
81
# File 'lib/yamlr/reader/builder.rb', line 74

def self.arr_parse(las, adr, val, upd)
  case upd
  when "eq" then self.array_val(las, val)
  when "lt" then self.array_val(las, val)
  when "gt" then self.array_new(las, adr, val)
  else; raise "error"
  end
end

.array_new(las, adr, val) ⇒ Object

new array in tree, provides logic for last modified object



152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
# File 'lib/yamlr/reader/builder.rb', line 152

def self.array_new(las, adr, val)
  case
  when las.is_a?(Array) && las.empty?
    x = [val]
    las = x
    adr << las.rindex(x)
  when las.is_a?(Array) && las.last.is_a?(String) && las.last.empty?
    x = [val]
    las[-1] = [val]
    adr << las.rindex(x)
  when las.is_a?(Array)
    x = [val]
    las << x
    adr << las.rindex(x)
  end
end

.array_val(las, val) ⇒ Object

add val to array in tree



184
185
186
187
188
189
190
191
192
# File 'lib/yamlr/reader/builder.rb', line 184

def self.array_val(las, val)
  case
  # when x is a hash, it's already addressed
  when las.is_a?(Array)
    las << val
  else
    raise las.inspect
  end
end

.blank(lst) ⇒ Object

add blank to list



232
233
234
# File 'lib/yamlr/reader/builder.rb', line 232

def self.blank(lst)
  self.add_to_list(lst, "#BLANK")
end

.build(hsh, phs) ⇒ Object

adds parsed_hash of line to hash



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/yamlr/reader/builder.rb', line 31

def self.build(hsh, phs)
  add = false
  upd = nil
  msg = phs[:msg]
  self.doc_new(hsh) if hsh.empty? && msg != "doc"
  val = phs[:val]
  lst = hsh[:lst]

  unless [:com, :mal, :bla].include?(msg)
    cur = self.cur(hsh)
    key = phs[:key]
    spc = phs[:spc]
    idt = phs[:opt][:indent]
    adr = hsh[:adr]
    idx = self.index(spc, idt)
    upd = self.update(adr, idx)
    las = self.adr_obj(hsh, hsh[:adr])
    add = true
  end

  case msg
  when :dcs then self.doc_start(hsh)
  when :dct then self.doc_term(hsh)
  when :hpr then self.hsh_pair(las, key, val)
  when :hky then self.hsh_key(las, adr, key)
  when :bla then self.blank(lst)
  when :arr
    raise RootNodeError if cur.is_a?(Hash) && !cur.empty? && spc == 0
    if las.is_a?(Hash) && las.empty?
      self.adr_obj_to_array(hsh, hsh[:adr])
      las = self.adr_obj(hsh, hsh[:adr])
    end
    self.arr_parse(las, adr, val, upd)
  when :com then self.comment(lst, val)
  when :mal then self.malformed(lst, val)
  end

  self.add_to_list(lst, adr) if add
end

.comment(lst, val) ⇒ Object

add comment to list



238
239
240
# File 'lib/yamlr/reader/builder.rb', line 238

def self.comment(lst, val)
  lst[lst.length + 1] = "#COMMENT: #{val}"
end

.cur(hsh) ⇒ Object

current hash, returns array of “doc”



85
86
87
# File 'lib/yamlr/reader/builder.rb', line 85

def self.cur(hsh)
  hsh[hsh.length - 2]
end

.doc_new(hsh) ⇒ Object

create keypair for new doc



141
142
143
144
145
146
147
148
# File 'lib/yamlr/reader/builder.rb', line 141

def self.doc_new(hsh)
  hsh[:lst] ||= {}
  hsh[:adr] ||= []
  len = hsh.length - 1
  hsh[len] = {}
  hsh[:adr].clear
  hsh[:adr] << len
end

.doc_start(hsh) ⇒ Object

start document



171
172
173
174
# File 'lib/yamlr/reader/builder.rb', line 171

def self.doc_start(hsh)
  self.doc_new(hsh)
  self.add_to_list(hsh[:lst], "#DOC_START")
end

.doc_term(hsh) ⇒ Object

document terminate



178
179
180
# File 'lib/yamlr/reader/builder.rb', line 178

def self.doc_term(hsh)
  self.add_to_list(hsh[:lst], "#DOC_TERM")
end

.hsh_key(las, adr, key) ⇒ Object

add hashkey to tree



196
197
198
199
200
201
202
203
204
205
206
# File 'lib/yamlr/reader/builder.rb', line 196

def self.hsh_key(las, adr, key)
  case
  when las.is_a?(Hash)
    las[key] = {}
  when las.is_a?(Array)
    x = {key => {}}
    las << x
    adr << las.rindex(x)
  end
  adr << key
end

.hsh_pair(las, key, val) ⇒ Object

add hashpair to tree



210
211
212
213
214
215
216
217
218
# File 'lib/yamlr/reader/builder.rb', line 210

def self.hsh_pair(las, key, val)
  case
  when las.is_a?(Array)
    x = {key => val}
    las << x
  when las.is_a?(Hash)
    las[key] = val
  end
end

.index(spc, idt) ⇒ Object

calculates index based on spaces divided by indent unit



118
119
120
# File 'lib/yamlr/reader/builder.rb', line 118

def self.index(spc, idt)
  ((spc % idt) != 0) ? 0 : spc / idt
end

.malformed(lst, val) ⇒ Object

add malformed to list



244
245
246
# File 'lib/yamlr/reader/builder.rb', line 244

def self.malformed(lst, val)
  lst[lst.length + 1] = "#MALFORMED: #{val}"
end

.to_adr(adr) ⇒ Object

address array to string usable in eval on root node



91
92
93
94
95
96
97
98
99
100
# File 'lib/yamlr/reader/builder.rb', line 91

def self.to_adr(adr)
  m = adr.map {|x|
    case
    when x.is_a?(Symbol) then "[:#{x}]"
    when x.is_a?(String) then "['#{x}']"
    when x.is_a?(Integer) then "[#{x}]"
    end
  }
  m.join
end

.update(adr, idx) ⇒ Object

if indentation less than before, jump up tree, remove extra indices



124
125
126
127
128
129
130
131
132
133
134
135
136
137
# File 'lib/yamlr/reader/builder.rb', line 124

def self.update(adr, idx)
  ret =  nil
  len = (adr.length - 1)
  if idx < len
    # remove indices after current index
    adr.replace(adr[0..idx])
    ret = "lt"
  elsif idx == len
    ret = "eq"
  elsif idx > len
    ret = "gt"
  end
  ret
end