mirror of
https://github.com/reality/dbot.git
synced 2024-11-27 14:29:29 +01:00
Merge branch 'master' of git://github.com/reality/depressionbot into weboverhaul
Conflicts: modules/quotes/quotes.js modules/users/users.js run.js
This commit is contained in:
commit
f91fc99d35
18
LICENCE
Normal file
18
LICENCE
Normal file
@ -0,0 +1,18 @@
|
||||
Copyright (c) 2012 Luke Slater (tinmachin3@gmail.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
this software and associated documentation files (the "Software"), to deal in
|
||||
the Software without restriction, including without limitation the rights to
|
||||
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
||||
the Software, and to permit persons to whom the Software is furnished to do so,
|
||||
subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
||||
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
||||
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
108
README.md
108
README.md
@ -3,8 +3,8 @@
|
||||
## Introduction
|
||||
|
||||
Depressionbot is an IRC bot which aims to be the fanciest IRC bot around - On
|
||||
the general standard of software fanciness, dbot is rated as being '81% the same
|
||||
as bathing in fine, fine grape juice.'
|
||||
the general standard of software fanciness, dbot is statistically rated as being
|
||||
'82% the same as bathing in fine, fine grape juice.'
|
||||
|
||||
Please note that this documentation is not complete and is a work in progress,
|
||||
given I started it rather a long time after I began development of the project.
|
||||
@ -18,108 +18,10 @@ Requirements:
|
||||
handles the IRC protocol.
|
||||
- Various modules have their own requirements also.
|
||||
|
||||
### JSBot
|
||||
### External Modules
|
||||
|
||||
JSBot can be imported by running the following commands in the cloned repository:
|
||||
JSBot and externally developed modules can be imported by running the following
|
||||
commands in the cloned repository:
|
||||
|
||||
git submodule init
|
||||
git submodule update
|
||||
|
||||
## Modules:
|
||||
|
||||
### Command
|
||||
|
||||
This handles the command execution logic for DBot.
|
||||
|
||||
1. Does the input match a command key in *dbot.commands* ?
|
||||
2. Is there a quote category which matches the first part of the input
|
||||
(*~category*)?
|
||||
3. Is there a command name similar to to the first part of the input (*~name*)
|
||||
in *dbot.commands*?
|
||||
|
||||
This is the only module which is force loaded, even if it's not in the
|
||||
configuration.
|
||||
|
||||
### Quotes
|
||||
|
||||
This is the original reason that DBot was created, stores and displays quotes.
|
||||
|
||||
Commands:
|
||||
|
||||
- _~q category_ - Display a random quote from a given category.
|
||||
- _~qadd category=newquote_ - Add a new quote to the database.
|
||||
- _~qstats_ - Show a list of the biggest quote categories.
|
||||
- _~qsearch category needle_ - Search for a quote in a given category.
|
||||
- _~rmlast [category]_ - Remove the last quote added to a given category, or the
|
||||
last quote added.
|
||||
- _~rm category quote_ - Remove a given quote from the given category.
|
||||
- _~qcount category_ - Show the number of quotes stored in the given category.
|
||||
- _~rq_ - Show a random quote from a random category.
|
||||
- _~d_ - Show a quote from the category which matches the bot's name.
|
||||
- _~link category_ - Create a link to the page on the web interface which displays the
|
||||
given category's quotes.
|
||||
- _~qprune_ - Delete empty quote categories.
|
||||
|
||||
Unfortunately, this module is fairly highly coupled with certain other areas of
|
||||
the program. I am working on this, but note, for example, that one can still
|
||||
access quotes with the *~category* syntax even if the quotes module isn't
|
||||
loaded.
|
||||
|
||||
### Admin
|
||||
|
||||
Various administration functionality such as banning users, hot-reloading the
|
||||
code and ordering him to talk. Note that commands added here are handled with
|
||||
their own listener, rather than being part of the command logic which is handled
|
||||
by the Command module. Functionality in this module can be slightly unsafe as
|
||||
not much error checking on the input is performed.
|
||||
|
||||
TODO: Add summaries for each command in this module.
|
||||
|
||||
### Spelling
|
||||
|
||||
Will attempt to correct a users' spelling by using the levenshtein distance
|
||||
algorithm. One corrects the spelling of their previous message by simply posting
|
||||
a message with their correction and an asterisk:
|
||||
|
||||
> user: I am a tutrle.
|
||||
> user: *turtle
|
||||
user meant: I am a turtle.
|
||||
|
||||
The regular expression for this module also accepts two asterisks at the
|
||||
beginning of the correction, or at the end; it also accepts several words as the
|
||||
correction and deals with these fairly intelligently. Users may also attempt
|
||||
to correct another users like so:
|
||||
|
||||
> userone: I am a tutrle.
|
||||
> usertwo: userone: *turtle
|
||||
> usertwo thinks userone meant: I am a turtle.
|
||||
|
||||
### JS
|
||||
|
||||
This module provides two commands which allow the execution of Javascript code.
|
||||
For regular users, there is the *~js* command, which is completely sandboxed,
|
||||
but can still be used for calculation and the like.
|
||||
|
||||
> ~js Array(16).join('wat'-1) + " Batman!";
|
||||
'NaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaN Batman!'
|
||||
|
||||
This feature is fairly safe as the user doesn't have access to anything
|
||||
dangerous, and is safe from infinite loops or locking DBot up because the code
|
||||
which is run is killed if it does not finish within a short amount of time.
|
||||
|
||||
For administrators, the incredibly useful *~ajs* command is also available. The
|
||||
input for this command is simply 'eval'-ed and therefore has full access to
|
||||
DBot's memory. Of course, this is incredibly unsafe, but I find it rather fun;
|
||||
remember to only give extremely trusted friends administrator access to DBot, as
|
||||
there's nothing to stop them wiping the database or something similar - if
|
||||
you're worried about that kind of thing, do not load this module.
|
||||
|
||||
However, it's useful for many things, such as administrative activity for
|
||||
which there isn't a command in the admin module. For example, you could hot-add
|
||||
a new administrator like this:
|
||||
|
||||
> ~ajs dbot.admin.push('batman');
|
||||
2
|
||||
|
||||
You can also use this for debugging, or even adding new commands while DBot is
|
||||
running.
|
||||
|
57
modules/admin/README.md
Normal file
57
modules/admin/README.md
Normal file
@ -0,0 +1,57 @@
|
||||
## Admin
|
||||
|
||||
Administrator functionality.
|
||||
|
||||
### Description
|
||||
|
||||
Various administration functionality such as banning users, hot-reloading the
|
||||
code and ordering him to talk. Note that commands added here are handled with
|
||||
their own listener, rather than being part of the command logic which is handled
|
||||
by the Command module. Functionality in this module can be slightly unsafe as
|
||||
not everything is thoroughly sanity checked.
|
||||
|
||||
### Commands
|
||||
|
||||
#### join [#channel]
|
||||
Join the given channel.
|
||||
|
||||
#### part [#channel]
|
||||
Leave the given channel.
|
||||
|
||||
#### opme [#channel]
|
||||
Gives the caller ops in a given channel if possible. If called without a
|
||||
channel, it will attempt to give the caller ops in the current channel.
|
||||
|
||||
#### greload
|
||||
Perform a git pull, and then execute the 'reload' command. Saves a lot of time
|
||||
updating!
|
||||
|
||||
#### reload
|
||||
Reload all of the modules currently in use by DBot. By using this, all module
|
||||
functionality should be reloadable and replaceable without having to restart the
|
||||
bot or interrupt the connection to the server.
|
||||
|
||||
#### say [#channel] [message]
|
||||
Have DBot post the given message in the given channel (uses the server from
|
||||
which you are sending the message). You may replace channel with '@' to have him
|
||||
post the message in the current channel. Channel may also be replaced with a
|
||||
nick on the server.
|
||||
|
||||
#### load [module]
|
||||
Load a new module. This works by adding a module name to the roster and then
|
||||
triggering a reload of all modules, at which point the new module is actually
|
||||
loaded by the standard DBot process.
|
||||
|
||||
#### unload [module]
|
||||
Unload a currently loaded module. This removes the module, and then triggers a
|
||||
reload of all modules.
|
||||
|
||||
#### ban [user] [command]
|
||||
Ban a user from using a command. Command may be replaced with '\*,' which will
|
||||
ban a user from use of all commands. Users banned from all commands will still
|
||||
be subject to module listeners.
|
||||
|
||||
#### unban [user] [command]
|
||||
Unban a user from using a given command. If a user was previously banned using
|
||||
the '\*' wildcard, they may also be unbanned from such by replacing command with
|
||||
an asterisk here as well.
|
@ -13,7 +13,7 @@ var admin = function(dbot) {
|
||||
'join': function(event) {
|
||||
var channel = event.params[1];
|
||||
if(event.allChannels.hasOwnProperty(channel)) {
|
||||
event.reply("I'm already in that channel.");
|
||||
event.reply(dbot.t('already_in_channel', {'channel': channel}));
|
||||
} else {
|
||||
dbot.instance.join(event, channel);
|
||||
event.reply(dbot.t('join', {'channel': channel}));
|
||||
@ -24,7 +24,7 @@ var admin = function(dbot) {
|
||||
'part': function(event) {
|
||||
var channel = event.params[1];
|
||||
if(!event.allChannels.hasOwnProperty(channel)) {
|
||||
event.reply("I'm not in that channel.");
|
||||
event.reply(dbot.t('not_in_channel', {'channel': channel}));
|
||||
} else {
|
||||
event.instance.part(event, channel);
|
||||
event.reply(dbot.t('part', {'channel': channel}));
|
||||
@ -44,9 +44,11 @@ var admin = function(dbot) {
|
||||
|
||||
// Do a git pull and reload
|
||||
'greload': function(event) {
|
||||
var child = exec("git pull", function (error, stdout, stderr) {
|
||||
event.reply(dbot.t('gpull'));
|
||||
commands.reload(event);
|
||||
exec("git pull", function (error, stdout, stderr) {
|
||||
exec("git submodule update", function (error, stdout, stderr) {
|
||||
event.reply(dbot.t('gpull'));
|
||||
commands.reload(event);
|
||||
}.bind(this));
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
@ -57,7 +59,7 @@ var admin = function(dbot) {
|
||||
event.reply(dbot.t('reload'));
|
||||
},
|
||||
|
||||
// Say something in a channel (TODO probably doesn't work.)
|
||||
// Say something in a channel
|
||||
'say': function(event) {
|
||||
var channel = event.params[1];
|
||||
if(event.params[1] === "@") {
|
||||
@ -116,13 +118,6 @@ var admin = function(dbot) {
|
||||
} else {
|
||||
event.reply(dbot.t('unban_error', {'user': username}));
|
||||
}
|
||||
},
|
||||
|
||||
// Lock quote category so quotes can't be removed
|
||||
'lock': function(event) {
|
||||
var category = event.params[1];
|
||||
dbot.db.locks.push(category);
|
||||
event.reply(dbot.t('qlock', {'category': category}));
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -1,3 +1,4 @@
|
||||
{
|
||||
"dbKeys": [ "bans", "locks" ]
|
||||
"dbKeys": [ "bans" ],
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/admin/README.md"
|
||||
}
|
||||
|
@ -64,5 +64,11 @@
|
||||
"spanish": "Cerrado la categoría: {category}",
|
||||
"na'vi": "{category}ìri oel 'upxareti fmoli",
|
||||
"welsh": "Categori wedi cloi: {category}"
|
||||
},
|
||||
"already_in_channel": {
|
||||
"english": "I'm already in {channel}"
|
||||
},
|
||||
"not_in_channel": {
|
||||
"english": "I'm not in {channel}"
|
||||
}
|
||||
}
|
||||
|
14
modules/command/README.md
Normal file
14
modules/command/README.md
Normal file
@ -0,0 +1,14 @@
|
||||
## Command
|
||||
|
||||
Handles the command execution logic for DBot.
|
||||
|
||||
### Description
|
||||
|
||||
1. Does the input match a command key in *dbot.commands* ?
|
||||
2. Is there a quote category which matches the first part of the input
|
||||
(*~category*)?
|
||||
3. Is there a command name similar to to the first part of the input (*~name*)
|
||||
in *dbot.commands*?
|
||||
|
||||
This is the only module which is force loaded, even if it's not specified in
|
||||
the configuration file.
|
@ -57,10 +57,34 @@ var command = function(dbot) {
|
||||
'~usage': function(event) {
|
||||
var commandName = event.params[1];
|
||||
if(dbot.usage.hasOwnProperty(commandName)) {
|
||||
event.reply('Usage for ' + commandName + ': ' +
|
||||
dbot.usage[commandName]);
|
||||
event.reply(dbot.t('usage', {
|
||||
'command': commandName,
|
||||
'usage': dbot.usage[commandName]
|
||||
}));
|
||||
} else {
|
||||
event.reply('No usage information for ' + commandName);
|
||||
event.reply(dbot.t('no_usage_info', {
|
||||
'command': commandName
|
||||
}));
|
||||
}
|
||||
},
|
||||
|
||||
'~help': function(event) {
|
||||
var moduleName = event.params[1];
|
||||
if(!dbot.modules.hasOwnProperty(moduleName)) {
|
||||
var moduleName = dbot.commandMap[moduleName];
|
||||
}
|
||||
|
||||
if(moduleName && dbot.config[moduleName].hasOwnProperty('help')) {
|
||||
var help = dbot.config[moduleName].help;
|
||||
event.reply(dbot.t('help_link', {
|
||||
'module': moduleName,
|
||||
'link': help
|
||||
}));
|
||||
} else {
|
||||
if(!moduleName) {
|
||||
moduleName = event.params[1];
|
||||
}
|
||||
event.reply(dbot.t('no_help', { 'module': moduleName }))
|
||||
}
|
||||
}
|
||||
},
|
||||
|
3
modules/command/config.json
Normal file
3
modules/command/config.json
Normal file
@ -0,0 +1,3 @@
|
||||
{
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/command/README.md"
|
||||
}
|
@ -10,5 +10,17 @@
|
||||
"spanish": "Sintaxis no válida. Iniciar incineración.",
|
||||
"na'vi": "Ngeyä pamrel keyawr lu. Nga skxawng lu.",
|
||||
"welsh": "Cystrawen annilys. Cychwyn orfflosgiad"
|
||||
},
|
||||
"usage": {
|
||||
"english": "Usage for {command}: {usage}."
|
||||
},
|
||||
"no_usage_info": {
|
||||
"english": "No usage information found for {command}."
|
||||
},
|
||||
"help_link": {
|
||||
"english": "Help for {module}: {link}"
|
||||
},
|
||||
"no_help": {
|
||||
"english": "No help found for {module}."
|
||||
}
|
||||
}
|
||||
|
26
modules/ignore/README.md
Normal file
26
modules/ignore/README.md
Normal file
@ -0,0 +1,26 @@
|
||||
## Ignore
|
||||
|
||||
Ignore modules.
|
||||
|
||||
### Description
|
||||
|
||||
Commands with which users can choose to ignore listeners and commands from
|
||||
certain modules persistently, by storing their choices in the database. This is
|
||||
an interface for the JSBot ignoreTag functionality which actually implements
|
||||
the ignoration.
|
||||
|
||||
### Configuration
|
||||
|
||||
All modules may return with them an 'ignorable' property, which defines whether
|
||||
or not their functionality may be ignored by users.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~ignore [module]
|
||||
Ignore a given module. If the user does not specify a module, or provides an
|
||||
invalid one a list of modules which are available to ignore will be given.
|
||||
|
||||
#### ~unignore [module]
|
||||
Unignore a previously ignored module. If the user does not specify a module, or
|
||||
provides an invalid choice a list of modules which are currently ignored will be
|
||||
given.
|
@ -1,3 +1,4 @@
|
||||
{
|
||||
"dbKeys": [ "ignores" ]
|
||||
"dbKeys": [ "ignores" ],
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/ignore/README.md"
|
||||
}
|
||||
|
@ -7,12 +7,11 @@
|
||||
var ignore = function(dbot) {
|
||||
var commands = {
|
||||
'~ignore': function(event) {
|
||||
var ignorableModules = [];
|
||||
for(var i=0;i<dbot.modules.length;i++) {
|
||||
if(dbot.modules[i].ignorable != null && dbot.modules[i].ignorable == true) {
|
||||
ignorableModules.push(dbot.modules[i].name);
|
||||
var ignorableModules = dbot.modules.filter(function(module) {
|
||||
if(module.ignorable != null && module.ignorable == true) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
});
|
||||
var module = event.params[1];
|
||||
|
||||
if(module === undefined) {
|
||||
|
40
modules/js/README.md
Normal file
40
modules/js/README.md
Normal file
@ -0,0 +1,40 @@
|
||||
## JS
|
||||
|
||||
Run JavaScript.
|
||||
|
||||
### Description
|
||||
|
||||
This module provides two commands which allow the execution of Javascript code
|
||||
from the bot.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~js [code]
|
||||
For regular users, there is the *~js* command, which is completely sandboxed,
|
||||
but can still be used for calculation and the like.
|
||||
|
||||
> ~js Array(16).join('wat'-1) + " Batman!";
|
||||
'NaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaN Batman!'
|
||||
|
||||
This feature is fairly safe as the user doesn't have access to anything
|
||||
dangerous, and is safe from infinite loops or locking DBot up because the code
|
||||
which is run is killed if it does not finish within a short amount of time.
|
||||
|
||||
#### ~ajs [code]
|
||||
For administrators, the incredibly useful *~ajs* command is also available. The
|
||||
input for this command is simply 'eval'-ed and therefore has full access to
|
||||
DBot's memory. Of course, this is incredibly unsafe, but I find it rather fun;
|
||||
remember to only give extremely trusted friends administrator access to your
|
||||
DBot instance, as there's nothing to stop them wiping the database or probably
|
||||
even your hard drive - if you're worried about that kind of thing, do not load
|
||||
this module.
|
||||
|
||||
However, it's useful for many things, such as administrative activity for
|
||||
which there isn't a command in the admin module. For example, you could hot-add
|
||||
a new administrator like this:
|
||||
|
||||
> ~ajs dbot.admin.push('batman');
|
||||
2
|
||||
|
||||
You can also use it for debugging, or even adding new commands while DBot is
|
||||
running.
|
3
modules/js/config.json
Normal file
3
modules/js/config.json
Normal file
@ -0,0 +1,3 @@
|
||||
{
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/js/README.md"
|
||||
}
|
17
modules/kick/README.md
Normal file
17
modules/kick/README.md
Normal file
@ -0,0 +1,17 @@
|
||||
## Kick
|
||||
|
||||
Kicking and kicking-related accessories.
|
||||
|
||||
### Description
|
||||
This module counts the number of times people are kicked from and kick people
|
||||
from channels, and provides commands for viewing this data. It also has the bot
|
||||
attempt to rejoin the channel if it is kicked.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~kickcount [username]
|
||||
Show the number of times a given user has been kicked and has kicked other
|
||||
people.
|
||||
|
||||
#### ~kickstats
|
||||
Show a list of top kickers and kickees.
|
@ -1,3 +1,4 @@
|
||||
{
|
||||
"dbKeys": [ "kicks", "kickers" ]
|
||||
"dbKeys": [ "kicks", "kickers" ],
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/kick/README.md"
|
||||
}
|
||||
|
21
modules/link/README.md
Normal file
21
modules/link/README.md
Normal file
@ -0,0 +1,21 @@
|
||||
## Link
|
||||
|
||||
Retrieves page titles.
|
||||
|
||||
### Description
|
||||
|
||||
This module stores the last posted link in each channel, and provides a command
|
||||
for retrieving the title of a given link or the last posted link in the channel.
|
||||
|
||||
### Configuration
|
||||
|
||||
#### autoTitle: false
|
||||
If this is set to true, the bot will automatically post the titles of links as
|
||||
they are posted in the channel.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~title [link]
|
||||
If called with a link, the bot will attempt to find and return the title of that
|
||||
page. If called without a link, the bot will attempt the same on the last link
|
||||
which was posted in the current channel.
|
4
modules/link/config.json
Normal file
4
modules/link/config.json
Normal file
@ -0,0 +1,4 @@
|
||||
{
|
||||
"autoTitle": false,
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/link/README.md"
|
||||
}
|
@ -7,6 +7,19 @@ var request = require('request');
|
||||
var link = function(dbot) {
|
||||
var urlRegex = /(\b(https?|ftp|file):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig;
|
||||
var links = {};
|
||||
var fetchTitle = function(event, link) {
|
||||
request(link, function (error, response, body) {
|
||||
if(!error && response.statusCode == 200) {
|
||||
body = body.replace(/(\r\n|\n\r|\n)/gm, " ");
|
||||
var title = body.valMatch(/<title>(.*)<\/title>/, 2);
|
||||
if(title) {
|
||||
event.reply(title[1]);
|
||||
} else {
|
||||
event.reply(dbot.t('title_not_found'));
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
var commands = {
|
||||
'~title': function(event) {
|
||||
@ -17,18 +30,7 @@ var link = function(dbot) {
|
||||
link = urlMatches[0];
|
||||
}
|
||||
}
|
||||
|
||||
request(link, function (error, response, body) {
|
||||
if(!error && response.statusCode == 200) {
|
||||
body = body.replace(/(\r\n|\n\r|\n)/gm, " ");
|
||||
var title = body.valMatch(/<title>(.*)<\/title>/, 2);
|
||||
if(title) {
|
||||
event.reply(title[1]);
|
||||
} else {
|
||||
event.reply('no title found');
|
||||
}
|
||||
}
|
||||
});
|
||||
fetchTitle(event, link);
|
||||
}
|
||||
};
|
||||
|
||||
@ -41,6 +43,10 @@ var link = function(dbot) {
|
||||
var urlMatches = event.message.match(urlRegex);
|
||||
if(urlMatches !== null) {
|
||||
links[event.channel.name] = urlMatches[0];
|
||||
|
||||
if(dbot.config.link.autoTitle == true) {
|
||||
fetchTitle(event, urlMatches[0]);
|
||||
}
|
||||
}
|
||||
},
|
||||
'on': 'PRIVMSG'
|
||||
|
5
modules/link/strings.json
Normal file
5
modules/link/strings.json
Normal file
@ -0,0 +1,5 @@
|
||||
{
|
||||
"title_not_found": {
|
||||
"english": "No page title found."
|
||||
}
|
||||
}
|
35
modules/poll/README.md
Normal file
35
modules/poll/README.md
Normal file
@ -0,0 +1,35 @@
|
||||
## Poll
|
||||
|
||||
Pollers gonna poll.
|
||||
|
||||
### Description
|
||||
This module allows creation of and voting in polls, with associated
|
||||
functionality.
|
||||
|
||||
Note that while in terms of the interface all votes are anonymous, users'
|
||||
voting choices are stored in the database for the purpose of users being
|
||||
able to change their votes. Therefore an admin can technically go delving in
|
||||
the database to see users' voting choices.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~newpoll [pollname] options=[each,poll,option] [Poll Description]
|
||||
Creates a new poll with the given name, options and descriptions. From this
|
||||
point people will be able to use the ~vote command to cast their vote in the
|
||||
poll.
|
||||
|
||||
#### ~addoption [pollname] [newoption]
|
||||
Using this command you can add a given option to a poll you are the creator of.
|
||||
|
||||
#### ~rmoption [pollname] [optiontoremove]
|
||||
Using this command you can remove a given option from a poll you are the creator
|
||||
of.
|
||||
|
||||
#### ~vote [pollname] [option]
|
||||
Cast your vote for the given option in the given poll. If you have already cast
|
||||
your vote in the given poll, your vote will be changed to the new option you
|
||||
have provided.
|
||||
|
||||
#### ~pdesc [pollname]
|
||||
Show the full description for a given poll name along with its available voting
|
||||
options.
|
3
modules/poll/config.json
Normal file
3
modules/poll/config.json
Normal file
@ -0,0 +1,3 @@
|
||||
{
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/poll/README.md"
|
||||
}
|
@ -1,25 +0,0 @@
|
||||
var puns = function(dbot) {
|
||||
var name = 'puns';
|
||||
var dbot = dbot;
|
||||
|
||||
return {
|
||||
'name': name,
|
||||
'ignorable': true,
|
||||
|
||||
'listener': function(event) {
|
||||
event.user = dbot.cleanNick(event.user);
|
||||
if(dbot.config.moduleNames.include('quotes') &&
|
||||
dbot.db.quoteArrs.hasOwnProperty(event.user)) {
|
||||
event.message = '~q ' + event.user;
|
||||
event.action = 'PRIVMSG';
|
||||
event.params = event.message.split(' ');
|
||||
dbot.instance.emit(event);
|
||||
}
|
||||
},
|
||||
'on': 'JOIN'
|
||||
};
|
||||
}
|
||||
|
||||
exports.fetch = function(dbot) {
|
||||
return puns(dbot);
|
||||
};
|
68
modules/quotes/README.md
Normal file
68
modules/quotes/README.md
Normal file
@ -0,0 +1,68 @@
|
||||
## Quotes
|
||||
|
||||
Stores and displays quotes.
|
||||
|
||||
### Description
|
||||
|
||||
This is the original reason that DBot was created, stores and displays quotes.
|
||||
|
||||
### Configuration
|
||||
|
||||
#### rmLimit: 10
|
||||
Amount of quotes which can be removed before admin approval is required.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~q [category]
|
||||
Display a random quote from a given category.
|
||||
|
||||
#### ~qadd [category] = [quote]
|
||||
Add a new quote to the database.
|
||||
|
||||
#### ~qstats
|
||||
Show a list of the biggest quote categories.
|
||||
|
||||
#### ~qsearch [category] = [needle]
|
||||
Search a category for quotes including the given text.
|
||||
|
||||
#### ~rmlast [category]
|
||||
Remove the last quote added to a given category.
|
||||
|
||||
#### ~rmstatus
|
||||
Show how many quotes are currently in the removal cache, and whether they will
|
||||
be randomly removed.
|
||||
|
||||
#### ~rm [category] = [quote]
|
||||
Remove a given quote from the given category.
|
||||
|
||||
#### ~qcount [category]
|
||||
Show the number of quotes stored in the given category, or if called without a
|
||||
category it will show the total number of quotes in the database.
|
||||
|
||||
#### ~rq
|
||||
Show a random quote from the database.
|
||||
|
||||
#### ~link [category]
|
||||
Show a link to the page on the web interface which shows this category's quotes.
|
||||
|
||||
### Admin-only Commands
|
||||
|
||||
#### ~rmconfirm
|
||||
Confirm that the quotes currently in the removal cache are okay to be removed,
|
||||
and permanently delete them.
|
||||
|
||||
#### ~rmdeny
|
||||
Re-instate the quotes that are currently in the removal cache back into the main
|
||||
quote database.
|
||||
|
||||
### Removal Spam Protection
|
||||
|
||||
When quotes are removed using either the ~rm or ~rmlast commands, the quotes are
|
||||
removed from the main database, but are stored in a removal cache which is cleared
|
||||
out ten minutes from the last time a quote was removed from the database. If the
|
||||
number of quotes removed from the database reaches a certain limit (as per rmLimit
|
||||
in config, default 10) then the counter is removed and the cache will not be deleted
|
||||
automatically. In such a case, a DBot admin needs to either run the ~rmconfim command
|
||||
to have the removal cache cleared, or ~rmdeny to re-instate all of the quotes in
|
||||
the removal cache back into the main quote database. This is to stop mass
|
||||
removal from the database without limiting the user interface.
|
@ -1,4 +1,5 @@
|
||||
{
|
||||
"dbKeys": [ "quoteArrs" ],
|
||||
"rmLimit": 10
|
||||
"rmLimit": 10,
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/quotes/README.md"
|
||||
}
|
||||
|
@ -55,6 +55,26 @@ var quotes = function(dbot) {
|
||||
}
|
||||
};
|
||||
|
||||
var api = {
|
||||
'getQuote': function(category) {
|
||||
var key = category.trim().toLowerCase();
|
||||
var altKey;
|
||||
if(key.split(' ').length > 0) {
|
||||
altKey = key.replace(/ /g, '_');
|
||||
}
|
||||
|
||||
if(key.charAt(0) !== '_') { // lol
|
||||
if(quotes.hasOwnProperty(key)) {
|
||||
return interpolatedQuote(key);
|
||||
} else if(quotes.hasOwnProperty(altKey)) {
|
||||
return interpolatedQuote(altKey);
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
var commands = {
|
||||
// Alternative syntax to ~q
|
||||
'~': function(event) {
|
||||
@ -101,19 +121,11 @@ var quotes = function(dbot) {
|
||||
// Retrieve quote from a category in the database.
|
||||
'~q': function(event) {
|
||||
var key = event.input[1].trim().toLowerCase();
|
||||
var altKey;
|
||||
if(key.split(' ').length > 0) {
|
||||
altKey = key.replace(/ /g, '_');
|
||||
}
|
||||
|
||||
if(key.charAt(0) !== '_') { // lol
|
||||
if(quotes.hasOwnProperty(key)) {
|
||||
event.reply(key + ': ' + interpolatedQuote(key));
|
||||
} else if(quotes.hasOwnProperty(altKey)) {
|
||||
event.reply(altKey + ': ' + interpolatedQuote(altKey));
|
||||
} else {
|
||||
event.reply(dbot.t('category_not_found', {'category': key}));
|
||||
}
|
||||
var quote = api.getQuote(event.input[1]);
|
||||
if(quote) {
|
||||
event.reply(key + ': ' + quote);
|
||||
} else {
|
||||
event.reply(dbot.t('category_not_found', {'category': key}));
|
||||
}
|
||||
},
|
||||
|
||||
@ -157,17 +169,13 @@ var quotes = function(dbot) {
|
||||
if(rmAllowed == true || dbot.config.admins.include(event.user)) {
|
||||
var key = event.input[1].trim().toLowerCase();
|
||||
if(quotes.hasOwnProperty(key)) {
|
||||
if(!dbot.db.locks.include(key) || dbot.config.admins.include(event.user)) {
|
||||
var quote = quotes[key].pop();
|
||||
if(quotes[key].length === 0) {
|
||||
delete quotes[key];
|
||||
}
|
||||
resetRemoveTimer(event, key, quote);
|
||||
|
||||
event.reply(dbot.t('removed_from', {'quote': quote, 'category': key}));
|
||||
} else {
|
||||
event.reply(dbot.t('locked_category', {'category': q[1]}));
|
||||
var quote = quotes[key].pop();
|
||||
if(quotes[key].length === 0) {
|
||||
delete quotes[key];
|
||||
}
|
||||
resetRemoveTimer(event, key, quote);
|
||||
|
||||
event.reply(dbot.t('removed_from', {'quote': quote, 'category': key}));
|
||||
} else {
|
||||
event.reply(dbot.t('no_quotes', {'category': q[1]}));
|
||||
}
|
||||
@ -182,22 +190,18 @@ var quotes = function(dbot) {
|
||||
var quote = event.input[2];
|
||||
|
||||
if(quotes.hasOwnProperty(key)) {
|
||||
if(!dbot.db.locks.include(key)) {
|
||||
var category = quotes[key];
|
||||
var index = category.indexOf(quote);
|
||||
if(index !== -1) {
|
||||
category.splice(index, 1);
|
||||
if(category.length === 0) {
|
||||
delete quotes[key];
|
||||
}
|
||||
resetRemoveTimer(event, key, quote);
|
||||
|
||||
event.reply(dbot.t('removed_from', {'category': key, 'quote': quote}));
|
||||
} else {
|
||||
event.reply(dbot.t('q_not_exist_under', {'category': key, 'quote': quote}));
|
||||
var category = quotes[key];
|
||||
var index = category.indexOf(quote);
|
||||
if(index !== -1) {
|
||||
category.splice(index, 1);
|
||||
if(category.length === 0) {
|
||||
delete quotes[key];
|
||||
}
|
||||
resetRemoveTimer(event, key, quote);
|
||||
|
||||
event.reply(dbot.t('removed_from', {'category': key, 'quote': quote}));
|
||||
} else {
|
||||
event.reply(dbot.t('locked_category', {'category': key}));
|
||||
event.reply(dbot.t('q_not_exist_under', {'category': key, 'quote': quote}));
|
||||
}
|
||||
} else {
|
||||
event.reply(dbot.t('category_not_found', {'category': key}));
|
||||
@ -295,11 +299,10 @@ var quotes = function(dbot) {
|
||||
'ignorable': true,
|
||||
'commands': commands,
|
||||
'pages': pages,
|
||||
'api': api,
|
||||
|
||||
'listener': function(event) {
|
||||
// Reality Once listener
|
||||
if((dbot.db.ignores.hasOwnProperty(event) &&
|
||||
dbot.db.ignores[event.user].include(name)) == false) {
|
||||
if(event.action == 'PRIVMSG') {
|
||||
if(event.user == 'reality') {
|
||||
var once = event.message.valMatch(/^I ([\d\w\s,'-]* once)/, 2);
|
||||
} else {
|
||||
@ -307,28 +310,19 @@ var quotes = function(dbot) {
|
||||
}
|
||||
|
||||
if(once) {
|
||||
if((dbot.db.bans.hasOwnProperty('~qadd') &&
|
||||
dbot.db.bans['~qadd'].include(event.user)) ||
|
||||
dbot.db.bans['*'].include(event.user)) {
|
||||
event.reply(dbot.t('command_ban', {'user': event.user}));
|
||||
} else {
|
||||
if(!dbot.db.quoteArrs.hasOwnProperty('realityonce')) {
|
||||
dbot.db.quoteArrs['realityonce'] = [];
|
||||
}
|
||||
if(dbot.db.quoteArrs['realityonce'].include('reality ' + once[1] + '.')) {
|
||||
event.reply(event.user + ': reality has already done that once.');
|
||||
} else {
|
||||
dbot.db.quoteArrs['realityonce'].push('reality ' + once[1] + '.');
|
||||
addStack.push('realityonce');
|
||||
rmAllowed = true;
|
||||
event.reply('\'reality ' + once[1] + '.\' saved.');
|
||||
}
|
||||
}
|
||||
event.message = '~qadd realityonce=reality ' + once[1];
|
||||
event.action = 'PRIVMSG';
|
||||
event.params = event.message.split(' ');
|
||||
dbot.instance.emit(event);
|
||||
}
|
||||
} else if(event.action == 'JOIN') {
|
||||
var userQuote = api.getQuote(event.user)
|
||||
if(userQuote) {
|
||||
event.reply(event.user + ': ' + api.getQuote(event.user));
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
'on': 'PRIVMSG'
|
||||
'on': ['PRIVMSG', 'JOIN']
|
||||
};
|
||||
};
|
||||
|
||||
|
19
modules/report/README.md
Normal file
19
modules/report/README.md
Normal file
@ -0,0 +1,19 @@
|
||||
## Report
|
||||
|
||||
Report users
|
||||
|
||||
### Description
|
||||
This module provides a command which allows users to report other users in a
|
||||
channel to the operators of the channel, as well as posting an alert in the
|
||||
administrative channel. It can be done either anonymously or publicly in the
|
||||
channel.
|
||||
|
||||
### Commands
|
||||
|
||||
#### ~report [#channel] [username] [reason for reporting]
|
||||
Report a user in a channel for a reason. This command can either be run publicly
|
||||
in a channel or anonymously in a PM to the bot. The result of using this command
|
||||
will be that all of the users which are currently marked as operators in the
|
||||
reporting channel will receive a PM telling them a user has been reported, by
|
||||
whom, in which channel and why. If there is an administrative channel for the
|
||||
reporting channel (e.g. ##channel), the report will be posted there as well.
|
3
modules/report/config.json
Normal file
3
modules/report/config.json
Normal file
@ -0,0 +1,3 @@
|
||||
{
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/report/README.md"
|
||||
}
|
@ -21,18 +21,21 @@ var report = function(dbot) {
|
||||
}
|
||||
|
||||
for(var i=0;i<ops.length;i++) {
|
||||
dbot.say(event.server, ops[i],
|
||||
'Attention: ' + event.user + ' has reported ' +
|
||||
nick + ' in ' + channelName + '. The reason ' +
|
||||
'given was: "' + reason + '."');
|
||||
dbot.say(event.server, ops[i], dbot.t('report', {
|
||||
'reporter': event.user,
|
||||
'reported': nick,
|
||||
'channel': channelName,
|
||||
'reason': reason
|
||||
}));
|
||||
}
|
||||
|
||||
event.reply('Thank you, ' + nick + ' has been reported the channel administrators.');
|
||||
event.reply(dbot.t('reported', { 'reported': nick }));
|
||||
} else {
|
||||
event.reply('User is not in that channel.');
|
||||
event.reply(dbot.t('user_not_found', { 'reported': nick,
|
||||
'channel': channelName }));
|
||||
}
|
||||
} else {
|
||||
event.reply('I am not in that channel.');
|
||||
event.reply(dbot.t('not_in_channel', { 'channel': channelName }));
|
||||
}
|
||||
}
|
||||
|
||||
|
14
modules/report/strings.json
Normal file
14
modules/report/strings.json
Normal file
@ -0,0 +1,14 @@
|
||||
{
|
||||
"report": {
|
||||
"english": "Attention: {reporter} has reported {reported} in {channel}. The reason given was: \"{reason}.\""
|
||||
},
|
||||
"reported": {
|
||||
"english": "Thank you, {reported} has been reported to the channel administrators."
|
||||
},
|
||||
"user_not_found": {
|
||||
"english": "{reported} does not appear to be in {channel}."
|
||||
},
|
||||
"not_in_channel": {
|
||||
"english": "I am not present in {channel}."
|
||||
}
|
||||
}
|
22
modules/spelling/README.md
Normal file
22
modules/spelling/README.md
Normal file
@ -0,0 +1,22 @@
|
||||
## Spelling
|
||||
|
||||
Fix your spelling.
|
||||
|
||||
### Description
|
||||
|
||||
Will attempt to correct a users' spelling by using the levenshtein distance
|
||||
algorithm. One corrects the spelling of their previous message by simply posting
|
||||
a message with their correction and an asterisk:
|
||||
|
||||
> user: I am a tutrle.
|
||||
> user: *turtle
|
||||
user meant: I am a turtle.
|
||||
|
||||
The regular expression for this module also accepts two asterisks at the
|
||||
beginning of the correction, or at the end; it also accepts several words as the
|
||||
correction and deals with these fairly intelligently. Users may also attempt
|
||||
to correct another users like so:
|
||||
|
||||
> userone: I am a tutrle.
|
||||
> usertwo: userone: *turtle
|
||||
> usertwo thinks userone meant: I am a turtle.
|
3
modules/spelling/config.json
Normal file
3
modules/spelling/config.json
Normal file
@ -0,0 +1,3 @@
|
||||
{
|
||||
"help": "http://github.com/reality/depressionbot/blob/master/modules/spelling/README.md"
|
||||
}
|
@ -1 +1 @@
|
||||
Subproject commit 8867e3592ea03b85093a5ab79017efb26c9156be
|
||||
Subproject commit cedfdb09ed857476298ba16eb90e3131f033ba60
|
20
modules/users/strings.json
Normal file
20
modules/users/strings.json
Normal file
@ -0,0 +1,20 @@
|
||||
{
|
||||
"alias": {
|
||||
"english": "{alias} is an alias of {user}"
|
||||
},
|
||||
"primary": {
|
||||
"english": "{user} is a primary user with {count} aliases."
|
||||
},
|
||||
"unknown_alias": {
|
||||
"english": "{alias} does not currently exist as an alias or known user."
|
||||
},
|
||||
"aliasparentset": {
|
||||
"english": "{newParent} is now the parent user, and {newAlias} is an alias."
|
||||
},
|
||||
"unprimary_error": {
|
||||
"english": "One of those users isn't currently recorded as a primary user."
|
||||
},
|
||||
"merged_users": {
|
||||
"english": "{old_user} and their aliases have been merged into {new_user}."
|
||||
}
|
||||
}
|
@ -4,15 +4,26 @@
|
||||
*/
|
||||
var users = function(dbot) {
|
||||
var knownUsers = dbot.db.knownUsers;
|
||||
var getServerUsers = function(event) {
|
||||
if(!knownUsers.hasOwnProperty(event.server)) {
|
||||
knownUsers[event.server] = { 'users': [], 'aliases': {} };
|
||||
var getServerUsers = function(server) {
|
||||
if(!knownUsers.hasOwnProperty(server)) {
|
||||
knownUsers[server] = { 'users': [], 'aliases': {} };
|
||||
}
|
||||
return knownUsers[event.server];
|
||||
return knownUsers[server];
|
||||
};
|
||||
|
||||
var updateAliases = function(event, oldUser, newUser) {
|
||||
var knownUsers = getServerUsers(event.server);
|
||||
for(var alias in knownUsers.aliases) {
|
||||
if(knownUsers.aliases.hasOwnProperty(alias)) {
|
||||
if(knownUsers.aliases[alias] === oldUser) {
|
||||
knownUsers.aliases[alias] = newUser;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dbot.instance.addListener('366', 'users', function(event) {
|
||||
var knownUsers = getServerUsers(event);
|
||||
var knownUsers = getServerUsers(event.server);
|
||||
for(var nick in event.channel.nicks) {
|
||||
if(!knownUsers.users.include(nick) && !knownUsers.aliases.hasOwnProperty(nick) &&
|
||||
event.channel.nicks.hasOwnProperty(nick)) {
|
||||
@ -80,33 +91,113 @@ var users = function(dbot) {
|
||||
},
|
||||
};
|
||||
|
||||
return {
|
||||
'name': 'users',
|
||||
'ignorable': false,
|
||||
var api = {
|
||||
'resolveUser': function(server, nick, useLowercase) {
|
||||
var knownUsers = getServerUsers(server);
|
||||
var user = nick;
|
||||
if(!knownUsers.users.include(nick) && knownUsers.aliases.hasOwnProperty(nick)) {
|
||||
user = knownUsers.aliases[nick];
|
||||
}
|
||||
|
||||
'commands': {
|
||||
'~alias': function(event) {
|
||||
var knownUsers = getServerUsers(event);
|
||||
var alias = event.params[1].trim();
|
||||
if(knownUsers.aliases.hasOwnProperty(alias)) {
|
||||
event.reply(alias + ' is an alias of ' + knownUsers.aliases[alias]);
|
||||
if(useLowercase) user = user.toLowerCase();
|
||||
return user;
|
||||
}
|
||||
};
|
||||
|
||||
var commands = {
|
||||
'~alias': function(event) {
|
||||
var knownUsers = getServerUsers(event.server);
|
||||
var alias = event.params[1].trim();
|
||||
if(knownUsers.users.include(alias)) {
|
||||
var aliasCount = 0;
|
||||
knownUsers.aliases.each(function(primaryUser) {
|
||||
if(primaryUser == alias) aliasCount += 1;
|
||||
}.bind(this));
|
||||
event.reply(dbot.t('primary', { 'user': alias, 'count': aliasCount }));
|
||||
} else if(knownUsers.aliases.hasOwnProperty(alias)) {
|
||||
event.reply(dbot.t('alias', { 'alias': alias,
|
||||
'user': knownUsers.aliases[alias] }));
|
||||
} else {
|
||||
event.reply(dbot.t('unknown_alias', { 'alias': alias }));
|
||||
}
|
||||
},
|
||||
|
||||
'~setaliasparent': function(event) {
|
||||
if(dbot.config.admins.include(event.user)) {
|
||||
var knownUsers = getServerUsers(event.server);
|
||||
var newParent = event.params[1];
|
||||
|
||||
if(knownUsers.aliases.hasOwnProperty(newParent)) {
|
||||
var newAlias = knownUsers.aliases[newParent];
|
||||
|
||||
// Replace users entry with new primary user
|
||||
var usersIndex = knownUsers.users.indexOf(newAlias);
|
||||
knownUsers.users.splice(usersIndex, 1);
|
||||
knownUsers.users.push(newParent);
|
||||
|
||||
// Remove alias for new parent & add alias for new alias
|
||||
delete knownUsers.aliases[newParent];
|
||||
knownUsers.aliases[newAlias] = newParent;
|
||||
|
||||
// Update aliases to point to new primary user
|
||||
updateAliases(event, newAlias, newParent);
|
||||
|
||||
event.reply(dbot.t('aliasparentset', { 'newParent': newParent,
|
||||
'newAlias': newAlias }));
|
||||
|
||||
dbot.api.stats.fixStats(event.server, newAlias);
|
||||
} else {
|
||||
event.reply(alias + ' is not known as an alias to me.');
|
||||
event.reply(dbot.t('unknown_alias', { 'alias': newParent}));
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
'~mergeusers': function(event) {
|
||||
if(dbot.config.admins.include(event.user)) {
|
||||
var knownUsers = getServerUsers(event.server);
|
||||
var primaryUser = event.params[1];
|
||||
var secondaryUser = event.params[2];
|
||||
|
||||
if(knownUsers.users.include(primaryUser) && knownUsers.users.include(secondaryUser)) {
|
||||
knownUsers.users.splice(knownUsers.users.indexOf(secondaryUser), 1);
|
||||
knownUsers.aliases[secondaryUser] = primaryUser;
|
||||
updateAliases(event, secondaryUser, primaryUser);
|
||||
|
||||
event.reply(dbot.t('merged_users', {
|
||||
'old_user': secondaryUser,
|
||||
'new_user': primaryUser
|
||||
}));
|
||||
|
||||
dbot.api.stats.fixStats(event.server, secondaryUser);
|
||||
} else {
|
||||
event.reply(dbot.t('unprimary_error'));
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
return {
|
||||
'name': 'users',
|
||||
'ignorable': false,
|
||||
'commands': commands,
|
||||
'api': api,
|
||||
'pages': pages,
|
||||
|
||||
'listener': function(event) {
|
||||
var knownUsers = getServerUsers(event);
|
||||
var knownUsers = getServerUsers(event.server);
|
||||
if(event.action == 'JOIN') {
|
||||
if(!knownUsers.users.include(event.user)) {
|
||||
knownUsers.users.push(event.user);
|
||||
}
|
||||
} else if(event.action == 'NICK') {
|
||||
var newNick = event.params.substr(1);
|
||||
knownUsers.aliases[newNick] = event.user;
|
||||
if(knownUsers.aliases.hasOwnProperty(event.user)) {
|
||||
knownUsers.aliases[newNick] = knownUsers.aliases[event.user];
|
||||
} else {
|
||||
if(!knownUsers.users.include(newNick)) {
|
||||
knownUsers.aliases[newNick] = event.user;
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
'on': ['JOIN', 'NICK'],
|
||||
|
7
modules/web/README.md
Normal file
7
modules/web/README.md
Normal file
@ -0,0 +1,7 @@
|
||||
## Web
|
||||
|
||||
Web interface
|
||||
|
||||
### Description
|
||||
|
||||
It's a web interface for DBot. What of it?
|
@ -1,4 +1,4 @@
|
||||
{
|
||||
"webHost": "localhost",
|
||||
"webPort": 8080
|
||||
"webPort": 8090
|
||||
}
|
||||
|
10
modules/youare/README.md
Normal file
10
modules/youare/README.md
Normal file
@ -0,0 +1,10 @@
|
||||
## youare
|
||||
|
||||
You're a loser!
|
||||
|
||||
### Description
|
||||
|
||||
This module occasionally comes back and says "You're a x" when somebody goes "y
|
||||
is x" or "y are x," with the intention of annoying people who are calling
|
||||
something crap. Warning: this module occasionally causes the bot to be nice to
|
||||
people.
|
13
run.js
13
run.js
@ -117,9 +117,10 @@ DBot.prototype.reloadModules = function() {
|
||||
}
|
||||
|
||||
this.rawModules = [];
|
||||
this.modules = [];
|
||||
this.pages = {};
|
||||
this.modules = {};
|
||||
this.commands = {};
|
||||
this.api = {};
|
||||
this.commandMap = {}; // Map of which commands belong to which modules
|
||||
this.usage = {};
|
||||
this.timers.clearTimers();
|
||||
@ -209,6 +210,11 @@ DBot.prototype.reloadModules = function() {
|
||||
}
|
||||
}
|
||||
|
||||
// Load module API
|
||||
if(module.api) {
|
||||
this.api[module.name] = module.api;
|
||||
}
|
||||
|
||||
// Load the module usage data
|
||||
try {
|
||||
var usage = JSON.parse(fs.readFileSync(moduleDir + 'usage.json', 'utf-8'));
|
||||
@ -241,7 +247,10 @@ DBot.prototype.reloadModules = function() {
|
||||
// Invalid or no string info
|
||||
}
|
||||
|
||||
this.modules.push(module);
|
||||
module.toString = function() {
|
||||
return this.name;
|
||||
}
|
||||
this.modules[module.name] = module;
|
||||
} catch(err) {
|
||||
console.log(this.t('module_load_error', {'moduleName': name}));
|
||||
if(this.config.debugMode) {
|
||||
|
15
snippets.js
15
snippets.js
@ -204,7 +204,15 @@ Object.prototype.filter = function(fun) {
|
||||
}
|
||||
}
|
||||
return filtered;
|
||||
}
|
||||
};
|
||||
|
||||
Object.prototype.each = function(fun) {
|
||||
for(var key in this) {
|
||||
if(this.hasOwnProperty(key)) {
|
||||
fun(this[key]);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/*** Integer ***/
|
||||
|
||||
@ -263,3 +271,8 @@ Number.prototype.numberFormat = function(dec_places){
|
||||
parts[0] = parts[0].replace(/\B(?=(\d{3})+(?!\d))/g, sep);
|
||||
return parts.join(dec_point);
|
||||
}
|
||||
|
||||
// http://simonwillison.net/2006/Jan/20/escape/#p-6
|
||||
String.prototype.escape = function() {
|
||||
return this.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&");
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user