[ConfigParser] conserver les espaces dans des valeurs multilignes

Le
Olivier Miakinen
Bonjour,

J'ai une question Í  propos du module configparser. Après lecture attentive
de la doc je pense que la réponse sera non, mais j'espère me tromper.

Je voudrais savoir s'il est possible de ne pas perdre les espaces au début
de chaque ligne dans une valeur multiligne. Je donne un exemple :

Contenu du fichier lu par ConfigParser.read() :
==[global]
filtre = AND
OR
AND
a
b
AND
c
==
Résultat de print(config.get('global', 'filtre')) :
==AND
OR
AND
a
b
AND
c
==
J'aurais souhaité avoir quelque chose comme :
==AND
OR
AND
a
b
AND
c
==

Cordialement,
--
Olivier Miakinen
  • Partager ce contenu :
Vos réponses Page 1 / 2
Trier par : date / pertinence
Julien Palard
Le #26574338
Le 5/29/21 Í  11:21 AM, Olivier Miakinen a écrit :
Je voudrais savoir s'il est possible de ne pas perdre les espaces au début
de chaque ligne dans une valeur multiligne.

Non, un petit .strip() dans l'implem va bien t'embêter [1].
Même avec des espaces insécables, couic.
Tu peux tenter avec un parseur toml [2] :
[global]
filtre = """
AND
OR
AND
a
b
AND
c
"""
[1]:
https://github.com/python/cpython/blob/af5a324843de395cecc562cb0c757b3768f2077f/Lib/configparser.py#L1042
[2]: https://pypi.org/project/toml/
--
[Julien Palard](https://mdk.fr)
Olivier Miakinen
Le #26574339
Le 29/05/2021 21:43, Julien Palard m'a répondu :
Je voudrais savoir s'il est possible de ne pas perdre les espaces au début
de chaque ligne dans une valeur multiligne.

Non, un petit .strip() dans l'implem va bien t'embêter [lien vers le code].

Ah oui, il y a un .strip() Í  chaque ligne après suppression des commentaires.
Même avec des espaces insécables, couic.

Tiens ? Pas bête, je n'y avais pas pensé. Cela dit je n'aurais pas pensé non
plus que .strip() virait aussi les espaces insécables, mais j'ai vérifié, c'est
vrai.
Tu peux tenter avec un parseur toml [2] :

Je ne connaissais pas. Je suis allé voir ton lien, et de lÍ  la page wikipédia
Tout d'abord je me suis dit que c'était génial parce qu'on peut décrire
directement dans le fichier différents types de données (entiers, chaÍ®nes,
booléens, listes, etc.)
Mais juste après je me suis rendu compte que ce n'était pas bien parce que
c'est le fichier de config qui décide des différents types de données au lieu
du programme. Du coup les erreurs de types risquent de ne pas être détectées
Í  la lecture du fichier, mais bien plus tard.
Bon, je vais donc rester sur le format INI. Pour les filtres, soit je mets
juste le nom d'un fichier externe dans le fichier INI et lui sera formatté
comme je le souhaite, soit je rajoute un caractère autre qu'une espace.
Par exemple :
================================[global]
filtre = AND
| OR
| AND
| a
| b
| AND
| c
=============================== Ou même :
================================[global]
filtre AND
| OR
| | AND
| | | a
| | | b
| AND
| | c
===============================
--
Olivier Miakinen
Olivier Miakinen
Le #26574342
Le 29/05/2021 22:58, j'écrivais :
Ou même :
================================> [global]
filtre > AND
| OR
| | AND
| | | a
| | | b
| AND
| | c
=============================== Adopté. Je n'ai eu besoin que de rajouter quelques octets dans une

regex pour être capable de gérer les filtres avec des caractères '|'
en plus des blancs de toutes sortes.
De plus, c'en est presque plus lisible.
--
Olivier Miakinen
Nicolas
Le #26574445
Bonjour,
Le 29/05/2021 Í  11:21, Olivier Miakinen a écrit :
Bonjour,
J'ai une question Í  propos du module configparser. Après lecture attentive
de la doc je pense que la réponse sera non, mais j'espère me tromper.
Je voudrais savoir s'il est possible de ne pas perdre les espaces au début
de chaque ligne dans une valeur multiligne. Je donne un exemple :
Contenu du fichier lu par ConfigParser.read() :
================================> [global]
filtre = AND
OR
AND
a
b
AND
c
================================>
Résultat de print(config.get('global', 'filtre')) :
================================> AND
OR
AND
a
b
AND
c
================================>
J'aurais souhaité avoir quelque chose comme :
================================> AND
OR
AND
a
b
AND
c
================================>

Une idée qui me vient comme ça : Est-ce qu'une chaine json serait
adaptée Í  ce que tu veux faire ? Ca aurait l'intérêt d'être plus
universel et non dépendant de l'indentation.
Nicolas
Cordialement,
Olivier Miakinen
Le #26574449
Bonjour,
Le 31/05/2021 08:41, Nicolas a écrit :
Une idée qui me vient comme ça : Est-ce qu'une chaine json serait
adaptée Í  ce que tu veux faire ? Ca aurait l'intérêt d'être plus
universel et non dépendant de l'indentation.

J'avais regardé JSON, et c'est moins adapté que configparser pour
plusieurs raisons. En particulier, tout comme TOML ou YAML, c'est le
fichier de config qui détermine le type des données. Alors c'est très
adapté comme format d'échange entre deux programmes, y compris sur
des architectures différentes, mais ça ne correspond pas Í  mon besoin.
Cela dit, merci de la proposition.
Cordialement,
--
Olivier Miakinen
Alain Ketterlin
Le #26574451
Olivier Miakinen
Le 29/05/2021 22:58, j'écrivais :
Ou même :
================================ >> [global]
filtre >> AND
| OR
| | AND
| | | a
| | | b
| AND
| | c
================================ >

Adopté. Je n'ai eu besoin que de rajouter quelques octets dans une
regex pour être capable de gérer les filtres avec des caractères '|'
en plus des blancs de toutes sortes.
De plus, c'en est presque plus lisible.

En voyant ton exemple, je me demande si un "vrai" parseur ne serait pas
plus adapté, pour écrire "filtre = a AND b OR c". Il y a divers
générateurs disponibles pour Python (je n'ai pas d'expérience récente,
désolé), et ce n'est pas très dur Í  écrire Í  la main (ymmv).
-- Alain.
P/S: je dis ça parce que ton exemple ressemble Í  une expression
booléenne, mais elle n'est pas correcte en l'état (ce qui n'a pas
d'importance ici).
Olivier Miakinen
Le #26574458
Bonjour Alain,
C'est drÍ´le comme maintenant que j'ai résolu mon problème vous êtes
plusieurs Í  vouloir me proposer une solution radicalement différente. ;-)
Le 31/05/2021 10:59, Alain Ketterlin m'a répondu :
Ou même :
================================>>> [global]
filtre >>> AND
| OR
| | AND
| | | a
| | | b
| AND
| | c
================================>


En voyant ton exemple, je me demande si un "vrai" parseur ne serait pas
plus adapté, pour écrire "filtre = a AND b OR c".

Sauf que pour décrire mon problème j'avais simplifié l'exemple (les a, b et c,
et aussi les commentaires) mais un peu compliqué par ailleurs (car la plupart
du temps il y aura un seul niveau).
En réalité, la plupart du temps mon filtre sera du type le plus simple :
OR
# spammeurs connus
from /un spammeur from /autre spammeur from /un autre encore # détection sur le titre, quelle que soit la casse, et singul. ou plur.
subject /solution.? manual/i
Et de temps en temps j'aurai juste besoin de le modifier, par exemple pour
exclure un ou deux Message-ID d'un spammeur lÍ  o͹ il n'a pas spammé :
OR
# spammeurs connus
from /un spammeur from /autre spammeur AND
from /un autre encore # on exclut deux MID
! message-id / ! message-id / # détection sur le titre, quelle que soit la casse, et singul. ou plur.
subject /solution.? manual/i
Dans ces conditions, avoir une ligne par condition est réellement la
meilleure solution. Par ailleurs la syntaxe basée sur l'indentation n'est
pas de nature Í  décontenancer un programmeur Python.
Cela dit, comme pour Nicolas, merci de la proposition.
--
Olivier Miakinen
yves
Le #26574459
Le Mon, 31 May 2021 17:15:59 +0200, Olivier Miakinen a écrit:
C'est drÍ´le comme maintenant que j'ai résolu mon problème vous êtes
plusieurs Í  vouloir me proposer une solution radicalement différente.
;-)

<troll on>
C'est parce que tu sembles avoir résolu le problème d'une manière pas
très pythonesque.
C'est comme du poil Í  gratter pour les amateurs.
<troll off>
@+
--
Yves
Nicolas
Le #26574478
Bonjour,
Le 31/05/2021 Í  09:21, Olivier Miakinen a écrit :
Bonjour,
Le 31/05/2021 08:41, Nicolas a écrit :
Une idée qui me vient comme ça : Est-ce qu'une chaine json serait
adaptée Í  ce que tu veux faire ? Ca aurait l'intérêt d'être plus
universel et non dépendant de l'indentation.

J'avais regardé JSON, et c'est moins adapté que configparser pour
plusieurs raisons. En particulier, tout comme TOML ou YAML, c'est le
fichier de config qui détermine le type des données. Alors c'est très
adapté comme format d'échange entre deux programmes, y compris sur
des architectures différentes, mais ça ne correspond pas Í  mon besoin.

Je ne vois pas o͹ il est question de type de données dans ta description
du problème. Tu écris/lis des chaines de caractères dans un fichier.
Ensuite, libre Í  toi d'interpréter ces chaines de caractères comme tu
l'entends. Ce que tu fais déjÍ  avec ton propre parseur...
Cela dit, merci de la proposition.
Pas de quoi.
Cordialement,


Nicolas
Olivier Miakinen
Le #26574495
Le 01/06/2021 09:21, Nicolas a écrit :
Une idée qui me vient comme ça : Est-ce qu'une chaine json serait
adaptée Í  ce que tu veux faire ? Ca aurait l'intérêt d'être plus
universel et non dépendant de l'indentation.

J'avais regardé JSON, et c'est moins adapté que configparser pour
plusieurs raisons. En particulier, tout comme TOML ou YAML, c'est le
fichier de config qui détermine le type des données. Alors c'est très
adapté comme format d'échange entre deux programmes, y compris sur
des architectures différentes, mais ça ne correspond pas Í  mon besoin.

Je ne vois pas o͹ il est question de type de données dans ta description
du problème. Tu écris/lis des chaines de caractères dans un fichier.
Ensuite, libre Í  toi d'interpréter ces chaines de caractères comme tu
l'entends. Ce que tu fais déjÍ  avec ton propre parseur...

Ah oui, tu veux dire que je pourrais utiliser un format TOML ou JSON
dans lequel toutes les données seraient des chaÍ®nes de caractères, donc
sans utiliser la possibilité d'exprimer des tableaux ou des dictionnaires
par exemple ?
Du coup je trouve dommage d'ajouter de la complexité (avec guillemets et
accolades) si c'est pour sous-utiliser les possibilités du format. D'autant
plus que mon seul problème concernait *un* type de données parmi tous ceux
que j'utilise, et que je l'ai résolu d'une façon qui préserve la philosophie
de python (l'indentation pour indiquer la struture). La seule différence
c'est que j'indente avec un choix de caractères qui ajoute le « | » aux
seules espaces et tabulations.
--
Olivier Miakinen
Poster une réponse
Anonyme