#!/usr/nlocal/bin/python import sys import os, string, regex import posix, time, socket import BaseHTTPServer import NaviHTTP from EditServer import HTTPError class CVSRequestHandler(NaviHTTP.NaviRequestHandler): work = '/afs/w3.org/pub' cvsroot = '/afs/w3.org/CVS-Repository' def find_module(self, path): self.separator = '' r = self.work p = self.translate_path(path) if p[:len(r)] == r: p = p[len(r):] if p[:4] == '/WWW': # @# Hack! p = p[4:] self.separator = '/WWW' return os.path.dirname(p)[1:], os.path.basename(p), p else: raise HTTPError, (403, 'Cannot find module for: ' + path) def start_cvs(self, module, cmd, args): return os.popen('cd %s%s/%s; CVSROOT=%s cvs %s %s' % \ (self.work, self.separator, module, self.cvsroot, cmd, args)) def run_cvs(self, module, cmd, args): f = self.start_cvs(module, cmd, args) f.read() f.close() def cvs_status(self, module, file): f = self.start_cvs(module, 'status', file) d = f.read() f.close() re = regex.compile("""Status: +\([^\n]+\)""") if re.search(d) >= 0: return re.group(1) def put(self): (module, file, path) = self.find_module(self.path) s = self.cvs_status(module, file) print "@@Status:", s commitargs = "-m 'HTTP put from %s (%s)' %s" \ % (self.address_string(), self.client_address, file) if s == 'Locally Modified': raise HTTPError, (403, "Working copy newer than checked-in version") elif s == 'Unknown': if os.path.exists(path): raise HTTPError, (403, "Working copy is not checked in") self.saveContent(module, file) self.run_cvs(module, 'add', file) self.run_cvs(module, 'commit', commitargs) elif s == 'Up-to-date': try: self.saveContent(module, file) self.run_cvs(module, 'commit', commitargs) except: # Restore previous version try: posix.unlink(path) except: pass f = self.run_cvs(module, 'update', file) raise sys.exc_type, sys.exc_value else: raise HTTPError, (403, "Status: " + `s`) self.send_response(200) self.send_header("Content-Type", "text/html") self.end_headers() self.wfile.write("
done!\n") def saveContent(self, module, file): P = os.path l = self.content_length() path = P.join(P.join(self.work + self.separator, module), file) # print "@@", path, self.headers.headers try: sv = open(path, "w") sv.write(self.rfile.read(l)) sv.close() except IOError: raise HTTPError, (500, "Error writing file: " + `sys.exc_type` + `sys.exc_value`) def test(): import sys r = CVSRequestHandler('/afs/w3.org/www-name/WWW-connolly', '/afs/w3.org/pub/WWW') r.rfile = sys.stdin r.wfile = sys.stdout r.client_address = ('beach.w3.org', 4000) r.handle() def main(argv): Usage = 'edit-server [port]' if len(argv) == 2: port = string.atoi(argv[1]) else: port = 8000 + (posix.getuid() % 1000) while 1: try: server_address = ('', port) httpd = BaseHTTPServer.HTTPServer(server_address, CVSRequestHandler) break except socket.error: print "Port", port, "in use. Trying another..." port = port + 1 nowstr = time.asctime(time.localtime(time.time())) print "Serving HTTP on port %d at %s\n" % (port, nowstr) logfile = open(posix.environ['HOME'] +'/edit-server-log', "a+", 0) sys.stdout = sys.stderr = logfile print "Serving HTTP on port %d at %s\n" % (port, nowstr) httpd.serve_forever() if __name__ == '__main__': import sys main(sys.argv)