diff --git a/config-sample.json b/config-sample.json index bc2fca2..135359d 100644 --- a/config-sample.json +++ b/config-sample.json @@ -7,5 +7,6 @@ "host": "0.0.0.0", "port": "6060", "x_forwarded_for": false, - "salt": "insert-randomly-generated-string-here" + "salt": "insert-randomly-generated-string-here", + "defaultBanDuration": "1h" } diff --git a/server.js b/server.js index a1fc8d6..4a13b97 100644 --- a/server.js +++ b/server.js @@ -11,6 +11,7 @@ function loadConfig(filename) { try { var data = fs.readFileSync(filename, 'utf8') config = JSON.parse(data) + config.defaultBanDuration = durationToMilliseconds(config.defaultBanDuration) console.log("Loaded config '" + filename + "'") } catch (e) { @@ -115,6 +116,30 @@ function hash(password) { return sha.digest('base64').substr(0, 6) } +function durationToMilliseconds(duration) { + if (duration == 'permanent') { + return Infinity + } + + var durationValue = parseInt(duration) + var durationUnit = duration[duration.length-1] + + switch (durationUnit) { + case '': // default: hours + case 'h': // fallthrough + durationValue *= 60 + case 'm': // fallthrough + durationValue *= 60 + case 's': // fallthrough + durationValue *= 1000 + break + default: + durationValue = null // postfix is not known + } + + return durationValue +} + function isAdmin(client) { return client.nick == config.admin } @@ -280,6 +305,16 @@ var COMMANDS = { // Moderator-only commands below this point + unban: function(args) { + if (!isMod(this)) { + return + } + + var ip = String(args.ip) + POLICE.free(ip) + console.log(this.nick + " [" + this.trip + "] unbanned ip " + ip) + }, + ban: function(args) { if (!isMod(this)) { return @@ -304,7 +339,7 @@ var COMMANDS = { return } - POLICE.arrest(getAddress(badClient)) + POLICE.arrest(getAddress(badClient), durationToMilliseconds(String(args.duration))) console.log(this.nick + " [" + this.trip + "] banned " + nick + " in " + this.channel) broadcast({cmd: 'info', text: "Banned " + nick}, this.channel) }, @@ -380,8 +415,12 @@ var POLICE = { frisk: function(id, deltaScore) { var record = this.search(id) - if (record.arrested) { - return true + if (record.arrestedUntil) { + if (Date.now() > record.arrestedUntil) { + delete record.arrestedUntil + } else { + return true + } } record.score *= Math.pow(2, -(Date.now() - record.time)/POLICE.halflife) @@ -393,11 +432,17 @@ var POLICE = { return false }, - arrest: function(id) { + arrest: function(id, duration) { var record = this.search(id) - if (record) { - record.arrested = true + if (!duration) { + duration = config.defaultBanDuration || 60 * 60 * 1000 // fallback: 1 hour } + record.arrestedUntil = Date.now() + duration + }, + + free: function(id) { + var record = this.search(id) + delete record.arrestedUntil }, }