From 8bc4135947d9a2fc1749ebc4a8cdbd4d72d7a74e Mon Sep 17 00:00:00 2001 From: Craig de Stigter Date: Mon, 18 Apr 2011 16:51:12 +1200 Subject: sane logging. remove sys.exit() calls (libraries should never ever call sys.exit()) and raise appropriate exceptions instead. backwards incompatible insofar as custom extensions may need tweaks if they're using old markdown logging (but they shouldn't, it was gross) --- markdown/__init__.py | 42 +++++++++++++++++++---------------------- markdown/blockprocessors.py | 5 ++--- markdown/commandline.py | 9 +++++---- markdown/etree_loader.py | 12 +++--------- markdown/extensions/__init__.py | 3 --- markdown/extensions/headerid.py | 4 +--- markdown/md_logging.py | 36 ----------------------------------- 7 files changed, 30 insertions(+), 81 deletions(-) delete mode 100644 markdown/md_logging.py diff --git a/markdown/__init__.py b/markdown/__init__.py index 0774174..b397f1b 100644 --- a/markdown/__init__.py +++ b/markdown/__init__.py @@ -35,8 +35,7 @@ version_info = (2,1,0, "Dev") import re import codecs -from logging import DEBUG, INFO, WARN, ERROR, CRITICAL -from md_logging import message +import logging import util from preprocessors import build_preprocessors from blockprocessors import build_block_parser @@ -49,7 +48,10 @@ import html4 # For backwards compatibility in the 2.0.x series # The things defined in these modules started off in __init__.py so third # party code might need to access them here. -from util import * +#from util import * + + +logger = logging.getLogger('MARKDOWN') class Markdown: @@ -139,13 +141,10 @@ class Markdown: if isinstance(ext, basestring): ext = self.build_extension(ext, configs.get(ext, [])) if isinstance(ext, Extension): - try: - ext.extendMarkdown(self, globals()) - except NotImplementedError, e: - message(ERROR, e) + # might raise NotImplementedError, but that's the extension author's problem + ext.extendMarkdown(self, globals()) else: - message(ERROR, - 'Extension "%s.%s" must be of type: "markdown.Extension".' \ + raise ValueError('Extension "%s.%s" must be of type: "markdown.Extension".' \ % (ext.__class__.__module__, ext.__class__.__name__)) return self @@ -179,17 +178,18 @@ class Markdown: try: # Old style (mdx_) module = __import__(module_name_old_style) except ImportError: - message(WARN, "Failed loading extension '%s' from '%s' or '%s'" - % (ext_name, module_name_new_style, module_name_old_style)) - # Return None so we don't try to initiate none-existant extension - return None + logger.warn("Failed loading extension '%s' from '%s' or '%s'" + % (ext_name, module_name_new_style, module_name_old_style)) + # Return None so we don't try to initiate none-existant extension + return None # If the module is loaded successfully, we expect it to define a # function called makeExtension() try: return module.makeExtension(configs.items()) except AttributeError, e: - message(CRITICAL, "Failed to initiate extension '%s': %s" % (ext_name, e)) + logger.warn("Failed to initiate extension '%s': %s" % (ext_name, e)) + return None def registerExtension(self, extension): """ This gets called by the extension """ @@ -214,8 +214,7 @@ class Markdown: try: self.serializer = self.output_formats[format.lower()] except KeyError: - message(CRITICAL, - 'Invalid Output Format: "%s". Use one of %s.' \ + raise KeyError('Invalid Output Format: "%s". Use one of %s.' \ % (format, self.output_formats.keys())) return self @@ -244,12 +243,9 @@ class Markdown: # Fixup the source text if not source.strip(): return u"" # a blank unicode string - try: - source = unicode(source) - except UnicodeDecodeError: - message(CRITICAL, - 'UnicodeDecodeError: Markdown only accepts unicode or ascii input.') - return u"" + + # if this raises UnicodeDecodeError, that's the caller's fault. + source = unicode(source) source = source.replace(util.STX, "").replace(util.ETX, "") source = source.replace("\r\n", "\n").replace("\r", "\n") + "\n\n" @@ -283,7 +279,7 @@ class Markdown: output = '' else: # We have a serious problem - message(CRITICAL, 'Failed to strip top level tags.') + raise ValueError('Markdown failed to strip top-level tags. Document=%r' % output.strip()) # Run the text post-processors for pp in self.postprocessors.values(): diff --git a/markdown/blockprocessors.py b/markdown/blockprocessors.py index 77fbc71..10a0177 100644 --- a/markdown/blockprocessors.py +++ b/markdown/blockprocessors.py @@ -15,8 +15,7 @@ as they need to alter how markdown blocks are parsed. import re import util from blockparser import BlockParser -from logging import CRITICAL -from md_logging import message +from markdown import logger def build_block_parser(md_instance, **kwargs): @@ -408,7 +407,7 @@ class HashHeaderProcessor(BlockProcessor): blocks.insert(0, after) else: # This should never happen, but just in case... - message(CRITICAL, "We've got a problem header!") + logger.warn("We've got a problem header: %r" % block) class SetextHeaderProcessor(BlockProcessor): diff --git a/markdown/commandline.py b/markdown/commandline.py index 049d2be..eab23bb 100644 --- a/markdown/commandline.py +++ b/markdown/commandline.py @@ -7,8 +7,9 @@ COMMAND-LINE SPECIFIC STUFF import markdown import sys import optparse -import logging -from logging import DEBUG, INFO, WARN, ERROR, CRITICAL +from logging import DEBUG, INFO, CRITICAL + +from markdown import logger # default logging level for command-line use COMMAND_LINE_LOGGING_LEVEL = CRITICAL @@ -69,8 +70,8 @@ def run(): # Parse options and adjust logging level if necessary options, logging_level = parse_options() - if not options: sys.exit(0) - if logging_level: logging.getLogger('MARKDOWN').setLevel(logging_level) + if not options: sys.exit(2) + if logging_level: logger.setLevel(logging_level) # Run markdown.markdownFromFile(**options) diff --git a/markdown/etree_loader.py b/markdown/etree_loader.py index 64966b5..60719d8 100644 --- a/markdown/etree_loader.py +++ b/markdown/etree_loader.py @@ -1,6 +1,3 @@ -from logging import CRITICAL -from md_logging import message -import sys ## Import def importETree(): @@ -20,18 +17,15 @@ def importETree(): try: # An earlier version of Python with Python ElementTree? import elementtree.ElementTree as etree except ImportError: - message(CRITICAL, "Failed to import ElementTree") - sys.exit(1) + raise ImportError("Failed to import ElementTree") if etree_in_c: if etree_in_c.VERSION < "1.0": - message(CRITICAL, "cElementTree version 1.0 or higher is required.") - sys.exit(1) + raise RuntimeError("cElementTree version 1.0 or higher is required.") # Third party serializers (including ours) test with non-c Comment etree_in_c.test_comment = Comment return etree_in_c elif etree.VERSION < "1.1": - message(CRITICAL, "ElementTree version 1.1 or higher is required") - sys.exit(1) + raise RuntimeError("ElementTree version 1.1 or higher is required") else: return etree diff --git a/markdown/extensions/__init__.py b/markdown/extensions/__init__.py index 1cc4762..4c1dcba 100644 --- a/markdown/extensions/__init__.py +++ b/markdown/extensions/__init__.py @@ -1,6 +1,3 @@ -from markdown.md_logging import message -from logging import DEBUG, INFO, WARN, ERROR, CRITICAL - """ Extensions ----------------------------------------------------------------------------- diff --git a/markdown/extensions/headerid.py b/markdown/extensions/headerid.py index 5e9793e..6d64a43 100644 --- a/markdown/extensions/headerid.py +++ b/markdown/extensions/headerid.py @@ -67,8 +67,6 @@ Dependencies: import markdown from markdown.util import etree -from logging import CRITICAL -from markdown.md_logging import message import re from string import ascii_lowercase, digits, punctuation @@ -121,7 +119,7 @@ class HeaderIdProcessor(markdown.blockprocessors.BlockProcessor): blocks.insert(0, after) else: # This should never happen, but just in case... - message(CRITICAL, "We've got a problem header!") + raise ValueError("Encountered a problem header: %r" % block) def _get_meta(self): """ Return meta data suported by this ext as a tuple """ diff --git a/markdown/md_logging.py b/markdown/md_logging.py deleted file mode 100644 index 463be15..0000000 --- a/markdown/md_logging.py +++ /dev/null @@ -1,36 +0,0 @@ -# -*- coding: utf-8 -*- -import logging -from logging import DEBUG, INFO, WARN, ERROR, CRITICAL -import sys -import warnings - -# -# Exceptions -# - -class MarkdownException(Exception): - """ A Markdown Exception. """ - pass - - -class MarkdownWarning(Warning): - """ A Markdown Warning. """ - pass - - -# -# Global functions -# - -def message(level, text): - """ A wrapper method for logging debug messages. """ - logger = logging.getLogger('MARKDOWN') - if logger.handlers: - # The logger is configured - logger.log(level, text) - if level > WARN: - sys.exit(0) - elif level > WARN: - raise MarkdownException, text - else: - warnings.warn(text, MarkdownWarning) \ No newline at end of file -- cgit v1.2.3