Allow spaces in section names.

Do not expose the __name__ when reporting the list of options available
for a section since that is for internal use.

This closes SourceForge bug #115357.

Additionally, define InterpolationDepthError and MAX_INTERPOLATION_DEPTH.
The exception is raised by get*() when value interpolation cannot be
completed within the defined recursion limit.  The constant is only
informative; changing it will not affect the allowed depth.

Fix the exit from get() so that None is not returned if the depth is met
or exceeded; either return the value of raise InterpolationDepthError.
This commit is contained in:
Fred Drake 2000-09-27 22:43:54 +00:00
parent 6372fe1e40
commit 2a37f9f862
1 changed files with 33 additions and 18 deletions

View File

@ -91,6 +91,8 @@ import re
DEFAULTSECT = "DEFAULT" DEFAULTSECT = "DEFAULT"
MAX_INTERPOLATION_DEPTH = 10
# exception classes # exception classes
@ -130,15 +132,16 @@ class InterpolationError(Error):
self.option = option self.option = option
self.section = section self.section = section
class MissingSectionHeaderError(Error): class InterpolationDepthError(Error):
def __init__(self, filename, lineno, line): def __init__(self, option, section, rawval):
Error.__init__( Error.__init__(self,
self, "Value interpolation too deeply recursive:\n"
'File contains no section headers.\nfile: %s, line: %d\n%s' % "\tsection: [%s]\n"
(filename, lineno, line)) "\toption : %s\n"
self.filename = filename "\trawval : %s\n"
self.lineno = lineno % (section, option, rawval))
self.line = line self.option = option
self.section = section
class ParsingError(Error): class ParsingError(Error):
def __init__(self, filename): def __init__(self, filename):
@ -150,6 +153,16 @@ class ParsingError(Error):
self.errors.append((lineno, line)) self.errors.append((lineno, line))
self._msg = self._msg + '\n\t[line %2d]: %s' % (lineno, line) self._msg = self._msg + '\n\t[line %2d]: %s' % (lineno, line)
class MissingSectionHeaderError(ParsingError):
def __init__(self, filename, lineno, line):
Error.__init__(
self,
'File contains no section headers.\nfile: %s, line: %d\n%s' %
(filename, lineno, line))
self.filename = filename
self.lineno = lineno
self.line = line
class ConfigParser: class ConfigParser:
@ -183,7 +196,7 @@ class ConfigParser:
The DEFAULT section is not acknowledged. The DEFAULT section is not acknowledged.
""" """
return self.__sections.has_key(section) return section in self.sections()
def options(self, section): def options(self, section):
"""Return a list of option names for the given section name.""" """Return a list of option names for the given section name."""
@ -192,15 +205,13 @@ class ConfigParser:
except KeyError: except KeyError:
raise NoSectionError(section) raise NoSectionError(section)
opts.update(self.__defaults) opts.update(self.__defaults)
if opts.has_key('__name__'):
del opts['__name__']
return opts.keys() return opts.keys()
def has_option(self, section, option): def has_option(self, section, option):
"""Return whether the given section has the given option.""" """Return whether the given section has the given option."""
try: return option in self.options(section)
opts = self.__sections[section]
except KeyError:
raise NoSectionError(section)
return opts.has_key(option)
def read(self, filenames): def read(self, filenames):
"""Read and parse a filename or a list of filenames. """Read and parse a filename or a list of filenames.
@ -266,10 +277,11 @@ class ConfigParser:
rawval = d[option] rawval = d[option]
except KeyError: except KeyError:
raise NoOptionError(option, section) raise NoOptionError(option, section)
# do the string interpolation
if raw: if raw:
return rawval return rawval
# do the string interpolation
value = rawval # Make it a pretty variable name value = rawval # Make it a pretty variable name
depth = 0 depth = 0
while depth < 10: # Loop through this until it's done while depth < 10: # Loop through this until it's done
@ -280,7 +292,10 @@ class ConfigParser:
except KeyError, key: except KeyError, key:
raise InterpolationError(key, option, section, rawval) raise InterpolationError(key, option, section, rawval)
else: else:
return value break
if value.find("%(") >= 0:
raise InterpolationDepthError(option, section, rawval)
return value
def __get(self, section, conv, option): def __get(self, section, conv, option):
return conv(self.get(section, option)) return conv(self.get(section, option))
@ -365,7 +380,7 @@ class ConfigParser:
# of \w, _ is allowed in section header names. # of \w, _ is allowed in section header names.
SECTCRE = re.compile( SECTCRE = re.compile(
r'\[' # [ r'\[' # [
r'(?P<header>[-\w_.*,(){}]+)' # a lot of stuff found by IvL r'(?P<header>[-\w_.*,(){} ]+)' # a lot of stuff found by IvL
r'\]' # ] r'\]' # ]
) )
OPTCRE = re.compile( OPTCRE = re.compile(