616fc2df5b3b7ad21b8c9761919dc47525db470f
[quix0rs-apt-p2p.git] / apt_dht / HTTPServer.py
1
2 from twisted.python import log
3 from twisted.internet import defer
4 from twisted.web2 import server, http, resource, channel
5 from twisted.web2 import static, http_headers, responsecode
6
7 class FileDownloader(static.File):
8     
9     def __init__(self, path, manager, defaultType="text/plain", ignoredExts=(), processors=None, indexNames=None):
10         self.manager = manager
11         super(FileDownloader, self).__init__(path, defaultType, ignoredExts, processors, indexNames)
12         
13     def renderHTTP(self, req):
14         log.msg('Got request for %s from %s' % (req.uri, req.remoteAddr))
15         resp = super(FileDownloader, self).renderHTTP(req)
16         if isinstance(resp, defer.Deferred):
17             resp.addCallback(self._renderHTTP_done, req)
18         else:
19             resp = self._renderHTTP_done(resp, req)
20         return resp
21         
22     def _renderHTTP_done(self, resp, req):
23         log.msg('Initial response to %s: %r' % (req.uri, resp))
24         
25         if self.manager:
26             path = 'http:/' + req.uri
27             if resp.code >= 200 and resp.code < 400:
28                 return self.manager.check_freshness(req, path, resp.headers.getHeader('Last-Modified'), resp)
29             
30             log.msg('Not found, trying other methods for %s' % req.uri)
31             return self.manager.get_resp(req, path)
32         
33         return resp
34
35     def createSimilarFile(self, path):
36         return self.__class__(path, self.manager, self.defaultType, self.ignoredExts,
37                               self.processors, self.indexNames[:])
38         
39         
40 class TopLevel(resource.Resource):
41     addSlash = True
42     
43     def __init__(self, directory, manager):
44         self.directory = directory
45         self.manager = manager
46         self.subdirs = {}
47
48     def setDirectories(self, dirs):
49         self.subdirs = {}
50         for k in dirs:
51             # Don't allow empty subdirectory
52             if k:
53                 self.subdirs[k] = dirs[k]
54         log.msg('new subdirectories initialized')
55     
56     def render(self, ctx):
57         return http.Response(
58             200,
59             {'content-type': http_headers.MimeType('text', 'html')},
60             """<html><body>
61             <h2>Statistics</h2>
62             <p>TODO: eventually some stats will be shown here.</body></html>""")
63
64     def locateChild(self, request, segments):
65         name = segments[0]
66         if name in self.subdirs:
67             log.msg('Sharing %s with %s' % (request.uri, request.remoteAddr))
68             return static.File(self.subdirs[name].path), segments[1:]
69         
70         if request.remoteAddr.host != "127.0.0.1":
71             log.msg('Blocked illegal access to %s from %s' % (request.uri, request.remoteAddr))
72             return None, ()
73             
74         if len(name) > 1:
75             return FileDownloader(self.directory.path, self.manager), segments[0:]
76         else:
77             return self, ()
78         
79 if __name__ == '__builtin__':
80     # Running from twistd -y
81     t = TopLevel('/home', None)
82     t.addDirectory('/tmp')
83     t.addDirectory('/var/log')
84     site = server.Site(t)
85     
86     # Standard twisted application Boilerplate
87     from twisted.application import service, strports
88     application = service.Application("demoserver")
89     s = strports.service('tcp:18080', channel.HTTPFactory(site))
90     s.setServiceParent(application)