Class: RepoManager::BaseAction
- Inherits:
-
Object
- Object
- RepoManager::BaseAction
- Defined in:
- lib/repo_manager/actions/base_action.rb
Overview
An abstract superclass for basic action functionality
Direct Known Subclasses
Instance Attribute Summary collapse
-
#args ⇒ Object
readonly
args as passed on command line.
-
#configuration ⇒ Object
readonly
main configuration hash.
-
#exit_code ⇒ Object
readonly
numeric exit code set from return of process method.
-
#option_parser ⇒ Object
bin wrapper option parser object.
-
#options ⇒ Object
readonly
options hash, read from configuration hash.
-
#output ⇒ Object
filename to write output.
-
#template ⇒ Object
filename to template for rendering.
Instance Method Summary collapse
- #after_execute ⇒ Object
-
#asset_options ⇒ Object
asset options separated from assets to make it easier to override assets.
-
#asset_type ⇒ Symbol
Used by asset factory to create assets.
-
#assets ⇒ Object
TODO: create items/app_item class with at least the ‘name’ accessor.
-
#before_execute ⇒ Object
callbacks.
- #execute ⇒ Object
-
#help(help_options = {}) ⇒ String
Convert method comments block to help text.
-
#initialize(args = [], config = {}) ⇒ BaseAction
constructor
A new instance of BaseAction.
-
#items ⇒ Array
items to be rendered, defaults to assets, override to suit.
-
#overwrite_output? ⇒ Boolean
True if output doesn’t exist or it is OK to overwrite.
-
#parse_options(parser_configuration = {}) {|option_parser| ... } ⇒ OptionParser
Parse generic action options for all decendant actions.
-
#process ⇒ Object
handle “assets to items” transformations, if any, and write to output.
-
#render(view_options = configuration) ⇒ String
Render items result to a string.
-
#write_to_output(content) ⇒ Object
TODO: add exception handler and pass return values.
Constructor Details
#initialize(args = [], config = {}) ⇒ BaseAction
Returns a new instance of BaseAction.
37 38 39 40 41 42 |
# File 'lib/repo_manager/actions/base_action.rb', line 37 def initialize(args=[], config={}) @configuration = config.deep_clone = @configuration[:options] || {} @args = args.dup logger.debug "initialize with args: #{@args.inspect}" end |
Instance Attribute Details
#args ⇒ Object (readonly)
args as passed on command line
23 24 25 |
# File 'lib/repo_manager/actions/base_action.rb', line 23 def args @args end |
#configuration ⇒ Object (readonly)
main configuration hash
17 18 19 |
# File 'lib/repo_manager/actions/base_action.rb', line 17 def configuration @configuration end |
#exit_code ⇒ Object (readonly)
numeric exit code set from return of process method
32 33 34 |
# File 'lib/repo_manager/actions/base_action.rb', line 32 def exit_code @exit_code end |
#option_parser ⇒ Object
bin wrapper option parser object
35 36 37 |
# File 'lib/repo_manager/actions/base_action.rb', line 35 def option_parser @option_parser end |
#options ⇒ Object (readonly)
options hash, read from configuration hash
20 21 22 |
# File 'lib/repo_manager/actions/base_action.rb', line 20 def end |
#output ⇒ Object
filename to write output
29 30 31 |
# File 'lib/repo_manager/actions/base_action.rb', line 29 def output @output end |
#template ⇒ Object
filename to template for rendering
26 27 28 |
# File 'lib/repo_manager/actions/base_action.rb', line 26 def template @template end |
Instance Method Details
#after_execute ⇒ Object
294 295 296 |
# File 'lib/repo_manager/actions/base_action.rb', line 294 def after_execute logger.debug "callback: after_execute" end |
#asset_options ⇒ Object
asset options separated from assets to make it easier to override assets
185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 |
# File 'lib/repo_manager/actions/base_action.rb', line 185 def # include all base action options result = .deep_clone # anything left on the command line should be filters as all options have # been consumed, for pass through options, filters must be ignored by overwritting them filters = args.dup filters += result[:filter] if result[:filter] result = result.merge(:filter => filters) unless filters.empty? # asset type to create type = result[:type] || asset_type result = result.merge(:type => type) # optional key: :assets_folder, absolute path or relative to config file if :base_folder is specified result = result.merge(:assets_folder => configuration[:folders][:assets]) if configuration[:folders] # optional key: :base_folder is the folder that contains the main config file result = result.merge(:base_folder => File.dirname(configuration[:configuration_filename])) if configuration[:configuration_filename] result end |
#asset_type ⇒ Symbol
Used by asset factory to create assets. Override in app_action.rb or a descendant to set the class to be instantiated by by the AssetManager.
180 181 182 |
# File 'lib/repo_manager/actions/base_action.rb', line 180 def asset_type :app_asset end |
#assets ⇒ Object
TODO: create items/app_item class with at least the ‘name’ accessor
assets: raw configuration handling system for items
171 172 173 174 |
# File 'lib/repo_manager/actions/base_action.rb', line 171 def assets return @assets if @assets @assets = AssetManager.new.assets() end |
#before_execute ⇒ Object
callbacks
290 291 292 |
# File 'lib/repo_manager/actions/base_action.rb', line 290 def before_execute logger.debug "callback: before_execute" end |
#execute ⇒ Object
138 139 140 141 142 143 144 |
# File 'lib/repo_manager/actions/base_action.rb', line 138 def execute before_execute @exit_code = process after_execute @exit_code end |
#help(help_options = {}) ⇒ String
Convert method comments block to help text
243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 |
# File 'lib/repo_manager/actions/base_action.rb', line 243 def help(={}) comment_starting_with = [:comment_starting_with] || "" located_in_file = [:located_in_file] || __FILE__ text = File.read(located_in_file) result = text.match(/(^\s*#\s*#{comment_starting_with}.*)^\s*class .* AppAction/m) result = $1 result = result.gsub(/ @example/, '') result = result.gsub(/ @return \[Number\]/, ' Exit code:') result = result.gsub(/ @return .*/, '') result = result.gsub(/ @see .*$/, '') # strip the leading whitespace, the '#' and space result = result.gsub(/^\s*# ?/, '') # strip surrounding whitespace result.strip end |
#items ⇒ Array
items to be rendered, defaults to assets, override to suit
211 212 213 |
# File 'lib/repo_manager/actions/base_action.rb', line 211 def items assets end |
#overwrite_output? ⇒ Boolean
Returns true if output doesn’t exist or it is OK to overwrite.
263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 |
# File 'lib/repo_manager/actions/base_action.rb', line 263 def overwrite_output? return true unless File.exists?(output) if [:force] logger.debug "overwriting output with --force option" return true end unless STDOUT.isatty logger.debug "TTY not detected, skipping overwrite prompt" return false end result = false print "File '#{output}' exists. Would you like overwrite? [y/n]: " case gets.strip when 'Y', 'y', 'yes' logger.debug "user answered yes to overwrite prompt" result = true else logger.debug "user answered no to overwrite prompt" end result end |
#parse_options(parser_configuration = {}) {|option_parser| ... } ⇒ OptionParser
Parse generic action options for all decendant actions
47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 |
# File 'lib/repo_manager/actions/base_action.rb', line 47 def (parser_configuration = {}) raise_on_invalid_option = parser_configuration.has_key?(:raise_on_invalid_option) ? parser_configuration[:raise_on_invalid_option] : true = parser_configuration.has_key?(:parse_base_options) ? parser_configuration[:parse_base_options] : true logger.debug "parsing args: #{@args.inspect}, raise_on_invalid_option: #{raise_on_invalid_option}, parse_base_options: #{parse_base_options}" @option_parser ||= OptionParser.new option_parser. = help + "\n\nOptions:" if option_parser.on("--template [NAME]", "Use a template to render output. (default=default.slim)") do |t| [:template] = t.nil? ? "default.slim" : t @template = [:template] end option_parser.on("--output FILENAME", "Render output directly to a file") do |f| [:output] = f @output = [:output] end option_parser.on("--force", "Overwrite file output without prompting") do |f| [:force] = f end option_parser.on("-r", "--repos a1,a2,a3", "--asset a1,a2,a3", "--filter a1,a2,a3", Array, "List of regex asset name filters") do |list| [:filter] = list end # NOTE: OptionParser will add short options, there is no way to stop '-m' from being the same as '--match' option_parser.on("--match [MODE]", "Asset filter match mode. MODE=ALL (default), FIRST, EXACT, or ONE (fails if more than 1 match)") do |m| [:match] = m || "ALL" [:match].upcase! unless ["ALL", "FIRST", "EXACT", "ONE"].include?([:match]) puts "invalid match mode option: #{options[:match]}" exit 1 end end end # allow decendants to add options yield option_parser if block_given? # reprocess args for known options, see binary wrapper for first pass # (first pass doesn't know about action specific options), find all # action options that may come after the action/subcommand (options # before subcommand have already been processed) and its args logger.debug "args before reprocessing: #{@args.inspect}" begin option_parser.order!(@args) rescue OptionParser::InvalidOption => e if raise_on_invalid_option puts "option error: #{e}" puts option_parser exit 1 else # parse and consume until we hit an unknown option (not arg), put it back so it # can be shifted into the new array e.recover(@args) end end logger.debug "args before unknown collection: #{@args.inspect}" unknown_args = [] while unknown_arg = @args.shift logger.debug "unknown_arg: #{unknown_arg.inspect}" unknown_args << unknown_arg begin # consume options and stop at an arg option_parser.order!(@args) rescue OptionParser::InvalidOption => e if raise_on_invalid_option puts "option error: #{e}" puts option_parser exit 1 else # parse and consume until we hit an unknown option (not arg), put it back so it # can be shifted into the new array e.recover(@args) end end end logger.debug "args after unknown collection: #{@args.inspect}" @args = unknown_args.dup logger.debug "args after reprocessing: #{@args.inspect}" logger.debug "configuration after reprocessing: #{@configuration.inspect}" logger.debug "options after reprocessing: #{@options.inspect}" option_parser end |
#process ⇒ Object
handle “assets to items” transformations, if any, and write to output
147 148 149 |
# File 'lib/repo_manager/actions/base_action.rb', line 147 def process write_to_output(render) end |
#render(view_options = configuration) ⇒ String
Render items result to a string
218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 |
# File 'lib/repo_manager/actions/base_action.rb', line 218 def render(=configuration) logger.debug "rendering" result = "" if template logger.debug "rendering with template : #{template}" view = AppView.new(items, ) view.template = template result = view.render else items.each_with_index do |item, index| result += "\n" unless index == 0 result += item.name.green + ":\n" if item.respond_to?(:attributes) attributes = item.attributes.deep_clone result += attributes.recursively_stringify_keys!.to_conf.gsub(/\s+$/, '') # strip trailing whitespace from YAML result += "\n" end end end result end |
#write_to_output(content) ⇒ Object
TODO: add exception handler and pass return values
152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 |
# File 'lib/repo_manager/actions/base_action.rb', line 152 def write_to_output(content) if output logger.debug "write_to_output called with output : #{output}" if overwrite_output? logger.debug "writing output to : #{output}" File.open(output, 'wb') {|f| f.write(content) } else logger.info "existing file not overwritten. To overwrite automatically, use the '--force' option." end else logger.debug "writing to STDOUT" print content end return 0 end |