2 # Copyright (c) 2008, Joerg Jaspert <joerg@debian.org>
10 import supybot
.log
as log
11 from supybot
.commands
import *
12 import supybot
.plugins
as plugins
13 import supybot
.ircmsgs
as ircmsgs
14 import supybot
.callbacks
as callbacks
15 import supybot
.schedule
as schedule
16 import supybot
.conf
as conf
18 class Dak(callbacks
.Plugin
):
19 """Little FTPMaster tools. Tells about dinstall times, warns if you have a lock set,
20 and lets people set/unset locks.
21 Possible commands are "lock", "unlock", "forceunlock", "locked", "setlastnew".
25 def __init__(self
, irc
):
26 self
.__parent
= super(Dak
, self
)
27 self
.__parent
.__init
__(irc
)
29 self
.fname
= "dinstallcheck"
30 self
.dinstallhour
= [1, 7, 13, 19]
31 self
.dinstallmin
= self
.registryValue('dinstallminute')
33 self
.warnframe
= [i
%60 for i
in range(self
.dinstallmin
-warntime
, self
.dinstallmin
+warntime
+1, 1)]
34 self
.dinstallframe
= [i
%60 for i
in range(self
.dinstallmin
, self
.dinstallmin
+5, 1)]
35 self
.channel
= self
.registryValue('channel')
39 (undef
, undef
, undef
, hour
, minute
, undef
, undef
, undef
, undef
) = time
.gmtime()
40 log
.debug("DAK: Regular dinstall time check")
41 if hour
in self
.dinstallhour
:
42 log
.debug("DAK: It is DINSTALL hour")
43 if minute
in self
.warnframe
:
44 log
.debug("DAK: In Dinstall Warnframe")
45 msgMaker
= ircmsgs
.privmsg
46 if minute
in self
.dinstallframe
:
47 log
.debug("DAK: In Dinstall timeframe")
48 # No longer time to warn only, now is time to act, if we haven't already
49 if self
.registryValue('dinstall') == True:
50 log
.debug("DAK: Already done once, dinstall flag is %s" %(self
.registryValue('dinstall')))
52 log
.debug("DAK: Not yet done, dinstall flag %s" % (self
.registryValue('dinstall')))
53 conf
.supybot
.plugins
.Dak
.get('dinstall').setValue(True)
54 conf
.supybot
.plugins
.Dak
.get('warned').setValue(True)
55 irc
.queueMsg(msgMaker(self
.channel
, "It is DINSTALL time"))
56 if len(self
.locks
) >= 1:
57 for key
in self
.locks
:
58 irc
.queueMsg(msgMaker(self
.channel
, "%s: DINSTALL time, stop working, unlocking %s" % (self
.locks
[key
], key
)))
61 else: # if minute in self.dinstallframe
62 # Not dinstall as far as we know, but we want to warn people if they have locks, dinstall is soon.
63 # We only want to warn once about locks people have, or we would do it every 30 seconds, which wouldnt be nice.
64 # Also, with warnframe larger than dinstallframe, this might warn in case the bot somehow misses dinstallframe.
65 # Like if it comes up late, or so. Or?
66 log
.debug("DAK: Not in Dinstall timeframe")
67 if self
.registryValue('warned') == True:
68 log
.debug("DAK: We already warned once, warn flag %s" % (self
.registryValue('warned')))
70 log
.debug("DAK: Not yet warned about upcoming Dinstall run, flag is %s." % (self
.registryValue('warned')))
72 if len(self
.locks
) >= 1:
73 conf
.supybot
.plugins
.Dak
.get('warned').setValue(True)
74 for key
in self
.locks
:
75 log
.debug("DAK: Warning %s, has %s locked." % (self
.locks
[key
], key
))
76 irc
.queueMsg(msgMaker(self
.channel
, "%s: DINSTALL soon, hurry up" % (self
.locks
[key
]) ))
78 irc
.queueMsg(msgMaker(self
.channel
, "%s: ALL locked. If you want to keep that, remember turning off cron" % (self
.locks
[key
]) ))
79 else: # if minute in self.warnframe
80 # Outside our warnframe.
81 log
.debug("DAK: Not in warnframe")
82 conf
.supybot
.plugins
.Dak
.get('dinstall').setValue(False)
83 conf
.supybot
.plugins
.Dak
.get('warned').setValue(False)
85 else: # if hour in self.dinstallhour
86 # We are far outside a dinstall start
87 log
.debug("DAK: Not even dinstall hour")
88 conf
.supybot
.plugins
.Dak
.get('dinstall').setValue(False)
89 conf
.supybot
.plugins
.Dak
.get('warned').setValue(False)
92 log
.info("DAK: Setting periodic scheduler for checktime")
94 schedule
.removePeriodicEvent(self
.fname
)
97 schedule
.addPeriodicEvent(checktime
, 30, self
.fname
, now
=False)
98 schedule
.addEvent(checktime
, time
.time()+1)
99 log
.info("DAK: Plugin loaded")
103 log
.info("DAK: We should die, removing periodic scheduler")
104 schedule
.removePeriodicEvent(self
.fname
)
109 def dinstall(self
, irc
, msg
, args
):
110 """takes no arguments
112 Returns the time until next dinstall
115 def deltatime(start
, stop
):
116 def toSeconds(timeString
):
117 hour
, min, sec
= map(int, timeString
.split(':'))
118 return (hour
* 60 + min) * 60 + sec
119 d_time_min
, d_time_sec
= divmod(toSeconds(stop
) - toSeconds(start
), 60)
120 d_time_hr
, d_time_min
= divmod(d_time_min
, 60)
121 return '%dhr %dmin %ssec' % (d_time_hr
% 24, d_time_min
, d_time_sec
)
123 (year
, month
, day
, hour
, minute
, second
, undef
, undef
, undef
) = time
.gmtime()
125 log
.debug("The latest run is at %s:%s" % (self
.dinstallhour
[-1], self
.dinstallmin
))
126 log
.debug("I think we now have %s:%s" % (hour
, minute
))
129 if minute
>= self
.dinstallmin
and newhour
in self
.dinstallhour
:
130 # If we already passed dinstallminute, we are running and want the next runtime.
131 log
.debug("We are past this hours dinstall already")
134 if newhour
> self
.dinstallhour
[-1]:
135 log
.debug("We are also past the last dinstall run for today")
136 # We are past the last dinstall today, so next one must be the first tomorrow, start searching at midnight
137 newhour
= self
.dinstallhour
[0]
139 while newhour
not in self
.dinstallhour
:
141 log
.debug("Looking at possible hour %s" % (newhour
))
145 log
.debug("I found that next dinstall will be at %s:%s" % (newhour
, self
.dinstallmin
))
147 start
="%s:%s:%s" % (hour
, minute
, second
)
148 stop
="%s:%s:00" % (newhour
, 52)
149 difference
=deltatime(start
, stop
)
150 irc
.reply("I guess the next dinstall will be in %s" % (difference
))
151 dinstall
= wrap(dinstall
)
153 def locked(self
, irc
, msg
, args
):
154 """takes no arguments
156 Returns the currently set locks
159 if len(self
.locks
) == 0:
160 irc
.reply("Nothing locked")
162 text
="Current self.locks: "
163 for key
in self
.locks
:
164 text
+= "[%s, by %s] " % (key
, self
.locks
[key
])
166 locked
= wrap(locked
)
168 def dakinfo(self
, irc
, msg
, what
):
169 """takes no arguments
171 Returns a little info about this plugins status"""
174 text
.append("Dak plugin for the FTPMaster channel %s." % (self
.channel
))
175 text
.append("Dinstall hour: %s, minute: %s" % (self
.dinstallhour
, self
.dinstallmin
))
176 if len(self
.locks
) > 1:
177 text
.append("Current locks: %d (%s)" % (len(self
.locks
), self
.locks
))
178 text
.append("Warnframe: %s" % (self
.warnframe
))
179 text
.append("Dinstallframe: %s" % (self
.dinstallframe
))
180 text
.append("Dinstall flag: %s, Warnflag: %s" % (conf
.supybot
.plugins
.Dak
.get('dinstall'), conf
.supybot
.plugins
.Dak
.get('warned')))
183 dakinfo
= wrap(dakinfo
)
185 def lock(self
, irc
, msg
, args
, what
):
190 if self
.locks
.has_key("ALL"):
191 irc
.error("No, %s has an ALL lock" % (self
.locks
["ALL"]))
193 if what
== "ALL" and len(self
.locks
) > 0:
194 irc
.error("Can't lock all, there are existing locks")
196 if self
.locks
.has_key(what
):
197 if self
.locks
[what
] == msg
.nick
:
198 irc
.reply("Loser, you already locked %s" % (what
) )
200 irc
.reply("You suck, this is already locked by %s" % (self
.locks
[what
]) )
202 self
.locks
[what
]=msg
.nick
203 irc
.reply("locked %s" % (what
) )
204 lock
= wrap(lock
, ['text'])
206 def unlock(self
, irc
, msg
, args
, what
):
209 Unlocks [lock] or everything locked from you.
211 if len(self
.locks
) == 0:
212 irc
.reply("Nothing locked")
215 unlocked
="unlocked: "
216 if self
.locks
.has_key(what
):
217 if self
.locks
[what
] == msg
.nick
:
218 del(self
.locks
[what
])
219 irc
.reply("unlocked %s" % (what
) )
221 irc
.reply("%s is locked by %s, not by you. Not unlocked." % (what
, self
.locks
[what
]) )
224 for key
in self
.locks
:
225 if self
.locks
[key
] == msg
.nick
:
229 unlocked
+= ", ".join(keys
)
231 unlock
= wrap(unlock
, [optional('text')])
233 def forceunlock(self
, irc
, msg
, args
, what
):
236 Force-Unlocks [lock] or everything locked from you.
238 if len(self
.locks
) == 0:
239 irc
.reply("Nothing locked")
242 if self
.locks
.has_key(what
):
243 msgMaker
= ircmsgs
.privmsg
244 irc
.queueMsg(msgMaker(self
.channel
, "%s: Careful, %s just forceunlocked %s from you!" % (self
.locks
[what
], msg
.nick
, what
)))
245 del(self
.locks
[what
])
246 irc
.reply("unlocked %s" % (what
))
247 forceunlock
= wrap(forceunlock
, ['text'])
249 def setlastnew(self
, irc
, msg
, args
):
252 setlastnew takes no parameter"""
254 re_topic
= re
.compile(r
"(.*)\s+\|\| last NEW ended:\s+\w{3} \d\d \d\d:\d\d UTC \d{4}(?:\s+\|\|\s+(.*))?")
255 topic
= irc
.state
.channels
[self
.channel
].topic
256 m
= re_topic
.match(topic
)
259 newtopic
= "%s || %s" % (m
.group(1),
260 time
.strftime("last NEW ended: %b %d %H:%M UTC %Y", time
.gmtime()))
262 newtopic
+= " || %s" % (m
.group(2))
264 # Woot, looks we never had this part in the topic yet
265 newtopic
= "%s || %s" % (topic
,
266 time
.strftime("last NEW ended: %b %d %H:%M UTC %Y", time
.gmtime()))
267 irc
.queueMsg(ircmsgs
.topic(self
.channel
, newtopic
))
268 irc
.reply("Ok master")
270 setlastnew
= wrap(setlastnew
)
274 # vim:set shiftwidth=4 tabstop=4 expandtab textwidth=79: