chiark / gitweb /
the products of larks twisted imagination
[irc.git] / acrobat-chiark-0.2.py
index a8b6cc8421ff93e2c5c1565c0609b49b39a3352b..bcc25dcd664b7ec8f86649befca594bfab786212 100755 (executable)
@@ -33,7 +33,7 @@
               back with the url.
 """
 
-import string, urllib, sys, cPickle, os, random
+import string, urllib, sys, cPickle, os, random, re, time
 from ircbot import SingleServerIRCBot
 from irclib import nm_to_n, irc_lower
 
@@ -49,6 +49,16 @@ class Acrobat(SingleServerIRCBot):
                                     [(server, port)], nickname, nickname)
         self.channel = channel
         self.owner = owner
+        self.quotatime = time.time()
+        #List of known !commands we respond to
+        self.known =['karma','trout','info','die','quiet','list','google','say','do','reload','flirt']
+        #Configurable stuff - how often do we add how many fish?
+        self.cur_fish=5
+        self.max_fish=5       #Maximum of 5 fish
+        self.fish_time_inc=60  #Add fish with 20s granularity
+        self.fish_inc=2        #Rate of increase is 2 fish per 60s
+        self.DoS=0             #Have we been told to shut up?
+        self.Boring_Git='Nobody' #Who told us to shut up?
         # load the karma db
         try:
             f = open("karmadump", "r")
@@ -62,6 +72,12 @@ class Acrobat(SingleServerIRCBot):
             f.close()
         except IOError:
             self.trouts = [ "hits %s with a wet trout.", "thwaps %s.", "questions %s's parentage.", "pokes its tounge out at %s.", "bites its thumb at %s."]
+        try:
+            f = open("flirts", "r")
+            self.flirts = [l.strip() for l in f.readlines() if l.find("%s") != -1]
+            f.close()
+        except IOError:
+            self.flirts = [ "falls madly in love with %s", "blows kisses at %s"]
 
     ## EVENT HANDLERS
             
@@ -78,15 +94,15 @@ class Acrobat(SingleServerIRCBot):
            and (irc_lower(a[0]) == irc_lower(self.connection.get_nickname())
                 or irc_lower(a[0])[:-1] == irc_lower(self.connection.get_nickname())):
 
-            self.do_command(self.channel, string.strip(a[1]), public = 1)
+            self.do_command(nm_to_n(evt.source()), string.strip(a[1]), public = 1)
         if a[0].endswith("++"):
             self.karmaup(a[0])
         if a[0].endswith("--"):
             self.karmadown(a[0])
         if payload[0] == "!" and len(payload)>1:
-            self.do_command(self.channel, string.strip(payload[1:]), public=1)
+            self.do_command(nm_to_n(evt.source()), string.strip(payload[1:]), public=1)
         if payload[0] == "~" and len(payload)>1:
-            self.do_command(self.channel, string.strip(payload[1:]), public=1)
+            self.do_command(nm_to_n(evt.source()), string.strip(payload[1:]), public=1)
 
     # And now bot commands;
 
@@ -134,21 +150,62 @@ class Acrobat(SingleServerIRCBot):
                             len(self.karma.dict.keys()))
     # query bot status
     def infoq(self, cmd, nick, conn, public):
+        # version control magic
+        acrorevision="$Revision$"
+        acrorev1=re.sub(r'\$Revision: (.*)',r'\1',acrorevision)
+        acroversion=re.sub(r'(.*) \$',r'\1',acrorev1)
         if public == 1:
             conn.privmsg(self.channel,
-                         "I am Acrobat 0.2.1chiark, on %s, as nick %s." %
-                         (self.channel, self.connection.get_nickname()))
+                         "I am Acrobat %s, on %s, as nick %s." %
+                         (acroversion, self.channel, self.connection.get_nickname()))
             conn.privmsg(self.channel,
                          "My owner is %s; I have karma on %s items." %
                          (self.owner, len(self.karma.dict.keys())))
         else:
-            conn.notice(nick, "I am Acrobat 0.2.1chiark, on %s, as nick %s." %
-                        (self.channel, self.connection.get_nickname()))
+            conn.notice(nick, "I am Acrobat %s, on %s, as nick %s." %
+                        (acroversion, self.channel, self.connection.get_nickname()))
             conn.notice(nick, "My owner is %s; I have karma on %s items." %
                         (self.owner, len(self.karma.dict.keys())))
 
+    # list know commands
+    def listq(self, cmd, nick, conn, public):
+        conn.notice(nick, "%s" % string.join(self.known))
+    # flirt with someone
+    def flirtq(self, cmd, nick, conn, public):
+        self.fish_quota()
+        if self.DoS == 1:
+            conn.notice(nick, "Sorry, but %s made me take Holy Orders." %
+                        self.Boring_Git)
+            return
+        if self.cur_fish <= 0:
+            conn.notice(nick, "My libido is over-used!")
+        else:
+            self.cur_fish -=1
+            try:
+                target = string.join(cmd.split()[1:])
+                me = self.connection.get_nickname()
+                trout_msg = random.choice(self.flirts)
+                # ...and touchy.
+                if me.lower() == target.lower():
+                    target = nick
+                if public == 0:
+                    if random.random() <= 0.1:
+                        trout_msg+= ' (but %s is their secret admirer)' % nick
+                conn.action(self.channel, trout_msg % target)
+            except IndexError:
+                conn.notice(nick, "Who do you wish me to flirt with?")
+    
     # trout someone
     def troutq(self, cmd, nick, conn, public):
+        self.fish_quota()
+        if self.DoS == 1:
+            conn.notice(nick, "Sorry, but %s is being a spoilsport." %
+                        self.Boring_Git)
+            return
+        if self.cur_fish <= 0:
+            conn.notice(nick, "Fish stocks exhausted.")
+        else:
+            self.cur_fish -=1
             try:
                 target = string.join(cmd.split()[1:])
                 me = self.connection.get_nickname()
@@ -159,10 +216,10 @@ class Acrobat(SingleServerIRCBot):
                 # ...and touchy.
                 if me.lower() == target.lower():
                     target = nick
-                conn.action(self.channel, trout_msg % target)
                 if public == 0:
                     if random.random() <= 0.1:
-                        conn.action(self.channel, "notes %s is conducting a whispering campaign" % nick)
+                        trout_msg+= ' (at the instigation of %s)' % nick
+                conn.action(self.channel, trout_msg % target)
             except IndexError:
                 conn.notice(nick, "Who do you wish me to trout?")
 
@@ -170,16 +227,41 @@ class Acrobat(SingleServerIRCBot):
     def reloadq(self, cmd, nick, conn, public):
         if irc_lower(nick) == irc_lower(self.owner):
             tback = self.trouts
+            fback = self.flirts
             try:
                 f = open("trouts", "r")
                 self.trouts = [l.strip() for l in f.readlines() if l.find("%s") != -1]
                 f.close()
+                f = open("flirts", "r")
+                self.flirts = [l.strip() for l in f.readlines() if l.find("%s") != -1]
                 conn.notice(nick, "I am re-armed!")
             except IOError:
                 conn.notice(nick, "Trout re-arming failed!")
                 self.trouts = tback
+                self.flirts = fback
         else:
             conn.notice(nick, "This command can only be invoked by my owner.")
+    # Shut up trouting for a minute
+    def nofish(self, cmd, nick, conn, public):
+        self.cur_fish=0
+        self.DoS=1
+        self.Boring_Git=nick
+        self.quotatime=time.time()
+        self.quotatime+=60 #60 seconds of no fishing
+        conn.notice(nick, "Fish stocks depleted, as you wish.")
+    # Check on fish stocks
+    def fish_quota(self):
+        if self.DoS==1:
+            if time.time()>=self.quotatime:
+                self.DoS=0
+            else:
+                return
+        if self.DoS==0:
+            if (time.time()-self.quotatime)>self.fish_time_inc:
+                self.cur_fish+=(((time.time()-self.quotatime)/self.fish_time_inc)*self.fish_inc)
+                if self.cur_fish>self.max_fish:
+                    self.cur_fish=self.max_fish
+                self.quotatime=time.time()
 
     # quit irc
     def quit(self, cmd, nick, conn, public):
@@ -206,17 +288,17 @@ class Acrobat(SingleServerIRCBot):
                 if public == 0:
                     conn.notice(nick, str(gsearch))
                 else: # we haven't found anything.
-                    conn.privmsg(nick, str(gsearch))
+                    conn.privmsg(self.channel, str(gsearch))
             else:
                 if public == 0:
                     conn.notice(nick, "No pages found.")
                 else:
-                    conn.privmsg(nick, "No pages found.")
+                    conn.privmsg(self.channel, "No pages found.")
         except IOError: # if the connection times out. This blocks. :(
             if public == 0:
                 conn,notice(nick, "The web's broken. Waah!")
             else:
-                conn.privmsg(nick, "The web's broken. Waah!")
+                conn.privmsg(self.channel, "The web's broken. Waah!")
                 
     # General query handler
     def do_command(self, nick, cmd, public=0):
@@ -237,16 +319,26 @@ class Acrobat(SingleServerIRCBot):
         if cmd == "info":
             self.infoq(cmd, nick, conn, public)
 
+        # Known commands
+        if cmd == "list":
+            self.listq(cmd, nick, conn, public)
         # weaponry
         if cmd.split()[0] == "trout":
             self.troutq(cmd, nick, conn, public)
+        if cmd.split()[0] == "flirt":
+            self.flirtq(cmd, nick, conn, public)
         if cmd == "reload":
             self.reloadq(cmd, nick, conn, public)
-        
-        #disconnect
-        if cmd == "disconnect": # hop off for 60s
-            self.disconnect(msg="Be right back.")
 
+#Disconnect disabled 'cos people hated it    
+#        #disconnect
+#        if cmd == "disconnect": # hop off for 60s
+#            self.disconnect(msg="Be right back.")
+
+        # No more trout
+        if cmd.split()[0] == "quiet":
+            self.nofish(cmd,nick,conn, public)
+        
         # say to msg/channel
         elif cmd.split()[0] == "say" \
              and irc_lower(nick) == irc_lower(self.owner):