def add_command(command, &callback)
      name = command_name(command[:syntax])

      # Add the command meta - used in the 'help' command response.
      add_command_meta(name, command)

      # Add the command spec - used for parsing incoming commands.
      add_command_spec(command, callback)

      # Add any command aliases to the command meta and spec
      unless command[:alias].nil?
        command[:alias].each { |a| add_command_alias(name, a, callback) }
      end
    end
def add_command(command, &callback)
      name = command_name(command[:syntax])

      # Add the command meta - used in the 'help' command response.
      add_command_meta(name, command)

      # Add the command spec - used for parsing incoming commands.
      add_command_spec(command, callback)

      # Add any command aliases to the command meta and spec
      unless command[:alias].nil?
        command[:alias].each { |a| add_command_alias(name, a, callback) }
      end
    end
Creates a new Jabber::Bot object with the specified +config+ Hash, which
 must contain +jabber_id+, +password+, and +master+ at a minimum.

 You may optionally give your bot a custom +name+. If +name+ is omitted,
 the username portion of +jabber_id+ is used instead.

 You may choose to restrict a Jabber::Bot to listen only to its master(s),
 or make it +public+.

 You may optionally specify a Jabber +presence+, +status+, and +priority+.
 If omitted, they each default to +nil+.

 By default, a Jabber::Bot has only a single command, 'help [<command>]',
 which displays a help message for the specified command, or all commands
 if <command> is omitted.

 If you choose to make a public bot, only the commands you specify as
 public, as well as the default 'help' command, will be public.

   # A minimally confiugured private bot with a single master.
   bot = Jabber::Bot.new(
     :jabber_id => 'bot@example.com',
     :password  => 'secret',
     :master    => 'master@example.com'
   )

   # A highly configured public bot with a custom name, mutliple masters,
   # Jabber presence, status, and priority.
   masters = ['master1@example.com', 'master2@example.com']

   bot = Jabber::Bot.new(
     :name      => 'PublicBot',
     :jabber_id => 'bot@example.com',
     :password  => 'secret',
     :master    => masters,
     :is_public => true,
     :presence  => :chat,
     :priority  => 5,
     :status    => 'Hello, I am PublicBot.'
   )

 Add a command to the bot's repertoire.

 Commands consist of a metadata Hash and a callback block. The metadata
 Hash *must* contain the command +syntax+, a +description+ for display with
 the builtin 'help' command, and a regular expression (+regex+) to detect
 the presence of the command in an incoming message.

 The command parameter(s) will be parsed from group(s) (text between
 parenthesis) in the +regex+. If there's none, one, or more than one
 occurrence, the callback block will receive respectively nil, a String,
 or an Array.
 e.g. With a command defined like this: /^cmd\s+(.+)\s+(.+)\s+(.+)$/,
 writing "cmd foo bar 42" will send ["foo", "bar", "42"] to the callback
 block.

 The metadata Hash may optionally contain an array of command aliases. An
 +alias+ consists of an alias +syntax+ and +regex+. Aliases allow the bot
 to understand command shorthands. For example, the default 'help' command
 has an alias '?'. Saying either 'help' or '?' will trigger the same
 command callback block.

 The metadata Hash may optionally contain a +is_public+ flag, indicating
 the bot should respond to *anyone* issuing the command, not just the bot
 master(s). Public commands are only truly public if the bot itself has
 been made public.

 The specified callback block will be triggered when the bot receives a
 message that matches the given command regex (or an alias regex). The
 callback block will have access to the sender and the parameter(s) (not
 including the command itself), and should either return a String response
 or +nil+. If a callback block returns a String response, the response will
 be delivered to the Jabber id that issued the command.

 Examples:

   # Say 'puts foo' or 'p foo' and 'foo' will be written to $stdout.
   # The bot will also respond with "'foo' written to $stdout."
   add_command(
     :syntax      => 'puts <string>',
     :description => 'Write something to $stdout',
     :regex       => /^puts\s+(.+)$/,
     :alias       => [ :syntax => 'p <string>', :regex => /^p\s+(.+)$/ ]
   ) do |sender, message|
     puts "#{sender} says #{message}."
     "'#{message}' written to $stdout."
   end

   # 'puts!' is a non-responding version of 'puts', and has two aliases,
   # 'p!' and '!'
   add_command(
     :syntax      => 'puts! <string>',
     :description => 'Write something to $stdout (without response)',
     :regex       => /^puts!\s+(.+)$/,
     :alias       => [
       { :syntax => 'p! <string>', :regex => /^p!\s+(.+)$/ },
       { :syntax => '! <string>', :regex => /^!\s+(.+)$/ }
     ]
   ) do |sender, message|
     puts "#{sender} says #{message}."
     nil
   end

  # 'rand' is a public command that produces a random number from 0 to 10
  add_command(
   :syntax      => 'rand',
   :description => 'Produce a random number from 0 to 10',
   :regex       => /^rand$/,
   :is_public   => true
  ) { rand(10).to_s }