Class: IOStreams::Builder

Inherits:
Object
  • Object
show all
Defined in:
lib/io_streams/builder.rb

Overview

Build the streams that need to be applied to a path druing reading or writing.

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(file_name = nil) ⇒ Builder

Returns a new instance of Builder.



7
8
9
10
11
# File 'lib/io_streams/builder.rb', line 7

def initialize(file_name = nil)
  @file_name = file_name
  @streams   = nil
  @options   = nil
end

Instance Attribute Details

#file_nameObject

Returns the value of attribute file_name.



4
5
6
# File 'lib/io_streams/builder.rb', line 4

def file_name
  @file_name
end

#optionsObject (readonly)

Returns the value of attribute options.



5
6
7
# File 'lib/io_streams/builder.rb', line 5

def options
  @options
end

#streamsObject (readonly)

Returns the value of attribute streams.



5
6
7
# File 'lib/io_streams/builder.rb', line 5

def streams
  @streams
end

Instance Method Details

#option(stream, **options) ⇒ Object

Supply an option that is only applied once the file name extensions have been parsed. Note:

  • Cannot set both ‘stream` and `option`

Raises:

  • (ArgumentError)


16
17
18
19
20
21
22
23
24
25
26
27
28
29
# File 'lib/io_streams/builder.rb', line 16

def option(stream, **options)
  stream = stream.to_sym unless stream.is_a?(Symbol)
  raise(ArgumentError, "Invalid stream: #{stream.inspect}") unless IOStreams.extensions.include?(stream)
  raise(ArgumentError, "Cannot call both #option and #stream on the same streams instance}") if @streams
  raise(ArgumentError, "Cannot call #option unless the `file_name` was already set}") unless file_name

  @options ||= {}
  if opts = @options[stream]
    opts.merge!(options)
  else
    @options[stream] = options.dup
  end
  self
end

#option_or_stream(stream, **options) ⇒ Object



51
52
53
54
55
56
57
58
59
# File 'lib/io_streams/builder.rb', line 51

def option_or_stream(stream, **options)
  if streams
    stream(stream, **options)
  elsif file_name
    option(stream, **options)
  else
    stream(stream, **options)
  end
end

#pipelineObject

Returns [Hash<Symbol:Hash>] the pipeline of streams with their options that will be applied when the reader or writer is invoked.



77
78
79
80
81
82
83
84
85
86
87
88
# File 'lib/io_streams/builder.rb', line 77

def pipeline
  return streams.dup.freeze if streams
  return {}.freeze unless file_name

  built_streams          = {}
  # Encode stream is always first
  built_streams[:encode] = options[:encode] if options&.key?(:encode)

  opts = options || {}
  parse_extensions.each { |stream| built_streams[stream] = opts[stream] || {} }
  built_streams.freeze
end

#reader(io_stream, &block) ⇒ Object



67
68
69
# File 'lib/io_streams/builder.rb', line 67

def reader(io_stream, &block)
  execute(:reader, pipeline, io_stream, &block)
end

#setting(stream) ⇒ Object

Return the options set for either a stream or option.



62
63
64
65
# File 'lib/io_streams/builder.rb', line 62

def setting(stream)
  return streams[stream] if streams
  options[stream] if options
end

#stream(stream, **options) ⇒ Object

Raises:

  • (ArgumentError)


31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
# File 'lib/io_streams/builder.rb', line 31

def stream(stream, **options)
  stream = stream.to_sym unless stream.is_a?(Symbol)
  raise(ArgumentError, "Cannot call both #option and #stream on the same streams instance}") if @options

  # To prevent any streams from being applied supply a stream named `:none`
  if stream == :none
    @streams = {}
    return self
  end
  raise(ArgumentError, "Invalid stream: #{stream.inspect}") unless IOStreams.extensions.include?(stream)

  @streams ||= {}
  if opts = @streams[stream]
    opts.merge!(options)
  else
    @streams[stream] = options.dup
  end
  self
end

#writer(io_stream, &block) ⇒ Object



71
72
73
# File 'lib/io_streams/builder.rb', line 71

def writer(io_stream, &block)
  execute(:writer, pipeline, io_stream, &block)
end