lib/thor/base.rb in thor-0.20.3 vs lib/thor/base.rb in thor-1.0.0
- old
+ new
@@ -1,19 +1,19 @@
-require "thor/command"
-require "thor/core_ext/hash_with_indifferent_access"
-require "thor/core_ext/ordered_hash"
-require "thor/error"
-require "thor/invocation"
-require "thor/parser"
-require "thor/shell"
-require "thor/line_editor"
-require "thor/util"
+require_relative "command"
+require_relative "core_ext/hash_with_indifferent_access"
+require_relative "error"
+require_relative "invocation"
+require_relative "nested_context"
+require_relative "parser"
+require_relative "shell"
+require_relative "line_editor"
+require_relative "util"
class Thor
- autoload :Actions, "thor/actions"
- autoload :RakeCompat, "thor/rake_compat"
- autoload :Group, "thor/group"
+ autoload :Actions, File.expand_path("actions", __dir__)
+ autoload :RakeCompat, File.expand_path("rake_compat", __dir__)
+ autoload :Group, File.expand_path("group", __dir__)
# Shortcuts for help.
HELP_MAPPINGS = %w(-h -? --help -D)
# Thor methods that should not be overwritten by the user.
@@ -87,10 +87,11 @@
@args = thor_args.remaining
end
class << self
def included(base) #:nodoc:
+ super(base)
base.extend ClassMethods
base.send :include, Invocation
base.send :include, Shell
end
@@ -151,21 +152,24 @@
!!check_unknown_options
end
# If you want to raise an error when the default value of an option does not match
# the type call check_default_type!
- # This is disabled by default for compatibility.
+ # This will be the default; for compatibility a deprecation warning is issued if necessary.
def check_default_type!
@check_default_type = true
end
- def check_default_type #:nodoc:
- @check_default_type ||= from_superclass(:check_default_type, false)
+ # If you want to use defaults that don't match the type of an option,
+ # either specify `check_default_type: false` or call `allow_incompatible_default_type!`
+ def allow_incompatible_default_type!
+ @check_default_type = false
end
- def check_default_type? #:nodoc:
- !!check_default_type
+ def check_default_type #:nodoc:
+ @check_default_type = from_superclass(:check_default_type, nil) unless defined?(@check_default_type)
+ @check_default_type
end
# If true, option parsing is suspended as soon as an unknown option or a
# regular argument is encountered. All remaining arguments are passed to
# the command as regular arguments.
@@ -351,26 +355,26 @@
end
# Returns the commands for this Thor class.
#
# ==== Returns
- # OrderedHash:: An ordered hash with commands names as keys and Thor::Command
- # objects as values.
+ # Hash:: An ordered hash with commands names as keys and Thor::Command
+ # objects as values.
#
def commands
- @commands ||= Thor::CoreExt::OrderedHash.new
+ @commands ||= Hash.new
end
alias_method :tasks, :commands
# Returns the commands for this Thor class and all subclasses.
#
# ==== Returns
- # OrderedHash:: An ordered hash with commands names as keys and Thor::Command
- # objects as values.
+ # Hash:: An ordered hash with commands names as keys and Thor::Command
+ # objects as values.
#
def all_commands
- @all_commands ||= from_superclass(:all_commands, Thor::CoreExt::OrderedHash.new)
+ @all_commands ||= from_superclass(:all_commands, Hash.new)
@all_commands.merge!(commands)
end
alias_method :all_tasks, :all_commands
# Removes a given command from this Thor class. This is usually done if you
@@ -413,18 +417,24 @@
# def this_is_not_a_command
# end
# remove_command :this_is_not_a_command
# end
#
- def no_commands
- @no_commands = true
- yield
- ensure
- @no_commands = false
+ def no_commands(&block)
+ no_commands_context.enter(&block)
end
+
alias_method :no_tasks, :no_commands
+ def no_commands_context
+ @no_commands_context ||= NestedContext.new
+ end
+
+ def no_commands?
+ no_commands_context.entered?
+ end
+
# Sets the namespace for the Thor or Thor::Group class. By default the
# namespace is retrieved from the class name. If your Thor class is named
# Scripts::MyScript, the help method, for example, will be called as:
#
# thor scripts:my_script -h
@@ -500,14 +510,20 @@
def handle_argument_error(command, error, args, arity) #:nodoc:
name = [command.ancestor_name, command.name].compact.join(" ")
msg = "ERROR: \"#{basename} #{name}\" was called with ".dup
msg << "no arguments" if args.empty?
msg << "arguments " << args.inspect unless args.empty?
- msg << "\nUsage: #{banner(command).inspect}"
+ msg << "\nUsage: \"#{banner(command).split("\n").join("\"\n \"")}\""
raise InvocationError, msg
end
+ # A flag that makes the process exit with status 1 if any error happens.
+ def exit_on_failure?
+ Thor.deprecation_warning "Thor exit with status 0 on errors. To keep this behavior, you must define `exit_on_failure?` in `#{self.name}`"
+ false
+ end
+
protected
# Prints the class options per group. If an option does not belong to
# any group, it's printed as Class option.
#
@@ -561,11 +577,11 @@
# ==== Parameters
# name<Symbol>:: The name of the argument.
# options<Hash>:: Described in both class_option and method_option.
# scope<Hash>:: Options hash that is being built up
def build_option(name, options, scope) #:nodoc:
- scope[name] = Thor::Option.new(name, options.merge(:check_default_type => check_default_type?))
+ scope[name] = Thor::Option.new(name, {:check_default_type => check_default_type}.merge!(options))
end
# Receives a hash of options, parse them and add to the scope. This is a
# fast way to set a bunch of options:
#
@@ -594,29 +610,30 @@
alias_method :find_and_refresh_task, :find_and_refresh_command
# Everytime someone inherits from a Thor class, register the klass
# and file into baseclass.
def inherited(klass)
+ super(klass)
Thor::Base.register_klass_file(klass)
- klass.instance_variable_set(:@no_commands, false)
+ klass.instance_variable_set(:@no_commands, 0)
end
# Fire this callback whenever a method is added. Added methods are
# tracked as commands by invoking the create_command method.
def method_added(meth)
+ super(meth)
meth = meth.to_s
if meth == "initialize"
initialize_added
return
end
# Return if it's not a public instance method
return unless public_method_defined?(meth.to_sym)
- @no_commands ||= false
- return if @no_commands || !create_command(meth)
+ return if no_commands? || !create_command(meth)
is_thor_reserved_word?(meth, :command)
Thor::Base.register_klass_file(self)
end
@@ -637,14 +654,9 @@
rescue TypeError
value
end
end
- end
-
- # A flag that makes the process exit with status 1 if any error happens.
- def exit_on_failure?
- false
end
#
# The basename of the program invoking the thor class.
#