[IMP] format : un formateur par contexte, ruff pour l'outillage

« make format » donnait isort et black à tout fichier Python : la cible py37,
plus petit dénominateur commun de six dépôts d'addons, imposait son style au
code de ce dépôt. Le contexte décide désormais — les modules Odoo gardent isort
et black, le reste passe par ruff, réglé dans .ruff.toml, comme la norme OCA
depuis qu'elle a quitté black. Les dépôts rapatriés sous script/ en sont
écartés, chemin nommé compris. La cible y reste py310 : dès 3.14 ruff écrit
« except A, B: » sans parenthèses, que le python3 des hooks ne sait pas lire.
Vérifié : un fichier reçoit deux normes selon son chemin, et aucun dépôt
rapatrié n'est touché.

--- EN ---

"make format" gave isort and black to every Python file: the py37 target,
lowest common denominator of six addons repositories, imposed its style on this
repository's code. Context now decides — Odoo modules keep isort and black,
everything else goes through ruff, set in .ruff.toml, as the OCA standard does
since it left black. The repositories checked out under script/ are excluded, a
named path included. The target stays py310 there: from 3.14 on, ruff writes
"except A, B:" unparenthesised, which the python3 of the hooks cannot read.
Checked: one file gets two standards by its path, and no checked-out
repository is touched.

Assisted-by: Claude Opus 5
This commit is contained in:
Mathieu Benoit 2026-09-24 13:29:11 -04:00
parent 4ecd9e313b
commit f2ba74fd59
8 changed files with 89 additions and 8 deletions

37
.ruff.toml Normal file
View file

@ -0,0 +1,37 @@
# Formatage et tri des imports de l'OUTILLAGE ERPLibre — script/, test/,
# long_test/ et les scripts de la racine.
#
# ruff et non black : black 24.8.0 ne connaît aucune cible au-delà de py313,
# quand l'outillage tourne sur conf/python-erplibre-version, et son tri
# d'imports remplace isort sans second outil. C'est aussi ce que la norme OCA
# emploie depuis qu'elle a quitté black.
#
# Les modules Odoo n'obéissent PAS à ce fichier : chaque dépôt d'addons porte
# sa propre norme. script/maintenance/format_python.sh aiguille entre les deux.
#
# target-version borne ce que le formateur ÉCRIT, et non ce qui exécute le
# code. py310 et non la version du venv : PEP 758 autorise depuis 3.14
# « except A, B: » sans parenthèses, et ruff l'écrirait — or les hooks de
# script/git/hooks portent « #!/usr/bin/env python3 » et tournent donc sur le
# Python du système, qu'une distribution livre encore en 3.10.
target-version = "py310"
# 79, la largeur que le dépôt tient déjà. La norme OCA en retient 88, déclarée
# dans les dépôts d'addons qui la suivent.
line-length = 79
# Des dépôts SÉPARÉS, rapatriés par Google Repo : ils portent leur propre
# configuration, et les reformater écrirait dans l'historique d'autrui.
# force-exclude : sans lui, l'exclusion ne vaut que pour les fichiers que ruff
# DÉCOUVRE, et un chemin nommé en argument y échappe — or format_python.sh
# passe les fichiers un par un.
force-exclude = true
extend-exclude = [
"addons",
"odoo*",
"script/OCA_maintainer-tools",
"script/OCA_odoo-module-migrator",
]
[lint]
# Le tri des imports seul : le lint du dépôt reste décrit par .flake8.
select = ["I"]

View file

@ -154,6 +154,8 @@ au [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
- A VM deployed with the cache upstream cut — QEMU form, Proxmox VE, or `deploy_qemu.py --offline` — has npm's security audit turned off (`NPM_CONFIG_AUDIT=false`): it queries a remote service no cache can replay, and failed on every offline install. An online VM keeps its audit
- Verifying a downloaded image no longer needs `--verify`: it runs by default for every distribution that publishes a sum, and `--no-verify` is what skips it — to be kept for offline runs, where a substituted image would otherwise pass unremarked
- `--bios` is refused on an image with no BIOS boot sector, and says why. Forced there, it gave a VM reported « running » with a silent console — the very failure that flag exists to avoid elsewhere
- `make format` picks the formatter from each file's context: an Odoo module keeps isort and black on `py37`, the series still supported going down that far, while this repository's own tooling goes through ruff, configured once in `.ruff.toml`. ruff follows CPython's versions, where black 24.8.0 stops at `py313`, and its import sorting replaces isort; it is also what the OCA standard uses since it left black
- The repositories that Google Repo checks out under `script/` are excluded from that formatting, a named path included: reformatting them would write in someone else's history. `target-version` stays at `py310` there, because the git hooks carry `#!/usr/bin/env python3` and a distribution still ships 3.10 — from 3.14 on, ruff would write `except A, B:` without parentheses
<!-- [fr] -->
@ -170,6 +172,8 @@ au [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
- Une VM déployée l'amont du cache coupé — formulaire QEMU, Proxmox VE, ou `deploy_qemu.py --offline` — a l'audit de sécurité de npm désactivé (`NPM_CONFIG_AUDIT=false`) : il interroge un service qu'aucun cache ne rejoue, et échouait à chaque installation hors ligne. Une VM en ligne garde son audit
- Vérifier une image téléchargée ne demande plus `--verify` : c'est le défaut pour toute distribution qui publie une somme, et `--no-verify` est ce qui la saute — à réserver aux essais hors ligne, où une image substituée passerait autrement sans un mot
- `--bios` est refusé sur une image sans secteur d'amorçage BIOS, et dit pourquoi. Forcé là, il donnait une VM « running » à console muette — la panne même que ce drapeau évite ailleurs
- `make format` choisit le formateur d'après le contexte de chaque fichier : un module Odoo garde isort et black en `py37`, la série la plus ancienne encore supportée, quand l'outillage de ce dépôt passe par ruff, réglé une fois dans `.ruff.toml`. ruff suit les versions de CPython, là où black 24.8.0 s'arrête à `py313`, et son tri d'imports remplace isort ; c'est aussi ce qu'emploie la norme OCA depuis qu'elle a quitté black
- Les dépôts que Google Repo rapatrie sous `script/` sont écartés de ce formatage, chemin nommé compris : les reformater écrirait dans l'historique d'autrui. `target-version` y reste à `py310`, parce que les hooks git portent `#!/usr/bin/env python3` et qu'une distribution livre encore 3.10 — à partir de 3.14, ruff écrirait `except A, B:` sans parenthèses
<!-- [en] -->
## Fixed

View file

@ -77,6 +77,8 @@ au [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
- Une VM déployée l'amont du cache coupé — formulaire QEMU, Proxmox VE, ou `deploy_qemu.py --offline` — a l'audit de sécurité de npm désactivé (`NPM_CONFIG_AUDIT=false`) : il interroge un service qu'aucun cache ne rejoue, et échouait à chaque installation hors ligne. Une VM en ligne garde son audit
- Vérifier une image téléchargée ne demande plus `--verify` : c'est le défaut pour toute distribution qui publie une somme, et `--no-verify` est ce qui la saute — à réserver aux essais hors ligne, où une image substituée passerait autrement sans un mot
- `--bios` est refusé sur une image sans secteur d'amorçage BIOS, et dit pourquoi. Forcé là, il donnait une VM « running » à console muette — la panne même que ce drapeau évite ailleurs
- `make format` choisit le formateur d'après le contexte de chaque fichier : un module Odoo garde isort et black en `py37`, la série la plus ancienne encore supportée, quand l'outillage de ce dépôt passe par ruff, réglé une fois dans `.ruff.toml`. ruff suit les versions de CPython, là où black 24.8.0 s'arrête à `py313`, et son tri d'imports remplace isort ; c'est aussi ce qu'emploie la norme OCA depuis qu'elle a quitté black
- Les dépôts que Google Repo rapatrie sous `script/` sont écartés de ce formatage, chemin nommé compris : les reformater écrirait dans l'historique d'autrui. `target-version` y reste à `py310`, parce que les hooks git portent `#!/usr/bin/env python3` et qu'une distribution livre encore 3.10 — à partir de 3.14, ruff écrirait `except A, B:` sans parenthèses
## Corrigé

View file

@ -77,6 +77,8 @@ to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
- A VM deployed with the cache upstream cut — QEMU form, Proxmox VE, or `deploy_qemu.py --offline` — has npm's security audit turned off (`NPM_CONFIG_AUDIT=false`): it queries a remote service no cache can replay, and failed on every offline install. An online VM keeps its audit
- Verifying a downloaded image no longer needs `--verify`: it runs by default for every distribution that publishes a sum, and `--no-verify` is what skips it — to be kept for offline runs, where a substituted image would otherwise pass unremarked
- `--bios` is refused on an image with no BIOS boot sector, and says why. Forced there, it gave a VM reported « running » with a silent console — the very failure that flag exists to avoid elsewhere
- `make format` picks the formatter from each file's context: an Odoo module keeps isort and black on `py37`, the series still supported going down that far, while this repository's own tooling goes through ruff, configured once in `.ruff.toml`. ruff follows CPython's versions, where black 24.8.0 stops at `py313`, and its import sorting replaces isort; it is also what the OCA standard uses since it left black
- The repositories that Google Repo checks out under `script/` are excluded from that formatting, a named path included: reformatting them would write in someone else's history. `target-version` stays at `py310` there, because the git hooks carry `#!/usr/bin/env python3` and a distribution still ships 3.10 — from 3.14 on, ruff would write `except A, B:` without parentheses
## Fixed

View file

@ -222,12 +222,12 @@ format_code_generator_template:
.PHONY: format_script
format_script:
#.venv.erplibre/bin/isort --profile black -l 79 ./script/ --gitignore
./script/maintenance/black.sh ./script/
.venv.erplibre/bin/ruff check --select I --fix ./script/
.venv.erplibre/bin/ruff format ./script/
.PHONY: format_script_isort_only
format_script_isort_only:
.venv.erplibre/bin/isort --profile black -l 79 ./script/ --gitignore
.venv.erplibre/bin/ruff check --select I --fix ./script/
#########
# log #

View file

@ -16,6 +16,9 @@ selenium
uvloop
python-randomword-fr
isort
# Formatage et tri des imports de l'outillage : il suit les versions de
# CPython, là où black 24.8.0 s'arrête à py313. Voir .ruff.toml.
ruff
pykeepass
cryptography
keyring

View file

@ -2,7 +2,9 @@
Red='\033[0;31m' # Red
Color_Off='\033[0m' # Text Reset
# This will format all python file
# Les MODULES ODOO, et eux seuls : les addons des séries encore supportées
# descendent jusqu'à Python 3.7, d'où la cible. L'outillage du dépôt passe par
# ruff — voir format_python.sh, qui aiguille, et .ruff.toml.
# argument 1: directory or file to format
source ./.venv.erplibre/bin/activate
black -l 79 --preview -t py37 "$@"

View file

@ -1,5 +1,36 @@
#!/usr/bin/env bash
source ./.venv.erplibre/bin/activate
isort --profile black -l 79 "$@"
#./.venv.erplibre/bin/isort --profile black -l 79 "$@"
./script/maintenance/black.sh "$@"
# © 2021-2026 TechnoLibre (http://www.technolibre.ca)
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl)
#
# Un fichier Python, le formateur de SON contexte.
#
# Un module Odoo et un script d'outillage ne suivent pas la même norme et ne
# tournent pas sur le même interpréteur : les addons vivent dans des dépôts
# séparés, dont la communauté fixe le style, quand script/ n'engage que ce
# dépôt. Un réglage unique servait donc mal les deux.
#
# addons/…, odoo*/addons/… isort + black, cible py37 : les séries d'Odoo
# encore supportées descendent jusque-là.
# tout le reste ruff, réglé par .ruff.toml à la racine.
VENV="$(xargs < conf/python-erplibre-venv 2> /dev/null)"
RUFF="./${VENV}/bin/ruff"
for fichier in "$@"; do
case "${fichier}" in
./addons/* | addons/* | ./odoo*/addons/* | odoo*/addons/*)
"./${VENV}/bin/isort" --profile black -l 79 "${fichier}"
./script/maintenance/black.sh "${fichier}"
;;
*)
if [[ ! -x "${RUFF}" ]]; then
echo "ruff absent de ${VENV} : ./script/install/install_erplibre.sh" >&2
exit 1
fi
# Le tri des imports d'abord : il déplace des lignes que le formatage
# remet ensuite à la bonne largeur.
"${RUFF}" check --select I --fix --quiet "${fichier}"
"${RUFF}" format --quiet "${fichier}"
;;
esac
done