[Python-Dev] ConfigParser shootout, preliminary entry

Carlos Ribeiro carribeiro at gmail.com
Wed Oct 20 18:40:35 CEST 2004

On Wed, 20 Oct 2004 08:25:34 -0700, Guido van Rossum
<gvanrossum at gmail.com> wrote:
> > The opt* property builders could be substituted by a single opt which
> > took the default value as an argument:
> >
> > opt(section_name, key_name, default_value)
> What if I want the default to be None?  Sometimes absence of a value
> is useful info. If you want a single factory function (not sure why)
> then maybe the type should be passed in (perhaps optional, only if no
> default is given).

I like the optional type idea:

    opt(section_name, key_name, default_value, type)

So it can be written this way:

    opt('section', 'key', None, StringType)

...but -- to answer your question -- the point here isn't really the
'singleness' of the factory function, but the fact that it is
type-independent, which (in principle) would allow it to be extended
to handle arbitrary types by delegating some functionality to the
types themselves. IMHO, it's just a different way to design it:
instead of writing a specialized property handler for each supported
type, use a standard interface provided by types themselves to handle
the conversion to & from the string representation that is used in the
config file. Unfortunately, this generalization is not as practical as
I thought it would be.

In my implementation, I used standard Python type constructors to
convert string values to the desired object type. It works for str,
int and float [see note #1], which solved nearly all cases in my own
experience. However, this trick doesn't work for bool(), which is an
important type. To solve it, I had to write my own adapt() method,
which just handles str, int and float using the builtin types, and
treats bool() as a particular case. User defined types have to expose
special conversion methods (as they should anyway). As it is, it's a
general solution, but it ended up being more confusing and convoluted
that I would like it to be.
> > It works well as far as the option names are unique. In some cases,
> > there are sections with a similar internal structure, and in this case
> > the use of nested structures to represent sections is better.
> "Better" is subjective. With my approach, you can give them different
> prefixes in the Python API independent from their names as seen by the
> user, and you only have to do this when there are actual conflicts
> (which are rare except when certain styles are used).

Agreed. It depends a lot on the particular application, and to some
extent, on personal taste. My own bias come from some of the
applications that I have written, where I feared that the use of
prefixes would end up cluttering the namespace. Besides the above
mentioned communications software example (where I had several
communication ports, each one stored into a section), another real
scenario is the configuration of user interface parameters for several
UI elements -- for example, font selection and background colors for
specific forms. The same parameters ('font', 'font-color',
'background-color', etc.) are repeated for several sections. But
surely, my own experience is limited, and I can't speak for other
people on this point.

[1]As an apart: I was *really* surprised when I first saw that this code worked:

>>> IntType('12')
>>> FloatType('-1e+12')

The following test also worked, but I expected it to convert the value
using an octal representation, but it didn't:

>>> IntType('012')

And finally, the bool test:

>>> BooleanType('False')

Which obviously don't work because the 'False' string converts to
True, as any other non-empty string do :-P. But it seemed a little bit
weird when a I first saw it, specially when compared to FloatType and


Carlos Ribeiro
Consultoria em Projetos
blog: http://rascunhosrotos.blogspot.com
blog: http://pythonnotes.blogspot.com
mail: carribeiro at gmail.com
mail: carribeiro at yahoo.com

More information about the Python-Dev mailing list