send multiple KICKs in the same line when possible

This commit is contained in:
jesopo 2020-02-17 15:16:00 +00:00
parent f43efbabcc
commit 7f98ba8310
4 changed files with 24 additions and 9 deletions

View file

@ -55,9 +55,9 @@ class Module(ModuleManager.BaseModule):
server.get_setting("default-kick-reason", server.get_setting("default-kick-reason",
self.bot.get_setting("default-kick-reson", KICK_REASON))) self.bot.get_setting("default-kick-reson", KICK_REASON)))
def _kick(self, server, channel, target_user, reason): def _kick(self, server, channel, nicknames, reason):
reason = reason or self._kick_reason(server, channel) reason = reason or self._kick_reason(server, channel)
channel.send_kick(target_user.nickname, reason) channel.send_kicks(nicknames, reason)
@utils.hook("received.command.kick") @utils.hook("received.command.kick")
@utils.hook("received.command.k", alias_of="kick") @utils.hook("received.command.k", alias_of="kick")
@ -66,8 +66,8 @@ class Module(ModuleManager.BaseModule):
@utils.kwarg("help", "Kick a user from a channel") @utils.kwarg("help", "Kick a user from a channel")
@utils.spec("!<#channel>r~channel !<nickname>cuser ?<reason>string") @utils.spec("!<#channel>r~channel !<nickname>cuser ?<reason>string")
def kick(self, event): def kick(self, event):
self._kick(event["server"], event["spec"][0], event["spec"][1], self._kick(event["server"], event["spec"][0],
event["spec"][2]) [event["spec"][1].nickname], event["spec"][2])
def _format_hostmask(self, user, s): def _format_hostmask(self, user, s):
vars = {} vars = {}
@ -143,9 +143,8 @@ class Module(ModuleManager.BaseModule):
users = event["spec"][2][1] users = event["spec"][2][1]
else: else:
users = [event["spec"][2][1]] users = [event["spec"][2][1]]
for user in users: self._kick(event["server"], event["spec"][0],
self._kick(event["server"], event["spec"][0], user, [u.nickname for u in users], event["spec"][3])
event["spec"][3])
@utils.hook("received.command.op") @utils.hook("received.command.op")
@utils.hook("received.command.up", alias_of="op") @utils.hook("received.command.up", alias_of="op")

View file

@ -215,17 +215,25 @@ class Channel(IRCObject.Object):
def send_tagmsg(self, tags: dict): def send_tagmsg(self, tags: dict):
return self.server.send_tagmsg(self.name, tags) return self.server.send_tagmsg(self.name, tags)
def _chunks(self, n: int, l: typing.List[str]):
return [l[i:i+n] for i in range(0, len(l), n)]
def send_mode(self, mode: str=None, target: typing.List[str]=None): def send_mode(self, mode: str=None, target: typing.List[str]=None):
return self.server.send_mode(self.name, mode, target) return self.server.send_mode(self.name, mode, target)
def send_modes(self, mode: str, add: bool, args: typing.List[str]): def send_modes(self, mode: str, add: bool, args: typing.List[str]):
chunk_n = int(self.server.isupport.get("MODES", "3") or "6") chunk_n = int(self.server.isupport.get("MODES", "3") or "6")
chunks = [args[i:i+chunk_n] for i in range(0, len(args), chunk_n)] for chunk in self._chunks(chunk_n, args):
for chunk in chunks:
mode_str = "%s%s" % ("+" if add else "-", mode*len(chunk)) mode_str = "%s%s" % ("+" if add else "-", mode*len(chunk))
self.server.send_mode(self.name, mode_str, chunk) self.server.send_mode(self.name, mode_str, chunk)
def send_kick(self, target: str, reason: str=None): def send_kick(self, target: str, reason: str=None):
return self.server.send_kick(self.name, target, reason) return self.server.send_kick(self.name, target, reason)
def send_kicks(self, targets: typing.List[str], reason: str=None):
chunk_n = self.server.targmax.get("KICK", 1)
for chunk in self._chunks(chunk_n, targets):
chan_str = ",".join([self.name]*len(chunk))
self.server.send_kick(chan_str, ",".join(chunk), reason)
def send_ban(self, hostmask: str): def send_ban(self, hostmask: str):
return self.server.send_mode(self.name, "+b", [hostmask]) return self.server.send_mode(self.name, "+b", [hostmask])
def send_unban(self, hostmask: str): def send_unban(self, hostmask: str):

View file

@ -62,6 +62,7 @@ class Server(IRCObject.Object):
self.channel_types = ["#"] self.channel_types = ["#"]
self.case_mapping = "rfc1459" self.case_mapping = "rfc1459"
self.statusmsg = [] # type: typing.List[str] self.statusmsg = [] # type: typing.List[str]
self.targmax = {}
self.motd_lines = [] # type: typing.List[str] self.motd_lines = [] # type: typing.List[str]
self.motd_done = False self.motd_done = False

View file

@ -61,6 +61,13 @@ def handle_005(events, event):
list_numeric = qiuet.get(2, "367") # RPL_BANLIST list_numeric = qiuet.get(2, "367") # RPL_BANLIST
end_numeric = quiet.get(3, "368") # RPL_ENDOFBANLIST end_numeric = quiet.get(3, "368") # RPL_ENDOFBANLIST
event["server"].quiet = [quiet[0], prefix, list_numeric, end_numeric] event["server"].quiet = [quiet[0], prefix, list_numeric, end_numeric]
if "TARGMAX" in isupport:
targmax = {}
for piece in isupport["TARGMAX"].split(","):
cmd, _, n = piece.partition(":")
if n:
targmax[cmd] = int(n)
event["server"].targmax = targmax
events.on("received.005").call(isupport=isupport, events.on("received.005").call(isupport=isupport,
server=event["server"]) server=event["server"])