lib/bauxite/core/context.rb in bauxite-0.4.6 vs lib/bauxite/core/context.rb in bauxite-0.5.0

- old
+ new

@@ -290,24 +290,57 @@ # ctx.exec_action 'open "http://www.ruby-lang.org"' # # => navigates to www.ruby-lang.org # def exec_action(text, log = true, file = '<unknown>', line = 0) data = Context::parse_action_default(text, file, line) - _exec_parsed_action(data[:action], data[:args], text, log, file, line) + exec_parsed_action(data[:action], data[:args], log, text, file, line) end # Executes the specified +file+. # # For example: # ctx.exec_file('file') # # => executes every action defined in 'file' # def exec_file(file) @parser.parse(file) do |action, args, text, file, line| - _exec_parsed_action(action, args, text, true, file, line) + exec_parsed_action(action, args, true, text, file, line) end end + + # Executes the specified action handling errors, logging and debug + # history. + # + # This method if part of the action execution chain and is intended + # for advanced use (e.g. in complex actions). To execute an Action + # directly, the #exec_action method is preferred. + # + # If +log+ is +true+, log the action execution (default behavior). + # + # For example: + # ctx.exec_action 'open "http://www.ruby-lang.org"' + # # => navigates to www.ruby-lang.org + # + def exec_parsed_action(action, args, log = true, text = nil, file = nil, line = nil) + ret = handle_errors(true) do + + action = get_action(action, args, text, file, line) + + if log + @logger.log_cmd(action) do + Readline::HISTORY << action.text + exec_action_object(action) + end + else + exec_action_object(action) + end + end + handle_errors(true) do + ret.call if ret.respond_to? :call # delayed actions (after log_cmd) + end + end + # Executes the +block+ inside a rescue block applying standard criteria of # error handling. # # The default behavior is to print the exception message and exit. @@ -472,11 +505,11 @@ # # This method if part of the action execution chain and is intended # for advanced use (e.g. in complex actions). To execute an Action # directly, the #exec_action method is preferred. # - def get_action(action, args, text, file, line) + def get_action(action, args, text = nil, file = nil, line = nil) while (alias_action = @aliases[action]) action = alias_action[:action] args = alias_action[:args].map do |a| a.gsub(/\$\{(\d+)(\*q?)?\}/) do |match| # expand ${1} to args[0], ${2} to args[1], etc. @@ -493,10 +526,12 @@ end end end text = ([action] + args.map { |a| '"'+a.gsub('"', '""')+'"' }).join(' ') unless text + file = @variables['__FILE__'] unless file + line = @variables['__LINE__'] unless line Action.new(self, action, args, text, file, line) end # Executes the specified action object injecting built-in variables. @@ -519,10 +554,39 @@ @variables['__FILE__'] = file @variables['__DIR__'] = File.absolute_path(dir) action.execute end + # Executes the specified +action+ and returns +true+ if the action + # succeeds and +false+ otherwise. + # + # This method is intended to simplify conditional actions that execute + # different code depending on the outcome of an action execution. + # + # For example: + # if ctx.try_exec_action(action, args) + # # => when action succeeds... + # else + # # => when action fails... + # end + # + def try_exec_action(action, args) + action = get_action(action, args) + + with_timeout Bauxite::Errors::AssertionError do + with_vars({ '__TIMEOUT__' => 0}) do + begin + ret = exec_action_object(action) + ret.call if ret.respond_to? :call + true + rescue Bauxite::Errors::AssertionError + false + end + end + end + end + # ======================================================================= # # :section: Metadata # ======================================================================= # @@ -663,28 +727,9 @@ def _load_extensions(dirs) dirs.each do |d| d = File.join(Dir.pwd, d) unless Dir.exists? d d = File.absolute_path(d) Dir[File.join(d, '**', '*.rb')].each { |file| require file } - end - end - - def _exec_parsed_action(action, args, text, log, file, line) - ret = handle_errors(true) do - - action = get_action(action, args, text, file, line) - - if log - @logger.log_cmd(action) do - Readline::HISTORY << action.text - exec_action_object(action) - end - else - exec_action_object(action) - end - end - handle_errors(true) do - ret.call if ret.respond_to? :call # delayed actions (after log_cmd) end end # ======================================================================= # # Hacks required to overcome the String#split(' ') behavior of folding the \ No newline at end of file