Package Products :: Package ZenModel :: Module SiteError |
[hide private]
[frames] | no frames]

# Source Code for Module Products.ZenModel.SiteError

      1  ##############################################################################
      2  #
      3  # Copyright (C) Zenoss, Inc. 2007, all rights reserved.
      4  #
      5  # This content is made available according to terms specified in
      6  # License.zenoss under the directory where your Zenoss product is installed.
      7  #
      8  ##############################################################################
      9
     10
     11  __doc__="""SiteError
     12
     13  SiteError consolidates code used to handle and report site errors.
     14  """
     15  import Globals
     16  import smtplib
     17  import re
     18  import cgi # for cgi.escape()
     19
     20 -class SiteError:
     21
     22      SMTP_HOST = 'mail.zenoss.com'
     23      ERRORS_ADDRESS = 'errors@zenoss.com'
     24
     25 -    def cleanUrl(cls, errorUrl):
     26          ''' Strip protocol and domain from the url
     27          '''
     28          stripDomain = False
     29          if errorUrl.startswith('http://'):
     30              errorUrl = errorUrl[len('http://'):]
     31              stripDomain = True
     32          elif errorUrl.startswith('https://'):
     33              errorUrl = errorUrl[len('https://'):]
     34              stripDomain = True
     35          if stripDomain and '/' in errorUrl:
     36              errorUrl = errorUrl[errorUrl.find('/'):]
     37          return errorUrl
     38      cleanUrl = classmethod(cleanUrl)
     39
     40
     41 -    def createEmailHeader(cls, fromAddress, toAddress, subject):
     42          ''' Create the smnp header for an error email
     43          '''
     44          header = 'To: %s\nFrom: %s\nSubject: %s\n' % (
     45                      toAddress, fromAddress, subject)
     46          return header
     47      createEmailHeader = classmethod(createEmailHeader)
     48
     49
     50 -    def createReport(cls, errorType, errorValue, errorTrace, errorUrl, revision,
     51                          versionShort,
     52                          inHtml=True, contactName=None, contactEmail=None,
     53                          comments=None):
     54          ''' Produce a summary of the given error details suitable for use
     55          in an error email (inHtml=false) or on a page (inHtml=true)
     56          '''
     57          def StripTags(s):
     58              ''' Strip html tags from string
     59              '''
     60              return re.sub('<[^>]*>', '', s)
     61
     62          # If not inHtml then strip html tags from the errorTrace
     63          if inHtml:
     64              linebreak = '<br />\n'
     65              contactName = cgi.escape(contactName)
     66              contactEmail = cgi.escape(contactEmail)
     67              comments = cgi.escape(comments)
     68          else:
     69              linebreak = '\n'
     70              errorType = StripTags(errorType)
     71              errorValue = StripTags(errorValue)
     72              errorTrace = StripTags(errorTrace)
     73              errorTrace = re.sub('\r\n\r\n', '\r\n', errorTrace)
     74          msg = linebreak.join(['Type: %s' % errorType,
     75                                  'Value: %s' % errorValue,
     76                                  'URL: %s' % cls.cleanUrl(errorUrl),
     77                                  'Revision: %s' % revision,
     78                                  'Version: %s' % versionShort,
     79                                  '%s' % errorTrace,
     80                                  'Contact name: %s' % (contactName or ''),
     81                                  'Email address: %s' % (contactEmail or ''),
     82                                  'Comments: %s' % (comments or '')])
     83          return msg
     84      createReport = classmethod(createReport)
     85
     86
     87 -    def sendErrorEmail(self, errorType, errorValue, errorTrace, errorUrl,
     88                          revision, versionShort,
     89                          contactName=None, contactEmail=None, comments=None,
     90                          smtphost=None, smtpport=25, usetls=False, usr='',
     91                          pwd=''):
     92          ''' Attempt to send an email to the zenoss errors email address
     93          with details of this error.
     94          Returns true if mail was sent, false otherwise.
     95          '''
     96          import socket
     97          fqdn = socket.getfqdn()
     98          fromAddress = 'errors@%s' % fqdn
     99          cleanUrl = self.cleanUrl(errorUrl)
    100          subject = '%s: %s (%s)' % (errorType, errorValue[:15], cleanUrl)
    101          header = self.createEmailHeader(
    102                      fromAddress, self.ERRORS_ADDRESS, subject)
    103          body = self.createReport(errorType, errorValue, errorTrace, cleanUrl,
    104                                  revision, versionShort,
    105                                  0, contactName, contactEmail, comments)
    106          mailSent = False
    107
    108          # Log in to the server using user's smtp or fall back to mail.zenoss.com
    109          if not smtphost:
    110              smtphost = self.SMTP_HOST
    111          server = smtplib.SMTP(smtphost, smtpport)
    112          if usetls:
    113              server.ehlo()
    114              server.starttls()
    115              server.ehlo()
    116          if usr: server.login(usr, pwd)
    117          try:
    118              server.sendmail(fromAddress, self.ERRORS_ADDRESS,
    119                              '%s\n\n%s' % (header, body))
    120              mailSent = True
    121          finally:
    122              try: server.quit()
    123              except: pass
    124          return mailSent
    125      sendErrorEmail = classmethod(sendErrorEmail)
    126