Module: XKeys::Set_
Overview
“Private” module for XKeys::Set_* common code
Instance Method Summary collapse
-
#_xkeys_new(key2, info, options) ⇒ Object
Return a new node for node suitable to hold key2.
-
#_xkeys_set(*args, &block) ⇒ Object
Common code for XKeys::Set_Hash and XKeys::Set_Auto.
Instance Method Details
#_xkeys_new(key2, info, options) ⇒ Object
Return a new node for node suitable to hold key2. Either key1 or key2 (or both) may be :[].
187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 |
# File 'lib/xkeys.rb', line 187 def _xkeys_new (key2, info, ) if respond_to? :xkeys_new # Note: #xkeys_new is responsible for cloning extensions # as desired or needed. xkeys_new key2, info, else node = info[:block].call(key2, ) ? [] : {} # Clone XKeys extensions from the root node node.extend XKeys::Get if is_a? XKeys::Get node.extend XKeys::Set_Auto if is_a? XKeys::Set_Auto node.extend XKeys::Set_Hash if is_a? XKeys::Set_Hash node end end |
#_xkeys_set(*args, &block) ⇒ Object
Common code for XKeys::Set_Hash and XKeys::Set_Auto. This method returns true if it is handling the set, or false if the caller should super to handle the set.
_xkeys_set(key1, ..., keyN[, option_hash], value) { |key, options| block }
If the root of the tree responds to the #xkeys_new method, it will be called as follows whenever a new node needs to be created:
xkeys_new(key2, info_hash, option_hash)
where info_hash contains
:node => The current node
:key1 => The key in the current node, or :[]
:block => The block passed to _xkeys_set
The returned new node will be assigned to node (or pushed onto the end of the array) and should be appropriate to accept key2.
Otherwise, the block should return true for array-like keys or false for hash-like keys. An array or hash node will be added accordingly.
If a key is :[], the current node responds to the #push method, and push mode has not been disabled (see below), a new node will be pushed onto the end of the current node.
Options:
:[] => false
Disable :[] push mode
141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 |
# File 'lib/xkeys.rb', line 141 def _xkeys_set (*args, &block) if args[-2].is_a?(Hash) then , last = args[-2], -3 else , last = {}, -2 end push_mode = [:[]] != false if args.count + last == 0 if args[0] == :[] && push_mode && respond_to?(:push) push args[-1] # array[:[]] = value true # done--don't caller-super else false # use caller-super to do it end else # root[key1, ..., keyN[, option_hash]] = value (node, key) = args[1..last].inject([self, args[0]]) do |nk1, k2| if nk1[1] == :[] && push_mode && nk1[0].respond_to?(:push) # Push a new node onto an array-like node node = _xkeys_new(k2, { :node => nk1[0], :key1 => nk1[1], :block => block }, ) nk1[0].push node [node, k2] elsif nk1[0][nk1[1]].nil? # Auto-vivify the specified key/index node = _xkeys_new(k2, { :node => nk1[0], :key1 => nk1[1], :block => block }, ) nk1[0][nk1[1]] = node [node, k2] else # Traverse an existing node [nk1[0][nk1[1]], k2] end end # Assign (or push) according to the final key. if key == :[] && push_mode && node.respond_to?(:push) node.push args[-1] else node[key] = args[-1] end true # done--don't caller-super end end |