cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync# -*- coding: utf-8 -*-
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync# $Id$
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync"""
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncTest Manager Core - Web Server Abstraction Base Class.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync"""
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync__copyright__ = \
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync"""
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncCopyright (C) 2012-2014 Oracle Corporation
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncThis file is part of VirtualBox Open Source Edition (OSE), as
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncavailable from http://www.virtualbox.org. This file is free software;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncyou can redistribute it and/or modify it under the terms of the GNU
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncGeneral Public License (GPL) as published by the Free Software
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncFoundation, in version 2 as it comes in the "COPYING" file of the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncVirtualBox OSE distribution. VirtualBox OSE is distributed in the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsynchope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncThe contents of this file may alternatively be used under the terms
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncof the Common Development and Distribution License Version 1.0
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync(CDDL) only, as it comes in the "COPYING.CDDL" file of the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncVirtualBox OSE distribution, in which case the provisions of the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncCDDL are applicable instead of those of the GPL.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncYou may elect to license modified versions of this file under the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncterms and conditions of either the GPL or the CDDL or both.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync"""
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync__version__ = "$Revision$"
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync# Standard python imports.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncimport cgitb
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncimport codecs;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncimport os
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncimport sys
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync# Validation Kit imports.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncfrom common import webutils, utils;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncfrom testmanager import config;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncclass WebServerGlueException(Exception):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync For exceptions raised by glue code.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync pass;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsyncclass WebServerGlueBase(object):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Web server interface abstraction and some HTML utils.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ## Enables more debug output.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync kfDebugInfoEnabled = True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ## The maximum number of characters to cache.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync kcchMaxCached = 65536;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ## Special getUserName return value.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync ksUnknownUser = 'Unknown User';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def __init__(self, sValidationKitDir, fHtmlDebugOutput = True):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sValidationKitDir = sValidationKitDir;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Debug
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.tsStart = utils.timestampNano();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._fHtmlDebugOutput = fHtmlDebugOutput; # For trace
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._oDbgFile = sys.stderr;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if config.g_ksSrcGlueDebugLogDst is not None and config.g_kfSrvGlueDebug is True:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._oDbgFile = open(config.g_ksSrcGlueDebugLogDst, 'a');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._afnDebugInfo = [];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # HTTP header.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._fHeaderWrittenOut = False;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._dHeaderFields = \
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync { \
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync 'Content-Type': 'text/html; charset=utf-8',
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync };
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Body.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sBodyType = None;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._dParams = dict();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sHtmlBody = '';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchCached = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchBodyWrittenOut = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Output.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.oOutputRaw = sys.stdout;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.oOutputText = codecs.getwriter('utf-8')(sys.stdout);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Get stuff.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getParameters(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Returns a dictionary with the query parameters.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync The parameter name is the key, the values are given as lists. If a
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync parameter is given more than once, the value is appended to the
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync existing dictionary entry.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return dict();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getClientAddr(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Returns the client address, as a string.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('getClientAddr is not implemented');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getMethod(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the HTTP request method.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return 'POST';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getLoginName(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets login name provided by Apache.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Returns kUnknownUser if not logged on.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return WebServerGlueBase.ksUnknownUser;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getUrlScheme(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets scheme name (aka. access protocol) from request URL, i.e. 'http' or 'https'.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync See also urlparse.scheme.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return 'http';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getUrlNetLoc(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the network location (server host name / ip) from the request URL.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync See also urlparse.netloc.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('getUrlNetLoc is not implemented');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getUrlPath(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the hirarchical path (relative to server) from the request URL.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync See also urlparse.path.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Note! This includes the leading slash.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('getUrlPath is not implemented');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getUrlBasePath(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the hirarchical base path (relative to server) from the request URL.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Note! This includes both a leading an trailing slash.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sPath = self.getUrlPath();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync iLastSlash = sPath.rfind('/');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if iLastSlash >= 0:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sPath = sPath[:iLastSlash];
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sPath = sPath.rstrip('/');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return sPath + '/';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getUrl(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the URL being accessed, sans parameters.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync For instance this will return, "http://localhost/testmanager/admin.cgi"
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync when "http://localhost/testmanager/admin.cgi?blah=blah" is being access.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return '%s://%s%s' % (self.getUrlScheme(), self.getUrlNetLoc(), self.getUrlPath());
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getBaseUrl(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the base URL (with trailing slash).
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync For instance this will return, "http://localhost/testmanager/" when
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync "http://localhost/testmanager/admin.cgi?blah=blah" is being access.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return '%s://%s%s' % (self.getUrlScheme(), self.getUrlNetLoc(), self.getUrlBasePath());
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getUserAgent(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the User-Agent field of the HTTP header, returning empty string
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if not present.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return '';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getContentType(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the Content-Type field of the HTTP header, parsed into a type
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync string and a dictionary.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return ('text/html', {});
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getContentLength(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the content length.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Returns int.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def getBodyIoStream(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Returns file object for reading the HTML body.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('getUrlPath is not implemented');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Output stuff.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def _writeHeader(self, sHeaderLine):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Worker function which child classes can override.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.oOutputText.write(sHeaderLine);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def flushHeader(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Flushes the HTTP header.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHeaderWrittenOut is False:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for sKey in self._dHeaderFields:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._writeHeader('%s: %s\n' % (sKey, self._dHeaderFields[sKey]));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._fHeaderWrittenOut = True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._writeHeader('\n'); # End of header indicator.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return None;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def setHeaderField(self, sField, sValue):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Sets a header field.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync assert self._fHeaderWrittenOut is False;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._dHeaderFields[sField] = sValue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def setRedirect(self, sLocation, iCode = 302):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Sets up redirection of the page.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Raises an exception if called too late.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHeaderWrittenOut is True:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('setRedirect called after the header was written');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if iCode != 302:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('Redirection code %d is not supported' % (iCode,));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.setHeaderField('Location', sLocation);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.setHeaderField('Status', '302 Found');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def _writeWorker(self, sChunkOfHtml):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Worker function which child classes can override.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.oOutputText.write(sChunkOfHtml);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def write(self, sChunkOfHtml):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Writes chunk of HTML, making sure the HTTP header is flushed first.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._sBodyType is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sBodyType = 'html';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync elif self._sBodyType is not 'html':
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('Cannot use writeParameter when body type is "%s"' % (self._sBodyType, ));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sHtmlBody += sChunkOfHtml;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchCached += len(sChunkOfHtml);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._cchCached > self.kcchMaxCached:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flush();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def writeRaw(self, abChunk):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Writes a raw chunk the document. Can be binary or any encoding.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync No caching.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._sBodyType is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sBodyType = 'html';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync elif self._sBodyType is not 'html':
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('Cannot use writeParameter when body type is "%s"' % (self._sBodyType, ));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flushHeader();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._cchCached > 0:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flush();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.oOutputRaw.write(abChunk);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def writeParams(self, dParams):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Writes one or more reply parameters in a form style response. The names
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync and values in dParams are unencoded, this method takes care of that.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Note! This automatically changes the content type to
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync 'application/x-www-form-urlencoded', if the header hasn't been flushed
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync already.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._sBodyType is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if not self._fHeaderWrittenOut:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.setHeaderField('Content-Type', 'application/x-www-form-urlencoded; charset=utf-8');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync elif self._dHeaderFields['Content-Type'] != 'application/x-www-form-urlencoded; charset=utf-8':
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('Cannot use writeParams when content-type is "%s"' % \
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync (self._dHeaderFields['Content-Type'],));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sBodyType = 'form';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync elif self._sBodyType is not 'form':
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync raise WebServerGlueException('Cannot use writeParams when body type is "%s"' % (self._sBodyType, ));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for sKey in dParams:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sValue = str(dParams[sKey]);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._dParams[sKey] = sValue;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchCached += len(sKey) + len(sValue);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._cchCached > self.kcchMaxCached:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flush();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def flush(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Flush the output.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flushHeader();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._sBodyType == 'form':
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync sBody = webutils.encodeUrlParams(self._dParams);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._writeWorker(sBody);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._dParams = dict();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchBodyWrittenOut += self._cchCached;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync elif self._sBodyType == 'html':
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._writeWorker(self._sHtmlBody);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sHtmlBody = '';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchBodyWrittenOut += self._cchCached;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchCached = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return None;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Paths.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def pathTmWebUI(self):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Gets the path to the TM 'webui' directory.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return os.path.join(self._sValidationKitDir, 'testmanager', 'webui');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Error stuff & Debugging.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync #
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def errorLog(self, sError, aXcptInfo, sLogFile):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Writes the error to a log file.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Easy solution for log file size: Only one report.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync try: os.unlink(sLogFile);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync except: pass;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Try write the log file.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fRc = True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fSaved = self._fHtmlDebugOutput;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync try:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile = open(sLogFile, 'w');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write(sError + '\n\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if aXcptInfo[0] is not None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write(' B a c k t r a c e\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write('===================\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write(cgitb.text(aXcptInfo, 5));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write('\n\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write(' D e b u g I n f o\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.write('=====================\n\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._fHtmlDebugOutput = False;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpStuff(oFile.write);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync oFile.close();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync except:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fRc = False;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._fHtmlDebugOutput = fSaved;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return fRc;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def errorPage(self, sError, aXcptInfo, sLogFile = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Displays a page with an error message.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if sLogFile is not None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.errorLog(sError, aXcptInfo, sLogFile);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Reset buffering, hoping that nothing was flushed yet.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sBodyType = None;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._sHtmlBody = '';
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._cchCached = 0;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if not self._fHeaderWrittenOut:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.setHeaderField('Content-Type', 'text/html; charset=utf-8');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.setHeaderField('Content-Type', 'text/plain; charset=utf-8');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync # Write the error page.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('<html><head><title>Test Manage Error</title></head>\n' +
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '<body><h1>Test Manager Error:</h1>\n' +
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '<p>' + sError + '</p>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write(' Test Manage Error\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '===================\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '' + sError + '\n\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if aXcptInfo[0] is not None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('<h1>Backtrace:</h1>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write(cgitb.html(aXcptInfo, 5));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('Backtrace\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '---------\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write(cgitb.text(aXcptInfo, 5));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('\n\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self.kfDebugInfoEnabled:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('<h1>Debug Info:</h1>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('Debug Info\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '----------\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpStuff();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for fn in self._afnDebugInfo:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync try:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fn(self, self._fHtmlDebugOutput);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync except Exception as oXcpt:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('\nDebug info callback %s raised exception: %s\n' % (fn, oXcpt));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.write('</body></html>');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flush();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugInfoPage(self, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Dumps useful debug info.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if fnWrite is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite = self.write;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('<html><head><title>Test Manage Debug Info</title></head>\n<body>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpStuff(fnWrite = fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('</body></html>');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.flush();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpDict(self, sName, dDict, fSorted = True, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Dumps dictionary.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if fnWrite is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite = self.write;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync asKeys = list(dDict.keys());
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if fSorted:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync asKeys.sort();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('<h2>%s</h2>\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '<table border="1"><tr><th>name</th><th>value</th></tr>\n' % (sName,));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for sKey in asKeys:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite(' <tr><td>' + webutils.escapeElem(sKey) + '</td><td>' \
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync + webutils.escapeElem(str(dDict.get(sKey))) \
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync + '</td></tr>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('</table>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for i in range(len(sName) - 1):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%s ' % (sName[i],));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%s\n\n' % (sName[-1],));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%28s Value\n' % ('Name',));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('------------------------------------------------------------------------\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for sKey in asKeys:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%28s: %s\n' % (sKey, dDict.get(sKey),));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpList(self, sName, aoStuff, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Dumps array.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if fnWrite is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite = self.write;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('<h2>%s</h2>\n'
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync '<table border="1"><tr><th>index</th><th>value</th></tr>\n' % (sName,));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for i in range(len(aoStuff)):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite(' <tr><td>' + str(i) + '</td><td>' + webutils.escapeElem(str(aoStuff[i])) + '</td></tr>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('</table>\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for i in range(len(sName) - 1):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%s ' % (sName[i],));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%s\n\n' % (sName[-1],));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('Index Value\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('------------------------------------------------------------------------\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for i in range(len(aoStuff)):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('%5u %s\n' % (i, str(aoStuff[i])));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpParameters(self, fnWrite):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """ Dumps request parameters. """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if fnWrite is None:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite = self.write;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync try:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dParams = self.getParameters();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return self.debugDumpDict('Parameters', dParams);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync except Exception as oXcpt:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self._fHtmlDebugOutput:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('<p>Exception %s while retriving parameters.</p>\n' % (oXcpt,))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync fnWrite('Exception %s while retriving parameters.\n' % (oXcpt,))
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return False;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpEnv(self, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """ Dumps os.environ. """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return self.debugDumpDict('Environment (os.environ)', os.environ, fnWrite = fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpArgv(self, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """ Dumps sys.argv. """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return self.debugDumpList('Arguments (sys.argv)', sys.argv, fnWrite = fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpPython(self, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Dump python info.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo = {};
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.version'] = sys.version;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.hexversion'] = sys.hexversion;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.api_version'] = sys.api_version;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.subversion'] = sys.subversion;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.platform'] = sys.platform;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.executable'] = sys.executable;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.copyright'] = sys.copyright;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.byteorder'] = sys.byteorder;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.exec_prefix'] = sys.exec_prefix;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.prefix'] = sys.prefix;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.path'] = sys.path;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.builtin_module_names'] = sys.builtin_module_names;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync dInfo['sys.flags'] = sys.flags;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return self.debugDumpDict('Python Info', dInfo, fnWrite = fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def debugDumpStuff(self, fnWrite = None):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Dumps stuff to the error page and debug info page.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Should be extended by child classes when possible.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpParameters(fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpEnv(fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpArgv(fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self.debugDumpPython(fnWrite);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def dprint(self, sMessage):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Prints to debug log (usually apache error log).
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if config.g_kfSrvGlueDebug is True:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if config.g_kfSrvGlueDebugTS is False:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._oDbgFile.write(sMessage);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if not sMessage.endswith('\n'):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._oDbgFile.write('\n');
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync else:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync tsNow = utils.timestampMilli();
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync tsReq = tsNow - (self.tsStart / 1000000)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync for sLine in sMessage.split('\n'):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._oDbgFile.write('%s/%03u: %s\n' % (tsNow, tsReq, sLine,));
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def registerDebugInfoCallback(self, fnDebugInfo):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Registers a debug info method for calling when the error page is shown.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync The fnDebugInfo function takes two parameters. The first is this
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync object, the second is a boolean indicating html (True) or text (False)
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync output. The return value is ignored.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self.kfDebugInfoEnabled:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync self._afnDebugInfo.append(fnDebugInfo);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync def unregisterDebugInfoCallback(self, fnDebugInfo):
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync Unregisters a debug info method previously registered by
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync registerDebugInfoCallback.
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync """
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync if self.kfDebugInfoEnabled:
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync try: self._afnDebugInfo.remove(fnDebugInfo);
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync except: pass;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync return True;
cf22150eaeeb72431bf1cf65c309a431454fb22bvboxsync