lib/mercenary/command.rb in mercenary-0.2.1 vs lib/mercenary/command.rb in mercenary-0.3.0
- old
+ new
@@ -6,35 +6,52 @@
attr_accessor :options
attr_accessor :commands
attr_accessor :actions
attr_reader :map
attr_accessor :parent
+ attr_reader :trace
# Public: Creates a new Command
#
# name - the name of the command
# parent - (optional) the instancce of Mercenary::Command which you wish to
# be the parent of this command
#
# Returns nothing
def initialize(name, parent = nil)
- @name = name
- @options = []
- @commands = {}
- @actions = []
- @map = {}
- @parent = parent
+ @name = name
+ @options = []
+ @commands = {}
+ @actions = []
+ @map = {}
+ @parent = parent
+ @trace = false
end
+ # Public: Sets or gets the command version
+ #
+ # version - the command version (optional)
+ #
+ # Returns the version and sets it if an argument is non-nil
+ def version(version = nil)
+ @version = version if version
+ @version
+ end
+
# Public: Sets or gets the syntax string
#
# syntax - the string which describes this command's usage syntax (optional)
#
# Returns the syntax string and sets it if an argument is present
def syntax(syntax = nil)
@syntax = syntax if syntax
- @syntax
+ syntax_list = []
+ if parent
+ syntax_list << parent.syntax.to_s.gsub(/<[\w\s-]+>/, '').gsub(/\[[\w\s-]+\]/, '').strip
+ end
+ syntax_list << (@syntax || name.to_s)
+ syntax_list.join(" ")
end
# Public: Sets or gets the command description
#
# description - the description of what the command does (optional)
@@ -69,12 +86,13 @@
# sym - the variable key which is used to identify the value of the switch
# at runtime in the options hash
#
# Returns nothing
def option(sym, *options)
- @options << options
- @map[options[0]] = sym
+ new_option = Option.new(sym, options)
+ @options << new_option
+ @map[new_option.hash] = sym
end
# Public: Adds a subcommand
#
# cmd_name - the name of the command
@@ -110,19 +128,20 @@
# Public: Fetch a Logger (stdlib)
#
# level - the logger level (a Logger constant, see docs for more info)
#
# Returns the instance of Logger
- def logger(level = Logger::INFO)
+ def logger(level = nil)
unless @logger
@logger = Logger.new(STDOUT)
+ @logger.level = level || Logger::INFO
@logger.formatter = proc do |severity, datetime, progname, msg|
- "#{ident} (#{severity}): #{msg}\n"
+ "#{identity} | " << "#{severity.downcase.capitalize}:".ljust(7) << " #{msg}\n"
end
end
- @logger.level = level
+ @logger.level = level unless level.nil?
@logger
end
# Public: Run the command
#
@@ -132,10 +151,11 @@
#
# Returns the command to be executed
def go(argv, opts, config)
opts.banner = "Usage: #{syntax}"
process_options(opts, config)
+ add_default_options(opts)
if argv[0] && cmd = commands[argv[0].to_sym]
logger.debug "Found subcommand '#{cmd.name}'"
argv.shift
cmd.go(argv, opts, config)
@@ -151,17 +171,40 @@
# opts - instance of OptionParser
# config - the Hash in which the option values should be placed
#
# Returns nothing
def process_options(opts, config)
- options.each do |o|
- opts.on(*o) do |x|
- config[map[o[0]]] = x
+ options.each do |option|
+ opts.on(*option.for_option_parser) do |x|
+ config[map[option.hash]] = x
end
end
end
+ # Public: Add version and help options to the command
+ #
+ # opts - instance of OptionParser
+ #
+ # Returns nothing
+ def add_default_options(opts)
+ option 'show_help', '-h', '--help', 'Show this message'
+ option 'show_version', '-v', '--version', 'Print the name and version'
+ opts.on("-v", "--version", "Print the version") do
+ puts "#{name} #{version}"
+ abort
+ end
+
+ opts.on('-t', '--trace', 'Show full backtrace if an error occurs') do
+ @trace = true
+ end
+
+ opts.on_tail("-h", "--help", "Show this message") do
+ puts self
+ exit
+ end
+ end
+
# Public: Execute all actions given the inputted args and options
#
# argv - (optional) command-line args (sans opts)
# config - (optional) the Hash configuration of string key to value
#
@@ -186,21 +229,41 @@
# Public: Identify this command
#
# Returns a string which identifies this command
def ident
- "<Command name=#{name}>"
+ "<Command name=#{identity}>"
end
+ # Public: Get the full identity (name & version) of this command
+ #
+ # Returns a string containing the name and version if it exists
+ def identity
+ "#{full_name} #{version if version}".strip
+ end
+
+ # Public: Get the name of the current command plus that of
+ # its parent commands
+ #
+ # Returns the full name of the command
+ def full_name
+ the_name = []
+ the_name << parent.full_name if parent && parent.full_name
+ the_name << name
+ the_name.join(" ")
+ end
+
+ # Public: Build a string containing a summary of the command
+ #
+ # Returns a one-line summary of the command.
+ def summarize
+ " #{name.to_s.ljust(20)} #{description}"
+ end
+
# Public: Build a string containing the command name, options and any subcommands
#
# Returns the string identifying this command, its options and its subcommands
def to_s
- msg = ''
- msg += "Command: #{name}\n"
- options.each { |o| msg += " " + o.inspect + "\n"}
- msg += "\n"
- commands.each { |k, v| msg += commands[k].inspect }
- msg
+ Presenter.new(self).print_command
end
end
end