Class: OnyxCord::Commands::Command

Inherits:
Object
  • Object
show all
Defined in:
lib/onyxcord/commands/parser.rb

Overview

Command that can be called in a chain

Instance Attribute Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#attributesHash (readonly)

Returns the attributes the command was initialized with.

Returns:

  • (Hash)

    the attributes the command was initialized with



7
8
9
# File 'lib/onyxcord/commands/parser.rb', line 7

def attributes
  @attributes
end

#nameSymbol (readonly)

Returns the name of this command.

Returns:

  • (Symbol)

    the name of this command



10
11
12
# File 'lib/onyxcord/commands/parser.rb', line 10

def name
  @name
end

#subcommandsHash{Symbol => Command} (readonly)

Returns subcommands registered on this command.

Returns:

  • (Hash{Symbol => Command})

    subcommands registered on this command.



114
115
116
# File 'lib/onyxcord/commands/parser.rb', line 114

def subcommands
  @subcommands
end

Instance Method Details

#after {|event, args, result| ... } ⇒ self

Registers an after hook. The hook receives the event, arguments, and the result.

Yield Parameters:

  • event (CommandEvent)

    The event.

  • args (Array<String>)

    The command arguments.

  • result (Object)

    The return value of the command block.

Returns:

  • (self)


96
97
98
99
# File 'lib/onyxcord/commands/parser.rb', line 96

def after(&hook)
  @after_hooks << hook
  self
end

#before {|event, args| ... } ⇒ self

Registers a before hook. The hook receives the event and arguments. Return false to cancel command execution.

Yield Parameters:

Returns:

  • (self)


86
87
88
89
# File 'lib/onyxcord/commands/parser.rb', line 86

def before(&hook)
  @before_hooks << hook
  self
end

#call(event, arguments, chained = false, check_permissions = true) ⇒ String

Calls this command and executes the code inside.

Parameters:

  • event (CommandEvent)

    The event to call the command with.

  • arguments (Array<String>)

    The attributes for the command.

  • chained (true, false) (defaults to: false)

    Whether or not this command is part of a command chain.

  • check_permissions (true, false) (defaults to: true)

    Whether the user's permission to execute the command (i.e. rate limits) should be checked.

Returns:

  • (String)

    the result of the execution.



145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
# File 'lib/onyxcord/commands/parser.rb', line 145

def call(event, arguments, chained = false, check_permissions = true)
  if arguments.length < @attributes[:min_args]
    response = "Too few arguments for command `#{name}`!"
    response += "\nUsage: `#{@attributes[:usage]}`" if @attributes[:usage]
    event.respond(response)
    return
  end
  if @attributes[:max_args] >= 0 && arguments.length > @attributes[:max_args]
    response = "Too many arguments for command `#{name}`!"
    response += "\nUsage: `#{@attributes[:usage]}`" if @attributes[:usage]
    event.respond(response)
    return
  end
  unless @attributes[:chain_usable] && !chained
    event.respond "Command `#{name}` cannot be used in a command chain!"
    return
  end

  if check_permissions
    rate_limited = event.bot.rate_limited?(@attributes[:bucket], event.author)
    if @attributes[:bucket] && rate_limited
      event.respond @attributes[:rate_limit_message].gsub('%time%', rate_limited.round(2).to_s) if @attributes[:rate_limit_message]
      return
    end
  end

  return unless @check.nil? || @check.call(event)

  @cog_before_invoke&.call(event)

  cancelled = @before_hooks.any? { |hook| hook.call(event, *arguments).is_a?(FalseClass) }
  return if cancelled

  result = @block.call(event, *arguments)
  event.drain_into(result)

  @after_hooks.each { |hook| hook.call(event, *arguments, result) }
  @cog_after_invoke&.call(event, result)

  result
rescue LocalJumpError => e # occurs when breaking
  result = e.exit_value
  event.drain_into(result)
rescue StandardError => e # Something went wrong inside our @block!
  rescue_value = @attributes[:rescue]
  return handle_rescue_value(rescue_value, event, e) if rescue_value
  return if @error_handler&.call(event, e)

  bot_rescue = event.bot.attributes[:rescue]
  return handle_rescue_value(bot_rescue, event, e) if bot_rescue

  raise e
end

#copy_for(receiver = nil) ⇒ Object



123
124
125
126
127
128
129
130
131
132
133
134
135
136
# File 'lib/onyxcord/commands/parser.rb', line 123

def copy_for(receiver = nil)
  block = @block
  copied = self.class.new(@name, @attributes.dup) do |event, *arguments|
    receiver ? receiver.instance_exec(event, *arguments, &block) : block.call(event, *arguments)
  end
  @before_hooks.each { |hook| copied.before { |event, *args| receiver ? receiver.instance_exec(event, *args, &hook) : hook.call(event, *args) } }
  @after_hooks.each { |hook| copied.after { |event, *args| receiver ? receiver.instance_exec(event, *args, &hook) : hook.call(event, *args) } }
  @subcommands.each { |name, sub| copied.subcommand(name) { |event, *args| sub.call(event, args) } }
  copied.instance_variable_set(:@check, proc { |event| receiver.__send__(:passed_cog_command_check?, event) }) if receiver
  copied.instance_variable_set(:@error_handler, proc { |event, error| receiver.__send__(:handled_cog_command_error?, event, error) }) if receiver
  copied.instance_variable_set(:@cog_before_invoke, proc { |event| receiver.__send__(:invoke_cog_before_invoke, event) }) if receiver
  copied.instance_variable_set(:@cog_after_invoke, proc { |event, result| receiver.__send__(:invoke_cog_after_invoke, event, result) }) if receiver
  copied
end

#find_subcommand(name) ⇒ Command?

Finds a subcommand by name.

Parameters:

  • name (Symbol, String)

    The subcommand name.

Returns:



119
120
121
# File 'lib/onyxcord/commands/parser.rb', line 119

def find_subcommand(name)
  @subcommands[name.to_sym]
end

#subcommand(name, attributes = {}) {|event, args| ... } ⇒ Command

Registers a subcommand on this command.

Parameters:

  • name (Symbol)

    The subcommand name.

  • attributes (Hash) (defaults to: {})

    Attributes forwarded to the subcommand.

Yield Parameters:

Returns:

  • (Command)

    The newly created subcommand.



107
108
109
110
111
# File 'lib/onyxcord/commands/parser.rb', line 107

def subcommand(name, attributes = {}, &block)
  sub = self.class.new(name, attributes, &block)
  @subcommands[name] = sub
  sub
end