Channel: Make 'invite' command's required capability configurable

It still requires 'op' by default, but can now be changed with a config value.

This can be useful on servers that do not have a 'free invite' channel mode
(like Charybdis/Solanum's +g)
This commit is contained in:
Valentin Lorentz 2025-04-19 20:11:41 +02:00
parent c81ff28697
commit df45a61f52
3 changed files with 50 additions and 4 deletions

View File

@ -1,7 +1,7 @@
###
# Copyright (c) 2004-2005, Jeremiah Fincher
# Copyright (c) 2009, James McCoy
# Copyright (c) 2010-2021, Valentin Lorentz
# Copyright (c) 2010-2025, Valentin Lorentz
# All rights reserved.
#
# Redistribution and use in source and binary forms, with or without
@ -63,4 +63,9 @@ conf.registerChannelValue(Channel, 'partMsg',
be used (they are optional in the IRC protocol). The standard
substitutions ($version, $nick, etc.) are all handled appropriately.""")))
conf.registerGroup(Channel, 'invite')
conf.registerChannelValue(Channel.invite, 'requireCapability',
registry.String('op', _("""Determines what capability (if any) the bot should
require people trying to use the 'invite' command to have.""")))
# vim:set shiftwidth=4 softtabstop=4 expandtab textwidth=79:

View File

@ -1,7 +1,7 @@
###
# Copyright (c) 2002-2005, Jeremiah Fincher
# Copyright (c) 2009-2012, James McCoy
# Copyright (c) 2010-2021, Valentin Lorentz
# Copyright (c) 2010-2025, Valentin Lorentz
# All rights reserved.
#
# Redistribution and use in source and binary forms, with or without
@ -508,10 +508,17 @@ class Channel(callbacks.Plugin):
to join <channel>. <channel> is only necessary if the message isn't
sent in the channel itself.
"""
capability = self.registryValue('invite.requireCapability',
channel, irc.network)
if capability:
capability = ircdb.makeChannelCapability(channel, capability)
if not ircdb.checkCapability(msg.prefix, capability):
irc.errorNoCapability(capability, Raise=True)
nick = nick or msg.nick
self._sendMsg(irc, ircmsgs.invite(nick, channel))
self.invites[(irc.getRealIrc(), ircutils.toLower(nick))] = irc
invite = wrap(invite, ['op', ('haveHalfop+', _('invite someone')),
invite = wrap(invite, [('haveHalfop+', _('invite someone')),
additional('nick')])
def do341(self, irc, msg):

View File

@ -1,7 +1,7 @@
###
# Copyright (c) 2002-2005, Jeremiah Fincher
# Copyright (c) 2009, James McCoy
# Copyright (c) 2010-2021, Valentin Lorentz
# Copyright (c) 2010-2025, Valentin Lorentz
# All rights reserved.
#
# Redistribution and use in source and binary forms, with or without
@ -414,5 +414,39 @@ class ChannelTestCase(ChannelPluginTestCase):
self.assertEqual(m.args[0], '#foo')
self.assertEqual(m.args[1], 'reason')
def testInvite(self):
self.irc.feedMsg(ircmsgs.op(self.channel, self.nick))
m = self.getMsg('invite foo')
self.assertEqual(m.command, 'INVITE')
self.assertEqual(m.args, ('foo', self.channel))
def testInviteNoCapability(self):
self.irc.feedMsg(ircmsgs.op(self.channel, self.nick))
m = self.assertError('invite foo',
frm='test!user@with__no_testcap__')
def testInviteCustomCapability(self):
self.irc.feedMsg(ircmsgs.op(self.channel, self.nick))
self.assertError('invite foo',
frm='test!user@with__no_testcap__')
with conf.supybot.plugins.Channel.invite.requireCapability.context('freeinvite'):
m = self.getMsg('invite foo',
frm='test!user@with__no_testcap__')
self.assertEqual(m.command, 'INVITE')
self.assertEqual(m.args, ('foo', self.channel))
self.assertNotError('channel capability set -freeinvite')
self.assertError('invite foo',
frm='test!user@with__no_testcap__')
with conf.supybot.plugins.Channel.invite.requireCapability.context(''):
m = self.getMsg('invite foo',
frm='test!user@with__no_testcap__')
self.assertEqual(m.command, 'INVITE')
self.assertEqual(m.args, ('foo', self.channel))
# vim:set shiftwidth=4 softtabstop=4 expandtab textwidth=79: