class Handler(BaseHTTPServer.BaseHTTPRequestHandler): server_version = _SERVER_VERSION _IO_BUFFER_SIZE = 8192 _STYLE = u""" body { background-color: #ffffff; color: #000000; font-family: sans-serif; } h1 { background-color: #f9f300; width: 100%; } td { border-width: 0; } tr { border-width: 0; } th { background-color: #dddddd; border-width: 0; } .ok { background-color: #ddffdd; } .error { background-color: #ffdddd; } """ _FOOTER = u"<hr><a href=\"http://roskakori.github.com/cutplace/\">cutplace</a> %s" % version.VERSION_NUMBER _FORM = u"""<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN"> <html> <head> <title>Cutplace</title> <style type="text/css">%s </style> </head><body> <h1>Cutplace</h1> <p>Validate data according to an interface control document.</p> <form action="cutplace" method="post" enctype="multipart/form-data"> <table border="0"> <tr> <td>ICD file:</td> <td><input name="icd" type="file" size="50"></td> </tr> <tr> <td>Data file:</td> <td><input name="data" type="file" size="50"></td> </tr> <tr> <td><input type="submit" value="Validate"></td> </tr> </table> </form> %s </body></html> """ % (_STYLE, _FOOTER) _ABOUT = u"""<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN"> <html> <head> <title>About cutplace</title> <style type="text/css">%s </style> </head><body> <h1>About cutplace</h1> <p>Cutplace: Version %s<br> Python: Version %s<br> Platform: %s</p> %s </body></html> """ % (_STYLE, version.VERSION_NUMBER, cgi.escape( _tools.pythonVersion()), cgi.escape(_tools.platformVersion()), _FOOTER) _SHUTDOWN = u"""<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN"> <html> <head> <title>Cutplace</title> <style type="text/css">%s </style> </head><body> <h1>Cutplace</h1> <p>The cutplace server has been shut down.</p> %s </body></html> """ % (_STYLE, _FOOTER) def do_GET(self): log = logging.getLogger("cutplace.web") log.info(u"%s %r", self.command, self.path) if (self.path == "/"): self.send_response(200) self.send_header("Content-type", "text/html") self.end_headers() self.wfile.write(Handler._FORM) self.wfile.close() elif (self.path == "/about"): self.send_response(200) self.send_header("Content-type", "text/html") self.end_headers() self.wfile.write(Handler._ABOUT) self.wfile.close() else: self.send_error(404) def do_POST(self): log = logging.getLogger("cutplace.web") log.info("%s %r" % (self.command, self.path)) # Parse POST option. Based on code by Pierre Quentel. ctype, pdict = cgi.parse_header(self.headers.getheader('content-type')) length = int(self.headers.getheader('content-length')) if ctype == 'multipart/form-data': fileMap = cgi.parse_multipart(self.rfile, pdict) elif ctype == 'application/x-www-form-urlencoded': qs = self.rfile.read(length) fileMap = cgi.parse_qs(qs, keep_blank_values=1) else: fileMap = {} # Unknown content-type if "icd" in fileMap: icdContent = fileMap["icd"][0] else: icdContent = None if "data" in fileMap: dataContent = fileMap["data"][0] else: dataContent = None if icdContent: try: icdData = StringIO.StringIO(icdContent) icd = interface.InterfaceControlDocument() icd.read(icdData) if dataContent: validationHtmlFile = tempfile.TemporaryFile( suffix=".html", prefix="cutplace-web-") try: log.debug(u"writing html to temporary file: %r", validationHtmlFile.name) validationHtmlFile.write(u"<table><tr>") # Write table headings. for title in icd.fieldNames: validationHtmlFile.write(u"<th>%s</th>" % cgi.escape(title)) validationHtmlFile.write(u"</tr>") # Start listening to validation events. htmlListener = _HtmlWritingValidationListener( validationHtmlFile, len(icd.fieldNames)) icd.addValidationListener(htmlListener) try: dataReadable = StringIO.StringIO(dataContent) icd.validate(dataReadable) icd.removeValidationListener(htmlListener) validationHtmlFile.write("</table>") self.send_response(200) self.send_header("Content-type", "text/html") self.end_headers() # Write the contents of the temporary HTML file to the web page. self.wfile.write( u"""<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN"> <html> <head> <title>Validation results</title> <style type="text/css">%s </style> </head><body> <h1>Validation results</h1> """ % (Handler._STYLE)) self.wfile.write(u"""<table> <tr><td>Rows accepted:</td><td>%d</td></tr> <tr><td>Rows rejected:</td><td>%d</td></tr> <tr><td>Checks at end failed:</td><td>%d</td></tr> </table> """ % (htmlListener.acceptedCount, htmlListener.rejectedCount, htmlListener.checkAtEndFailedCount)) validationHtmlFile.seek(0) htmlFileBuffer = validationHtmlFile.read( Handler._IO_BUFFER_SIZE) while htmlFileBuffer: self.wfile.write(htmlFileBuffer) htmlFileBuffer = validationHtmlFile.read( Handler._IO_BUFFER_SIZE) self.wfile.write(Handler._FOOTER) except: self.send_error( 400, u"cannot validate data: %s" % cgi.escape(str(sys.exc_info()[1]))) finally: validationHtmlFile.close() else: log.info("ICD is valid") self.send_response(200) self.send_header("Content-type", "text/html") self.end_headers() self.wfile.write(u"ICD file is valid.") except: log.error(u"cannot parse ICD", exc_info=1) self.send_error( 400, u"cannot parse ICD: %s" % cgi.escape(str(sys.exc_info()[1]))) else: errorMessage = "ICD file must be specified" log.error(errorMessage) self.send_error(400, u"%s." % cgi.escape(errorMessage))
def testCanQueryVersion(self): # Simply exercise these functions, their results do not really matter. _tools.platformVersion() _tools.pythonVersion()
def print_version(self, targetFile=None): # No super() due to old style class. optparse.OptionParser.print_version(self, targetFile) if self.version: print >> targetFile, "Python %s, %s" % (_tools.pythonVersion(), _tools.platformVersion())