RAPPORT D'AUDIT Qt5 → Qt6 / QGIS3 → QGIS4
====================================================================================================

1. RÉSUMÉ GLOBAL
----------------------------------------------------------------------------------------------------
Dossier numérisé : C:\Users\thevandfr\AppData\Roaming\QGIS\QGIS4\profiles\default\python\plugins\plugin_translator
Fichiers Python trouvés : 13
Fichiers modifiés : 11
Fichiers avec correctifs : 14
Fichiers avec résultats : 5
Remplacements automatiques : 57
Résultats critiques (ERREUR) : 0
Avertissements (AVERTISSEMENT) : 43

source qt_compat : C:\Users\thevandfr\AppData\Roaming\QGIS\QGIS4\profiles\default\python\plugins\scan_qt6_compat\qt_compat.py
destination qt_compat : C:\Users\thevandfr\AppData\Roaming\QGIS\QGIS4\profiles\default\python\plugins\plugin_translator\qt_compat.py
statut qt_compat : copied

2. QT5 → STATISTIQUES QT6
----------------------------------------------------------------------------------------------------
2.1 Remplacements automatiques par catégorie

  - Centraliser l'assistant de mise à jour: 12
  - Qt.Checked: 8
  - Qt.Unchecked: 7
  - Qt.UserRole: 6
  - QMessageBox.Yes: 4
  - Qt.ItemIsUserCheckable: 3
  - QMessageBox.No: 2
  - Qt.PartiallyChecked: 2
  - Qt.WindowStaysOnTopHint: 2
  - Réécrire detector_pylupdate vers la version sécurisée de Qt5/Qt6: 2
  - Réécrivez QEvent.LanguageChange en EVENT_LANGUAGE_CHANGE: 2
  - QFile.ReadOnly: 1
  - QFileDialog.ShowDirsOnly: 1
  - QListWidget.NoSelection: 1
  - Qt.AlignLeft -> ALIGN_LEFT: 1
  - Qt.AlignVCenter -> ALIGN_VCENTER: 1
  - Qt.Window: 1
  - Réparation import cassé QApplication.instance(): 1
  - Réécrire la commande pylupdate portable: 1
  - Supprimer shell=True du sous-processus pylupdate: 1

2.2 Correctifs détaillés par règle appliquée

  - Remplacement d'énumération/jeton: 38
  - Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6: 13
  - Supprimer l'assistant local _qt_compat_build_ts_generator_command: 12
  - Ajout/fusion import qt_compat pour alias MSGBOX_*: 3
  - Réécrire detector_pylupdate vers la version sécurisée de Qt5/Qt6: 2
  - Réécrivez QEvent.LanguageChange en EVENT_LANGUAGE_CHANGE: 2
  - Ajout import modules qgis.PyQt: 1
  - Ajouter prend en charge Qt6 après qgisMaximumVersion: 1
  - Incrémenter la version des métadonnées: 1
  - Mettre à jour le bloc de métadonnées : changelog: 1
  - Mettre à jour le bloc de métadonnées : changelog[fr]: 1
  - Qt.AlignLeft -> ALIGN_LEFT: 1
  - Qt.AlignVCenter -> ALIGN_VCENTER: 1
  - Réparation import cassé QApplication.instance(): 1
  - Réécrire la commande pylupdate portable: 1
  - Supprimer shell=True du sous-processus pylupdate: 1

3. RÉSUMÉ DES CONSTATATIONS RESTANTES
----------------------------------------------------------------------------------------------------
Erreurs critiques : 0

Avertissements : 43
  - plugin_translator.py:1125 | Pylupdate potentiellement non portable | pylupdate5
  - plugin_translator.py:1255 | Pylupdate PyQt5 codée en dur | PyQt5.pylupdate_main
  - plugin_translator.py:1255 | Pylupdate potentiellement non portable | PyQt5.pylupdate_main
  - plugin_translator.py:1265 | La commande pylupdate5 n'est pas portable | cmd
  - plugin_translator.py:1265 | python -m PyQt5.pylupdate_main non portable | cmd
  - tools\create_ts_files.py:9 | Pylupdate potentiellement non portable | pylupdate5
  - tools\create_ts_files.py:49 | Pylupdate potentiellement non portable | pylupdate5
  - tools\create_ts_files.py:50 | detect_pylupdate à examiner | Qt5 and Qt6 candidates detected together
  - tools\create_ts_files.py:56 | Pylupdate potentiellement non portable | pylupdate5
  - tools\create_ts_files.py:57 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\create_ts_files.py:77 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\create_ts_files.py:81 | Pylupdate potentiellement non portable | pylupdate5.exe
  - tools\create_ts_files.py:82 | Pylupdate potentiellement non portable | pylupdate5-script.py
  - tools\create_ts_files.py:83 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\create_ts_files.py:109 | Pylupdate potentiellement non portable | pylupdate5.exe
  - tools\create_ts_files.py:209 | Pylupdate potentiellement non portable | pylupdate5
  - tools\create_ts_files.py:241 | Pylupdate potentiellement non portable | pylupdate5
  - tools\i18n_utils.py:32 | Pylupdate PyQt5 codée en dur | PyQt5.pylupdate_main
  - tools\i18n_utils.py:32 | Pylupdate potentiellement non portable | PyQt5.pylupdate_main
  - tools\i18n_utils.py:60 | Pylupdate PyQt5 codée en dur | PyQt5.pylupdate_main
  - tools\i18n_utils.py:60 | Pylupdate potentiellement non portable | PyQt5.pylupdate_main
  - tools\i18n_utils.py:254 | detect_pylupdate à examiner | Qt5 and Qt6 candidates detected together
  - tools\i18n_utils.py:260 | Pylupdate potentiellement non portable | pylupdate5
  - tools\i18n_utils.py:261 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\i18n_utils.py:281 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\i18n_utils.py:285 | Pylupdate potentiellement non portable | pylupdate5.exe
  - tools\i18n_utils.py:286 | Pylupdate potentiellement non portable | pylupdate5-script.py
  - tools\i18n_utils.py:287 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\i18n_utils.py:314 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\i18n_utils.py:315 | Pylupdate PyQt5 codée en dur | pylupdate_main
  - tools\i18n_utils.py:317 | Pylupdate potentiellement non portable | pylupdate5-script.py
  - tools\i18n_utils.py:319 | Pylupdate potentiellement non portable | pylupdate5.exe
  - translate_ts_html_gui_API_google.py:64 | Alias ​​MSGBOX_* utilisé sans importation qt_compat | MSGBOX_NO
  - translate_ts_html_gui_API_google.py:65 | Alias ​​MSGBOX_* utilisé sans importation qt_compat | MSGBOX_YES
  - ts_generator_core.py:132 | Pylupdate potentiellement non portable | pylupdate5
  - ts_generator_core.py:132 | Pylupdate potentiellement non portable | pylupdate5-script.py
  - ts_generator_core.py:132 | Pylupdate potentiellement non portable | pylupdate5.exe
  - ts_generator_core.py:154 | Pylupdate potentiellement non portable | pylupdate5
  - ts_generator_core.py:212 | Pylupdate potentiellement non portable | pylupdate5
  - ts_generator_core.py:223 | Pylupdate potentiellement non portable | pylupdate5
  - ts_generator_core.py:237 | Pylupdate potentiellement non portable | pylupdate5
  - ts_generator_core.py:243 | Pylupdate potentiellement non portable | pylupdate5
  - ts_generator_core.py:247 | Pylupdate potentiellement non portable | pylupdate5

4. AUDIT FICHIER PAR FICHIER
----------------------------------------------------------------------------------------------------

FICHIER : __init__.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 15
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : help\source\conf.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 2
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : metadata.txt
====================================================================================================
Correctifs appliqués : 4
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 5
Règle : Ajouter prend en charge Qt6 après qgisMaximumVersion
Avant:
    [missing line]
Après:
    supportsQt6 = True

Ligne : 6
Règle : Incrémenter la version des métadonnées
Avant:
    version = 1.3.0
Après:
    version = 1.3.1

Ligne : 17
Règle : Mettre à jour le bloc de métadonnées : changelog
Avant:
    changelog = 1.3.0 Fixed a bug under Qgis4
    			1.2.0 Fixed a bug in the translation of multiple sentences
    			1.1.1 Added zone and language icons, display of native language names.
    			1.1.0 Interface improvements, added detection of the plugin's source language, and performance fixes during folder selection. Automatic translation of metadata.txt is now supported.
Après:
    changelog = 1.3.1 : Mise en conformité conjointe Qgis3/Qgis4 - Plugin scan_qt6_compat
    			1.3.0 Fixed a bug under Qgis4
    			1.2.0 Fixed a bug in the translation of multiple sentences
    			1.1.1 Added zone and language icons, display of native language names.
    			1.1.0 Interface improvements, added detection of the plugin's source language, and performance fixes during folder selection. Automatic translation of metadata.txt is now supported.

Ligne : 21
Règle : Mettre à jour le bloc de métadonnées : changelog[fr]
Avant:
    changelog[fr] = 1.2.0 Correction d'un bug dans la traduction des phrases multiples
    				1.1.1 Ajout des icônes de zones et de langues, affichage des noms natifs des langues
    				1.1.0 Améliorations de l'interface, ajout de la détection de la langue source du plugin et correctifs de performances lors de la sélection des dossiers. Prise en compte de la traduction automatique du metadata.txt
Après:
    changelog[fr] = 1.3.1 : Mise en conformité conjointe Qgis3/Qgis4 - Plugin scan_qt6_compat
    				1.2.0 Correction d'un bug dans la traduction des phrases multiples
    				1.1.1 Ajout des icônes de zones et de langues, affichage des noms natifs des langues
    				1.1.0 Améliorations de l'interface, ajout de la détection de la langue source du plugin et correctifs de performances lors de la sélection des dossiers. Prise en compte de la traduction automatique du metadata.txt

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : plugin_translator.py
====================================================================================================
Correctifs appliqués : 13
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 5

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajout/fusion import qt_compat pour alias MSGBOX_*
Avant:
    [imports qt_compat avant ajout] manquants: MSGBOX_NO, MSGBOX_YES
Après:
    [imports qt_compat ajoutés/fusionnés] ajoutés: MSGBOX_NO, MSGBOX_YES

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 68
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

Ligne : 272
Règle : Remplacement d'énumération/jeton
Avant:
    QFile.ReadOnly
Après:
    FILE_READ_ONLY

Ligne : 594
Règle : Réécrivez QEvent.LanguageChange en EVENT_LANGUAGE_CHANGE
Avant:
    QEvent.LanguageChange
Après:
    EVENT_LANGUAGE_CHANGE

Ligne : 642
Règle : Qt.AlignLeft -> ALIGN_LEFT
Avant:
    Qt.AlignLeft
Après:
    ALIGN_LEFT

Ligne : 642
Règle : Qt.AlignVCenter -> ALIGN_VCENTER
Avant:
    Qt.AlignVCenter
Après:
    ALIGN_VCENTER

Ligne : 1071
Règle : Remplacement d'énumération/jeton
Avant:
    QFileDialog.ShowDirsOnly
Après:
    OPTION_SHOW_DIRS_ONLY

Ligne : 1395
Règle : Remplacement d'énumération/jeton
Avant:
    QMessageBox.No
Après:
    MSGBOX_NO

Ligne : 1395
Règle : Remplacement d'énumération/jeton
Avant:
    QMessageBox.Yes
Après:
    MSGBOX_YES

Ligne : 1398
Règle : Remplacement d'énumération/jeton
Avant:
    QMessageBox.Yes
Après:
    MSGBOX_YES

Ligne : 1520
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Window
Après:
    WINDOW

Ligne : 1520
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.WindowStaysOnTopHint
Après:
    WINDOW_STAYS_ON_TOP_HINT

4.2 Constatations restantes

[WARNING] ligne 1125
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 1255
  Rule : Pylupdate PyQt5 codée en dur
  Code : PyQt5.pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 1255
  Rule : Pylupdate potentiellement non portable
  Code : PyQt5.pylupdate_main
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 1265
  Rule : La commande pylupdate5 n'est pas portable
  Code : cmd
  Hint : Sous QGIS4/Qt6, remplacez par un assistant sécurisé Qt5/Qt6.

[WARNING] ligne 1265
  Rule : python -m PyQt5.pylupdate_main non portable
  Code : cmd
  Hint : Sous Qt6, évitez PyQt5.pylupdate_main ; préférez pylupdate6 ou un helper.


FICHIER : plugin_upload.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 12
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : resources.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 2
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : tools\create_ts_files.py
====================================================================================================
Correctifs appliqués : 18
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 12

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajout/fusion import qt_compat pour alias MSGBOX_*
Avant:
    [imports qt_compat avant ajout] manquants: MSGBOX_NO, MSGBOX_YES
Après:
    [imports qt_compat ajoutés/fusionnés] ajoutés: MSGBOX_NO, MSGBOX_YES

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 1
Règle : Réécrire la commande pylupdate portable
Avant:
    cmd = [str(self.pylupdate)] + py_files + ["-ts", str(ts_path)]
Après:
    if self.pylupdate.suffix.lower() == ".py": ...

Ligne : 1
Règle : Supprimer shell=True du sous-processus pylupdate
Avant:
    subprocess.run(cmd, check=True, shell=True)
Après:
    subprocess.run(cmd, check=True)

Ligne : 20
Règle : Réparation import cassé QApplication.instance()
Avant:
    from qgis.PyQt.QtWidgets import (
        QApplication, QWidget, QVBoxLayout, QHBoxLayout, QPushButton,
        QFileDialog, QListWidget, QListWidgetItem, QLabel, QMessageBox, QLineEdit
    )
Après:
    from qgis.PyQt.QtWidgets import (
        QApplication,
        QWidget,
        QVBoxLayout,
        QHBoxLayout,
        QPushButton,
        QFileDialog,
        QListWidget,
        QListWidgetItem,
        QLabel,
        QMessageBox,
        QLineEdit,
    )

Ligne : 34
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

Ligne : 51
Règle : Réécrire detector_pylupdate vers la version sécurisée de Qt5/Qt6
Avant:
    def detect_pylupdate() -> Path:
        import shutil
        found = shutil.which("pylupdate5.exe")
        if found:
            return Path(found)
Après:
    def detect_pylupdate() -> Tuple[Optional[Path], Optional[Path]]:
        """
        Détection pylupdate compatible QGIS 3 (Qt5) et QGIS 4 (Qt6).
    
        Priorité :
        1. pylupdate6 sous Qt6
        2. pylupdate5 sous Qt5
        3. fallback pylupdate_main.py en dernier recours
        """
        from qgis.PyQt.QtCore import QT_VERSION_STR
    
        qgis_prefix = Path(QgsApplication.prefixPath()).resolve()
        apps_root = qgis_prefix.parent
    
        python_candidates = [
            apps_root / "Python312" / "python.exe",
            apps_root / "Python310" / "python.exe",
        ]
        python_exec = next((p for p in python_candidates if p.exists()), None)
        if python_exec is None:
            return None, None
    
        qt_major = int((QT_VERSION_STR or "5").split(".")[0])
    
        qt6_candidates = [
            apps_root / "Python312" / "Scripts" / "pylupdate6.exe",
            apps_root / "Python312" / "Scripts" / "pylupdate6-script.py",
            apps_root / "Python312" / "Lib" / "site-packages" / "PyQt6" / "pylupdate_main.py",
        ]
    
        qt5_candidates = [
            apps_root / "Python312" / "Scripts" / "pylupdate5.exe",
            apps_root / "Python312" / "Scripts" / "pylupdate5-script.py",
            apps_root / "Python312" / "Lib" / "site-packages" / "PyQt5" / "pylupdate_main.py",
        ]
    
        if qt_major >= 6:
            candidates = qt6_candidates
        else:
            candidates = qt5_candidates + qt6_candidates
    
        for pylu in candidates:
            if pylu.exists():
                return python_exec, pylu
    
        return None, None

Ligne : 142
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.WindowStaysOnTopHint
Après:
    WINDOW_STAYS_ON_TOP_HINT

Ligne : 180
Règle : Remplacement d'énumération/jeton
Avant:
    QListWidget.NoSelection
Après:
    NO_SELECTION

Ligne : 189
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.ItemIsUserCheckable
Après:
    ITEM_IS_USER_CHECKABLE

Ligne : 190
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 190
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 191
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.UserRole
Après:
    USER_ROLE

Ligne : 226
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.UserRole
Après:
    USER_ROLE

Ligne : 228
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 274
Règle : Remplacement d'énumération/jeton
Avant:
    QMessageBox.No
Après:
    MSGBOX_NO

Ligne : 274
Règle : Remplacement d'énumération/jeton
Avant:
    QMessageBox.Yes
Après:
    MSGBOX_YES

Ligne : 276
Règle : Remplacement d'énumération/jeton
Avant:
    QMessageBox.Yes
Après:
    MSGBOX_YES

4.2 Constatations restantes

[WARNING] ligne 9
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 49
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 50
  Rule : detect_pylupdate à examiner
  Code : Qt5 and Qt6 candidates detected together
  Hint : Candidats Qt5 et Qt6 détectés ; vérification de la priorité et de la logique de repli.

[WARNING] ligne 56
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 57
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 77
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 81
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5.exe
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 82
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5-script.py
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 83
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 109
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5.exe
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 209
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 241
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.


FICHIER : tools\i18n_utils.py
====================================================================================================
Correctifs appliqués : 3
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 15

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 22
Règle : Ajout import modules qgis.PyQt
Avant:
    [import qgis.PyQt absent]
Après:
    from qgis.PyQt import QtCore

Ligne : 212
Règle : Réécrire detector_pylupdate vers la version sécurisée de Qt5/Qt6
Avant:
    def detect_pylupdate() -> Tuple[Optional[Path], Optional[Path]]:
        """
        Détection pylupdate robuste pour QGIS Windows (OSGeo4W / LTR / Qt5 / Qt6).
        """
Après:
    def detect_pylupdate() -> Tuple[Optional[Path], Optional[Path]]:
        """
        Détection pylupdate compatible QGIS 3 (Qt5) et QGIS 4 (Qt6).
    
        Priorité :
        1. pylupdate6 sous Qt6
        2. pylupdate5 sous Qt5
        3. fallback pylupdate_main.py en dernier recours
        """
        from qgis.PyQt.QtCore import QT_VERSION_STR
    
        qgis_prefix = Path(QgsApplication.prefixPath()).resolve()
        apps_root = qgis_prefix.parent
    
        python_candidates = [
            apps_root / "Python312" / "python.exe",
            apps_root / "Python310" / "python.exe",
        ]
        python_exec = next((p for p in python_candidates if p.exists()), None)
        if python_exec is None:
            return None, None
    
        qt_major = int((QT_VERSION_STR or "5").split(".")[0])
    
        qt6_candidates = [
            apps_root / "Python312" / "Scripts" / "pylupdate6.exe",
            apps_root / "Python312" / "Scripts" / "pylupdate6-script.py",
            apps_root / "Python312" / "Lib" / "site-packages" / "PyQt6" / "pylupdate_main.py",
        ]
    
        qt5_candidates = [
            apps_root / "Python312" / "Scripts" / "pylupdate5.exe",
            apps_root / "Python312" / "Scripts" / "pylupdate5-script.py",
            apps_root / "Python312" / "Lib" / "site-packages" / "PyQt5" / "pylupdate_main.py",
        ]
    
        if qt_major >= 6:
            candidates = qt6_candidates
        else:
            candidates = qt5_candidates + qt6_candidates
    
        for pylu in candidates:
            if pylu.exists():
                return python_exec, pylu
    
        return None, None

4.2 Constatations restantes

[WARNING] ligne 32
  Rule : Pylupdate PyQt5 codée en dur
  Code : PyQt5.pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 32
  Rule : Pylupdate potentiellement non portable
  Code : PyQt5.pylupdate_main
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 60
  Rule : Pylupdate PyQt5 codée en dur
  Code : PyQt5.pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 60
  Rule : Pylupdate potentiellement non portable
  Code : PyQt5.pylupdate_main
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 254
  Rule : detect_pylupdate à examiner
  Code : Qt5 and Qt6 candidates detected together
  Hint : Candidats Qt5 et Qt6 détectés ; vérification de la priorité et de la logique de repli.

[WARNING] ligne 260
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 261
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 281
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 285
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5.exe
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 286
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5-script.py
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 287
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 314
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 315
  Rule : Pylupdate PyQt5 codée en dur
  Code : pylupdate_main
  Hint : Commande pylupdate PyQt5 codée en dur ; sous QGIS4 / Qt6, il est préférable d'utiliser un assistant d'exécution compatible avec Qt5/Qt6.

[WARNING] ligne 317
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5-script.py
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 319
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5.exe
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.


FICHIER : tools\lang_tree.py
====================================================================================================
Correctifs appliqués : 23
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 17
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

Ligne : 209
Règle : Réécrivez QEvent.LanguageChange en EVENT_LANGUAGE_CHANGE
Avant:
    QEvent.LanguageChange
Après:
    EVENT_LANGUAGE_CHANGE

Ligne : 222
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.UserRole
Après:
    USER_ROLE

Ligne : 223
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.ItemIsUserCheckable
Après:
    ITEM_IS_USER_CHECKABLE

Ligne : 224
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 233
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.UserRole
Après:
    USER_ROLE

Ligne : 235
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.ItemIsUserCheckable
Après:
    ITEM_IS_USER_CHECKABLE

Ligne : 238
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 238
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 256
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.UserRole
Après:
    USER_ROLE

Ligne : 259
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 262
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 265
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 267
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 269
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.PartiallyChecked
Après:
    PARTIALLY_CHECKED

Ligne : 281
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 282
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.UserRole
Après:
    USER_ROLE

Ligne : 303
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 304
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Checked
Après:
    CHECKED

Ligne : 305
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 306
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.Unchecked
Après:
    UNCHECKED

Ligne : 308
Règle : Remplacement d'énumération/jeton
Avant:
    Qt.PartiallyChecked
Après:
    PARTIALLY_CHECKED

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : tools\persistence.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 20
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : tools\settings_keys.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 6
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : translate_ts_html_gui_API_google.py
====================================================================================================
Correctifs appliqués : 3
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 2

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajout/fusion import qt_compat pour alias MSGBOX_*
Avant:
    [imports qt_compat avant ajout] manquants: MSGBOX_NO, MSGBOX_YES
Après:
    [imports qt_compat ajoutés/fusionnés] ajoutés: MSGBOX_NO, MSGBOX_YES

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 76
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

[WARNING] ligne 64
  Rule : Alias ​​MSGBOX_* utilisé sans importation qt_compat
  Code : MSGBOX_NO
  Hint : Ajoutez ou fusionnez l'importation depuis qt_compat.

[WARNING] ligne 65
  Rule : Alias ​​MSGBOX_* utilisé sans importation qt_compat
  Code : MSGBOX_YES
  Hint : Ajoutez ou fusionnez l'importation depuis qt_compat.


FICHIER : translation_tester.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 0

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 14
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

Aucune conclusion restante.


FICHIER : ts_generator_core.py
====================================================================================================
Correctifs appliqués : 2
Résultats ERREUR : 0
Résultats AVERTISSEMENT : 9

4.1 Correctifs appliqués

Ligne : 1
Règle : Ajouter un assistant de génération TS sécurisé pour Qt5/Qt6
Avant:
    [missing helper]
Après:
    def _qt_compat_build_ts_generator_command(...): ...

Ligne : 22
Règle : Supprimer l'assistant local _qt_compat_build_ts_generator_command
Avant:
    
    
    def _qt_compat_build_ts_generator_command():
        import shutil
        import sys
        from pathlib import Path
        from qgis.PyQt import QtCore
    
        qt_major = int(QtCore.QT_VERSION_STR.split(".")[0])
    
        if qt_major < 6:
            return [sys.executable, "-m", "PyQt5.pylupdate_main"]
    
        for candidate in ("lupdate", "lupdate6"):
            exe = shutil.which(candidate)
            if exe:
                return [exe]
    
        prefixes = [
            Path(sys.prefix),
            Path(sys.executable).resolve().parent,
            Path(sys.executable).resolve().parent.parent,
        ]
    
        possible = []
        for prefix in prefixes:
            possible.extend([
                prefix / "Library" / "bin" / "lupdate.exe",
                prefix / "bin" / "lupdate.exe",
                prefix / "apps" / "Qt6" / "bin" / "lupdate.exe",
                prefix / "apps" / "qt6" / "bin" / "lupdate.exe",
            ])
    
        for p in possible:
            if p.exists():
                return [str(p)]
    
        raise RuntimeError(
            "No Qt6-compatible lupdate tool was found. "
            "Under QGIS 4, PyQt5.pylupdate_main must not be used."
        )
    
    
Après:
    

4.2 Constatations restantes

[WARNING] ligne 132
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 132
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5-script.py
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 132
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5.exe
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 154
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 212
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 223
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 237
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 243
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.

[WARNING] ligne 247
  Rule : Pylupdate potentiellement non portable
  Code : pylupdate5
  Hint : Sous QGIS4/Qt6, préférez pylupdate6 et évitez shell=True pour les commandes pylupdate.


5. ANNEXE - RÉSUMÉ DES REMPLACEMENTS COMPACTS
----------------------------------------------------------------------------------------------------

Centraliser l'assistant de mise à jour : 12 -> remove local _qt_compat_build_ts_generator_command
QFile.ReadOnly : 1 -> FILE_READ_ONLY
QFileDialog.ShowDirsOnly : 1 -> OPTION_SHOW_DIRS_ONLY
QListWidget.NoSelection : 1 -> NO_SELECTION
QMessageBox.No : 2 -> MSGBOX_NO
QMessageBox.Yes : 4 -> MSGBOX_YES
Qt.AlignLeft -> ALIGN_LEFT : 1 -> ALIGN_LEFT
Qt.AlignVCenter -> ALIGN_VCENTER : 1 -> ALIGN_VCENTER
Qt.Checked : 8 -> CHECKED
Qt.ItemIsUserCheckable : 3 -> ITEM_IS_USER_CHECKABLE
Qt.PartiallyChecked : 2 -> PARTIALLY_CHECKED
Qt.Unchecked : 7 -> UNCHECKED
Qt.UserRole : 6 -> USER_ROLE
Qt.Window : 1 -> WINDOW
Qt.WindowStaysOnTopHint : 2 -> WINDOW_STAYS_ON_TOP_HINT
Réparation import cassé QApplication.instance() : 1 -> QApplication
Réécrire detector_pylupdate vers la version sécurisée de Qt5/Qt6 : 2 -> detect_pylupdate
Réécrire la commande pylupdate portable : 1 -> cmd
Réécrivez QEvent.LanguageChange en EVENT_LANGUAGE_CHANGE : 2 -> EVENT_LANGUAGE_CHANGE
Supprimer shell=True du sous-processus pylupdate : 1 -> subprocess.run


====================================================================================================
RECHARGEMENT DU PLUGIN
====================================================================================================
Plugin rechargé : plugin_translator
Le code Python a été rechargé.
Plugin marqué comme activé dans QSettings : plugin_translator
Métadonnées du gestionnaire de plugins rechargées. Fermez et rouvrez la fenêtre Plugins si elle est déjà ouverte.
Actualisation de l'interface utilisateur : processusÉvénements OK | Actualisation de la fenêtre principale OK | Échec de la mise à jour de l'interface du gestionnaire de plugins : 'QgsPluginManagerInterface' object has no attribute 'update'
Si la fenêtre Plugins est déjà ouverte, fermez-la et rouvrez-la.
Un redémarrage de QGIS peut encore être nécessaire pour certains champs du gestionnaire de plugins.
