Rails チュートリアル 1章 勉強メモ6

Rails チュートリアルの勉強メモ

railstutorial.jp

  • dispatch から読んでいきます

1章続き rails new 何やってんの?

  • gems/thor-0.20.3/lib/thor.rb
    # The method responsible for dispatching given the args.
    def dispatch(meth, given_args, given_opts, config) #:nodoc: # rubocop:disable MethodLength
      meth ||= retrieve_command_name(given_args)
      command = all_commands[normalize_command_name(meth)]

      if !command && config[:invoked_via_subcommand]
        # We're a subcommand and our first argument didn't match any of our
        # commands. So we put it back and call our default command.
        given_args.unshift(meth)
        command = all_commands[normalize_command_name(default_command)]
      end

      if command
        args, opts = Thor::Options.split(given_args)
        if stop_on_unknown_option?(command) && !args.empty?
          # given_args starts with a non-option, so we treat everything as
          # ordinary arguments
          args.concat opts
          opts.clear
        end
      else
        args = given_args
        opts = nil
        command = dynamic_command_class.new(meth)
      end

      opts = given_opts || opts || []
      config[:current_command] = command
      config[:command_options] = command.options

      instance = new(args, opts, config)
      yield instance if block_given?
      args = instance.args
      trailing = args[Range.new(arguments.size, -1)]
      instance.invoke_command(command, trailing || [])
    end

qiita.com

  • コマンドの解釈をしているみたい
  • instance の中身
[19] pry(Rails::Command::ApplicationCommand)> instance
=> #<Rails::Command::ApplicationCommand:0x00007f912910b6b8
 @_initializer=[["new", "hello_app"], [], {:current_command=>#<struct Thor::Command name="application", description="", long_description=nil, usage="", options={}, ancestor_name=nil>}],
 @_invocations={},
 @args=["new", "hello_app"],
 @options={},
 @shell=#<Thor::Shell::Color:0x00007f912925f690 @always_force=false, @base=#<Rails::Command::ApplicationCommand:0x00007f912910b6b8 ...>, @mute=false, @padding=0>>
  • instance.invoke_command(command, trailing || []) でコマンド実行
  • 一応 invoke_command の中身
    121: def invoke_command(command, *args) #:nodoc:
    122:   current = @_invocations[self.class]
    123: 
    124:   unless current.include?(command.name)
    125:     current << command.name
 => 126:     command.run(self, *args)
    127:   end
    128: end
  • この時点での self
[25] pry(#<Rails::Command::ApplicationCommand>)> self
=> #<Rails::Command::ApplicationCommand:0x00007f912910b6b8
 @_initializer=[["new", "hello_app"], [], {:current_command=>#<struct Thor::Command name="application", description="", long_description=nil, usage="", options={}, ancestor_name=nil>}],
 @_invocations={Rails::Command::ApplicationCommand=>["application"]},
 @args=["new", "hello_app"],
 @options={},
 @shell=#<Thor::Shell::Color:0x00007f912925f690 @always_force=false, @base=#<Rails::Command::ApplicationCommand:0x00007f912910b6b8 ...>, @mute=false, @padding=0>>
  • run の中身
  • gems/thor-0.20.3/lib/thor/command.rb
    20: def run(instance, args = [])
    21:   arity = nil
    22: 
    23:   if private_method?(instance)
    24:     instance.class.handle_no_command_error(name)
    25:   elsif public_method?(instance)
    26:     arity = instance.method(name).arity
 => 27:     instance.__send__(name, *args)
    28:   elsif local_method?(instance, :method_missing)
    29:     instance.__send__(:method_missing, name.to_sym, *args)
    30:   else
    31:     instance.class.handle_no_command_error(name)
    32:   end
    33: rescue ArgumentError => e
    34:   handle_argument_error?(instance, e, caller) ? instance.class.handle_argument_error(self, e, args, arity) : (raise e)
    35: rescue NoMethodError => e
    36:   handle_no_method_error?(instance, e, caller) ? instance.class.handle_no_command_error(name) : (raise e)
    37: end
  • send は 第一引数のメソッドを実行する name は application
  • step したら Rails::Command::ApplicationCommand#perform へ飛んだ(なんで?
  • instance は Rails::Command::ApplicationCommand なので instance.application を実行...のはず
  • pry で見ると 'instance.application' は確かにある
[1] pry(#<Thor::Command>)> instance.
Display all 105 possibilities? (y or n)
instance.__binding__                           instance.freeze                                instance.options                               instance.send
instance.__id__                                instance.frozen?                               instance.options=                              instance.set_application_directory!
instance.__send__                              instance.hash                                  instance.parent_options                        instance.set_color
instance._parse_initialization_options         instance.help                                  instance.parent_options=                       instance.shell
instance._retrieve_class_and_command           instance.inspect                               instance.perform                               instance.shell=
instance._retrieve_class_and_task              instance.instance_eval                         instance.presence                              instance.singleton_class
instance._shared_configuration                 instance.instance_exec                         instance.present?                              instance.singleton_method
instance.application                           instance.instance_of?                          instance.pretty_inspect                        instance.singleton_methods
instance.args                                  instance.instance_variable_defined?            instance.pretty_print                          instance.taint
instance.args=                                 instance.instance_variable_get                 instance.pretty_print_cycle                    instance.tainted?
instance.ask                                   instance.instance_variable_set                 instance.pretty_print_inspect                  instance.tap
instance.blank?                                instance.instance_variables                    instance.pretty_print_instance_variables       instance.terminal_width
instance.byebug                                instance.invoke                                instance.print_in_columns                      instance.then
instance.class                                 instance.invoke_all                            instance.print_table                           instance.to_enum
instance.class_eval                            instance.invoke_command                        instance.print_wrapped                         instance.to_json
instance.clone                                 instance.invoke_task                           instance.private_methods                       instance.to_s
instance.current_command_chain                 instance.invoke_with_padding                   instance.protected_methods                     instance.to_yaml
instance.debugger                              instance.is_a?                                 instance.pry                                   instance.trust
instance.define_singleton_method               instance.itself                                instance.public_method                         instance.untaint
instance.display                               instance.kind_of?                              instance.public_methods                        instance.untrust
instance.dup                                   instance.load_generators                       instance.public_send                           instance.untrusted?
instance.enum_for                              instance.load_tasks                            instance.remote_byebug                         instance.with_padding
instance.eql?                                  instance.method                                instance.remove_instance_variable              instance.yes?
instance.equal?                                instance.methods                               instance.require_application_and_environment!  instance.yield_self
instance.error                                 instance.nil?                                  instance.respond_to?                           
instance.extend                                instance.no?                                   instance.say                                   
instance.file_collision                        instance.object_id                             instance.say_status   
  • 眠すぎて application を見つけられないのでこの先は次に・・・