Class | CommandLine::Application |
In: |
lib/commandline/CVS/Base/application.rb
lib/commandline/application.rb |
Parent: | Object |
DEFAULT_CONSOLE_WIDTH | = | 70 | TODO: Consolidate these with OptionParser - put in command line | |
MIN_CONSOLE_WIDTH | = | 10 | ||
DEFAULT_BODY_INDENT | = | 4 | ||
DEFAULT_CONSOLE_WIDTH | = | 70 | TODO: Consolidate these with OptionParser - put in command line | |
MIN_CONSOLE_WIDTH | = | 10 | ||
DEFAULT_BODY_INDENT | = | 4 |
initialize | -> | __child_initialize |
initialize | -> | __child_initialize |
args | [R] | |
argv | [R] |
# File lib/commandline/application.rb, line 269 269: def self.__set_auto_run 270: at_exit { @@child_class.run } 271: end
# File lib/commandline/CVS/Base/application.rb, line 247 247: def self.inherited(child_class) 248: @@appname = caller[0][/.*:/][0..-2] 249: @@child_class = child_class 250: if @@appname == $0 251: at_exit { @@child_class.run } 252: end 253: end
# File lib/commandline/application.rb, line 261 261: def self.inherited(child_class) 262: @@appname = caller[0][/.*:/][0..-2] 263: @@child_class = child_class 264: if @@appname == $0 265: __set_auto_run 266: end 267: end
# File lib/commandline/application.rb, line 41 41: def initialize 42: @synopsis = "" 43: @arg_arity = [0,0] 44: @options = [] 45: @arg_names = [] 46: @args = [] 47: @replay = false 48: @replay_file = ".replay" 49: 50: __initialize_text_formatting 51: 52: # Call the child usurped initialize 53: __child_initialize if 54: self.class.private_instance_methods(false).include?("__child_initialize") 55: 56: @option_parser ||= CommandLine::OptionParser.new(@options) 57: end
# File lib/commandline/CVS/Base/application.rb, line 36 36: def initialize 37: @synopsis = "" 38: @arg_arity = [0,0] 39: @options = [] 40: @arg_names = [] 41: @args = [] 42: @argv ||= ARGV 43: @replay = false 44: 45: __init_format 46: 47: __child_initialize if 48: self.class.private_instance_methods(false).include?("__child_initialize") 49: 50: @option_parser ||= CommandLine::OptionParser.new(@options) 51: end
# File lib/commandline/CVS/Base/application.rb, line 226 226: def self.run(argv=ARGV) 227: if self.private_instance_methods(false).include?("initialize") 228: $VERBOSE, verbose = nil, $VERBOSE 229: self.class_eval { 230: alias :__child_initialize :initialize 231: remove_method :initialize 232: } 233: $VERBOSE = verbose 234: end 235: obj = self.new 236: obj.__parse_command_line(argv) 237: obj.main 238: 239: #alias :user_init :initialize 240: #@@child_class.new.main if ($0 == @@appname) 241: obj 242: rescue => err 243: puts "ERROR: #{err}" 244: exit(-1) 245: end
# File lib/commandline/application.rb, line 238 238: def self.run(argv=ARGV) 239: # Usurp an existing initialize so ours can be called first. 240: # We rename it __child_initialize and call it from initialize. 241: if self.private_instance_methods(false).include?("initialize") 242: $VERBOSE, verbose = nil, $VERBOSE 243: self.class_eval { 244: alias :__child_initialize :initialize 245: remove_method :initialize 246: } 247: $VERBOSE = verbose 248: end 249: obj = self.new 250: obj.__parse_command_line(argv) 251: obj.main 252: 253: #alias :user_init :initialize 254: #@@child_class.new.main if ($0 == @@appname) 255: obj 256: rescue => err 257: puts "ERROR: #{err}" 258: exit(-1) 259: end
# File lib/commandline/application.rb, line 405 405: def __debug 406: { 407: :names => %w(--debug -d), 408: :arity => [0,0], 409: :opt_description => "Sets debug to true.", 410: :arg_description => "", 411: :opt_found => lambda { $DEBUG = true } 412: } 413: end
# File lib/commandline/CVS/Base/application.rb, line 363 363: def __debug 364: { 365: :names => %w(--debug -d), 366: :arity => [0,0], 367: :opt_description => "Sets debug to true.", 368: :arg_description => "", 369: :opt_found => lambda { $DEBUG = true } 370: } 371: end
# File lib/commandline/CVS/Base/application.rb, line 322 322: def __help 323: { 324: :names => %w(--help -h), 325: :arity => [0,0], 326: :opt_description => "Displays help page.", 327: :arg_description => "", 328: :opt_found => lambda { puts man; exit }, 329: :opt_not_found => false 330: } 331: end
# File lib/commandline/application.rb, line 364 364: def __help 365: { 366: :names => %w(--help -h), 367: :arity => [0,0], 368: :opt_description => "Displays help page.", 369: :arg_description => "", 370: :opt_found => lambda { puts man; exit }, 371: :opt_not_found => false 372: } 373: end
# File lib/commandline/CVS/Base/application.rb, line 293 293: def __init_format 294: # 295: # Formatting defaults 296: # 297: console_width = ENV["COLUMNS"] 298: @columns = 299: if console_width.nil? 300: DEFAULT_CONSOLE_WIDTH 301: elsif console_width < MIN_CONSOLE_WIDTH 302: console_width 303: else 304: console_width - DEFAULT_BODY_INDENT 305: end 306: @body_indent = DEFAULT_BODY_INDENT 307: @tag_paragraph = false 308: @order = :index # | :alpha 309: end
# File lib/commandline/application.rb, line 334 334: def __initialize_text_formatting 335: # 336: # Formatting defaults 337: # 338: console_width = ENV["COLUMNS"] 339: @columns = 340: if console_width.nil? 341: DEFAULT_CONSOLE_WIDTH 342: elsif console_width < MIN_CONSOLE_WIDTH 343: console_width 344: else 345: console_width - DEFAULT_BODY_INDENT 346: end 347: @body_indent = DEFAULT_BODY_INDENT 348: @tag_paragraph = false 349: @order = :index # | :alpha 350: end
# File lib/commandline/CVS/Base/application.rb, line 261 261: def __parse_command_line(argv) 262: if argv.empty? && 0 != @arg_arity[0] 263: puts usage 264: exit(0) 265: end 266: 267: begin 268: @option_data = @option_parser.parse(argv) 269: @args = @option_data.args 270: rescue => err 271: puts err 272: puts 273: puts usage 274: exit(-1) 275: end 276: 277: __validate_args(@option_data.args) 278: @arg_names.each_with_index { |name, idx| 279: instance_variable_set("@#{name}", @option_data.args[idx]) 280: } 281: end
# File lib/commandline/application.rb, line 297 297: def __parse_command_line(argv) 298: @argv = argv 299: if @replay && File.exist?(@replay_file) && !@argv.grep("-r").empty? 300: __restore_argv 301: elsif @argv.empty? && @arg_arity[0] != 0 302: puts usage 303: exit(0) 304: end 305: 306: begin 307: @option_data = @option_parser.parse(@argv) 308: @args = @option_data.args 309: rescue => err 310: puts err 311: puts 312: puts usage 313: exit(-1) 314: end 315: 316: __validate_args(@option_data.args) 317: @arg_names.each_with_index { |name, idx| 318: instance_variable_set("@#{name}", @option_data.args[idx]) 319: } 320: 321: __save_argv 322: end
# File lib/commandline/application.rb, line 292 292: def __restore_argv 293: @argv = File.read(@replay_file).gsub(/\n/, "").split 294: raise "Bad @argv" unless @argv.kind_of?(Array) 295: end
# File lib/commandline/application.rb, line 279 279: def __save_argv 280: return unless @replay 281: 282: line = 0 283: File.open(@replay_file, "w") { |f| 284: @argv.each { |arg| 285: f.puts "\n" if arg[0] == ?- && line != 0 286: f.print " #{arg}" 287: line += 1 288: } 289: } 290: end
# File lib/commandline/CVS/Base/application.rb, line 283 283: def __validate_arg_arity(arity) 284: min, max = *arity 285: raise(InvalidArgumentArityError, "Minimum argument arity '#{min}' must be "+ 286: "greater than or equal to 0.") unless min >= 0 287: raise(InvalidArgumentArityError, "Maximum argument arity '#{max}' must be "+ 288: "greater than or equal to -1.") if max < -1 289: raise(InvalidArgumentArityError, "Maximum argument arity '#{max}' must be "+ 290: "greater than minimum arg_arity '#{min}'.") if max < min && max != -1 291: end
# File lib/commandline/application.rb, line 324 324: def __validate_arg_arity(arity) 325: min, max = *arity 326: raise(InvalidArgumentArityError, "Minimum argument arity '#{min}' must be "+ 327: "greater than or equal to 0.") unless min >= 0 328: raise(InvalidArgumentArityError, "Maximum argument arity '#{max}' must be "+ 329: "greater than or equal to -1.") if max < -1 330: raise(InvalidArgumentArityError, "Maximum argument arity '#{max}' must be "+ 331: "greater than minimum arg_arity '#{min}'.") if max < min && max != -1 332: end
# File lib/commandline/CVS/Base/application.rb, line 311 311: def __validate_args(od_args) 312: size = od_args.size 313: min, max = @arg_arity 314: max = 1.0/0.0 if -1 == max 315: raise(ArgumentError, 316: "Missing expected arguments. Found #{size} but expected #{min}.\n"+ 317: "#{usage}") if size < min 318: raise(ArgumentError, "Too many arguments. Found #{size} but "+ 319: "expected #{max}.\n#{usage}") if size > max 320: end
# File lib/commandline/application.rb, line 352 352: def __validate_args(od_args) 353: size = od_args.size 354: min, max = @arg_arity 355: max = 1.0/0.0 if -1 == max 356: raise(ArgumentError, 357: "Missing expected arguments. Found #{size} but expected #{min}. "+ 358: "#{od_args.inspect}\n"+ 359: "#{usage}") if size < min 360: raise(ArgumentError, "Too many arguments. Found #{size} but "+ 361: "expected #{max}.\n#{usage}") if size > max 362: end
# File lib/commandline/CVS/Base/application.rb, line 333 333: def __verbose 334: { 335: :names => %w(--verbose -v), 336: :arity => [0,0], 337: :opt_description => "Sets verbosity level. Subsequent "+ 338: "flags increase verbosity level", 339: :arg_description => "", 340: :opt_found => lambda { @verbose ||= -1; @verbose += 1 }, 341: :opt_not_found => nil 342: } 343: end
# File lib/commandline/application.rb, line 375 375: def __verbose 376: { 377: :names => %w(--verbose -v), 378: :arity => [0,0], 379: :opt_description => "Sets verbosity level. Subsequent "+ 380: "flags increase verbosity level", 381: :arg_description => "", 382: :opt_found => lambda { @verbose ||= -1; @verbose += 1 }, 383: :opt_not_found => nil 384: } 385: end
# File lib/commandline/CVS/Base/application.rb, line 345 345: def __version 346: { 347: :names => %w(--version -V), 348: :arity => [0,0], 349: :opt_description => "Displays application version.", 350: :arg_description => "", 351: :opt_found => lambda { 352: begin 353: version 354: rescue 355: puts "No version specified" 356: end; 357: exit 358: }, 359: :opt_not_found => nil 360: } 361: end
# File lib/commandline/application.rb, line 387 387: def __version 388: { 389: :names => %w(--version -V), 390: :arity => [0,0], 391: :opt_description => "Displays application version.", 392: :arg_description => "", 393: :opt_found => lambda { 394: begin 395: puts "#{name} - Version: #{version}" 396: rescue 397: puts "No version specified" 398: end; 399: exit 400: }, 401: :opt_not_found => nil 402: } 403: end
# File lib/commandline/CVS/Base/application.rb, line 218 218: def append_arg 219: CommandLine::OptionParser::GET_ARG_ARRAY 220: end
# File lib/commandline/application.rb, line 230 230: def append_arg 231: CommandLine::OptionParser::GET_ARG_ARRAY 232: end
expected_args :cmd Now, what to do if command line has more args than expected app —app-option cmd —cmd-option arg-for-cmd
# File lib/commandline/CVS/Base/application.rb, line 123 123: def expected_args(*exp_args) 124: @arg_names = [] 125: case exp_args.size 126: when 0 then @arg_arity = [0,0] 127: when 1 128: case exp_args[0] 129: when Fixnum 130: v = exp_args[0] 131: @arg_arity = [v,v] 132: when Symbol 133: @arg_names = exp_args 134: @arg_arity = [1,1] 135: when Array 136: v = exp_args[0] 137: __validate_arg_arity(v) 138: @arg_arity = v 139: else 140: raise(InvalidArgumentArityError, 141: "Args must be a Fixnum or Array: #{exp_args[0].inspect}.") 142: end 143: else 144: @arg_names = exp_args 145: size = exp_args.size 146: @arg_arity = [size, size] 147: end 148: end
expected_args :cmd Now, what to do if command line has more args than expected app —app-option cmd —cmd-option arg-for-cmd
# File lib/commandline/application.rb, line 134 134: def expected_args(*exp_args) 135: @arg_names = [] 136: case exp_args.size 137: when 0 then @arg_arity = [0,0] 138: when 1 139: case exp_args[0] 140: when Fixnum 141: v = exp_args[0] 142: @arg_arity = [v,v] 143: when Symbol 144: @arg_names = exp_args 145: @arg_arity = [1,1] 146: when Array 147: v = exp_args[0] 148: __validate_arg_arity(v) 149: @arg_arity = v 150: else 151: raise(InvalidArgumentArityError, 152: "Args must be a Fixnum or Array: #{exp_args[0].inspect}.") 153: end 154: else 155: @arg_names = exp_args 156: size = exp_args.size 157: @arg_arity = [size, size] 158: end 159: end
# File lib/commandline/CVS/Base/application.rb, line 213 213: def get_arg 214: CommandLine::OptionParser::GET_ARGS 215: end
# File lib/commandline/application.rb, line 225 225: def get_arg 226: CommandLine::OptionParser::GET_ARGS 227: end
# File lib/commandline/application.rb, line 273 273: def main 274: #raise(MissingMainError, "Method #main must be defined in class #{@@child_class}.") 275: @@child_class.class_eval %{ def main; end } 276: #self.class_eval %{ def main; end } 277: end
# File lib/commandline/CVS/Base/application.rb, line 255 255: def main 256: #raise(MissingMainError, "Method #main must be defined in class #{@@child_class}.") 257: @@child_class.class_eval %{ def main; end } 258: #self.class_eval %{ def main; end } 259: end
# File lib/commandline/CVS/Base/application.rb, line 158 158: def man 159: require 'text/format' 160: f = Text::Format.new 161: f = Text::Format.new 162: f.columns = @columns 163: f.first_indent = 4 164: f.body_indent = @body_indent 165: f.tag_paragraph = false 166: 167: s = [] 168: s << ["NAME\n"] 169: 170: nm = "#{short_description}".empty? ? name : "#{name} - #{short_description}" 171: s << f.format(nm) 172: 173: sn = "#{synopsis}".empty? ? "" : "#{name} #{synopsis}" 174: unless sn.empty? 175: s << "SYNOPSIS\n" 176: s << f.format(sn) 177: end 178: 179: dc = "#{long_description}" 180: unless dc.empty? 181: s << "DESCRIPTION\n" 182: s << f.format(dc) 183: end 184: 185: op = option_parser.to_s 186: unless op.empty? 187: s << option_parser.to_s 188: end 189: 190: ar = "#{author}" 191: unless ar.empty? 192: s << "AUTHOR: #{ar}" 193: end 194: 195: 196: ct = "COPYRIGHT (c) #{copyright}" 197: unless "#{copyright}".empty? 198: s << ct 199: end 200: 201: s.join("\n") 202: end
# File lib/commandline/application.rb, line 170 170: def man 171: require 'text/format' 172: f = Text::Format.new 173: f = Text::Format.new 174: f.columns = @columns 175: f.first_indent = 4 176: f.body_indent = @body_indent 177: f.tag_paragraph = false 178: 179: s = [] 180: s << ["NAME\n"] 181: 182: nm = "#{short_description}".empty? ? name : "#{name} - #{short_description}" 183: s << f.format(nm) 184: 185: sn = "#{synopsis}".empty? ? "" : "#{name} #{synopsis}" 186: unless sn.empty? 187: s << "SYNOPSIS\n" 188: s << f.format(sn) 189: end 190: 191: dc = "#{long_description}" 192: unless dc.empty? 193: s << "DESCRIPTION\n" 194: s << f.format(dc) 195: end 196: 197: op = option_parser.to_s 198: unless op.empty? 199: s << option_parser.to_s 200: end 201: 202: ar = "#{author}" 203: unless ar.empty? 204: s << "AUTHOR: #{ar}" 205: end 206: 207: 208: ct = "COPYRIGHT (c) #{copyright}" 209: unless "#{copyright}".empty? 210: s << ct 211: end 212: 213: s.join("\n") 214: end
# File lib/commandline/CVS/Base/application.rb, line 205 205: def name 206: File.basename(pathname) 207: end
Alternative for @option_data["<—opt>"], but with symbols
# File lib/commandline/application.rb, line 81 81: def opt 82: @option_data 83: end
# File lib/commandline/CVS/Base/application.rb, line 57 57: def option(*args) 58: @options ||= [] 59: new_list = [] 60: args.each { |arg| 61: new_list << 62: case arg 63: when :help then __help 64: when :debug then __debug 65: when :verbose then __verbose 66: when :version then __version 67: else arg 68: end 69: } 70: #p new_list 71: @options << CommandLine::Option.new(*new_list) 72: end
# File lib/commandline/application.rb, line 63 63: def option(*args) 64: @options ||= [] 65: new_list = [] 66: args.each { |arg| 67: new_list << 68: case arg 69: when :help then __help 70: when :debug then __debug 71: when :verbose then __verbose 72: when :version then __version 73: else arg 74: end 75: } 76: #p new_list 77: @options << CommandLine::Option.new(*new_list) 78: end
# File lib/commandline/CVS/Base/application.rb, line 53 53: def options(*opts) 54: opts.each { |opt| option(*[opt].flatten) } 55: end
# File lib/commandline/application.rb, line 59 59: def options(*opts) 60: opts.each { |opt| option(*[opt].flatten) } 61: end
# File lib/commandline/CVS/Base/application.rb, line 222 222: def required 223: CommandLine::OptionParser::OPT_NOT_FOUND_BUT_REQUIRED 224: end
# File lib/commandline/application.rb, line 234 234: def required 235: CommandLine::OptionParser::OPT_NOT_FOUND_BUT_REQUIRED 236: end
# File lib/commandline/CVS/Base/application.rb, line 154 154: def usage 155: " Usage: #{name} #{synopsis}" 156: end
# File lib/commandline/application.rb, line 166 166: def usage 167: " Usage: #{name} #{synopsis}" 168: end
# File lib/commandline/CVS/Base/application.rb, line 150 150: def use_replay 151: @replay = true 152: end