NightMAREbotDev

This is a place for documentation and development discussion related to NightMAREbot. Request features with the comment box under Development discussion.

How he works

NightMAREbot is a combination of TinyFugue macros, MARE-side softcode, and shell scripting. The core code consists of several TinyFugue macros and triggers. The TinyFugue code is used to to provide an interaction between the softcode and the shell scripts, as well as provide softcode with channel text.

TinyFugue: the guts

Connection-related and convenience

The reconnect hook causes NightMAREbot to attempt to connect when a connection to a world fails. This hook does not fire if NightMAREbot QUITs or is kicked off with .@boot.

/def -p0 -mglob -h'CONFAIL onfail' = 
   /connect %1

There are a handful of convenience hooks, gags, and macros to help make the experience more pleasant for whoever is connected to NightMAREbot's TinyFugue session.

  • First off is the keep-alive gag. This trigger gags the output from NightMAREbot's keep-alive message. Once a minute the Player Character .@echos @@-IGNORE-@@ to keep QBFreak's NAT from dropping the connection when things get quiet
  • Another convenience hook is provided to automatically switch worlds on activity. It comes with a gags to hide the activity notification that typically displays before the switch is made
  • The BACKGROUND hook hides the macro in <world> notification
  • The redraw_status command can be used to redraw the status line, it is often corrupted when TinyFugue throws an error

/def -p0 -ag -mglob -t'@@-IGNORE-@@'
/def -p0 -h'ACTIVITY' = /fg %1
/def -Fp1 -ag -mglob -h'ACTIVITY '
/def -p1 -ag -mglob -h'BACKGROUND '
/def redraw_status = /set status_fields=%{status_fields}


/broadcast command

The /broadcast macro /send=s commands to all MAREs except the current one. The primary use is for the intermare channel. Each line sent is then stored in the =lastinter variable.

/def broadcast =
   /require -q lisp.tf %;
   /if ({lastinter} !~ {*})
      /let worlds=$(/remove ${world_name} %{marelist}) %;
      /while /test ($(/length %{worlds}) > 0) %;
         /do /send -w$(/car %{worlds}) intermare %{*} %;
         /let worlds=$(/cdr %{worlds}) %;
      /done %;
   /endif %;
   /set lastinter=%{*}


/procchan trigger

NightMAREbot sends all channel activity back to the MARE, this is one of the few things on the MARE that cannot be obtained directly through softcode. All channel activity is sent back exactly as it is received, to the procchan command. The trigger is defined as a fall-through so that other triggers can match channel output as well.

/def -Fp1 -mregexp -t'^\[[^ ]+\] .*' procchan = procchan %*


/intermare trigger

As an experiment, QBFreak set up the ChannelIntermare[intermare]] channel, the goal was to see if NightMAREbot could reliably provide inter-mare communication. While successful, it lacks polish and only links FreeMARE to SluggyMARE. The feature is considered to be in an alpha state and may be removed at any time.

/def -Fp1 -mregexp -t'^\[intermare\] .*' intermare =
   /broadcast $(/cdr %*)


/gettitle trigger

NightMAREbot will send page titles back to the MARE whenever he sees a link starting with http:// in a channel. The softcode is responsible for handling this properly. In addition to a space, the trigger uses the following characters as URL terminators: <>;|. This is done to prevent specially crafted URLs from running commands in the shell.

/def -Fp1 -mregexp -t'^\[([^ ]+)\].*(http://[^ <>;|]*)' gettitle =
   /quote title %{P1} !"~/gettitle.pl %{P2}"


His soft chocolaty inside (well, softcode)

On the softcode side, very little is on the bot's Player Character itself. Most events are handled by custom commands on other objects. Each object or parent is documented in it's own topic. Currently the objects communicate with the bot and each other through whatever method seemed easiest at the time. A common set of commands will be implimented in the near future.

The following parents are used on the PC:

A growing number of other objects are used to provide specific features. Disabling these features is often as easy as setting the object's haven flag. A list of these objects follows:

The outer candy shell (scripts)

getusage.pl

getusage.pl retreives command usage from the TWiki. It requires the topic name as the first argument and returns all lines that match the following TWiki-markup criteria:
  • The line starts and ends with an equal sign (text that looks like this)
  • The line exists after the first level three heading (---+++)
  • Lines not matching the first criteria have been found after the second criteria yet

That description is rather confusing, here is an example match that might clarify it:
1: ---++ HelpText
2: ---+++ @Foo
3: =@foo &lt;bar&gt;=
4: =@foo &lt;bar&gt;=&lt;baz&gt;=
5: 
6: @Foo does not exist. It is only used for illustration purposes.
The matching begins after finding the heading on line 2. The following lines that start and end with = (lines 3 and 4) are returned. The matching stops when line 5 is encountered.

Each topic requested is cached in the file .bot.usage.temp and the URL is stored in .bot.usage.lasturl. If the URL for the topic requested matches the URL in .bot.usage.lasturl then the cached page is processed instead of re-requesting the topic. The cache can be cleared by requesting a new or non-existant topic.

If the requested topic cannot be found, the script responds with Sorry, that command isn't in the TWiki., if no parameters are passed it responds with Ack! Tell QB that the usage trigger is broken..


gettitle.pl

gettitle.pl retreives the contents of the title tags from a web page. It has one required parameter, the URL to the page. If no parameter is passed or the title tags cannot be found the script exits silently. When retreiving the page the script instructs wget to only accept MIME types containing the string text, this prevents the script from downloading image, archive, executable, or other binary files.


Todo list

  • Design and impliment a set of common commands for objects to communicate with the bot and eachother

Development discussion

Discuss development and related topics of NightMAREbot here. You can request features here, but please don't request the same feature twice (variations of an existing feature are ok).

note If SluggyQBFreak or another admin is considering implimenting a feature it will be listed on NightMAREbot's page in the appropriate category.


Command handler

SluggyTheFool suggested an order type feature. I'm thinking the best way to do this would be to write a common command handler, to either catch all 'nmb foo commands, all !foo commands or both.

This could easilly be integrated into the existing design by creating a new object that accepts and parses the procchan command and then fires a new botcmd command.

Suggestions and comments on this are welcome.

-- SluggyQBFreak - 08 Jan 2006


Botlets

NightMAREbotBotlets are parented objects that provide a common interface for bot programming.

-- SluggyQBFreak - 21 Jan 2006

 

-- SluggyQBFreak - 08 Jan 2006
Topic revision: r2 - 21 Jan 2006, SluggyQBFreak
This site is powered by FoswikiCopyright © by the contributing authors. All material on this collaboration platform is the property of the contributing authors.
Ideas, requests, problems regarding WikiMARE? Send feedback