Class: WAB::Impl::Configuration

Inherits:
Object
  • Object
show all
Defined in:
lib/wab/impl/configuration.rb

Overview

Handles the configuration for a Shell Implementation and the Ruby Runner

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(usage, options) ⇒ Configuration

Returns a new instance of Configuration.



14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# File 'lib/wab/impl/configuration.rb', line 14

def initialize(usage, options)
  @map = {}
  opts = OptionParser.new(usage)
  config_file = nil
  log_level = Logger::WARN
  
  opts.on('-c', '--config PATH', String, 'Configuration file.') { |c| config_file = c }
  opts.on('-r', '--require LIBRARY', String, 'Require.')        { |r| require r }
  opts.on('-v', '--verbose', 'Increase verbosity.')             { log_level += 1 }
  opts.on('-h', '--help', 'Show this display.')                 { puts opts.help; Process.exit!(0) }

  # Process command-line arguments and append them, in order, to an empty hash @map
  add_options(opts, options)

  modes = opts.parse(ARGV)
  @map[:mode] = 0 < modes.length ? modes[0] : 'run'
  @map[:rest] =  modes[1..-1] if 1 < modes.length

  unless ['run', 'new', 'init'].include?(@map[:mode])
    puts "\n*-*-* #{@map[:mode]} is not a valid mode"
    puts opts.help
    Process.exit!(-1)
  end

  # Move the @map sideways and replace with defaults.
  command_line_map = @map
  @map = {}
  build_default_map(options)

  config_file = './config/wabur.conf' if config_file.nil?

  # Load it and merge th econfig file into @map.
  @map = merge_map(@map, parse_config_file(config_file))

  # Merge in the command line map.
  @map = merge_map(@map, command_line_map) unless command_line_map.empty?
end

Instance Attribute Details

#mapObject

Returns the value of attribute map.



12
13
14
# File 'lib/wab/impl/configuration.rb', line 12

def map
  @map
end

Instance Method Details

#add_options(opts, options, path = '') ⇒ Object

Walks the options map and calls opts.on for each option so that all are provided when --help is called.



54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
# File 'lib/wab/impl/configuration.rb', line 54

def add_options(opts, options, path='')
  options.each_pair { |k,v|
    next unless v.is_a?(Hash)
    key_path = path.empty? ? k.to_s : "#{path}.#{k}"
    if v.has_key?(:val)
      default = v[:val]
      switch = "--#{key_path} #{v[:arg]}"
      doc_with_default = "#{v[:doc]} Default: #{default}"
      if default.is_a?(Array)
        if v.has_key?(:short)
          opts.on(v[:short], switch, String, v[:doc]) { |val| arg_append(key_path, val, v[:parse]) }
        else
          opts.on(switch, String, v[:doc]) { |val| arg_append(key_path, val, v[:parse]) }
        end
      elsif v.has_key?(:short)
        opts.on(v[:short], switch, v[:type], doc_with_default) { |val| set(key_path, val) }
      else 
        opts.on(switch, v[:type], doc_with_default) { |val| set(key_path, val) }
      end
    else
      add_options(opts, v, key_path)
    end
  }
end

#arg_append(path, val, parse) ⇒ Object

Appends an arg to an array in the configuration.



80
81
82
83
84
85
86
87
88
89
90
91
92
# File 'lib/wab/impl/configuration.rb', line 80

def arg_append(path, val, parse)
  parts = val.split('=')
  if 1 < parts.length
    val = {}
    parse.each_index { |i| val[parse[i].to_sym] = parts[i] }
  end
  a = get(path)
  if a.nil?
    a = []
    set(path, a)
  end
  a.push(val)
end

#build_default_map(options, path = '') ⇒ Object

Builds a map from the default options passed in.



95
96
97
98
99
100
101
102
103
104
105
# File 'lib/wab/impl/configuration.rb', line 95

def build_default_map(options, path='')
  options.each_pair { |k,v|
    next unless v.is_a?(Hash)
    key_path = path.empty? ? k.to_s : "#{path}.#{k}"
    if v.has_key?(:val)
      set(key_path, v[:val])
    else
      build_default_map(v, key_path)
    end
  }
end

#get(path) ⇒ Object Also known as: []



177
178
179
# File 'lib/wab/impl/configuration.rb', line 177

def get(path)
  Utils.get_node(@map, path)
end

#merge_map(prime, other) ⇒ Object

Recursive merge of other into prime.



108
109
110
111
112
113
114
115
116
117
118
119
# File 'lib/wab/impl/configuration.rb', line 108

def merge_map(prime, other)
  prime.merge(other) { |key,prime_value,other_value|
    case prime_value
    when Hash
      merge_map(prime_value, other_value)
    when Array
      prime_value + other_value
    else
      other_value
    end
  }
end

#parse_conf_file(file) ⇒ Object

Returns a Hash containing data obtained by parsing a UNIX style conf file.

For example, handler.sample.count = 63 and handler.sample.path = /v1 will be parsed into the following:

{ handler: { sample: { count: 63, path: "/v1" } } }


153
154
155
156
157
158
159
160
161
162
163
164
165
# File 'lib/wab/impl/configuration.rb', line 153

def parse_conf_file(file)
  config = {}

  File.open(File.expand_path(file)) do |f|
    f.each_line do |line|
      line.strip!
      next if line.empty? || line.start_with?('#')
      key, value = line.split('=').map(&:strip)
      set_map(config, key, value)
    end
  end
  config
end

#parse_config_file(file) ⇒ Object

Returns a Hash of configuration data.

TBD: Add validation to ensure only a Hash object is returned



124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
# File 'lib/wab/impl/configuration.rb', line 124

def parse_config_file(file)
  return {} unless File.exist?(file)

  case File.extname(file)
  when /\.conf$/i
    parse_conf_file(file)
  when /\.json$/i
    Oj.load_file(file, mode: :strict, symbol_keys: true)
  when /\.ya?ml$/i
    begin
      require 'safe_yaml/load'
      SafeYAML.load_file(file) || {}
    rescue LoadError
      # Re-raise with a more descriptive message. This should generally
      # abort the configuration loading.
      raise LoadError.new(%{Could not load the requested resource. Please install the 'safe_yaml' gem via
Bundler or directly, and try loading again.
})
    end
  end
end

#set(path, value) ⇒ Object Also known as: []=



172
173
174
# File 'lib/wab/impl/configuration.rb', line 172

def set(path, value)
  set_map(@map, path, value)
end

#set_map(node, path, value) ⇒ Object



167
168
169
170
# File 'lib/wab/impl/configuration.rb', line 167

def set_map(node, path, value)
  return node if path.empty?
  Utils.set_value(node, path, value)
end