Unité 8 / 12

Refactoring et gestion technique de la dette

Gains :

  • Possibilité de mettre en place un filet de sécurité de test qui capture le comportement actuel avant la refactorisation
  • Capacité à demander à l'IA de petites transformations en une seule étape, préservant le comportement, et à valider chaque étape
  • Capacité à identifier et prioriser la dette technique dans le contexte commercial

Le refactoring consiste à améliorer la structure interne d'un code sans modifier son comportement externe : le rendre plus lisible, plus simple, plus maintenable. La dette technique, en revanche, est un compromis de conception fait dans l'intérêt d'une solution rapide et remboursé « avec intérêts » au fil du temps : chaque coin que vous coupez aujourd'hui se traduira par un ralentissement ou un bug demain. L'intelligence artificielle est un assistant puissant qui accélère les tâches de refactoring répétitives et mécaniques ; Mais il existe une règle d’or en matière de refactoring, et l’IA seule ne peut la garantir : le comportement ne doit pas changer.

Dans cette unité, nous apprenons comment effectuer un refactoring sécurisé avec l'IA : petites étapes réversibles, protection avec des tests, détection des odeurs de code et priorisation de la dette technique. Le point critique est le suivant : ce sont les tests réussis, et non la parole de l'IA, qui prouvent que le comportement est préservé.

La règle d'or du refactoring : le comportement reste constant

Ce qui rend le refactoring dangereux, c'est de changer de comportement sans le savoir en disant « je m'améliore ». Supprimer un cas limite lors de la simplification d'une condition, rompre l'ordre lors de la transformation d'une boucle, manquer un effet secondaire lors du fractionnement d'une fonction : tout cela produit un code "épuré" mais cassé.

C'est pourquoi les tests sont une condition préalable au refactoring : avant de modifier, vous devez disposer de tests qui capturent le comportement existant. Ces tests constituent un « filet de sécurité » ; Si vous cassez accidentellement quelque chose pendant la refactorisation, ils se briseront et vous avertiront. Si vous n'avez pas de tests, écrivez d'abord des tests qui corrigent le comportement existant (comme nous l'avons appris dans l'unité 5) - c'est là que l'IA prend un bon départ.

Attention : le refactoring assisté par l'IA sans testnet est l'une des sources de bugs les plus insidieuses. Il est facile de dire « j'ai préservé le comportement » ; La preuve en est que les mêmes tests passent avant et après le changement.

Étape par étape : flux de refactorisation sécurisé

  1. Mettez en place le filet de sécurité. Qu'il y ait des tests qui capturent le comportement actuel du code que vous allez refactoriser ; Sinon, notez-les d’abord (et regardez-les passer).
  2. Nommez l’odeur. Qu’améliorez-vous et pourquoi ? "Cette fonction fait 3 choses", "la même logique se répète à 4 endroits", "les noms sont trompeurs".
  3. Demandez de petites étapes en une seule étape. Demandez à l'IA une seule transformation (par exemple, « divisez simplement cette fonction en deux »), pour ne pas réécrire l'intégralité du fichier.
  4. Exécutez les tests. Après chaque étape. Si c'est vert, continuez, si c'est rouge, reprenez-le.
  5. Lisez Diff. Confirmez ligne par ligne que le changement préserve effectivement le comportement ; Il peut y avoir un dérapage logique lorsque l’on dit que l’IA n’est « qu’une structure ».
  6. Mélanger en petits morceaux. Les PR de refactorisation ponctuels importants sont à la fois risqués et non révisables.

Trois mini-étuis

Cas 1 — Fonction de 220 lignes divisée en toute sécurité. Une équipe disposait d’une fonction de traitement des commandes de 220 lignes. Les 14 premiers tests ont été écrits (avec l'aide de l'IA) pour capturer le comportement actuel, ils ont tous réussi. Ensuite, la fonction a été divisée en 5 fonctions plus petites étape par étape par l'IA ; Des tests ont été effectués après chaque étape. Deux tests ont été interrompus en une seule étape – l’IA avait raté le retour dans un cas limite. Les tests ont détecté ce problème immédiatement et l'ont corrigé. Sans le réseau, l’erreur aurait pu aller jusqu’à la production.

Cas 2 — Catastrophe sans testnet. Un autre développeur a "nettoyé" un module de calcul de date qui n'avait aucun test avec l'IA. Le code avait l'air meilleur, mais il calculait incorrectement l'année bissextile ; Le bug est apparu deux semaines plus tard avec une plainte d'un client. La perte a largement dépassé le temps gagné grâce à la refactorisation. Leçon : refactoriser sans tester est un pari.

Cas 3 — Priorisation de la dette technique. Une équipe a attribué à l’IA un arriéré d’une trentaine de points « améliorables » et a fait noter chacun d’entre eux sur un axe « fréquence de changement × risque × effort ». Dans le tableau résultant, un module laid et rarement touché était en réalité une faible priorité, tandis qu'un module de complexité moyenne qui changeait fréquemment était une priorité élevée. L’équipe a dirigé son énergie au bon endroit.

Quatre modèles copiables

Détection et priorisation des odeurs de code :

Répertoriez les « odeurs » des candidats à la refactorisation dans ce code : fonction longue, répétition (DRYViolation), nom trompeur, condition profondément imbriquée, effet secondaire caché, nombre magique. Pour chacun : emplacement, pourquoi le problème, petite étape suggérée, risque estimé (faible/moyen/élevé). NE CHANGEZ PAS le code pour l'instant, planifiez simplement.{{code}}

Transformation en une étape qui préserve les comportements :

Faites JUSTE ceci : {{conversion unique, par ex. Divisez cette fonction en 3 fonctions nommées plus petites}}. MODIFIEZ le comportement visible, la signature et les valeurs de retour. Écrivez en 1 phrase pourquoi tout ce que vous avez modifié préserve le comportement.{{code}}

Filet de sécurité avant refactor (tests de caractérisation) :

Écrire des tests qui capturent le comportement ACTUEL de cette fonction (correct ou non) ; le but est de détecter si le comportement change pendant la refactorisation. Incluez les entrées typiques + Edge. Écrivez les attentes en fonction de la sortie actuelle de la fonction.{{function}}

Génération d’enregistrements de dette technique (arriéré) :

Versez la liste d'odeurs suivante dans un tableau de priorisation : substance, zone affectée, fréquence de changement (ma connaissance : {{...}}), risque, effort estimé, priorité recommandée. Mettez ceux à fort impact et à faible effort en haut. {{smell_list}}

Invite faible/Invite forte

Faible : "Nettoyez ce code et améliorez-le."
Fort : "Divisez cette fonction de 90 lignes en 3 fonctions plus petites avec une seule responsabilité, sans modifier son comportement externe et sa signature. Gardez les effets secondaires (écritures de base de données) dans l'ordre actuel. J'ai des tests, le comportement doit rester le même. Donnez la différence et expliquez en une phrase pourquoi chaque division préserve le comportement. [code]"

Version puissante ; Elle nécessite une seule transformation spécifique, impose explicitement une contrainte de comportement et de signature et exige une justification. Des demandes vagues telles que « faire mieux » conduisent à des changements incontrôlés et risqués.

Type de refactorisation

Fiabilité de l'IA

Prérequis

renommer

haut

La portée est-elle correcte ?

Division des fonctions

moyen-élevé

Testnet est un incontournable

Partager la répétition

moyen

La différence de comportement peut être cachée

Changement d'algorithme/de structure

faible

Tests approfondis + validation humaine

Réaménagement architectural

faible

Dirigé par l’humain et soutenu par l’IA

Gérer la dette technique, pas la réinitialiser

La dette technique n’est pas entièrement mauvaise ; Parfois, emprunter consciemment (pour faire face à une livraison) est la bonne décision. L’objectif n’est pas d’éliminer la dette, mais de la rendre visible et gérable. L’IA est rapide pour détecter et prioriser les dettes, mais décider « quelle dette doit être payée et laquelle doit être abandonnée » nécessite un contexte commercial : à quelle fréquence ce module change-t-il, combien de personnes est-il concerné, quel est le risque ? Cette décision est prise par l'équipe qui connaît la base de code et le produit ; L'IA clarifie simplement les options.

Astuce : séparez votre PR de refactorisation des PR qui impliquent un changement de comportement. Pouvoir dire « ce PR n'est qu'un refactoring, le comportement est le même » facilite l'enquête et vous permet d'affiner rapidement la cause si un problème survient.

Erreurs courantes

  • Refactoring sans testnet. Il ne vous reste rien pour prouver que le comportement est préservé.
  • Cela signifie "effacer tout le fichier". Des changements importants et incontrôlés masquent l’erreur et ne peuvent pas être examinés.
  • Accepter Diff sans le lire. L’IA a peut-être échappé à la logique lorsqu’elle a dit « juste une structure ».
  • Confondre refactoring et changement de comportement. Faire les deux dans le même PR rend impossible le suivi des causes profondes.
  • J'essaie de réparer chaque odeur. Un code laid qui change rarement est souvent peu prioritaire ; Allouez de l’énergie à l’endroit qui change fréquemment.

En résumé

La seule règle du refactoring est que le comportement reste constant, et les tests en sont la preuve. L'IA est puissante pour détecter les odeurs de code, les transformations en une étape et la priorisation de la dette technique ; mais vous devez mettre en place le filet de sécurité, exécuter les tests et lire le diff après chaque étape. Faites de petits pas réversibles ; distinguer le refactoring du changement de comportement ; et laissez l’équipe qui connaît le contexte commercial décider quelle dette payer.

Tâche de candidature

Choisissez une fonction de votre base de code qui vous semble longue ou complexe. Imprimez d'abord les tests qui capturent son comportement actuel avec le modèle « filet de sécurité » et voyez s'ils réussissent tous. Ensuite, faites refactoriser la fonction d'une seule manière (par exemple en la divisant en deux) avec le modèle « transformation en une étape préservant le comportement » et exécutez à nouveau les tests. Si un test échoue, découvrez pourquoi ; Si cela ne casse pas du tout, lisez la différence ligne par ligne pour confirmer que le comportement est bien conservé.

liste de contrôle

  • [ ] Je sais que le refactoring ne devrait pas changer le comportement et il existe des tests pour le prouver.
  • [ ] Je mets en place un filet de sécurité qui détecte le comportement actuel avant de refactoriser.
  • [ ] Je veux de petites transformations en une seule étape grâce à l’IA, pas de grandes transformations ponctuelles.
  • [ ] Après chaque étape, j'exécute les tests et lis le diff.
  • [ ] Je continue de refactoriser les relations publiques séparément des relations publiques de changement de comportement.
  • [ ] Je donne la priorité à la dette technique en fonction du contexte commercial, sans essayer aveuglément de la réduire à zéro.