Skip to content

Instantly share code, notes, and snippets.

Created August 23, 2014 21:48
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save anonymous/e8d42545c4772ba9486f to your computer and use it in GitHub Desktop.
Save anonymous/e8d42545c4772ba9486f to your computer and use it in GitHub Desktop.
ChatGuard mod 0.0.1
--
-- ChatGuard server protection mod
--
-- This mod checks players chat messages for oversized or to frequent
-- messages. Players abusing chat will be kicked or even baned.
--
-- Serverconfig:
-- chatguard_max_message_length = nil
-- maximum allowed length of a message (check disabled by default)
--
-- chatguard_max_overlength_messages = 10
-- amount of overlenth messages causing a player to be kicked
--
-- chatguard_max_messages = nil
-- maximum amount of messages allowed to be sent per second and player
--
-- chatguard_max_overcount_messages = 50
-- maximum number of messages a player may send more then allowed per second prior beeing kicked
--
-- chatguard_ban_overcount_players = nil
-- set to true to automaticaly ban players exceeding number of messages per second
--
local version = "0.0.1"
local chat_guard_data = {
max_message_length = core.setting_get("chatguard_max_message_length"),
player_overlength_kick_threshold = core.setting_get("chatguard_max_overlength_messages") or 10,
max_messages_per_second = core.setting_get("chatguard_max_messages") or -1,
player_overcount_kick_threshold = core.setting_get("chatguard_max_overcount_messages") or 50,
ban_overcount = core.setting_get("chatguard_ban_overcount_players"),
playerlist = {},
toadd = 0
}
-- initialize player chat quota on join
core.register_on_joinplayer(function(player)
if not player:is_player() then
core.log("error", "ChatGuard: on_joinplayer called without valid player object")
return
end
local playername = player:get_player_name()
if playername == "" then
core.log("error", "ChatGuard: on_joinplayer failed to get player name")
return
end
chat_guard_data.playerlist[playername] = {
message_quota = max_messages_per_second,
overlength_messages = 0
}
end)
-- cleanup internal data on player leaving
core.register_on_leaveplayer(function(player)
if not player:is_player() then
core.log("error", "ChatGuard: on_leaveplayer called without valid player object")
return
end
local playername = player:get_player_name()
if playername == "" then
core.log("error", "ChatGuard: on_leaveplayer failed to get player name")
return
end
chat_guard_data.playerlist[playername] = nil
end)
-- check players chat messages
core.register_on_chat_message(function(playername, message)
if chat_guard_data.playerlist[playername] == nil then
core.log("action", "ChatGuard: message by unknown player \"" .. playername .. "\", discarding")
return true
end
-- only do this if length is configured
if chat_guard_data.max_message_length ~= nil and
message:length() > chat_guard_data.max_message_length then
chat_guard_data.playerlist[playername].overlength_messages =
chat_guard_data.playerlist[playername].overlength_messages +1
if chat_guard_data.playerlist[playername].overlength_messages >
chat_guard_data.player_overlength_kick_threshold then
core.kick_player(playername,"ChatGuard: too many overlength chat messages")
else
core.chat_send_player(playername, "ChatGuard: your message was to long. Don't do this again or you will be kicked!")
end
return true
end
-- check if message count check is disabled
if chat_guard_data.max_messages_per_second < 0 then
return false
end
chat_guard_data.playerlist[playername].message_quota =
chat_guard_data.playerlist[playername].message_quota -1
if chat_guard_data.playerlist[playername].message_quota <
-chat_guard_data.player_overcount_kick_threshold then
core.kick_player(playername, "ChatGuard: Kicked due to excessive spawning!")
if chat_guard_data.ban_overcount then
core.ban_player(playername)
end
end
-- player has still messages left to be sent
if chat_guard_data.playerlist[playername].message_quota > -1 then
return false
end
-- player exceeded his quota don't send this message
return true
end)
-- give credit back to players
core.register_globalstep(function(dtime)
-- don't do anything if message amount limiting is disabled
if chat_guard_data.max_messages_per_second < 0 then
return
end
chat_guard_data.toadd = chat_guard_data.toadd +
dtime * chat_guard_data.max_messages_per_second
if chat_guard_data.toadd > 1 then
for k,v in pairs(chat_guard_data.playerlist) do
v.message_quota = math.min(
v.message_quota + chat_guard_data.toadd,
chat_guard_data.max_messages_per_second)
end
chat_guard_data.toadd = 0
end
end)
core.log("action", "ChatGuard mod version " .. version .. " initialized ...")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment