summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAlexander Sulfrian <alexander@sulfrian.net>2015-12-04 02:19:11 +0100
committerAlexander Sulfrian <alexander@sulfrian.net>2015-12-04 02:21:41 +0100
commit9c21bd7be0380e8e0d62a2c54cfb97f37d5b131e (patch)
treeb69c04a019ef869786b08f5ce25444a1eeb2cf39
parent26889378aabfd6994ff30023c1c9de1c8620e592 (diff)
downloadupdate-topic-9c21bd7be0380e8e0d62a2c54cfb97f37d5b131e.tar.gz
update-topic-9c21bd7be0380e8e0d62a2c54cfb97f37d5b131e.tar.bz2
update-topic-9c21bd7be0380e8e0d62a2c54cfb97f37d5b131e.zip
Initial plugin to keep the spline topic up-to-date
-rw-r--r--update_topic.py124
1 files changed, 124 insertions, 0 deletions
diff --git a/update_topic.py b/update_topic.py
new file mode 100644
index 0000000..2a67aa2
--- /dev/null
+++ b/update_topic.py
@@ -0,0 +1,124 @@
+#!/usr/bin/env python
+"""
+update_topic.py - Keep topic in #spline up-to-date
+Copyright 2015, Alexander Sulfrian <alex@spline.inf.fu-berlin.de>
+Licensed under the Eiffel Forum License 2.
+
+http://inamidst.com/phenny/
+"""
+
+import asyncore
+import re
+import socket
+import threading
+from datetime import datetime, timedelta
+from dateutil.relativedelta import relativedelta
+from calendar import TUESDAY
+
+
+CHANNEL = '#spline'
+FROMAT = 'http://pad.spline.de/treffen%y%m%d'
+REGEX = re.compile(r'.*(http://pad\.spline\.de/treffen[0-9]{6}).*')
+
+
+def setup(phenny):
+ Scheduler(phenny)
+
+
+class Timer(object):
+ def __init__(self, sock):
+ self.sock = sock
+ self.start()
+
+ def start(self):
+ sleep = seconds_until(get_next_meeting() + timedelta(days=1))
+ self.timer = threading.Timer(sleep, self.run)
+ self.timer.start()
+
+ def run(self):
+ self.sock.send('.')
+ self.start()
+
+ def cancel(self):
+ self.timer.cancel()
+
+
+class Scheduler(asyncore.dispatcher):
+ def __init__(self, phenny):
+ self.phenny = phenny
+ self.phenny._orig_close = self.phenny.close
+ self.phenny.close = (lambda: self._phenny_close())
+
+ recv_timer, send_timer = socket.socketpair()
+ self.timer = Timer(send_timer)
+ asyncore.dispatcher.__init__(self, recv_timer)
+
+ def _phenny_close(self):
+ self.close()
+ self.phenny._orig_close()
+
+ def close(self):
+ self.timer.cancel()
+ asyncore.dispatcher.close()
+
+ def handle_read(self):
+ data = self.recv(8192)
+ if data:
+ self._exec()
+ else:
+ self.close()
+
+ def _exec(self):
+ # get topic, topic update is handled if a topic is received
+ self.phenny.write(['TOPIC'], CHANNEL)
+
+
+def seconds_until(when):
+ today = datetime.today().date()
+ return (when - today).total_seconds()
+
+
+def get_next_meeting():
+ today = datetime.today()
+ return (today + relativedelta(months=+1, day=1, weekday=TUESDAY)).date()
+
+
+def update_topic(phenny, channel, topic):
+ if channel != CHANNEL:
+ return
+
+ match = REGEX.match(topic)
+ if match is None:
+ return
+
+ new_topic = topic.replace(
+ match.groups()[0],
+ get_next_meeting().strftime(FROMAT),
+ 1)
+
+ if new_topic != topic:
+ print('Updating topic')
+ phenny.msg('ChanServ', 'TOPIC %s %s' % (channel, new_topic))
+
+
+def topic_change(phenny, input):
+ update_topic(phenny, input.sender, input)
+topic_change.event = 'TOPIC'
+topic_change.rule = r'.*'
+
+
+def topic_reply(phenny, input):
+ update_topic(phenny, input.args[1], input)
+topic_reply.event = '332'
+topic_reply.rule = r'.*'
+
+
+def request_topic(phenny, input):
+ parts = input.split(None, 1)
+ if len(parts) < 2:
+ phenny.notice(input.nick, 'Usage: %s #channel' % parts[0])
+ else:
+ phenny.write(['TOPIC'], parts[1])
+ phenny.notice(input.nick, 'Done.')
+request_topic.rule = r'^!(update|topic|update-topic)(?: +(.*))?$'
+request_topic.event = 'NOTICE'