| 1 |
|
|---|
| 2 |
|
|---|
| 3 |
|
|---|
| 4 |
|
|---|
| 5 |
""" |
|---|
| 6 |
Maintainer: Jp Calderone |
|---|
| 7 |
""" |
|---|
| 8 |
|
|---|
| 9 |
from twisted.news import nntp |
|---|
| 10 |
from twisted.internet import protocol, reactor |
|---|
| 11 |
|
|---|
| 12 |
import time |
|---|
| 13 |
|
|---|
| 14 |
class NNTPFactory(protocol.ServerFactory): |
|---|
| 15 |
"""A factory for NNTP server protocols.""" |
|---|
| 16 |
|
|---|
| 17 |
protocol = nntp.NNTPServer |
|---|
| 18 |
|
|---|
| 19 |
def __init__(self, backend): |
|---|
| 20 |
self.backend = backend |
|---|
| 21 |
|
|---|
| 22 |
def buildProtocol(self, connection): |
|---|
| 23 |
p = self.protocol() |
|---|
| 24 |
p.factory = self |
|---|
| 25 |
return p |
|---|
| 26 |
|
|---|
| 27 |
|
|---|
| 28 |
class UsenetClientFactory(protocol.ClientFactory): |
|---|
| 29 |
def __init__(self, groups, storage): |
|---|
| 30 |
self.lastChecks = {} |
|---|
| 31 |
self.groups = groups |
|---|
| 32 |
self.storage = storage |
|---|
| 33 |
|
|---|
| 34 |
|
|---|
| 35 |
def clientConnectionLost(self, connector, reason): |
|---|
| 36 |
pass |
|---|
| 37 |
|
|---|
| 38 |
|
|---|
| 39 |
def clientConnectionFailed(self, connector, reason): |
|---|
| 40 |
print 'Connection failed: ', reason |
|---|
| 41 |
|
|---|
| 42 |
|
|---|
| 43 |
def updateChecks(self, addr): |
|---|
| 44 |
self.lastChecks[addr] = time.mktime(time.gmtime()) |
|---|
| 45 |
|
|---|
| 46 |
|
|---|
| 47 |
def buildProtocol(self, addr): |
|---|
| 48 |
last = self.lastChecks.setdefault(addr, time.mktime(time.gmtime()) - (60 * 60 * 24 * 7)) |
|---|
| 49 |
p = nntp.UsenetClientProtocol(self.groups, last, self.storage) |
|---|
| 50 |
p.factory = self |
|---|
| 51 |
return p |
|---|
| 52 |
|
|---|
| 53 |
|
|---|
| 54 |
|
|---|
| 55 |
class UsenetServerFactory(NNTPFactory): |
|---|
| 56 |
"""A factory for NNTP Usenet server protocols.""" |
|---|
| 57 |
|
|---|
| 58 |
protocol = nntp.NNTPServer |
|---|
| 59 |
|
|---|
| 60 |
def __init__(self, backend, remoteHosts = None, updatePeriod = 60): |
|---|
| 61 |
NNTPFactory.__init__(self, backend) |
|---|
| 62 |
self.updatePeriod = updatePeriod |
|---|
| 63 |
self.remoteHosts = remoteHosts or [] |
|---|
| 64 |
self.clientFactory = UsenetClientFactory(self.remoteHosts, self.backend) |
|---|
| 65 |
|
|---|
| 66 |
|
|---|
| 67 |
def startFactory(self): |
|---|
| 68 |
self._updateCall = reactor.callLater(0, self.syncWithRemotes) |
|---|
| 69 |
|
|---|
| 70 |
|
|---|
| 71 |
def stopFactory(self): |
|---|
| 72 |
if self._updateCall: |
|---|
| 73 |
self._updateCall.cancel() |
|---|
| 74 |
self._updateCall = None |
|---|
| 75 |
|
|---|
| 76 |
|
|---|
| 77 |
def buildProtocol(self, connection): |
|---|
| 78 |
p = self.protocol() |
|---|
| 79 |
p.factory = self |
|---|
| 80 |
return p |
|---|
| 81 |
|
|---|
| 82 |
|
|---|
| 83 |
def syncWithRemotes(self): |
|---|
| 84 |
for remote in self.remoteHosts: |
|---|
| 85 |
reactor.connectTCP(remote, 119, self.clientFactory) |
|---|
| 86 |
self._updateCall = reactor.callLater(self.updatePeriod, self.syncWithRemotes) |
|---|
| 87 |
|
|---|
| 88 |
|
|---|
| 89 |
|
|---|
| 90 |
Factory = UsenetServerFactory |
|---|