+++ /dev/null
-var _ = require('underscore');\r
-\r
-\r
-\r
-\r
-var ClientCommandset = function (client) {\r
- this.client = client;\r
-};\r
-module.exports.ClientCommandset = ClientCommandset;\r
-\r
-ClientCommandset.prototype.run = function (command, args, irc_connection, callback) {\r
- // Do we have a function to handle this command?\r
- if (!listeners[command.toUpperCase()]) {\r
- return;\r
- }\r
-\r
- return listeners[command.toUpperCase()](args, irc_connection, callback);\r
-};\r
-\r
-\r
-\r
-\r
-var listeners = {\r
- PRIVMSG: function (args, irc_connection, callback) {\r
- if (args.target && (args.msg)) {\r
- // TODO: Enable plugin support here again\r
- //obj = kiwi.kiwi_mod.run('msgsend', args, {websocket: websocket});\r
- //if (obj !== null) {\r
- irc_connection.write('PRIVMSG ' + args.target + ' :' + args.msg, callback);\r
- //}\r
- }\r
- },\r
- \r
-\r
- CTCP: function (args, irc_connection, callback) {\r
- if ((args.target) && (args.type)) {\r
- if (args.request) {\r
- irc_connection.write('PRIVMSG ' + args.target + ' :' + String.fromCharCode(1) + args.type.toUpperCase() + ' ' + args.params + String.fromCharCode(1), callback);\r
- } else {\r
- irc_connection.write('NOTICE ' + args.target + ' :' + String.fromCharCode(1) + args.type.toUpperCase() + ' ' + args.params + String.fromCharCode(1), callback);\r
- }\r
- }\r
- },\r
-\r
-\r
- RAW: function (args, irc_connection, callback) {\r
- irc_connection.write(args.data, callback);\r
- },\r
-\r
-\r
- JOIN: function (args, irc_connection, callback) {\r
- if (args.channel) {\r
- channels = args.channel.split(",");\r
- keys = (args.key) ? args.key.split(",") : [];\r
- _.each(channels, function (chan, index) {\r
- irc_connection.write('JOIN ' + chan + ' ' + (keys[index] || ''), callback);\r
- });\r
- }\r
- },\r
-\r
-\r
- PART: function (args, irc_connection, callback) {\r
- if (args.channel) {\r
- _.each(args.channel.split(","), function (chan) {\r
- irc_connection.write('PART ' + chan, callback);\r
- });\r
- }\r
- },\r
-\r
-\r
- TOPIC: function (args, irc_connection, callback) {\r
- if (args.channel) {\r
- if (args.topic) {\r
- irc_connection.write('TOPIC ' + args.channel + ' :' + args.topic, callback);\r
- } else {\r
- irc_connection.write('TOPIC ' + args.channel, callback);\r
- }\r
- }\r
- },\r
-\r
-\r
- KICK: function (args, irc_connection, callback) {\r
- if ((args.channel) && (args.nick)) {\r
- irc_connection.write('KICK ' + args.channel + ' ' + args.nick + ':' + args.reason, callback);\r
- }\r
- },\r
-\r
-\r
- QUIT: function (args, irc_connection, callback) {\r
- websocket.ircConnection.end('QUIT :' + args.message + '\r\n');\r
- websocket.sentQUIT = true;\r
- websocket.ircConnection.destroySoon();\r
- websocket.disconnect();\r
- },\r
-\r
-\r
- NOTICE: function (args, irc_connection, callback) {\r
- if ((args.target) && (args.msg)) {\r
- irc_connection.write('NOTICE ' + args.target + ' :' + args.msg, callback);\r
- }\r
- },\r
-\r
-\r
- MODE: function (args, irc_connection, callback) {\r
- if ((args.target) && (args.mode)) {\r
- irc_connection.write('MODE ' + args.target + ' ' + args.mode + ' ' + args.params, callback);\r
- }\r
- },\r
-\r
-\r
- NICK: function (args, irc_connection, callback) {\r
- if (args.nick) {\r
- irc_connection.write('NICK ' + args.nick, callback);\r
- }\r
- },\r
-\r
-\r
- KIWI: function (args, irc_connection, callback) {\r
- if ((args.target) && (args.data)) {\r
- irc_connection.write('PRIVMSG ' + args.target + ': ' + String.fromCharCode(1) + 'KIWI ' + args.data + String.fromCharCode(1), callback);\r
- }\r
- }\r
-};\r
+++ /dev/null
-var util = require('util'),
- events = require('events'),
- _ = require('underscore'),
- IRCConnection = require('./irc-connection.js').IRCConnection,
- IRCCommands = require('./irc-commands.js'),
- ClientCommandset = require('./client-commands.js').ClientCommandset;
-
-var Client = function (websocket) {
- var c = this;
-
- events.EventEmitter.call(this);
- this.websocket = websocket;
-
- this.IRC_connections = [];
- this.next_connection = 0;
-
- this.buffer = {
- list: [],
- motd: ''
- };
-
- // Handler for any commands sent from the client
- this.client_commands = new ClientCommandset(this);
-
- websocket.on('irc', function () {
- handleClientMessage.apply(c, arguments);
- });
- websocket.on('kiwi', function () {
- kiwi_command.apply(c, arguments);
- });
- websocket.on('disconnect', function () {
- disconnect.apply(c, arguments);
- });
- websocket.on('error', function () {
- error.apply(c, arguments);
- });
-};
-util.inherits(Client, events.EventEmitter);
-
-module.exports.Client = Client;
-
-// Callback API:
-// Callbacks SHALL accept 2 arguments, error and response, in that order.
-// error MUST be null where the command is successul.
-// error MUST otherwise be a truthy value and SHOULD be a string where the cause of the error is known.
-// response MAY be given even if error is truthy
-
-Client.prototype.sendIRCCommand = function (command, data, callback) {
- var c = {command: command, data: data};
- //console.log('C<--', c);
- this.websocket.emit('irc', c, callback);
-};
-
-Client.prototype.sendKiwiCommand = function (command, callback) {
- this.websocket.emit('kiwi', command, callback);
-};
-
-var handleClientMessage = function (msg, callback) {
- var server, args, obj, channels, keys;
-
- // Make sure we have a server number specified
- if ((msg.server === null) || (typeof msg.server !== 'number')) {
- return (typeof callback === 'function') ? callback('server not specified') : undefined;
- } else if (!this.IRC_connections[msg.server]) {
- return (typeof callback === 'function') ? callback('not connected to server') : undefined;
- }
-
- // The server this command is directed to
- server = this.IRC_connections[msg.server];
-
- if (typeof callback !== 'function') {
- callback = null;
- }
-
- try {
- msg.data = JSON.parse(msg.data);
- } catch (e) {
- kiwi.log('[handleClientMessage] JSON parsing error ' + msg.data);
- return;
- }
-
- // Run the client command
- this.client_commands.run(msg.data.method, msg.data.args, server, callback);
-};
-
-
-
-
-var kiwi_command = function (command, callback) {
- var that = this;
- console.log(typeof callback);
- if (typeof callback !== 'function') {
- callback = function () {};
- }
- switch (command.command) {
- case 'connect':
- if ((command.hostname) && (command.port) && (command.nick)) {
- var con = new IRCConnection(command.hostname, command.port, command.ssl,
- command.nick, {hostname: this.websocket.handshake.revdns, address: this.websocket.handshake.address.address},
- command.password, null);
-
- var con_num = this.next_connection++;
- this.IRC_connections[con_num] = con;
-
- var binder = new IRCCommands.Binder(con, con_num, this);
- binder.bind_irc_commands();
-
- con.on('connected', function () {
- console.log("con.on('connected')");
- return callback(null, con_num);
- });
-
- con.on('error', function (err) {
- this.websocket.sendKiwiCommand('error', {server: con_num, error: err});
- });
-
- con.on('close', function () {
- that.IRC_connections[con_num] = null;
- });
- } else {
- return callback('Hostname, port and nickname must be specified');
- }
- break;
- default:
- callback();
- }
-};
-
-var extension_command = function (command, callback) {
- if (typeof callback === 'function') {
- callback('not implemented');
- }
-};
-
-var disconnect = function () {
- _.each(this.IRC_connections, function (irc_connection, i, cons) {
- if (irc_connection) {
- irc_connection.end('QUIT :Kiwi IRC');
- cons[i] = null;
- }
- });
- this.emit('destroy');
-};
-
-var error = function () {
- this.emit('destroy');
-};
"servers": [
{
"secure": true,
- "hsts": true,
"port": 7777,
"address": "0.0.0.0",
"cap_options": [],
"handle_http": true,
- "public_http": "client_backbone/",
+ "public_http": "./../client/",
"max_client_conns": 2,
+++ /dev/null
-var url = require('url'),
- node_static = require ('node-static');
-
-var HTTPHandler = function (config) {
- this.static_file_server = new StaticFileServer(config.public_html);
-};
-
-module.exports.HTTPHandler = HTTPHandler;
-
-var StaticFileServer = function (public_html) {
- public_html = public_html || 'client_backbone/';
- this.fileServer = new node_static.Server(public_html);
-};
-
-StaticFileServer.prototype.serve = function (request, response) {
- // Any requests for /client to load the index file
- if (request.url.match(/^\/client/)) {
- request.url = '/';
- }
-
- this.fileServer.serve(request, response, function (err) {
- if (err) {
- response.writeHead(err.status, err.headers);
- response.end();
- }
- });
-};
-
-HTTPHandler.prototype.handler = function (request, response) {
- var uri, subs;
-
- uri = url.parse(request.url, true);
- subs = uri.pathname.substr(0, 4);
-
- if (uri.pathname.substr(0, 10) === '/socket.io') {
- return;
- } else {
- this.static_file_server.serve(request, response);
- }
-};
\ No newline at end of file
+++ /dev/null
-var _ = require('underscore');
-
-var irc_numerics = {
- RPL_WELCOME: '001',
- RPL_MYINFO: '004',
- RPL_ISUPPORT: '005',
- RPL_WHOISREGNICK: '307',
- RPL_WHOISUSER: '311',
- RPL_WHOISSERVER: '312',
- RPL_WHOISOPERATOR: '313',
- RPL_WHOISIDLE: '317',
- RPL_ENDOFWHOIS: '318',
- RPL_WHOISCHANNELS: '319',
- RPL_LISTSTART: '321',
- RPL_LIST: '322',
- RPL_LISTEND: '323',
- RPL_NOTOPIC: '331',
- RPL_TOPIC: '332',
- RPL_TOPICWHOTIME: '333',
- RPL_NAMEREPLY: '353',
- RPL_ENDOFNAMES: '366',
- RPL_BANLIST: '367',
- RPL_ENDOFBANLIST: '368',
- RPL_MOTD: '372',
- RPL_MOTDSTART: '375',
- RPL_ENDOFMOTD: '376',
- RPL_WHOISMODES: '379',
- ERR_NOSUCHNICK: '401',
- ERR_CANNOTSENDTOCHAN: '404',
- ERR_TOOMANYCHANNELS: '405',
- ERR_NICKNAMEINUSE: '433',
- ERR_USERNOTINCHANNEL: '441',
- ERR_NOTONCHANNEL: '442',
- ERR_NOTREGISTERED: '451',
- ERR_LINKCHANNEL: '470',
- ERR_CHANNELISFULL: '471',
- ERR_INVITEONLYCHAN: '473',
- ERR_BANNEDFROMCHAN: '474',
- ERR_BADCHANNELKEY: '475',
- ERR_CHANOPRIVSNEEDED: '482',
- RPL_STARTTLS: '670'
-};
-
-
-var Binder = function (irc_connection, con_num, client) {
- this.irc_connection = irc_connection;
- this.con_num = con_num;
- this.client = client;
-};
-module.exports.Binder = Binder;
-
-Binder.prototype.bind_irc_commands = function () {
- var that = this;
- _.each(listeners, function (listener, command) {
- var s = command.substr(0, 4);
- if ((s === 'RPL_') || (s === 'ERR_')) {
- command = irc_numerics[command];
- }
- that.irc_connection.on('irc_' + command, function () {
- listener.apply(that, arguments);
- });
- });
-};
-
-var listeners = {
- 'RPL_WELCOME': function (command) {
- var nick = command.params[0];
- this.irc_connection.registered = true;
- this.client.sendIRCCommand('connect', {server: this.con_num, nick: nick});
- },
- 'RPL_ISUPPORT': function (command) {
- var options, i, option, matches, j;
- options = command.params;
- for (i = 1; i < options.length; i++) {
- option = options[i].split("=", 2);
- option[0] = option[0].toUpperCase();
- this.irc_connection.options[option[0]] = (typeof option[1] !== 'undefined') ? option[1] : true;
- if (_.include(['NETWORK', 'PREFIX', 'CHANTYPES', 'CHANMODES', 'NAMESX'], option[0])) {
- if (option[0] === 'PREFIX') {
- matches = /\(([^)]*)\)(.*)/.exec(option[1]);
- if ((matches) && (matches.length === 3)) {
- this.irc_connection.options.PREFIX = [];
- for (j = 0; j < matches[2].length; j++) {
- this.irc_connection.options.PREFIX.push({symbol: matches[2].charAt(j), mode: matches[1].charAt(j)});
- }
- }
- } else if (option[0] === 'CHANTYPES') {
- this.irc_connection.options.CHANTYPES = this.irc_connection.options.CHANTYPES.split('');
- } else if (option[0] === 'CHANMODES') {
- this.irc_connection.options.CHANMODES = option[1].split(',');
- } else if (option[0] === 'NAMESX') {
- this.irc_connection.write('PROTOCTL NAMESX');
- }
- }
- }
- //this.client.sendIRCCommand({server: this.con_num, command: 'RPL_ISUPPORT', options: this.irc_connection.options});
- //websocket.sendClientEvent('options', {server: '', "options": irc_connection.IRC.options});
- this.client.sendIRCCommand('options', {server: this.con_num, options: this.irc_connection.options});
- },
- 'RPL_ENDOFWHOIS': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_ENDOFWHOIS';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: true});
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], msg: command.trailing, end: true});
- },
- 'RPL_WHOISUSER': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_WHOISUSER';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: false});
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], ident: command.params[2], host: command.params[3], msg: command.trailing, end: false});
- },
- 'RPL_WHOISSERVER': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_WHOISSERVER';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: false});
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], server: command.params[2], end: false});
- },
- 'RPL_WHOISOPERATOR': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_WHOISOPERATOR';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: false});
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], msg: command.trailing, end: false});
- },
- 'RPL_WHOISCHANNELS': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_WHOISCHANNELS';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: false});
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], chans: command.trailing, end: false});
- },
- 'RPL_WHOISMODES': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_WHOISMODES';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: false});
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], msg: command.trailing, end: false});
- },
- 'RPL_WHOISIDLE': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_WHOISIDLE';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('whois', {server: '', nick: msg.params.split(" ", 3)[1], "msg": msg.trailing, end: false});
- if (command.params[3]) {
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], idle: command.params[2], logon: command.params[3], end: false});
- } else {
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], idle: command.params[2], end: false});
- }
- },
- 'RPL_WHOISREGNICK': function (command) {
- this.client.sendIRCCommand('whois', {server: this.con_num, nick: command.params[1], msg: command.trailing, end: false});
- },
- 'RPL_LISTSTART': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_LISTSTART';
- this.client.sendIRCCommand(command);*/
- this.client.sendIRCCommand('list_start', {server: this.con_num});
- this.client.buffer.list = [];
- },
- 'RPL_LISTEND': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_LISTEND';
- this.client.sendIRCCommand(command);*/
- if (this.client.buffer.list.length > 0) {
- this.client.buffer.list = _.sortBy(this.client.buffer.list, function (channel) {
- return channel.num_users;
- });
- this.client.sendIRCCommand('list_channel', {server: this.con_num, chans: this.client.buffer.list});
- this.client.buffer.list = [];
- }
- this.client.sendIRCCommand('list_end', {server: this.con_num});
- },
- 'RPL_LIST': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_LIST';
- this.client.sendIRCCommand(command);*/
- this.client.buffer.list.push({server: this.con_num, channel: command.params[1], num_users: parseInt(command.params[2], 10), topic: command.trailing});
- if (this.client.buffer.list.length > 200){
- this.client.buffer.list = _.sortBy(this.client.buffer.list, function (channel) {
- return channel.num_users;
- });
- this.client.sendIRCCommand('list_channel', {server: this.con_num, chans: this.client.buffer.list});
- this.client.buffer.list = [];
- }
- },
- 'RPL_MOTD': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_MOTD';
- this.client.sendIRCCommand(command);*/
- this.client.buffer.motd += command.trailing + '\n';
- },
- 'RPL_MOTDSTART': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_MOTDSTART';
- this.client.sendIRCCommand(command);*/
- this.client.buffer.motd = '';
- },
- 'RPL_ENDOFMOTD': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_ENDOFMOTD';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('motd', {server: '', 'msg': websocket.kiwi.buffer.motd});
- this.client.sendIRCCommand('motd', {server: this.con_num, msg: this.client.buffer.motd});
- },
- 'RPL_NAMEREPLY': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_NAMEREPLY';
- this.client.sendIRCCommand(command);*/
- var members = command.trailing.split(' ');
- var member_list = [];
- var that = this;
- var i = 0;
- _.each(members, function (member) {
- var j, k, modes = [];
- for (j = 0; j < member.length; j++) {
- for (k = 0; k < that.irc_connection.options.PREFIX.length; k++) {
- if (member.charAt(j) === that.irc_connection.options.PREFIX[k].symbol) {
- modes.push(that.irc_connection.options.PREFIX[k].mode);
- i++;
- }
- }
- }
- member_list.push({nick: member, modes: modes});
- if (i++ >= 50) {
- that.client.sendIRCCommand('userlist', {server: that.con_num, users: member_list, channel: command.params[2]});
- member_list = [];
- i = 0;
- }
- });
- if (i > 0) {
- this.client.sendIRCCommand('userlist', {server: this.con_num, users: member_list, channel: command.params[2]});
- }
- },
- 'RPL_ENDOFNAMES': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_ENDOFNAMES';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('userlist_end', {server: '', channel: msg.params.split(" ")[1]});
- this.client.sendIRCCommand('userlist_end', {server: this.con_num, channel: command.params[1]});
- },
- 'RPL_BANLIST': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_BANLIST';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('banlist', {server: '', channel: params[1], banned: params[2], banned_by: params[3], banned_at: params[4]});
- this.client.sendIRCCommand('banlist', {server: this.con_num, channel: command.params[1], banned: command.params[2], banned_by: command.params[3], banned_at: command.params[4]});
- },
- 'RPL_ENDOFBANLIST': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_ENDOFBANLIST';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('banlist_end', {server: '', channel: msg.params.split(" ")[1]});
- this.client.sendIRCCommand('banlist_end', {server: this.con_num, channel: command.params[1]});
- },
- 'RPL_TOPIC': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_TOPIC';
- this.client.sendIRCCommand(command);*/
- //{nick: '', channel: msg.params.split(" ")[1], topic: msg.trailing};
- this.client.sendIRCCommand('topic', {server: this.con_num, nick: '', channel: command.params[1], topic: command.trailing});
- },
- 'RPL_NOTOPIC': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_NOTOPIC';
- this.client.sendIRCCommand(command);*/
- this.client.sendIRCCommand('topic', {server: this.con_num, nick: '', channel: command.params[1], topic: ''});
- },
- 'RPL_TOPICWHOTIME': function (command) {
- /*command.server = this.con_num;
- command.command = 'RPL_TOPICWHOTIME';
- this.client.sendIRCCommand(command);*/
- //{nick: nick, channel: channel, when: when};
- this.client.sendIRCCommand('topicsetby', {server: this.con_num, nick: command.params[2], channel: command.params[1], when: command.params[3]});
- },
- 'PING': function (command) {
- this.irc_connection.write('PONG ' + command.trailing);
- },
- 'JOIN': function (command) {
- var channel;
- if (typeof command.trailing === 'string' && command.trailing !== '') {
- channel = command.trailing;
- } else if (typeof command.params[0] === 'string' && command.params[0] !== '') {
- channel = command.params[0];
- }
- /*command.server = this.con_num;
- command.command = 'JOIN';
- command.params = [channel];
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('join', {nick: msg.nick, ident: msg.ident, hostname: msg.hostname, channel: channel});
- this.client.sendIRCCommand('join', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, channel: channel});
-
- if (command.nick === this.nick) {
- this.irc_connection.write('NAMES ' + channel);
- }
- },
- 'PART': function (command) {
- /*command.server = this.con_num;
- command.command = 'PART';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('part', {nick: msg.nick, ident: msg.ident, hostname: msg.hostname, channel: msg.params.trim(), message: msg.trailing});
- this.client.sendIRCCommand('part', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, channel: command.params[0], message: command.trailing});
- },
- 'KICK': function (command) {
- /*command.server = this.con_num;
- command.command = 'KICK';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('kick', {kicked: params[1], nick: msg.nick, ident: msg.ident, hostname: msg.hostname, channel: params[0].trim(), message: msg.trailing});
- this.client.sendIRCCommand('kick', {server: this.con_num, kicked: command.params[1], nick: command.nick, ident: command.ident, hostname: command.hostname, channel: command.params[0], message: command.trailing});
- },
- 'QUIT': function (command) {
- /*command.server = this.con_num;
- command.command = 'QUIT';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('quit', {nick: msg.nick, ident: msg.ident, hostname: msg.hostname, message: msg.trailing});
- this.client.sendIRCCommand('quit', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, message: command.trailing});
- },
- 'NOTICE': function (command) {
- /*command.server = this.con_num;
- command.command = 'NOTICE';
- this.client.sendIRCCommand(command);*/
- if ((command.trailing.charAt(0) === String.fromCharCode(1)) && (command.trailing.charAt(command.trailing.length - 1) === String.fromCharCode(1))) {
- // It's a CTCP response
- //websocket.sendClientEvent('ctcp_response', {nick: msg.nick, ident: msg.ident, hostname: msg.hostname, channel: msg.params.trim(), msg: msg.trailing.substr(1, msg.trailing.length - 2)});
- this.client.sendIRCCommand('ctcp_response', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, channel: command.params[0], msg: command.trailing.substr(1, command.trailing.length - 2)});
- } else {
- //websocket.sendClientEvent('notice', {nick: msg.nick, ident: msg.ident, hostname: msg.hostname, target: msg.params.trim(), msg: msg.trailing});
- this.client.sendIRCCommand('notice', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, target: command.params[0], msg: command.trailing});
- }
- },
- 'NICK': function (command) {
- /*command.server = this.con_num;
- command.command = 'NICK';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('nick', {nick: msg.nick, ident: msg.ident, hostname: msg.hostname, newnick: msg.trailing});
- this.client.sendIRCCommand('nick', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, newnick: command.trailing});
- },
- 'TOPIC': function (command) {
- /*command.server = this.con_num;
- command.command = 'TOPIC';
- this.client.sendIRCCommand(command);*/
- //{nick: msg.nick, channel: msg.params, topic: msg.trailing};
- this.client.sendIRCCommand('topic', {server: this.con_num, nick: command.nick, channel: command.params[0], topic: command.trailing});
- },
- 'MODE': function (command) {
- var chanmodes = this.irc_connection.options.CHANMODES,
- prefixes = this.irc_connection.options.PREFIX,
- always_param = chanmodes[0].concat(chanmodes[1]),
- modes = [],
- has_param, i, j, add;
-
- prefixes = _.reduce(prefixes, function (list, prefix) {
- list.push(prefix.mode);
- return list;
- }, []);
- always_param = always_param.split('').concat(prefixes);
-
- has_param = function (mode, add) {
- if (_.find(always_param, function (m) {
- return m === mode;
- })) {
- return true;
- } else if (add && _.find(chanmodes[2].split(''), function (m) {
- return m === mode;
- })) {
- return true;
- } else {
- return false;
- }
- };
-
- if (!command.params[1]) {
- command.params[1] = command.trailing;
- }
- j = 0;
- for (i = 0; i < command.params[1].length; i++) {
- switch (command.params[1][i]) {
- case '+':
- add = true;
- break;
- case '-':
- add = false;
- break;
- default:
- if (has_param(command.params[1][i], add)) {
- modes.push({mode: (add ? '+' : '-') + command.params[1][i], param: command.params[2 + j]});
- j++;
- } else {
- modes.push({mode: (add ? '+' : '-') + command.params[1][i], param: null});
- }
- }
- }
-
- this.client.sendIRCCommand('mode', {
- server: this.con_num,
- target: command.params[0],
- nick: command.nick || command.prefix || '',
- modes: modes
- });
- },
- 'PRIVMSG': function (command) {
- /*command.server = this.con_num;
- command.command = 'PRIVMSG';
- this.client.sendIRCCommand(command);*/
- var tmp, namespace;
- if ((command.trailing.charAt(0) === String.fromCharCode(1)) && (command.trailing.charAt(command.trailing.length - 1) === String.fromCharCode(1))) {
- //CTCP request
- if (command.trailing.substr(1, 6) === 'ACTION') {
- this.client.sendIRCCommand('action', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, channel: command.params[0], msg: command.trailing.substr(7, command.trailing.length - 2)});
- } else if (command.trailing.substr(1, 4) === 'KIWI') {
- tmp = command.trailing.substr(6, command.trailing.length - 2);
- namespace = tmp.split(' ', 1)[0];
- this.client.sendIRCCommand('kiwi', {server: this.con_num, namespace: namespace, data: tmp.substr(namespace.length + 1)});
- } else if (command.trailing.substr(1, 7) === 'VERSION') {
- this.irc_connection.write('NOTICE ' + command.nick + ' :' + String.fromCharCode(1) + 'VERSION KiwiIRC' + String.fromCharCode(1));
- } else {
- this.client.sendIRCCommand('ctcp_request', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, channel: command.params[0], msg: command.trailing.substr(1, command.trailing.length - 2)});
- }
- } else {
- //{nick: msg.nick, ident: msg.ident, hostname: msg.hostname, channel: msg.params.trim(), msg: msg.trailing}
- this.client.sendIRCCommand('msg', {server: this.con_num, nick: command.nick, ident: command.ident, hostname: command.hostname, channel: command.params[0], msg: command.trailing});
- }
- },
- 'ERROR': function (command) {
- /*command.server = this.con_num;
- command.command = 'ERROR';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'error', reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'error', reason: command.trailing});
- },
- ERR_LINKCHANNEL: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_LINKCHANNEL';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('channel_redirect', {from: params[1], to: params[2]});
- this.client.sendIRCCommand('channel_redirect', {server: this.con_num, from: command.params[1], to: command.params[2]});
- },
- ERR_NOSUCHNICK: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_NOSUCHNICK';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'no_such_nick', nick: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'no_such_nick', nick: command.params[1], reason: command.trailing});
- },
- ERR_CANNOTSENDTOCHAN: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_CANNOTSENDTOCHAN';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'cannot_send_to_chan', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'cannot_send_to_chan', channel: command.params[1], reason: command.trailing});
- },
- ERR_TOOMANYCHANNELS: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_TOOMANYCHANNELS';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'too_many_channels', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'too_many_channels', channel: command.params[1], reason: command.trailing});
- },
- ERR_USERNOTINCHANNEL: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_USERNOTINCHANNEL';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'user_not_in_channel', nick: params[0], channel: params[1], reason: msg.trainling});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'user_not_in_channel', nick: command.params[0], channel: command.params[1], reason: command.trailing});
- },
- ERR_NOTONCHANNEL: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_NOTONCHANNEL';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'not_on_channel', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'not_on_channel', channel: command.params[1], reason: command.trailing});
- },
- ERR_CHANNELISFULL: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_CHANNELISFULL';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'channel_is_full', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'channel_is_full', channel: command.params[1], reason: command.trailing});
- },
- ERR_INVITEONLYCHAN: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_INVITEONLYCHAN';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'invite_only_channel', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'invite_only_channel', channel: command.params[1], reason: command.trailing});
- },
- ERR_BANNEDFROMCHAN: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_BANNEDFROMCHAN';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'banned_from_channel', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'banned_from_channel', channel: command.params[1], reason: command.trailing});
- },
- ERR_BADCHANNELKEY: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_BADCHANNELKEY';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'bad_channel_key', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'bad_channel_key', channel: command.params[1], reason: command.trailing});
- },
- ERR_CHANOPRIVSNEEDED: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_CHANOPRIVSNEEDED';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'chanop_privs_needed', channel: msg.params.split(" ")[1], reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'chanop_privs_needed', channel: command.params[1], reason: command.trailing});
- },
- ERR_NICKNAMEINUSE: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_NICKNAMEINUSE';
- this.client.sendIRCCommand(command);*/
- //websocket.sendClientEvent('irc_error', {error: 'nickname_in_use', nick: _.last(msg.params.split(" ")), reason: msg.trailing});
- this.client.sendIRCCommand('irc_error', {server: this.con_num, error: 'nickname_in_use', nick: command.params[1], reason: command.trailing});
- },
- ERR_NOTREGISTERED: function (command) {
- /*command.server = this.con_num;
- command.command = 'ERR_NOTREGISTERED';
- this.client.sendIRCCommand(command);*/
- }
-};
+++ /dev/null
-var net = require('net'),
- tls = require('tls'),
- events = require('events'),
- util = require('util');
-
-var IRCConnection = function (hostname, port, ssl, nick, user, pass, webirc) {
- var that = this;
- events.EventEmitter.call(this);
-
- if (ssl) {
- this.socket = tls.connect(port, hostname, {}, connect_handler);
- } else {
- this.socket = net.createConnection(port, hostname);
- this.socket.on('connect', function () {
- connect_handler.apply(that, arguments);
- });
- }
-
- this.socket.on('error', function () {
- var a = Array.prototype.slice.call(arguments);
- a.unshift('error');
- that.emit.apply(this, a);
- });
-
- this.socket.setEncoding('utf-8');
-
- this.socket.on('data', function () {
- parse.apply(that, arguments);
- });
-
- this.socket.on('close', function () {
- that.emit('close');
- });
-
- this.connected = false;
- this.registered = false;
- this.nick = nick;
- this.user = user;
- this.ssl = !(!ssl);
- this.options = Object.create(null);
-
- this.webirc = webirc;
- this.password = pass;
- this.hold_last = false;
- this.held_data = '';
-};
-util.inherits(IRCConnection, events.EventEmitter);
-
-IRCConnection.prototype.write = function (data, callback) {
- console.log('S<--', data);
- write.call(this, data + '\r\n', 'utf-8', callback);
-};
-
-IRCConnection.prototype.end = function (data, callback) {
- console.log('S<--', data);
- console.log('Closing docket');
- end.call(this, data + '\r\n', 'utf-8', callback);
-};
-
-var write = function (data, encoding, callback) {
- this.socket.write(data, encoding, callback);
-};
-
-var end = function (data, encoding, callback) {
- this.socket.end(data, encoding, callback);
-};
-
-module.exports.IRCConnection = IRCConnection;
-
-var connect_handler = function () {
- if (this.webirc) {
- this.write('WEBIRC ' + this.webirc.pass + ' KiwiIRC ' + this.user.hostname + ' ' + this.user.address);
- }
- if (this.password) {
- this.write('PASS ' + this.password);
- }
- //this.write('CAP LS');
- this.write('NICK ' + this.nick);
- this.write('USER kiwi_' + this.nick.replace(/[^0-9a-zA-Z\-_.]/, '') + ' 0 0 :' + this.nick);
-
- this.connected = true;
- console.log("IRCConnection.emit('connected')");
- this.emit('connected');
-};
-
-parse_regex = /^(?::(?:([a-z0-9\x5B-\x60\x7B-\x7D\.\-]+)|([a-z0-9\x5B-\x60\x7B-\x7D\.\-]+)!([a-z0-9~\.\-_|]+)@?([a-z0-9\.\-:\/]+)?) )?(\S+)(?: (?!:)(.+?))?(?: :(.+))?$/i;
-//alt_regex = /(?::(([0-9a-z][\x2d0-9a-z]*[0-9a-z]*(?:\x2e[0-9a-z][\x2d0-9a-z]*[0-9a-z]*)*|[\x5b-\x7d][\x2d0-9\x5b-\x7d]{0,8})(?:(?:!([\x01-\t\v\f\x0e-\x1f!-\x3f\x5b-\xff]+))?@([0-9a-z][\x2d0-9a-z]*[0-9a-z]*(?:\x2e[0-9a-z][\x2d0-9a-z]*[0-9a-z]*)*|\d{1,3}\x2e\d{1,3}\x2e\d{1,3}\x2e\d{1,3}|[0-9a-f]+(?::[0-9a-f]+){7}|0:0:0:0:0:(?:0|ffff):\d{1,3}\x2e\d{1,3}\x2e\d{1,3}\x2e\d{1,3}))?)\x20)?([a-z]+|\d{3})((?:\x20[\x01-\t\v\f\x0e-\x1f!-9;-@\x5b-\xff][\x01-\t\v\f\x0e-\x1f!-@\x5b-\xff]*){0,14}(?:\x20:[\x01-\t\v\f\x0e-@\x5b-\xff]*)?|(?:\x20[\x01-\t\v\f\x0e-\x1f!-9;-@\x5b-\xff][\x01-\t\v\f\x0e-\x1f!-@\x5b-\xff]*){14}(?:\x20:?[\x01-\t\v\f\x0e-@\x5b-\xff]*)?)?/i;
-
-var parse = function (data) {
- var i,
- msg,
- msg2,
- trm;
-
- if ((this.hold_last) && (this.held_data !== '')) {
- data = this.held_data + data;
- this.hold_last = false;
- this.held_data = '';
- }
- if (data.substr(-1) !== '\n') {
- this.hold_last = true;
- }
- data = data.split("\n");
- for (i = 0; i < data.length; i++) {
- if (data[i]) {
- if ((this.hold_last) && (i === data.length - 1)) {
- this.held_data = data[i];
- break;
- }
-
- // We have a complete line of data, parse it!
- msg = parse_regex.exec(data[i].replace(/^\r+|\r+$/, ''));
- //msg2 = alt_regex.exec(data[i].replace(/^\r+|\r+$/, ''));
- console.log('S-->', data[i]);
- console.log('Matches', msg);
- if (msg) {
- msg = {
- prefix: msg[1],
- nick: msg[2],
- ident: msg[3],
- hostname: msg[4] || '',
- command: msg[5],
- params: msg[6] || '',
- trailing: (msg[7]) ? msg[7].trim() : ''
- };
- msg.params = msg.params.split(' ');
-
- console.log('Parsed', msg);
-
- this.emit('irc_' + msg.command.toUpperCase(), msg);
- } else {
- console.log("Malformed IRC line: " + data[i].replace(/^\r+|\r+$/, ''));
- }
- }
- }
-};
-var fs = require('fs'),
- _ = require('underscore'),
- WebListener = require('./web.js').WebListener;
+/*jslint continue: true, forin: true, regexp: true, undef: false, node: true, nomen: true, plusplus: true, maxerr: 50, indent: 4 */
+"use strict";
+var tls = require('tls'),
+ net = require('net'),
+ http = require('http'),
+ https = require('https'),
+ node_static = require('node-static'),
+ fs = require('fs'),
+ url = require('url'),
+ dns = require('dns'),
+ crypto = require('crypto'),
+ events = require("events"),
+ util = require('util'),
+ ws = require('socket.io'),
+ jsp = require("uglify-js").parser,
+ pro = require("uglify-js").uglify,
+ _ = require('./lib/underscore.min.js'),
+ starttls = require('./lib/starttls.js'),
+ app = require(__dirname + '/app.js');
-//load config
+// Libraries may need to know kiwi.js path as __dirname
+// only gives that librarys path. Set it here for usage later.
+this.kiwi_root = __dirname;
+
+
+
+// How to handle log output
+this.log = function(str, level) {
+ level = level || 0;
+ console.log(str);
+}
+
+
+/*
+ * Configuration and rehashing routines
+ */
var config_filename = 'config.json',
- config_dirs = ['/etc/kiwiirc/', __dirname + '/'];
-
-var config = Object.create(null);
-for (var i in config_dirs) {
- try {
- if (fs.lstatSync(config_dirs[i] + config_filename).isDirectory() === false) {
- config = JSON.parse(fs.readFileSync(config_dirs[i] + config_filename, 'utf-8'));
- console.log('Loaded config file ' + config_dirs[i] + config_filename);
- break;
+ config_dirs = ['/etc/kiwiirc/', this.kiwi_root + '/'];
+
+this.config = {};
+this.loadConfig = function () {
+ var i, j,
+ nconf = {},
+ cconf = {},
+ found_config = false;
+
+ for (i in config_dirs) {
+ try {
+ if (fs.lstatSync(config_dirs[i] + config_filename).isDirectory() === false) {
+ found_config = true;
+ nconf = JSON.parse(fs.readFileSync(config_dirs[i] + config_filename, 'ascii'));
+ for (j in nconf) {
+ // If this has changed from the previous config, mark it as changed
+ if (!_.isEqual(this.config[j], nconf[j])) {
+ cconf[j] = nconf[j];
+ }
+
+ this.config[j] = nconf[j];
+ }
+
+ this.log('Loaded config file ' + config_dirs[i] + config_filename);
+ break;
+ }
+ } catch (e) {
+ switch (e.code) {
+ case 'ENOENT': // No file/dir
+ break;
+ default:
+ this.log('An error occured parsing the config file ' + config_dirs[i] + config_filename + ': ' + e.message);
+ return false;
+ }
+ continue;
}
- } catch (e) {
- switch (e.code) {
- case 'ENOENT': // No file/dir
- break;
- default:
- console.log('An error occured parsing the config file ' + config_dirs[i] + config_filename + ': ' + e.message);
- return false;
+ }
+ if (Object.keys(this.config).length === 0) {
+ if (!found_config) {
+ this.log('Couldn\'t find a config file!');
}
- continue;
+ return false;
}
+ return [nconf, cconf];
+};
+
+
+// Reloads the config during runtime
+this.rehash = function () {
+ return app.rehash();
}
-if (Object.keys(config).length === 0) {
- console.log('Couldn\'t find a valid config file!');
- process.exit(1);
+// Reloads app.js during runtime for any recoding
+this.recode = function () {
+ if (typeof require.cache[this.kiwi_root + '/app.js'] !== 'undefined'){
+ delete require.cache[this.kiwi_root + '/app.js'];
+ }
+
+ app = null;
+ app = require(__dirname + '/app.js');
+
+ var objs = {tls:tls, net:net, http:http, https:https, node_static:node_static, fs:fs, url:url, dns:dns, crypto:crypto, events:events, util:util, ws:ws, jsp:jsp, pro:pro, _:_, starttls:starttls};
+ app.init(objs);
+ app.rebindIRCCommands();
+
+ return true;
}
-if ((!config.servers) || (config.servers.length < 1)) {
- console.log('No servers defined in config file');
- process.exit(2);
+
+
+
+
+
+/*
+ * Before we continue we need the config loaded
+ */
+if (!this.loadConfig()) {
+ process.exit(0);
+}
+
+
+
+
+
+
+
+/*
+ * HTTP file serving
+ */
+if (this.config.handle_http) {
+ this.fileServer = new (require('node-static').Server)(__dirname + this.config.public_http);
+ this.cache = {alljs: '', html: []};
+}
+this.httpServers = [];
+this.httpHandler = function (request, response) {
+ return app.httpHandler(request, response);
+}
+
+
+
+
+
+
+/*
+ * Websocket handling
+ */
+this.connections = {};
+this.io = [];
+this.websocketListen = function (servers, handler) {
+ return app.websocketListen(servers, handler);
+}
+this.websocketConnection = function (websocket) {
+ return app.websocketConnection(websocket);
+}
+this.websocketDisconnect = function () {
+ return app.websocketDisconnect(this);
+}
+this.websocketMessage = function (msg, callback) {
+ return app.websocketMessage(this, msg, callback);
+}
+this.websocketKiwiMessage = function (msg, callback) {
+ return app.websocketKiwiMessage(this, msg, callback);
+}
+this.websocketIRCConnect = function (nick, host, port, ssl, callback) {
+ return app.websocketIRCConnect(this, nick, host, port, ssl, callback);
}
-//Create web listeners
-var clients = [];
-_.each(config.servers, function (server) {
- var wl = new WebListener(server, config.transports);
- wl.on('connection', function (client) {
- clients.push(client);
- });
- wl.on('destroy', function (client) {
- clients = _.reject(clients, function (c) {
- return client === c;
- });
- });
-});
-//Set process title
-process.title = 'Kiwi IRC';
+/*
+ * IRC handling
+ */
+this.parseIRCMessage = function (websocket, ircSocket, data) {
+ return app.parseIRCMessage(websocket, ircSocket, data);
+}
+this.ircSocketDataHandler = function (data, websocket, ircSocket) {
+ return app.ircSocketDataHandler(data, websocket, ircSocket);
+}
+this.IRCConnection = function (websocket, nick, host, port, ssl, password, callback) {
+ return app.IRCConnection.call(this, websocket, nick, host, port, ssl, password, callback);
+}
+util.inherits(this.IRCConnection, events.EventEmitter);
-//Change UID/GID
-if ((config.user) && (config.user !== '')) {
- process.setuid(config.user);
+this.bindIRCCommands = function (irc_connection, websocket) {
+ return app.bindIRCCommands.call(this, irc_connection, websocket);
}
-if ((config.group) && (config.group !== '')) {
- process.setgid(config.group);
+this.rebindIRCCommands = function () {
+ return app.rebindIRCCommands.call(this);
}
-//Listen to STDIN
+
+
+
+
+
+/*
+ * Load up main application source
+ */
+if (!this.recode()) {
+ process.exit(0);
+}
+
+
+
+// Set the process title
+app.setTitle();
+
+
+
+/*
+ * Load the modules as set in the config and print them out
+ */
+this.kiwi_mod = require('./lib/kiwi_mod.js');
+this.kiwi_mod.loadModules(this.kiwi_root, this.config);
+this.kiwi_mod.printMods();
+
+
+// Make sure Kiwi doesn't simply quit on an exception
+//process.on('uncaughtException', function (e) {
+// console.log('[Uncaught exception] ' + e);
+//});
+
+// Start the server up
+this.websocketListen(this.config.servers, this.httpHandler);
+
+// Now we're listening on the network, set our UID/GIDs if required
+app.changeUser();
+
+// Listen for controll messages
process.stdin.resume();
-process.stdin.on('data', function (data) {
- console.log(data.toString());
-});
+process.stdin.on('data', function (data) { app.manageControll(data); });
+
+
+
+
+++ /dev/null
-var ws = require('socket.io'),
- events = require('events'),
- http = require('http'),
- https = require('https'),
- util = require('util'),
- fs = require('fs'),
- dns = require('dns'),
- _ = require('underscore'),
- Client = require('./client.js').Client,
- HTTPHandler = require('./http-handler.js').HTTPHandler;
-
-var WebListener = function (config, transports) {
- var handler,
- hs,
- opts,
- that = this;
-
- events.EventEmitter.call(this);
-
- http_handler = new HTTPHandler(config);
-
- if (config.secure) {
- opts = {
- key: fs.readFileSync(__dirname + '/' + config.ssl_key),
- cert: fs.readFileSync(__dirname + '/' + config.ssl_cert)
- };
- // Do we have an intermediate certificate?
- if (typeof config.ssl_ca !== 'undefined') {
- opts.ca = fs.readFileSync(__dirname + '/' + config.ssl_ca);
- }
- hs = https.createServer(opts, function (request, response) {
- http_handler.handler(request, response);
- });
-
- this.ws = ws.listen(hs, {secure: true});
- hs.listen(config.port, config.address);
- console.log('Listening on ' + config.address + ':' + config.port.toString() + ' with SSL');
- } else {
- // Start some plain-text server up
- hs = http.createServer(function (request, response) {
- http_handler.handler(request, response);
- });
- this.ws = ws.listen(hs, {secure: false});
- hs.listen(config.port, config.address);
- console.log('Listening on ' + config.address + ':' + config.port.toString() + ' without SSL');
- }
-
- this.ws.set('log level', 1);
- this.ws.enable('browser client minification');
- this.ws.enable('browser client etag');
- this.ws.set('transports', transports);
-
- this.ws.of('/kiwi').authorization(authorisation).on('connection', function () {
- connection.apply(that, arguments);
- });
- this.ws.of('/kiwi').on('error', console.log);
-};
-util.inherits(WebListener, events.EventEmitter);
-
-module.exports.WebListener = WebListener;
-
-var authorisation = function (handshakeData, callback) {
- dns.reverse(handshakeData.address.address, function (err, domains) {
- handshakeData.revdns = (err) ? handshakeData.address.address : _.first(domains);
- callback(null, true);
- });
-};
-
-var connection = function (websocket) {
- //console.log(websocket);
- this.emit('connection', new Client(websocket));
-};
+++ /dev/null
------BEGIN CERTIFICATE-----
-MIICKzCCAZQCCQCHW0Kmpb9HBTANBgkqhkiG9w0BAQUFADBaMQswCQYDVQQGEwJH
-QjERMA8GA1UEChMIS2l3aSBJUkMxFzAVBgNVBAMTDktpd2kgV3JhbmdsZXJzMR8w
-HQYJKoZIhvcNAQkBFhBraXdpQGtpd2lpcmMuY29tMB4XDTExMDcxNjE1NDQxM1oX
-DTExMDgxNTE1NDQxM1owWjELMAkGA1UEBhMCR0IxETAPBgNVBAoTCEtpd2kgSVJD
-MRcwFQYDVQQDEw5LaXdpIFdyYW5nbGVyczEfMB0GCSqGSIb3DQEJARYQa2l3aUBr
-aXdpaXJjLmNvbTCBnzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEA0h+kOA69tiJD
-u0COP0Wh0I9wVqAENQlRA5GowcH7r2Y3D9CbBIguw4Ss48kfXhDQa6sP9qsGvEAR
-kSkHcxIt+BRVtGjmzrZbGzObyOOm8rStcLiYCXas7m5U/mxy4vppL2eAX26az5wy
-f1vYGukhH1XRUdObxNNnLoNDWPJG8+sCAwEAATANBgkqhkiG9w0BAQUFAAOBgQBU
-fARp2ZADZ89EiqUTRsCe8b8gXTO0Z3ov9LFTYhlpwH0RZ3fn9sE9A4mwrRlJC44W
-Z21sflIuXNFDerraedmx+fQwmwNBR6MMJgVN5nYw/x24QJf0C7ujIZrs4lxJdqwf
-yBRE6B7pJYPkk+aPHx/LSsbi9avMBfW+LQtkVOCuZg==
------END CERTIFICATE-----
+++ /dev/null
-{
- "servers": [
- {
- "secure": true,
- "port": 7777,
- "address": "0.0.0.0",
-
- "ssl_key": "server.key",
- "ssl_cert": "cert.pem"
- },
- {
- "secure": false,
- "port": 7778,
- "address": "0.0.0.0"
- }
-
- ],
-
- "user": "",
- "group": "",
-
- "quit_message": "KiwiIRC",
- "cap_options": [],
-
- "handle_http": true,
- "public_http": "./../client/",
-
- "max_client_conns": 2,
-
- "module_dir": "./kiwi_modules/",
- "modules": ["spamfilter", "statistics"],
-
- "webirc": true,
- "webirc_pass": {
- "irc.example.com": "examplepassword",
- "127.0.0.1": "foobar"
- },
-
- "transports": [
- "websocket",
- "flashsocket",
- "htmlfile",
- "xhr-polling",
- "jsonp-polling"
- ],
-
- "client_defaults": {
- "server": "irc.anonnet.org",
- "port": 6667,
- "port_ssl": 6697,
- "ssl": false
- }
-}
+++ /dev/null
-/*jslint continue: true, forin: true, regexp: true, undef: false, node: true, nomen: true, plusplus: true, maxerr: 50, indent: 4 */
-"use strict";
-var tls = require('tls'),
- net = require('net'),
- http = require('http'),
- https = require('https'),
- node_static = require('node-static'),
- fs = require('fs'),
- url = require('url'),
- dns = require('dns'),
- crypto = require('crypto'),
- events = require("events"),
- util = require('util'),
- ws = require('socket.io'),
- jsp = require("uglify-js").parser,
- pro = require("uglify-js").uglify,
- _ = require('./lib/underscore.min.js'),
- starttls = require('./lib/starttls.js'),
- app = require(__dirname + '/app.js');
-
-
-// Libraries may need to know kiwi.js path as __dirname
-// only gives that librarys path. Set it here for usage later.
-this.kiwi_root = __dirname;
-
-
-
-// How to handle log output
-this.log = function(str, level) {
- level = level || 0;
- console.log(str);
-}
-
-
-/*
- * Configuration and rehashing routines
- */
-var config_filename = 'config.json',
- config_dirs = ['/etc/kiwiirc/', this.kiwi_root + '/'];
-
-this.config = {};
-this.loadConfig = function () {
- var i, j,
- nconf = {},
- cconf = {},
- found_config = false;
-
- for (i in config_dirs) {
- try {
- if (fs.lstatSync(config_dirs[i] + config_filename).isDirectory() === false) {
- found_config = true;
- nconf = JSON.parse(fs.readFileSync(config_dirs[i] + config_filename, 'ascii'));
- for (j in nconf) {
- // If this has changed from the previous config, mark it as changed
- if (!_.isEqual(this.config[j], nconf[j])) {
- cconf[j] = nconf[j];
- }
-
- this.config[j] = nconf[j];
- }
-
- this.log('Loaded config file ' + config_dirs[i] + config_filename);
- break;
- }
- } catch (e) {
- switch (e.code) {
- case 'ENOENT': // No file/dir
- break;
- default:
- this.log('An error occured parsing the config file ' + config_dirs[i] + config_filename + ': ' + e.message);
- return false;
- }
- continue;
- }
- }
- if (Object.keys(this.config).length === 0) {
- if (!found_config) {
- this.log('Couldn\'t find a config file!');
- }
- return false;
- }
- return [nconf, cconf];
-};
-
-
-// Reloads the config during runtime
-this.rehash = function () {
- return app.rehash();
-}
-
-// Reloads app.js during runtime for any recoding
-this.recode = function () {
- if (typeof require.cache[this.kiwi_root + '/app.js'] !== 'undefined'){
- delete require.cache[this.kiwi_root + '/app.js'];
- }
-
- app = null;
- app = require(__dirname + '/app.js');
-
- var objs = {tls:tls, net:net, http:http, https:https, node_static:node_static, fs:fs, url:url, dns:dns, crypto:crypto, events:events, util:util, ws:ws, jsp:jsp, pro:pro, _:_, starttls:starttls};
- app.init(objs);
- app.rebindIRCCommands();
-
- return true;
-}
-
-
-
-
-
-
-/*
- * Before we continue we need the config loaded
- */
-if (!this.loadConfig()) {
- process.exit(0);
-}
-
-
-
-
-
-
-
-/*
- * HTTP file serving
- */
-if (this.config.handle_http) {
- this.fileServer = new (require('node-static').Server)(__dirname + this.config.public_http);
- this.cache = {alljs: '', html: []};
-}
-this.httpServers = [];
-this.httpHandler = function (request, response) {
- return app.httpHandler(request, response);
-}
-
-
-
-
-
-
-/*
- * Websocket handling
- */
-this.connections = {};
-this.io = [];
-this.websocketListen = function (servers, handler) {
- return app.websocketListen(servers, handler);
-}
-this.websocketConnection = function (websocket) {
- return app.websocketConnection(websocket);
-}
-this.websocketDisconnect = function () {
- return app.websocketDisconnect(this);
-}
-this.websocketMessage = function (msg, callback) {
- return app.websocketMessage(this, msg, callback);
-}
-this.websocketKiwiMessage = function (msg, callback) {
- return app.websocketKiwiMessage(this, msg, callback);
-}
-this.websocketIRCConnect = function (nick, host, port, ssl, callback) {
- return app.websocketIRCConnect(this, nick, host, port, ssl, callback);
-}
-
-
-
-
-/*
- * IRC handling
- */
-this.parseIRCMessage = function (websocket, ircSocket, data) {
- return app.parseIRCMessage(websocket, ircSocket, data);
-}
-this.ircSocketDataHandler = function (data, websocket, ircSocket) {
- return app.ircSocketDataHandler(data, websocket, ircSocket);
-}
-this.IRCConnection = function (websocket, nick, host, port, ssl, password, callback) {
- return app.IRCConnection.call(this, websocket, nick, host, port, ssl, password, callback);
-}
-util.inherits(this.IRCConnection, events.EventEmitter);
-
-this.bindIRCCommands = function (irc_connection, websocket) {
- return app.bindIRCCommands.call(this, irc_connection, websocket);
-}
-this.rebindIRCCommands = function () {
- return app.rebindIRCCommands.call(this);
-}
-
-
-
-
-
-
-/*
- * Load up main application source
- */
-if (!this.recode()) {
- process.exit(0);
-}
-
-
-
-// Set the process title
-app.setTitle();
-
-
-
-/*
- * Load the modules as set in the config and print them out
- */
-this.kiwi_mod = require('./lib/kiwi_mod.js');
-this.kiwi_mod.loadModules(this.kiwi_root, this.config);
-this.kiwi_mod.printMods();
-
-
-// Make sure Kiwi doesn't simply quit on an exception
-//process.on('uncaughtException', function (e) {
-// console.log('[Uncaught exception] ' + e);
-//});
-
-// Start the server up
-this.websocketListen(this.config.servers, this.httpHandler);
-
-// Now we're listening on the network, set our UID/GIDs if required
-app.changeUser();
-
-// Listen for controll messages
-process.stdin.resume();
-process.stdin.on('data', function (data) { app.manageControll(data); });
-
-
-
-
+++ /dev/null
------BEGIN RSA PRIVATE KEY-----
-MIICXQIBAAKBgQDSH6Q4Dr22IkO7QI4/RaHQj3BWoAQ1CVEDkajBwfuvZjcP0JsE
-iC7DhKzjyR9eENBrqw/2qwa8QBGRKQdzEi34FFW0aObOtlsbM5vI46bytK1wuJgJ
-dqzublT+bHLi+mkvZ4BfbprPnDJ/W9ga6SEfVdFR05vE02cug0NY8kbz6wIDAQAB
-AoGBANBlPVOzmwfWd+JxJiMuhkv41uuzDDklokmt3vc70sik0ZtHw1b9UZPsNCQ+
-RnPerTb7k3uLJ8TwrfuP+6lusFL8bwzXBaPZOZmSf2aQz8o6MAyY8B8gxjDi/NoW
-b5jtpXGFNayjc5O7tDjBsd/g88vk3EjnpJZ0P4H3gC+hhCCRAkEA7lGFVou8/ht7
-vTpbHEP13mjYG7OUmJqTXavkrit9UDDcZukt6I7TAB42LPyI7DnjB8i358bdmQQj
-x4R1mNZadQJBAOG2msKY+PFQGUpP18HlFze7JPbc0L5CLeiVIrXV9+xY7FgyGzwU
-UvI9ZyHhqzsgU2/9yW2+beaS8S8LCkGAiN8CQQCcmfMNiOua6wJnuQYPz9Sr3qdL
-pLjbgo+duQufK7K/1CuwcD+bluauKCwfaZ6r4+n8vneilXoeR6sfOzpvQUPVAkBJ
-ZJUB/bfEz6TJkxi3BYT9LC8izj5Z/y7qV8QHmGGbSnbfXruYV4t5FRo53CVPfn1j
-BwS+WJNnzBP8lfxpvB/FAkAf6mPKzWlMnWYXg6gII9lQZQ1EIn258Hi7vrFw9+Ic
-lDbndynaxh97wqKoloRckXF3D9FZM0w7YIS541Cih42u
------END RSA PRIVATE KEY-----