class Lita::Handlers::DiscordHelp

Public Instance Methods

help(response) click to toggle source

Outputs help information about Lita commands. @param response [Lita::Response] The response object. @return [void]

# File lib/lita/handlers/discord_help.rb, line 21
def help(response)
  output = build_help(response)
  output = filter_help(output, response)
  first_message = true

  output = output.join("\n")

  messages = split_message(output)

  Lita.logger.debug(messages)

  messages.each { |message|
    if first_message
      response.reply_privately("```\n#{message}\n```")
      first_message = false
    else
      response.reply_privately("|||NOMENTION|||```\n#{message}\n```")
    end
  }

  if messages.length > 1
    response.reply_privately('Sorry for splitting that up in multiple messages, Discord doesn\'t allow me to send responses longer than 2000 characters :(')
  end

end

Private Instance Methods

authorized?(user, required_groups) click to toggle source

Checks if the user is authorized to at least one of the given groups.

# File lib/lita/handlers/discord_help.rb, line 125
def authorized?(user, required_groups)
  required_groups.nil? || required_groups.any? do |group|
    robot.auth.user_in_group?(user, group)
  end
end
build_help(response) click to toggle source

Creates an array of help info for all registered routes.

# File lib/lita/handlers/discord_help.rb, line 132
def build_help(response)
  robot.handlers.map do |handler|
    next unless handler.respond_to?(:routes)

    handler.routes.map do |route|
      route.help.map do |command, description|
        if authorized?(response.user, route.required_groups)
          help_command(route, command, description)
        end
      end
    end
  end.flatten.compact
end
filter_help(output, response) click to toggle source

Filters the help output by an optional command.

# File lib/lita/handlers/discord_help.rb, line 147
def filter_help(output, response)
  filter = response.matches[0][0]

  if filter
    output.select { |line| /(?:@?#{name}[:,]?)?#{filter}/i === line }
  else
    output
  end
end
get_message_part(message, limit) click to toggle source
# File lib/lita/handlers/discord_help.rb, line 76
def get_message_part(message, limit)
  Lita.logger.debug("Getting message part from #{message}")

  Lita.logger.debug('Message was short enough, returning without modifications') if message.length <= limit
  return message if message.length <= limit # No need to check anything if the message is short enough

  part = message.to_s[0...limit - 1]
  break_index = part.rindex("\n")

  Lita.logger.debug("Break index: #{break_index}")

  if break_index != nil && break_index != 0
    message[0, break_index]
  else
    message
  end
end
help_command(route, command, description) click to toggle source

Formats an individual command's help message.

# File lib/lita/handlers/discord_help.rb, line 158
def help_command(route, command, description)
  command = "#{name}: #{command}" if route.command?

  table_row(command, description)
end
name() click to toggle source

The way the bot should be addressed in order to trigger a command.

# File lib/lita/handlers/discord_help.rb, line 165
def name
  robot.config.robot.mention_name || robot.config.robot.name
end
split_message(message) click to toggle source
# File lib/lita/handlers/discord_help.rb, line 49
def split_message(message)
  max_length = 2000 - 30 # Substract 25 for mention safety
  messages = Array.new

  if message.length < max_length
    messages.push(message)
  else
    message_copy = message

    loop do
      Lita.logger.debug("Message copy: #{message_copy}")
      # part = 'Lorem ipsum, dolor sit amet' # I don't know why we need this, but we do

      part = get_message_part(message_copy, max_length)

      Lita.logger.debug("Part: #{part}")
      part = message_copy.slice!(part)
      messages.push(part)

      break if message_copy.length <= 0
    end

  end

  messages
end
table_row(key, value) click to toggle source
# File lib/lita/handlers/discord_help.rb, line 94
def table_row(key, value)
  key_width = 30
  value_width = 107

  key_text = key.ljust(key_width, ' ')

  value_words = value.split(' ')

  value_text = ''
  value_line = ''

  value_words.each do |word|
    new_value_line = "#{value_line} #{word}"

    if new_value_line.length > value_width
      value_text += "#{value_line}\n" + ''.ljust(key_width + 1, ' ')
      value_line = word
    else
      value_line = "#{value_line} #{word}"
    end

  end

  if value_line.length > 0
    value_text = "#{value_text}\n" + ''.ljust(key_width + 1, ' ') + "#{value_line}"
  end

  key_text + value_text + "\n"
end