Skip to content
Browse files

Initial checking for Logbot

  • Loading branch information...
0 parents commit d00ddf5e1fe7c720a1e7754ba7a4011856bbdf18 @gmcquillan gmcquillan committed Oct 4, 2011
Showing with 195 additions and 0 deletions.
  1. 0 logbot/__init__.py
  2. +161 −0 logbot/logbot.py
  3. +34 −0 setup.py
0 logbot/__init__.py
No changes.
161 logbot/logbot.py
@@ -0,0 +1,161 @@
+#!/usr/bin/env python
+"""
+An example IRC log bot - logs a channel's events to a file.
+
+This was compiled from a couple of examples on the internet while
+Gavin was watching StarTrek: don't judge.
+
+If someone says the bot's name in the channel followed by a ':',
+e.g.
+
+ <foo> logbot: hello!
+
+the bot will reply:
+
+ <logbot> foo: I am a log bot
+
+Run this script with two arguments, the channel name the bot should
+connect to, and file to log to, e.g.:
+
+ $ python ircLogBot.py test test.log
+
+will log channel #test to the file 'test.log'.
+"""
+
+
+# twisted imports
+from twisted.words.protocols import irc
+from twisted.internet import reactor, protocol
+from twisted.python import log
+
+# system imports
+import time, sys
+
+
+class MessageLogger:
+ """
+ An independent logger class (because separation of application
+ and protocol logic is a good thing).
+ """
+ def __init__(self, file):
+ self.file = file
+
+ def log(self, message):
+ """Write a message to the file."""
+ timestamp = time.strftime("[%H:%M:%S]", time.localtime(time.time()))
+ self.file.write('%s %s\n' % (timestamp, message))
+ self.file.flush()
+
+ def close(self):
+ self.file.close()
+
+
+class LogBot(irc.IRCClient):
+ """A logging IRC bot."""
+
+ nickname = "logbot"
+
+ def connectionMade(self):
+ irc.IRCClient.connectionMade(self)
+ self.logger = MessageLogger(open(self.factory.filename, "a"))
+ self.logger.log("[connected at %s]" %
+ time.asctime(time.localtime(time.time())))
+
+ def connectionLost(self, reason):
+ irc.IRCClient.connectionLost(self, reason)
+ self.logger.log("[disconnected at %s]" %
+ time.asctime(time.localtime(time.time())))
+ self.logger.close()
+
+
+ # callbacks for events
+
+ def signedOn(self):
+ """Called when bot has succesfully signed on to server."""
+ self.join(self.factory.channel)
+
+ def joined(self, channel):
+ """This will get called when the bot joins the channel."""
+ self.logger.log("[I have joined %s]" % channel)
+
+ def privmsg(self, user, channel, msg):
+ """This will get called when the bot receives a message."""
+ user = user.split('!', 1)[0]
+ self.logger.log("<%s> %s" % (user, msg))
+
+ # Check to see if they're sending me a private message
+ if channel == self.nickname:
+ msg = "It isn't nice to whisper! Play nice with the group."
+ self.msg(user, msg)
+ return
+
+ # Otherwise check to see if it is a message directed at me
+ if msg.startswith(self.nickname + ":"):
+ msg = "%s: view logs at https://logs.urbanairship.com/" % user
+ self.msg(channel, msg)
+ self.logger.log("<%s> %s" % (self.nickname, msg))
+
+ def action(self, user, channel, msg):
+ """This will get called when the bot sees someone do an action."""
+ user = user.split('!', 1)[0]
+ self.logger.log("* %s %s" % (user, msg))
+
+ # irc callbacks
+
+ def irc_NICK(self, prefix, params):
+ """Called when an IRC user changes their nickname."""
+ old_nick = prefix.split('!')[0]
+ new_nick = params[0]
+ self.logger.log("%s is now known as %s" % (old_nick, new_nick))
+
+
+ # For fun, override the method that determines how a nickname is changed on
+ # collisions. The default method appends an underscore.
+ def alterCollidedNick(self, nickname):
+ """
+ Generate an altered version of a nickname that caused a collision in an
+ effort to create an unused related name for subsequent registration.
+ """
+ return nickname + '^'
+
+
+
+class LogBotFactory(protocol.ClientFactory):
+ """A factory for LogBots.
+
+ A new protocol instance will be created each time we connect to the server.
+ """
+
+ # the class of the protocol to build when new connection is made
+ protocol = LogBot
+
+ def __init__(self, channel):
+ self.channel = channel
+ self.filename = "logs/%s.log" % (channel,)
+
+ def clientConnectionLost(self, connector, reason):
+ """If we get disconnected, reconnect to server."""
+ connector.connect()
+
+ def clientConnectionFailed(self, connector, reason):
+ print "connection failed:", reason
+ reactor.stop()
+
+
+def main():
+ # initialize logging
+ log.startLogging(sys.stdout)
+
+ # create factory protocol and application
+ #f = LogBotFactory(sys.argv[1], sys.argv[2])
+ # TODO: pass a list of challens directly into one (and only one) factory.
+ channels = sys.argv[1].split()
+ logbots = []
+ for chan in channels:
+ logbots.append(LogBotFactory(chan))
+
+ # connect factory to this host and port
+ [reactor.connectTCP("localhost", 6667, f) for f in logbots]
+
+ # run bot
+ reactor.run()
34 setup.py
@@ -0,0 +1,34 @@
+try:
+ from setuptools import setup, find_packages
+except ImportError:
+ from distutils.core import setup, find_packages
+
+setup(name="Logbot",
+ version="dev",
+ packages=find_packages(),
+ namespace_packages=['logbot'],
+ include_package_data=True,
+ author='Gavin McQuillan',
+ author_email='gavin.mcquillan@gmail.com',
+ description='Prototype Twisted Logbot',
+ long_description='',
+ zip_safe=False,
+ platforms='any',
+ license='MIT',
+ url='https://github.com/urbanairship/logbot',
+ classifiers=[
+ 'Development Status :: 1 - Planning',
+ 'Environment :: Console',
+ 'Intended Audience :: Education',
+ 'License :: OSI Approved :: BSD License',
+ 'Programming Language :: Python :: 2.7',
+ 'Operating System :: Unix',
+ ],
+
+ entry_points={
+ 'console_scripts': [
+ 'logbot=logot.logbot:main',
+ ],
+ },
+ )
+

0 comments on commit d00ddf5

Please sign in to comment.
Something went wrong with that request. Please try again.