   This file documents Bobot++ by Clinton Ebadi and Etienne Bernard
(original author, no longer works on program).

   This document describes Bobot++ by Clinton Ebadi and Etienne Bernard
(original author, no longer works on program).

   This document applies to version 2.1.0 of the program named Bobot++

   Copyright 2002 Clinton Ebadi

   Permission is granted to copy, distribute and/or modify this document
under the terms of the GNU Free Documentation License, Version 1.1 or
any later version published by the Free Software Foundation; with no
Invariant Sections, with no Front-Cover Texts, and with no Back-Cover
Texts.

Introduction
************

   This manual feels abused and neglected because it has almost no
content.

Configuration
*************

   Bobot++ is easy to configure. The configuration file format may be
changing in the 2.1 series, so it is not documented for now. See the
`examples' directory for an example configuration.

Configuration File Syntax
=========================

   Not here yet.

Configuration File Placement
============================

   Bobot++ will look in `/etc/bobotpp/default/' for its default config
if none is specified on the command line. Put the configuration files
you want to be loaded by default in this directory. If you are not root
or you want to have your own personal configration, put it in
`~/.bobotpp/config/default/'.

Using Bobot++
*************

   FIXME: stuff here...

User Levels
===========

   There are five levels that a user may be when interfacing with a bot:
NONE, USER, TRUSTED_USER, FRIEND, MASTER. All users default to NONE
unless they are changed by a script, the `!adduser' command or the
`bot.users' file. NONE is for everyone--very few commands (e.g. help)
are available to the users and almost everyone should be this level. A
USER can execute many of the bot commands, but can't use masks on kicks
and bans. A TRUSTED user can everything a USER can do, but can also use
masks on kicks and bans. A FRIEND can do everything except for stopping
the bot (be careful who you give this to!). The MASTER level is for the
bot's owner (probably you) and can do _everything_ to the bot. Be
_very_ careful if you give MASTER level access to anyone else. You
cannot use this symbolic levels with the `!adduser' command. See
(FIXME: ref) for the numbers you must use with `!adduser'.

Scripting
*********

   Bobot++'s most powerful feature is its scripting system. You write
scripts using Guile Scheme. This manual does not cover how to use Guile
or how to learn Scheme. See Guile Reference Manual (guile), for
the Guile reference manual and
<http://www.ccs.neu.edu/home/dorai/t-y-scheme/t-y-scheme.html> for a
good tutorial on Scheme.

   Note that in previous versions the scripting commands where in the
form `bot-FUNCTION'. They are now in the form `bot:FUNCTION'. The old
names are still available, but are deprecated and will be removed in
Bobot++ 2.4. The command `perl -pi -e ``s/bot-/bot:/g'' YOUR-FILES'
should be enough to convert your code to use the new functions.

Adding New Commands
===================

   Adding a new command is simple. To register a new command use
`bot:addcommand'. The prototype for `bot:addcommand' is
`(bot:addcommand name func needs-channel? num-of-args min-level)'. The
`name' is a string representing the name of the command being added.
`func' is a function accepting `num-of-args' arguments.
`needs-channel?' is a bool that is true if the function needs the
channel name as its first arg, and false otherwise. `num-of-args' is
the number of args `func' will take and must be within zero (0) and
twenty (20). `min-level' is one of the Scheme User Levels. A
user must be at least a `min-level' user to use the new command. None
of the arguments are guaranteed to be passed; if they aren't they are
set to the empty string `""'. An example of a new command would be:

     (define (hello channel name)
       (if (string=? name "")
         (bot:say channel "Hello world!")
         (bot:say channel (string-append "Hello " name "!")))

     (bot:addcommand "hello" hello #t 2 0)

   This will display "Hello World!" if called as `!hello' and "Hello
World `USER'" if called as `!hello USER'.

Hooks
=====

   Hooks are a powerful feature of Bobot++. Hooks are a hybrid of ircII
and tiny fugue (a MUD bot) hooks with a little bit of extra stuff added
in. The basic idea of a hook if that you match a text against regular
expression and call a function if text in a message matches that regex.
The different types of hooks provided by Bobot++ correspond to the
different classes of messages that Bobot++ can recieve. A Hook also has
several properties, including its priority and whether or not it is a
fallthrough hook. Higher priority hooks are executed before lower
priority hooks and fallthrough hooks are executed before
non-fallthrough hooks of the same priority. A fallthrough hook can
match and processing of hooks will continue; as soon as the first
non-fallthrough hooks matches processing of hooks stops.

Creating a Hook
---------------

   To add a new hook you use the function `bot:addhook'. `bot:addhook'
is prototyped as `(bot:addhook type regex function pri fall name)'.
`type' specifies the type of hook (the types of hooks are listed in
Hook Types). `regex' is a standard regular expression. If
`regex' is matched, `function' will be called. `function' will take a
different number of args depending on the hook type. `pri' specifies
the priority of the hook--higher priority hooks are executed first.
This argument is optional and defaults to `0'. `fall' is `#t' if the
hook is a fallthrough hook and `#f' is the hook is not a fallthrough
hook. This arg is also optional and default to `#t'. `name' is the
optional name of the hook that defaults to "DEFAULT". If you set the
name then you can have more than one hook that matches the same regexp,
as long as they have the same name. E.g. in a log script you could have
the regexps for the log function all be `".*"' and set their names to
`"log"' to avoid a conflict with other hooks.

Hook Types
----------

   Here is a list of the various hooks are notes on each one. The
general format of a hook is:

   * `hooks/name' (this is the Scheme variable name of the hook)
        - Description of the hook

        - ARG1 ARG2 ... ARGN
             - ARG1: desc

             - ARG2: desc

             - ...

             - ARGN: desc

   That said, here is the list of available hooks: FIXME: write docs

   * `hooks/action'
        - This hook is triggered when someone performs an action.

        - FROM, TO, ACTION
             - FROM: this is the address of the person that performed
               the action in the form `NICK ! USER @ HOST' (without the
               spaces).

             - TO: This is the target of the action, which is either a
               channel or the Bot's nick.

             - ACTION: This is the text of the action. E.g. if someone
               did `* foobar does baz', then ACTION would be the string
               `"does baz"'.

   * `hooks/nickname'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/signoff'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/ctcp'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/ctcp-reply'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/disconnect'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/flood'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/invite'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/join'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/kick'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/part'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/mode'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/message'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/notice'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/public'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/public-notice'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/raw'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/timer'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/topic'
        - Description of the hook

        - # of args
             - `arg1': desc

   * `hooks/dcc/begin'
        - This hook is triggered when a user begins a DCC CHAT with the
          bot.

        - FROM
             - FROM: This is the user's address in the form
               `nick!user@host'.

   * `hooks/dcc/message'
        - This hook is triggered when a user sends a message to the bot
          through a DCC CHAT

        - FROM MESSAGE
             - FROM: This is the user's address in the form
               `nick!user@host'.

             - MESSAGE: This is the message the user sent to the bot.

Scheme User Levels
==================

   There are five levels that a user may be when interfacing with a bot:
NONE, USER, TRUSTED_USER, FRIEND, MASTER. The Scheme variables for the
user levels are `bot:user-none', `bot:user-user', `bot:user-trusted',
`bot:user-friend', and `bot:user-master'. See User Levels for
more information on User Levels.

   When adding a new command, think about who should be able to use it.
Is your command a general purpose command that helps the channel (e.g.
`!seen') that everyone should be able to use? Or is it something that
should be restricted? See User Levels for information on what
level users can do what with the built in bot commands and think about
what level a user your command is targetted towards. You must be _very_
careful when giving new commands to lower level users because you can
do basically everything the bot can do with a script. As the scripting
interface becomes more powerful, you must think more about what users
can use new commands you add.

Sending Messages
================

   There are several types of messages you can send with Bobot++ from
scripts. There is the simple, but rather limited, `bot:say',
`bot:action' and `bot:msg', and the more powerful, but lower level,
`bot:send-MESSAGE' functions. Most bots will probably only need the
higher level functions, but for the sake of why-not Bobot++ lets you
use the lower level functions.

"High Level" Message Functions
------------------------------

   ...

"Low Level" Message Functions
-----------------------------

   The "Low Level" messaging functions allow you to do things like send
CTCP messages. You probably want to read rfc 2812 and the CTCP spec
before using these. If you have no idea what these do, read rfc 2812
(IRC Client Protocol) and CTCP spec. These functions all return
`*unspecified*' always, so don't use the return value for anything.

   * `bot:send-CTCP to command message' `to' is the target of your CTCP
     message, `command' is the CTCP command, and `message' is the
     message (or arguments) of the command. Make sure to
     `bot:ctcp-quote' the message!

Misc. Scripting Stuff
=====================

   These are a few useful things that I thought people writing scripts
might want to know.

   If you want to execute code when the bot exits, just do `add-hook!
bot:exit-hook THUNK' where THUNK is an argumentless procedure (a
thunk). When the bot exits your thunk will be called.

Concept Index
*************

Function Index
**************