Claves únicas de ConfigParser de Python por sección

Leí la parte de los documentos y vi que ConfigParser devuelve una lista de pares clave / valor para las opciones dentro de una sección. Pensé que las claves no tenían que ser únicas dentro de una sección, de lo contrario, el analizador simplemente devolvería un mapeo. Diseñé mi esquema de archivo de configuración en torno a este supuesto, y luego me di cuenta de que no es así:

 >>> from ConfigParser import ConfigParser >>> from StringIO import StringIO >>> fh = StringIO(""" ... [Some Section] ... spam: eggs ... spam: ham ... """) >>> parser = ConfigParser() >>> parser.readfp(fh) >>> print parser.items('Some Section') [('spam', 'ham')] 

Luego volví y encontré la parte de los documentos que debería haber leído:

Las secciones se almacenan normalmente en un diccionario incorporado. Se puede pasar un tipo de diccionario alternativo al constructor ConfigParser. Por ejemplo, si se pasa un tipo de diccionario que ordena sus claves, las secciones se ordenarán por escrito, al igual que las claves dentro de cada sección.

Para mantener mi esquema de archivo de configuración existente (que realmente me gusta ahora), estoy pensando en pasar un objeto similar a la asignación como se mencionó anteriormente que acumula valores en lugar de golpearlos. ¿Hay una forma más sencilla de evitar el colapso de clave / valor que me estoy perdiendo? En lugar de hacer un adaptador loco (que podría romperse si ConfigParser la implementación de ConfigParser ), ¿debería simplemente escribir una variante del ConfigParser ?

Siento que este puede ser uno de esos momentos “duh” en los que solo veo las soluciones difíciles.

    [Editar:] Este es un ejemplo más preciso de cómo me gustaría usar la misma clave varias veces:

     [Ignored Paths] ignore-extension: .swp ignore-filename: tags ignore-directory: bin 

    No me gusta la syntax de la lista delimitada por comas porque es difícil para la vista cuando la escala a muchos valores; por ejemplo, una lista delimitada por comas de cincuenta extensiones no sería particularmente legible.

    ConfigParser no está diseñado para manejar tales condiciones. Además, tu archivo de configuración no tiene sentido para mí.

    ConfigParser le brinda una estructura similar a dict para cada sección, por lo que cuando llama a parser.items (sección), estoy esperando una salida similar a dict.items (), que es solo una lista de tuplas clave / valor. Nunca esperaría ver algo como:

     [('spam', 'eggs'), ('spam', 'ham')] 

    Sin mencionar, ¿cómo esperas que se comporte lo siguiente ?:

     parser.get('Some Section', 'spam') 

    ¿Cuál es la forma pretendida para recuperar los valores.

    Si desea almacenar varios valores para la misma clave, sugeriría algo como esto en su archivo de configuración:

     [Some Section] spam: eggs, ham 

    Y esto en tu código:

     spam_values = [v.strip() for v in parser.get('Some Section', 'spam').split(',')] 

    Por supuesto, esto solo funcionará para los valores que no contengan comas ni manejen las citas. Para eso, debes emplear una técnica más avanzada (mira esto y esto ).

    EDITAR: Si no le importa la dependencia adicional, puede revisar ConfigObj , que soporta de forma nativa las listas como un tipo de valor.

    Esta deficiencia de ConfigParser es la razón por la cual Pyglet usó la versión parcheada de epydoc para reemplazar ConfigParser ini con este formato simple :

     name: pyglet url: http://www.pyglet.org/ output: html target: doc/api/ ... module: pyglet exclude: pyglet.gl.gl exclude: pyglet.gl.agl exclude: pyglet.gl.lib_agl exclude: pyglet.gl.wgl ... 

    Si no necesita secciones, este enfoque puede ser útil.