Class: Sycl::Array
- Inherits:
-
Array
- Object
- Array
- Sycl::Array
- Defined in:
- lib/sycl.rb
Overview
A Sycl::Array is like an Array, but creating one from an array blesses any child Array or Hash objects into Sycl::Array or Sycl::Hash objects. All the normal Array methods are supported, and automatically promote any inputs into Sycl equivalents. The following example illustrates this:
h = { 'a' => { 'b' => 'Hello, world!' } }
a = Sycl::Array.new
a << h
puts a.first.a.b # outputs 'Hello, world!'
A Sycl::Array supports YAML preprocessing and postprocessing, and having individual nodes marked as being rendered in inline style. YAML output is always sorted, unless individual nodes are marked as being rendered unsorted.
a = Sycl::Array.from_array %w{bravo delta charlie alpha}
a.render_inline!
a.yaml_preprocessor { |x| x.each { |e| e.capitalize! } }
a.yaml_postprocessor { |yaml| yaml.sub(/\A---\s+/, '') }
puts a.first # outputs 'bravo'
puts a.to_yaml # outputs '[Alpha, Bravo, Charlie, Delta]'
Defined Under Namespace
Classes: MockNativeType
Constant Summary collapse
- @@default_sorting =
true
Class Method Summary collapse
-
.[](*args) ⇒ Object
:nodoc:.
-
.default_sorting=(sort) ⇒ Object
Set Default Array Sorting.
-
.from_array(array) ⇒ Object
Create a Sycl::Array from a normal Array, or, really, any object that supports Enumerable#each().
-
.load_file(filename) ⇒ Object
Like Sycl::load_file(), a shortcut method to create a Sycl::Array from loading and parsing YAML from a file.
Instance Method Summary collapse
-
#<<(e) ⇒ Object
:nodoc:.
-
#[]=(*args) ⇒ Object
Make sure that if we write to this array, we promote any inputs to their Sycl equivalents.
-
#collect!(&block) ⇒ Object
:nodoc:.
-
#concat(a) ⇒ Object
:nodoc:.
-
#encode_with(coder) ⇒ Object
:nodoc:.
-
#fill(*args, &block) ⇒ Object
:nodoc:.
-
#initialize(*args) ⇒ Array
constructor
:nodoc:.
-
#insert(i, *args) ⇒ Object
:nodoc:.
-
#map!(&block) ⇒ Object
:nodoc:.
-
#method(sym) ⇒ Object
:nodoc:.
-
#push(*args) ⇒ Object
:nodoc:.
-
#render_inline! ⇒ Object
Make this array, and its children, rendered in inline/flow style.
-
#render_sorted! ⇒ Object
Sort this array when it is rendered as YAML.
-
#render_unsorted! ⇒ Object
Do not sort this array when it is rendered as YAML.
-
#render_values_inline! ⇒ Object
Keep rendering this array in block (multi-line) style, but, make this array’s children rendered in inline/flow style.
-
#replace(a) ⇒ Object
:nodoc:.
-
#to_yaml(opts = {}) ⇒ Object
Render this object as YAML.
-
#unshift(*args) ⇒ Object
:nodoc:.
-
#yaml_postprocess(yaml) ⇒ Object
:nodoc:.
-
#yaml_postprocessor(&block) ⇒ Object
Set a postprocessor hook which runs after YML is dumped, for example, via to_yaml() or Sycl::dump().
-
#yaml_preprocess! ⇒ Object
:nodoc:.
-
#yaml_preprocessor(&block) ⇒ Object
Set a preprocessor hook which runs before each time YAML is dumped, for example, via to_yaml() or Sycl::dump().
Constructor Details
#initialize(*args) ⇒ Array
:nodoc:
130 131 132 133 134 135 136 |
# File 'lib/sycl.rb', line 130 def initialize(*args) # :nodoc: @yaml_preprocessor = nil @yaml_postprocessor = nil @yaml_style = nil @render_sorted = @@default_sorting super end |
Class Method Details
.[](*args) ⇒ Object
:nodoc:
138 139 140 |
# File 'lib/sycl.rb', line 138 def self.[](*args) # :nodoc: Sycl::Array.from_array super end |
.default_sorting=(sort) ⇒ Object
166 167 168 |
# File 'lib/sycl.rb', line 166 def self.default_sorting=(sort) @@default_sorting = sort end |
.from_array(array) ⇒ Object
Create a Sycl::Array from a normal Array, or, really, any object that supports Enumerable#each(). Every child Array or Hash gets promoted to a Sycl::Array or Sycl::Hash.
153 154 155 156 157 |
# File 'lib/sycl.rb', line 153 def self.from_array(array) # :nodoc: retval = Sycl::Array.new array.each { |e| retval << Sycl::from_object(e) } retval end |
.load_file(filename) ⇒ Object
Like Sycl::load_file(), a shortcut method to create a Sycl::Array from loading and parsing YAML from a file.
145 146 147 |
# File 'lib/sycl.rb', line 145 def self.load_file(filename) Sycl::Array.from_array YAML::load_file filename end |
Instance Method Details
#<<(e) ⇒ Object
:nodoc:
183 184 185 186 187 188 |
# File 'lib/sycl.rb', line 183 def <<(e) # :nodoc: unless e.is_a?(Sycl::Hash) || e.is_a?(Sycl::Array) e = Sycl::from_object(e) end super end |
#[]=(*args) ⇒ Object
Make sure that if we write to this array, we promote any inputs to their Sycl equivalents. This lets dot notation, styled YAML, and other Sycl goodies continue.
175 176 177 178 179 180 181 |
# File 'lib/sycl.rb', line 175 def []=(*args) # :nodoc: raise ArgumentError => 'wrong number of arguments' unless args.size > 1 unless args[-1].is_a?(Sycl::Hash) || args[-1].is_a?(Sycl::Array) args[-1] = Sycl::from_object(args[-1]) end super end |
#collect!(&block) ⇒ Object
:nodoc:
190 191 192 |
# File 'lib/sycl.rb', line 190 def collect!(&block) # :nodoc: super { |o| Sycl::from_object(block.call o) } end |
#concat(a) ⇒ Object
:nodoc:
198 199 200 201 |
# File 'lib/sycl.rb', line 198 def concat(a) # :nodoc: a = Sycl::Array.from_array(a) unless a.is_a?(Sycl::Array) super end |
#encode_with(coder) ⇒ Object
:nodoc:
389 390 391 392 |
# File 'lib/sycl.rb', line 389 def encode_with(coder) # :nodoc: coder.style = Psych::Nodes::Sequence::FLOW if @yaml_style == :inline coder.represent_seq nil, sort end |
#fill(*args, &block) ⇒ Object
:nodoc:
203 204 205 206 207 208 209 210 211 212 213 |
# File 'lib/sycl.rb', line 203 def fill(*args, &block) # :nodoc: raise ArgumentError => 'wrong number of arguments' if args.empty? if block_given? super { |idx| Sycl::from_object(block.call idx) } else unless args[0].is_a?(Sycl::Hash) || args[0].is_a?(Sycl::Array) args[0] = Sycl::from_object(args[0]) end super end end |
#insert(i, *args) ⇒ Object
:nodoc:
215 216 217 218 219 220 221 222 223 |
# File 'lib/sycl.rb', line 215 def insert(i, *args) # :nodoc: raise ArgumentError => 'wrong number of arguments' if args.empty? args.collect! do |o| unless o.is_a?(Sycl::Hash) || o.is_a?(Sycl::Array) o = Sycl::from_object(o) end end super end |
#map!(&block) ⇒ Object
:nodoc:
194 195 196 |
# File 'lib/sycl.rb', line 194 def map!(&block) # :nodoc: super { |o| Sycl::from_object(block.call o) } end |
#method(sym) ⇒ Object
:nodoc:
352 353 354 |
# File 'lib/sycl.rb', line 352 def method(sym) # :nodoc: sym == :to_yaml ? MockNativeType.new : super end |
#push(*args) ⇒ Object
:nodoc:
225 226 227 228 229 230 231 232 233 |
# File 'lib/sycl.rb', line 225 def push(*args) # :nodoc: raise ArgumentError => 'wrong number of arguments' if args.empty? args.collect! do |o| unless o.is_a?(Sycl::Hash) || o.is_a?(Sycl::Array) o = Sycl::from_object(o) end end super end |
#render_inline! ⇒ Object
Make this array, and its children, rendered in inline/flow style. The default is to render arrays in block (multi-line) style.
Example:
a = Sycl::Array::from_array %w{one two}
a.yaml_postprocessor { |yaml| yaml.sub(/\A---\s+/, '') }
puts a.to_yaml # output: "- one\n- two"
a.render_inline!
puts a.to_yaml # output: '[one, two]'
263 264 265 |
# File 'lib/sycl.rb', line 263 def render_inline! @yaml_style = :inline end |
#render_sorted! ⇒ Object
Sort this array when it is rendered as YAML. Useful when the default_sorting has been set to false and arrays should be sorted.
298 299 300 |
# File 'lib/sycl.rb', line 298 def render_sorted! @render_sorted = true end |
#render_unsorted! ⇒ Object
Do not sort this array when it is rendered as YAML. Usually we want elements sorted so that diffs are human-readable, however, there are certain cases where array ordering is significant (for example, a sorted list of queues).
291 292 293 |
# File 'lib/sycl.rb', line 291 def render_unsorted! @render_sorted = false end |
#render_values_inline! ⇒ Object
Keep rendering this array in block (multi-line) style, but, make this array’s children rendered in inline/flow style.
Example:
a = Sycl::Array::from_array ['one', {'two' => ['three']}]
a.yaml_postprocessor { |yaml| yaml.sub(/\A---\s+/, '') }
a.render_values_inline!
puts a.to_yaml # output: "- one\n- two: [three]"
a.render_inline!
puts a.to_yaml # output: '[one, {two: [three]}]'
280 281 282 283 284 |
# File 'lib/sycl.rb', line 280 def render_values_inline! self.each do |e| e.render_inline! if e.respond_to?(:render_inline!) end end |
#replace(a) ⇒ Object
:nodoc:
235 236 237 238 |
# File 'lib/sycl.rb', line 235 def replace(a) # :nodoc: a = Sycl::Array.from_array(a) unless a.is_a?(Sycl::Array) super end |
#to_yaml(opts = {}) ⇒ Object
Render this object as YAML. Before rendering, run the object through any yaml_preprocessor() code block. After rendering, filter the YAML text through any yaml_postprocessor() code block.
Nodes marked with render_inline!() or render_values_inline!() will be output in flow/inline style, all hashes and arrays will be sorted, and we set a long line width to more or less support line wrap under the Psych library.
366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 |
# File 'lib/sycl.rb', line 366 def to_yaml(opts = {}) yaml_preprocess! if defined?(YAML::ENGINE) && YAML::ENGINE.yamler == 'psych' opts ||= {} opts[:line_width] ||= 999999 # Psych doesn't let you disable line wrap yaml = super else yaml = YAML::quick_emit(self, opts) do |out| if @render_sorted out.seq(nil, @yaml_style || to_yaml_style) do |seq| sort.each { |e| seq.add(e) } end else out.seq(nil, @yaml_style || to_yaml_style) do |seq| each { |e| seq.add(e) } end end end end yaml_postprocess yaml end |
#unshift(*args) ⇒ Object
:nodoc:
240 241 242 243 244 245 246 247 248 |
# File 'lib/sycl.rb', line 240 def unshift(*args) # :nodoc: raise ArgumentError => 'wrong number of arguments' if args.empty? args.collect! do |o| unless o.is_a?(Sycl::Hash) || o.is_a?(Sycl::Array) o = Sycl::from_object(o) end end super end |
#yaml_postprocess(yaml) ⇒ Object
:nodoc:
337 338 339 |
# File 'lib/sycl.rb', line 337 def yaml_postprocess(yaml) # :nodoc: @yaml_postprocessor ? @yaml_postprocessor.call(yaml) : yaml end |
#yaml_postprocessor(&block) ⇒ Object
Set a postprocessor hook which runs after YML is dumped, for example, via to_yaml() or Sycl::dump(). The hook is a block that gets the YAML text string as an argument, and returns a new, possibly different, YAML text string.
A common example use case is to suppress the initial document separator, which is just visual noise when humans are viewing or editing a single YAML file:
a.yaml_postprocessor { |yaml| yaml.sub(/\A---\s+/, '') }
Your conventions might also prohibit trailing whitespace, which at least the Syck library will tack on the end of YAML hash keys:
a.yaml_postprocessor { |yaml| yaml.gsub(/:\s+$/, '') }
329 330 331 |
# File 'lib/sycl.rb', line 329 def yaml_postprocessor(&block) @yaml_postprocessor = block if block_given? end |
#yaml_preprocess! ⇒ Object
:nodoc:
333 334 335 |
# File 'lib/sycl.rb', line 333 def yaml_preprocess! # :nodoc: @yaml_preprocessor.call(self) if @yaml_preprocessor end |
#yaml_preprocessor(&block) ⇒ Object
Set a preprocessor hook which runs before each time YAML is dumped, for example, via to_yaml() or Sycl::dump(). The hook is a block that gets the object itself as an argument. The hook can then set render_inline!() or similar style arguments, prune nil or empty leaf values from hashes, or do whatever other styling needs to be done before a Sycl object is rendered as YAML.
309 310 311 |
# File 'lib/sycl.rb', line 309 def yaml_preprocessor(&block) @yaml_preprocessor = block if block_given? end |