source: svnbot/trunk/svnbot.py

Last change on this file was 18, checked in by simon, 18 years ago

Add license blurb.

File size: 6.3 KB
Line 
1# -*- coding: utf-8 -*-
2
3# Copyright © 2005, Simon E. Ward
4#
5# This file is part of SvnBot.
6#
7# SvnBot is free software; you can redistribute it and/or modify it
8# under the terms of version 2 of the GNU General Public License as
9# published by the Free Software Foundation.
10#
11# SvnBot is distributed in the hope that it will be useful, but
12# WITHOUT ANY WARRANTY; without even the implied warranty of
13# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14# General Public License for more details.
15#
16# You should have received a copy of the GNU General Public License
17# along with SvnBot; if not, write to the Free Software Foundation,
18# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
19
20import sys
21from twisted.application import service, internet
22from twisted.words.protocols import irc
23from twisted.internet import protocol
24from twisted.python import log
25from twisted.web import server, xmlrpc
26
27
28class SvnBotXmlrpc(xmlrpc.XMLRPC):
29
30    def __init__(self, bot, channel, tracurl=None):
31        self.bot = bot
32        self.channel = channel
33        self.tracurl = tracurl
34        xmlrpc.XMLRPC.__init__(self)
35
36    def xmlrpc_say(self, msg):
37        self.bot.say(self.channel, msg)
38        return 0
39
40    def xmlrpc_showCommitSummary(self, rev, author):
41        self.bot.say(self.channel,
42                "Revision %s committed by %s: %s" % (
43                    rev, author, self.tracurl+'changeset/'+rev))
44        return 0
45
46
47class SvnBot(irc.IRCClient):
48    """A bot that retrieves subversion repository metadata."""
49    xmlrpcService = None
50    pingerService = None
51
52    def __init__(self):
53        self.nickname = "svnbot"
54        self.realname = "Subversion Bot"
55
56    #def sendLine(self, line):
57    #    irc.IRCClient.sendLine(self, line)
58
59    #def join(self, channel, key=None):
60    #    irc.IRCClient.join(self, channel, key)
61
62    #def mode(self, chan, set, modes, limit = None, user = None, mask = None):
63    #    irc.IRCClient.mode(self, chan, set, modes, limit, user, mask)
64
65    #def say(self, channel, message, length = None):
66    #    irc.IRCClient.say(self, channel, message, length)
67
68    #def ping(self, user, text=None):
69    #    irc.IRCClient.ping(self, user, text)
70
71    #def pong(self, user, secs):
72    #    irc.IRCClient.pong(self, user, secs)
73
74    def connectionMade(self):
75        irc.IRCClient.connectionMade(self)
76        x = SvnBotXmlrpc(self, self.factory.channel,
77                tracurl=self.factory.tracurl)
78        if self.xmlrpcService is None:
79            self.xmlrpcService = internet.TCPServer(7080, server.Site(x),
80                    interface='localhost')
81            self.xmlrpcService.setServiceParent(serviceCollection)
82        else:
83            self.xmlrpcService.startService()
84        #if self.pingerService is None:
85        #    self.pingerService = internet.TimerService(120,
86        #            self.ping, self.nickname, text=None)
87        #    self.pingerService.setServiceParent(serviceCollection)
88        #else:
89        #    self.pingerService.startService()
90
91    def connectionLost(self, reason):
92        irc.IRCClient.connectionLost(self, reason)
93        self.xmlrpcService.stopService()
94        #self.pingerService.stopService()
95
96    def signedOn(self):
97        """Called when bot has succesfully signed on to server."""
98        irc.IRCClient.signedOn(self)
99        self.mode(self.nickname, 1, 'B')
100        self.join(self.factory.channel)
101
102    #def lineReceived(self, line):
103    #    irc.IRCClient.dataReceived(self, line)
104
105    #def joined(self, channel):
106    #    irc.IRCClient.joined(self, channel)
107
108    #def left(self, channel):
109    #    irc.IRCClient.left(self, channel)
110
111    #def irc_PING(self, prefix, params):
112    #    irc.IRCClient.irc_PING(self, prefix, params)
113
114    #def irc_unknown(self, prefix, command, params):
115    #    irc.IRCClient.irc_unknown(self, prefix, command, params)
116
117
118class SvnBotFactory(protocol.ReconnectingClientFactory):
119    """A factory for SvnBots.
120
121    A new protocol instance will be created each time we connect to the server.
122    """
123
124    # The class of the protocol to build when new connection is made
125    protocol = SvnBot
126
127    def __init__(self, channel, tracurl=None):
128        self.channel = channel
129        self.tracurl = tracurl
130
131    #def clientConnectionFailed(self, connector, reason):
132    #    """Called when a connection has failed to connect."""
133    #    protocol.ReconnectingClientFactory.clientConnectionFailed(
134    #            self, connector, reason)
135
136    #def clientConnectionLost(self, connector, unused_reason):
137    #    protocol.ReconnectingClientFactory.clientConnectionLost(
138    #            self, connector, unused_reason)
139
140    #def resetDelay(self):
141    #    """Call me after a successful connection to reset."""
142    #    protocol.ReconnectingClientFactory.resetDelay(self)
143
144    #def retry(self, connector=None):
145    #    """Have this connector connect again, after a suitable delay."""
146    #    protocol.ReconnectingClientFactory.retry(self, connector)
147
148    #def stopTrying(self):
149    #    """I put a stop to any attempt to reconnect in progress."""
150    #    protocol.ReconnectingClientFactory.stopTrying(self)
151
152    #def startedConnecting(self, connector):
153    #    """Called when a connection has been started."""
154    #    protocol.ReconnectingClientFactory.startedConnecting(self, connector)
155
156    def buildProtocol(self, addr):
157        """Create an instance of a subclass of Protocol."""
158        self.resetDelay()
159        return protocol.ReconnectingClientFactory.buildProtocol(self, addr)
160
161    #def doStart(self):
162    #    """Make sure startFactory is called."""
163    #    protocol.ReconnectingClientFactory.doStart(self)
164
165    #def doStop(self):
166    #    """Make sure stopFactory is called."""
167    #    protocol.ReconnectingClientFactory.doStop(self)
168
169    #def startFactory(self):
170    #    """This will be called before I begin listening on a Port or
171    #    Connector."""
172    #    protocol.ReconnectingClientFactory.startFactory(self)
173
174    #def stopFactory(self):
175    #    """This will be called before I stop listening on all
176    #    Ports/Connectors."""
177    #    protocol.ReconnectingClientFactory.stopFactory(self)
178
179
180application = service.Application('svnbot')
181serviceCollection = service.IServiceCollection(application)
182svnBot = SvnBotFactory(channel='#test')
183tcpClient = internet.TCPClient('irc.example.com', 6667, svnBot)
184tcpClient.setServiceParent(serviceCollection)
185
Note: See TracBrowser for help on using the repository browser.