]> jfr.im git - irc/rizon/acid.git/blob - pyva/pyva/src/main/python/limitserv/limitserv.py
8e56574090409aa9375c9cd94818ac7af8d2a9e7
[irc/rizon/acid.git] / pyva / pyva / src / main / python / limitserv / limitserv.py
1 #!/usr/bin/python pseudoserver.py
2 #psm-limitserv.py
3 # module for pypseudoserver
4 # written by celestin - martin <martin@rizon.net>
5
6 import sys
7 import types
8 from istring import istring
9 from pseudoclient import sys_log, sys_options, sys_channels, inviteable
10 from utils import *
11
12 from pyva import *
13 import logging
14 from core import *
15 from plugin import *
16
17 import cmd_admin, sys_auth, limitmanager
18
19 import pyva_net_rizon_acid_core_Acidictive as Acidictive
20 import pyva_net_rizon_acid_core_AcidCore as AcidCore
21 import pyva_net_rizon_acid_core_User as User
22 import pyva_net_rizon_acid_core_Channel as Channel
23
24 class limitserv(
25 AcidPlugin,
26 inviteable.InviteablePseudoclient
27 ):
28 initialized = False
29
30 def start_threads(self):
31 self.options.start()
32 self.channels.start()
33 self.auth.start()
34 self.limit_monitor.start()
35
36 def bind_function(self, function):
37 func = types.MethodType(function, self, limitserv)
38 setattr(limitserv, function.__name__, func)
39 return func
40
41 def bind_admin_commands(self):
42 list = cmd_admin.get_commands()
43 self.commands_admin = []
44
45 for command in list:
46 self.commands_admin.append((command, {'permission': 'j', 'callback': self.bind_function(list[command][0]),
47 'usage': list[command][1]}))
48
49 def __init__(self):
50 AcidPlugin.__init__(self)
51
52 self.name = "limitserv"
53 self.log = logging.getLogger(__name__)
54
55 try:
56 self.nick = istring(self.config.get('limitserv').get('nick'))
57 except Exception, err:
58 self.log.exception("Error reading 'limitserv:nick' configuration option: %s" % err)
59 raise
60
61 try:
62 self.chan = istring(self.config.get('limitserv').get('channel'))
63 except Exception, err:
64 self.log.exception("Error reading 'limitserv:channel' configuration option: %s" % err)
65 raise
66
67 self.bind_admin_commands()
68
69 def start(self):
70 try:
71 self.dbp.execute("CREATE TABLE IF NOT EXISTS limitserv_chans (item SMALLINT(5) NOT NULL AUTO_INCREMENT, channel VARCHAR(35), \
72 PRIMARY KEY (item), UNIQUE KEY (channel));")
73 except Exception, err:
74 self.log.exception("Error creating table for limitserv module (%s)" % err)
75 raise
76
77 try:
78 AcidPlugin.start(self)
79 inviteable.InviteablePseudoclient.start(self)
80
81 self.options = sys_options.OptionManager(self)
82 self.elog = sys_log.LogManager(self)
83 self.auth = sys_auth.LimitServAuthManager(self)
84 self.channels = sys_channels.ChannelManager(self)
85 self.limit_monitor = limitmanager.LimitManager(self)
86 except Exception, err:
87 self.log.exception('Error initializing subsystems for limitserv module (%s)' % err)
88 raise
89
90 for channel in self.channels.list_valid():
91 self.join(channel.name)
92
93 self.elog.debug('Joined channels.')
94
95 try:
96 self.start_threads()
97 except Exception, err:
98 self.log.exception('Error starting threads for limitserv module (%s)' % err)
99 raise
100
101 self.initialized = True
102 self.elog.debug('Started threads.')
103 return True
104
105 def onSync(self):
106 for channel in self.channels.list_valid():
107 self.msg('ChanServ', 'OP %s' % channel.name)
108
109 def stop(self):
110 if hasattr(self, 'auth'):
111 self.auth.stop()
112
113 if hasattr(self, 'channels'):
114 if self.initialized:
115 self.channels.force()
116
117 self.channels.stop()
118 self.channels.db_close()
119
120 if hasattr(self, 'options'):
121 if self.initialized:
122 self.options.force()
123
124 self.options.stop()
125 self.options.db_close()
126
127 if hasattr(self, 'limit_monitor'):
128 self.limit_monitor.stop()
129
130 def join(self, channel):
131 super(limitserv, self).join(channel)
132 if Acidictive.me and not Acidictive.me.isBursting():
133 self.msg('ChanServ', 'OP %s' % channel) # and the channel is not empty. For now, use /cs op
134
135 def msg(self, target, message):
136 if message != '':
137 Acidictive.privmsg(self.nick, target, format_ascii_irc(message))
138
139 def multimsg(self, target, count, intro, separator, pieces, outro = ''):
140 cur = 0
141
142 while cur < len(pieces):
143 self.msg(target, intro + separator.join(pieces[cur:cur + count]) + outro)
144 cur += count
145
146 def notice(self, target, message):
147 if message != '':
148 Acidictive.notice(self.nick, target, format_ascii_irc(message))
149
150 def onPrivmsg(self, source, target, message):
151 if inviteable.InviteablePseudoclient.onPrivmsg(self, source, target, message) and \
152 target == self.nick:
153 # if inviteable fell through, we don't have anything else to do
154 self.msg(source, 'Invalid message. Say help for a list of valid messages.')
155
156 def do_accept(self, nick, channel):
157 chan = Channel.findChannel(channel)
158 if chan.size() < self.options.get('required_users', int, 20):
159 self.auth.reject_not_enough_users(nick, channel)
160 else:
161 # super call
162 inviteable.InviteablePseudoclient.do_accept(self, nick, channel)
163
164 def onChanModes(self, prefix, channel, modes):
165 if not self.initialized:
166 return
167
168 if not modes == '-z':
169 return
170
171 if channel in self.channels:
172 self.channels.remove(channel)
173 self.elog.request('Channel @b%s@b was dropped. Deleting it.' % channel)
174
175 def onJoin(self, user, channel):
176 if self.channels.is_valid(channel) and channel not in self.limit_monitor:
177 self.limit_monitor.insert(channel)
178
179 def onPart(self, user, channel):
180 self.onJoin(None, channel)
181
182 def onKick(self, kicker, victim, channel, reason):
183 self.onJoin(None, channel)
184
185 def getCommands(self):
186 return self.commands_admin