instructure/canvas-lms · error · ArgumentError

block is required if module_name is not passed

Error message

block is required if module_name is not passed

What it means

The Autoextend.hook DSL requires exactly one extension source: either a module_name (an existing module to prepend/extend with) or a &block (an inline module definition). Passing neither leaves the Extension with no code to apply, so hook raises ArgumentError immediately rather than failing later at class-load time.

Solutions

  1. Pass the block: Autoextend.hook('User', :create) { prepend UserExtensions }
  2. Pass an existing module: Autoextend.hook('User', 'UserExtensions', :create)
  3. Fix code that computes module_name dynamically so it resolves to a non-nil value
  4. Mark the hook optional:/guard it so it only registers when the module is actually defined

Example fix

// before
Autoextend.hook('ConversationParticipant', :create)
// after
Autoextend.hook('ConversationParticipant', :create) do
  def after_create_hook; end
end
Defensive patterns

Strategy: validation

Validate before calling

raise 'Autoextend.hook needs module_name or block' if mod_name.nil? && !block_given?

Try / catch

begin
  Autoextend.hook(const_name, mod_name, method, &blk)
rescue ArgumentError => e
  Rails.logger.error("bad autoextend hook: #{e.message}")
end

Prevention

When it happens

Trigger: Calling Autoextend.hook(ConstName, method: ...) with a nil/omitted module_name and no block, e.g. Autoextend.hook('User', :create) or a variable module_name that is nil at call time.

Common situations: Refactoring an old hook from a module to a block (or vice versa) and deleting the wrong argument; conditional logic that computes module_name which evaluates to nil; typos like passing module name as positional after a keyword arg mismatch.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of instructure/canvas-lms@1c9f0bb801 (2026-09-15). Data as JSON: /api/errors/7c36617924c221b0. Report an issue: GitHub.

Appendix: source

Thrown at gems/autoextend/lib/autoextend.rb:65

    #
    # If User is already defined, it will immediately include
    # the MyUserExtension module into it. It then sets up a hook
    # to automatically include in User if it becomes defined again
    # (like from ActiveSupport reloading).
    #
    # You can make an extension optional, which is for information only,
    # so that if you have a spec that checks if all extensions were used
    # it can ignore optional extensions.
    def hook(const_name,
             module_name = nil,
             method: :include,
             singleton: false,
             after_load: false,
             optional: false,
             before: [],
             after: [],
             &block)
      raise ArgumentError, "block is required if module_name is not passed" if !module_name && !block
      raise ArgumentError, "cannot pass both a module_name and a block" if module_name && block

      extension = Extension.new(const_name,
                                module_name,
                                method,
                                block,
                                singleton,
                                optional,
                                Array(before),
                                Array(after))

      const_extensions = extensions_hash[const_name.to_sym] ||= []
      const_extensions << extension

      if module_name.is_a?(Module)
        module_name = module_name.name
      end

View on GitHub (pinned to 1c9f0bb801)