BDS
smart-contracts, security-audits, ethereum-solidity

Mettre à niveau les contrats intelligents grâce à des modèles proxy : guide complet

February 23, 2026
12 min
c
Architecture de modèle proxy montrant l'interaction entre le contrat proxy, le contrat d'implémentation et les interfaces utilisateur.

Introduction

Les contrats intelligents sont programmés pour être permanents et immuables une fois qu'ils sont déployés sur un réseau blockchain. Cette immuabilité est une source de sécurité et de confiance, mais elle pose aussi des défis quand les développeurs doivent corriger des bugs ou ajouter de nouvelles fonctionnalités.

Quand des modifications sont nécessaires, les développeurs doivent publier un tout nouveau contrat avec une adresse différente. Même si cette permanence est super pour la sécurité, elle peut être contraignante quand les choses tournent mal ou doivent être améliorées.

L'histoire montre que les failles dans les contrats intelligents peuvent causer des pertes financières énormes. Un exemple marquant, c'est cet incident majeur où des millions de dollars ont été perdus à cause d'une faille exploitable.

Ces incidents montrent à quel point c'est important de pouvoir régler les problèmes de sécurité et les bugs après le déploiement. Rendre les contrats évolutifs permet de corriger les problèmes sans perdre l'état actuel et l'expérience utilisateur, ce qui est un aspect clé de l'évolutivité des contrats intelligents.

Cette capacité peut être importante pour éviter des pertes importantes et garder le système en bon état.

Il y a plein de façons de mettre en place des contrats intelligents évolutifs, comme les modèles de proxy de contrats intelligents et les techniques de séparation des données. Cet article parle surtout de comment rendre les contrats évolutifs en utilisant des modèles de proxy, ce qui est une méthode populaire pour régler ce problème dans le monde du développement blockchain.

Comprendre le modèle proxy

Le modèle proxy est un modèle de conception structurel dans lequel un contrat implémente une interface pour un autre contrat. Cette architecture comporte deux parties principales : le contrat proxy et le contrat d'implémentation.

Au lieu de communiquer directement avec le contrat d'implémentation, l'utilisateur communiquera avec le contrat proxy, qui transmettra ensuite les demandes en conséquence.

Dans cette configuration, le contrat proxy et le contrat d'implémentation ne sont pas modifiés après leur déploiement. Cependant, la possibilité de mise à niveau est assurée en permettant au proxy de faire référence à différents contrats d'implémentation au fil du temps.

Ça veut dire que les utilisateurs peuvent continuer à utiliser la même adresse et la même interface pendant que les fonctionnalités sous-jacentes sont mises à jour. Du point de vue de l'utilisateur, l'application continue de fonctionner parfaitement même si la logique backend change.

Le contrat proxy gère les interactions avec les utilisateurs et stocke toutes les données. Il garde l'adresse du contrat d'implémentation dans un endroit spécial.

Quand les utilisateurs appellent des fonctions sur le contrat proxy, une fonction de secours est appelée. La fonction suivante utilise un mécanisme delegatecall ethereum pour invoquer le code à partir du contrat d'implémentation, mais tout changement d'état est enregistré dans le stockage du contrat proxy.

Principales implémentations de modèles proxy

Modèle de proxy transparent

Le modèle Transparent Proxy intègre la fonctionnalité de mise à niveau dans le contrat proxy lui-même. Le proxy dispose d'une méthode upgradeTo qui sert à mettre à jour l'adresse pointant vers le contrat d'implémentation.

Ça pose un problème potentiel : si le contrat proxy et le contrat d'implémentation contiennent tous les deux une méthode upgradeTo, on ne sait pas trop laquelle appeler quand un utilisateur utilise cette fonction.

Pour résoudre cette ambiguïté, une solution a été trouvée : la décision concernant la personne à qui déléguer est basée sur l'auteur de l'appel du contrat.

Si l'appelant est l'administrateur du proxy, les appels sont gérés par le contrat proxy lui-même. Sinon, les appels sont délégués au contrat d'implémentation. Cette approche garantit que les fonctions sont exécutées clairement et qu'il n'y a pas de confusion entre les opérations administratives et celles des utilisateurs réguliers.

Norme universelle de proxy évolutif

La norme Universal Upgradeable Proxy Standard a une approche différente en mettant la fonctionnalité de mise à niveau dans le contrat d'implémentation, pas dans le proxy. Le proxy délègue tous les appels au contrat d'implémentation, qui a la méthode upgradeTo pour pointer vers les versions plus récentes.

Ce modèle donne aux développeurs plus de contrôle sur le chemin de mise à niveau. Si un développeur décide de ne plus inclure la méthode upgradeTo dans une version future, le contrat est désormais définitivement immuable et ne peut plus être mis à niveau.

Ça peut être utile quand un contrat a été bien testé et que l'équipe de développement veut le figer dans son état final.

Comme la logique de mise à niveau est dans le contrat d'implémentation, la fonction de secours du proxy n'a pas besoin de vérifier si l'appelant est un administrateur avant de déléguer les appels.

Ça rend le modèle plus efficace que le modèle de proxy transparent. Le risque de conflit de noms est aussi éliminé, car la méthode upgradeTo n'existe que dans le contrat d'implémentation.

Modèle de proxy Beacon

Le modèle Beacon Proxy propose une architecture à trois composants : le contrat proxy, un contrat beacon et le contrat d'implémentation. Au lieu de sauvegarder l'adresse de l'implémentation, le proxy sauvegarde l'adresse du contrat beacon.

Le contrat de balise contient à son tour l'adresse du contrat d'implémentation.

Quand un utilisateur appelle le proxy, il va d'abord chercher l'adresse du contrat de balise, puis il va appeler la balise pour avoir l'adresse du contrat d'implémentation. Enfin, il laisse l'appel au contrat d'implémentation.

Cette couche supplémentaire d'indirection a un but bien précis.

Ce modèle est super utile quand plusieurs contrats proxy doivent utiliser la même implémentation. Dans des modèles plus simples, pour mettre à jour l'implémentation, il faudrait mettre à jour l'adresse dans chaque contrat proxy individuellement. Avec le modèle beacon, seul le contrat beacon doit être mis à jour et tous les proxys qui y sont associés pointent automatiquement vers la nouvelle implémentation.

Principales implémentations de modèles proxy

Modèle Diamond Proxy

Le modèle Diamond Proxy résout le problème de la taille limitée des contrats intelligents, qui sont généralement limités à environ 24 kilo-octets. Ce modèle sépare les fonctionnalités en plusieurs contrats plus petits appelés facettes.

Le contrat proxy garde une correspondance entre les sélecteurs de fonction et l'adresse des facettes qui contiennent ces fonctions.

Quand une fonction est appelée sur le proxy, il utilise le sélecteur de fonction pour chercher la facette qui contient la fonction et délègue l'appel de fonction à la facette appropriée.

Les mises à niveau se font en modifiant les adresses des facettes dans le proxy. Ce modèle permet une fonctionnalité totale bien plus grande en répartissant la fonctionnalité sur plusieurs contrats, chaque facette restant en dessous de la limite de taille.

Comparer les approches de modèles proxy

Chaque modèle de proxy a des caractéristiques différentes qui le rendent adapté à différents cas d'utilisation. Les quatre modèles ont besoin d'un contrat de proxy et utilisent la délégation pour transférer les appels vers les contrats d'implémentation.

Le modèle Transparent Proxy place les fonctions de mise à niveau dans le contrat proxy et UUPS place les fonctions de mise à niveau dans le contrat d'implémentation. Le modèle Beacon met la capacité de mise à niveau dans son propre contrat beacon et le modèle Diamond met généralement la capacité de mise à niveau dans les contrats d'implémentation, mais ce n'est pas strictement spécifié.

En ce qui concerne l'immuabilité, les modèles UUPS et Diamond peuvent rendre les contrats immuables de façon permanente en supprimant la fonction de mise à niveau des versions futures. Les modèles Transparent et Beacon n'offrent pas cette flexibilité.

Quand on a affaire à plusieurs proxys, le modèle Beacon a un avantage certain. Avec les modèles Transparent, UUPS et Diamond, chaque proxy doit être modifié individuellement lors de la mise en œuvre d'une nouvelle implémentation.

Avec le modèle Beacon, seul le contrat Beacon doit être mis à jour, et tous les proxys utiliseront automatiquement la nouvelle implémentation.

L'efficacité énergétique varie selon les modèles. Le modèle transparent demande de vérifier si l'appelant est un administrateur avant chaque délégation, ce qui le rend plus coûteux.

UUPS est plus efficace, car il n'a pas besoin de faire cette vérification. Tous les modèles, sauf Diamond, ont des coûts de gaz supplémentaires pour les opérations de recherche en plus.

Tous les modèles, sauf Diamond, sont limités à 24 kilo-octets par contrat. Le modèle Diamond permet à chaque facette d'avoir une taille maximale de 24 kilo-octets, ce qui permet d'avoir une fonctionnalité totale beaucoup plus importante sur plusieurs facettes.

Maîtrisez la sécurité des contrats intelligents

Apprenez des techniques avancées pour créer des contrats sécurisés et évolutifs grâce à nos cours dispensés par des experts.

Considérations importantes et risques

Problèmes de collision de stockage

Les conflits de stockage sont un gros risque quand on met en place des modèles proxy. Les variables des contrats sont stockées dans des emplacements spécifiques et si les variables du contrat proxy et celles du contrat de mise en œuvre sont stockées dans les mêmes emplacements, elles vont se gêner mutuellement.

En plus, si l'ordre des variables dans le contrat d'implémentation change d'une version à l'autre, les emplacements de stockage peuvent être réattribués, ce qui peut abîmer les données.

Contrats d'implémentation non initialisés

Les contrats d'implémentation doivent être initialisés une seule fois via une fonction d'initialisation, qui est un concept similaire à un constructeur dans les contrats traditionnels.

Les développeurs oublient aussi d'initialiser l'implémentation ou oublient d'inclure des protections pour éviter que la fonction d'initialisation soit appelée plus d'une fois.

Quand ça arrive, les attaquants peuvent lancer eux-mêmes la fonction d'initialisation et potentiellement prendre le contrôle du contrat ou manipuler son état.

Incidents de sécurité réels

Un programme de prime aux bogues a trouvé une faille grave dans les contrats proxy de coffre-fort où les contrats d'implémentation n'étaient pas initialisés correctement. Cette faille aurait pu être utilisée par un pirate pour détruire le contrat d'implémentation, rendant les contrats proxy associés inutiles. Dans un autre incident survenu à un certain moment en juillet, des contrats intelligents ont été piratés à cause d'une faille dans le code d'initialisation, où la fonction d'initialisation pouvait être appelée plusieurs fois.

Autres façons de rendre les trucs plus faciles à mettre à jour

Modèle de séparation des données

Une alternative aux modèles proxy est l'approche de séparation des données. Cette approche repose sur l'utilisation de contrats distincts pour le stockage et la logique. Le contrat logique communique avec le contrat de stockage pour lire ou mettre à jour les données.

Même si on peut remplacer le contrat logique par de nouvelles versions, le contrat de stockage est fixe et ne peut pas être modifié. Ça offre un modèle différent pour la mise à niveau, qui peut être utile dans certaines situations.

Niveaux de vérification

Aucun des modèles de proxy couramment utilisés n'a de moyen de vérifier qu'un nouveau contrat d'implémentation est valide avant la mise à niveau.

Les nouvelles versions doivent absolument inclure toute la logique métier nécessaire, les fonctions de secours et les autres composants essentiels.

Pour ça, on peut ajouter une couche de vérification à côté de la couche proxy, de la couche logique métier et de la couche stockage. Cette couche supplémentaire s'assure que les mises à niveau respectent certains critères avant d'être autorisées.

Bonnes pratiques pour les contrats évolutifs

Les développeurs qui conçoivent des contrats évolutifs doivent suivre certaines directives clés pour garantir la sécurité et la fiabilité :

  • Au lieu de ça, utilisez des implémentations bien testées provenant de bibliothèques bien testées qui ont été soigneusement examinées et vérifiées.
  • Assure-toi toujours d'initialiser correctement les contrats d'implémentation et vérifie que les fonctions d'initialisation ne peuvent être appelées qu'une seule fois.
  • N'initialisez jamais les variables d'état lors de leur déclaration ou dans un constructeur, utilisez la fonction d'initialisation pour toute la configuration d'état.
  • Ne change pas l'ordre ou les types des variables d'état quand tu crées de nouvelles versions des contrats d'implémentation.
  • Si de nouvelles variables sont nécessaires, ajoute-les après toutes les variables existantes.
  • Pour les implémentations du modèle Diamond, utilisez des méthodes de stockage spéciales optimisées pour ce modèle.
  • La méthode UUPS est préférable au modèle de proxy transparent quand c'est possible, car elle consomme moins de gaz pour les opérations courantes.
  • Assure-toi que le compte administrateur du proxy est super sécurisé, car c'est lui qui gère le processus de mise à niveau et c'est un point de sécurité super important.
  • Enfin, fais vérifier tous les contrats par des pros expérimentés en sécurité des contrats intelligents avant de les mettre en place.

Dernières réflexions

Les modèles de proxy offrent un super moyen de mettre à niveau les contrats intelligents tout en gardant la même adresse et le même état. Le contrat proxy utilise delegateCall pour passer l'exécution aux contrats d'implémentation, ce qui permet de changer la logique sous-jacente sans toucher à l'interface utilisateur.

Mais, si les contrats évolutifs ne sont pas bien mis en place, ils peuvent créer de gros problèmes de sécurité.

Les développeurs doivent bien réfléchir aux compromis entre les différents types de modèles de proxy, suivre les bonnes pratiques établies et s'assurer que des audits de sécurité appropriés sont réalisés pour créer des contrats intelligents fiables, sécurisés et évolutifs.

Comparaison des modèles de proxy

Quand on compare les différents modèles de proxy, il y a plusieurs trucs à prendre en compte :

Comparaison des modèles de proxy

FonctionnalitéTransparentUUPSBeaconDiamant
Mettre à jour l'emplacementContrat de procurationContrat de mise en œuvreContrat BeaconContrats de mise en œuvre
Immuabilité permanenteNonOuiNonOui
Proxys multiplesMises à jour individuellesMises à jour individuellesMise à jour unique de la baliseMises à jour individuelles
Efficacité énergétiqueCoût plus élevé (vérification administrative)Coût réduitMoyen (recherche supplémentaire)Moyen (recherche par facette)
Limite de taille du contrat24 Ko24 Ko24 Ko24 Ko par facette
Complexité de la mise en œuvreMoyenMoyenMoyenMoyen

Considérations relatives à la sélection des modèles

Points clés à prendre en compte pour choisir un modèle :

  • Tous les modèles ont besoin d'un contrat proxy et utilisent la délégation pour transmettre les appels.
  • Le modèle Transparent Proxy Pattern sert à stocker les fonctions de mise à niveau dans le contrat proxy lui-même.
  • UUPS met les fonctions de mise à niveau dans le contrat d'implémentation.
  • Le modèle Beacon utilise un contrat Beacon distinct pour les mises à niveau.
  • Le modèle Diamond met souvent les fonctions de mise à niveau dans les contrats d'implémentation, mais la spécification ne dit pas qu'il faut faire ça.
  • Seuls les modèles UUPS et Diamond peuvent rendre les contrats définitivement immuables en supprimant la fonction de mise à niveau des versions futures.
  • Le modèle Beacon est parfait si tu as plusieurs proxys à mettre à niveau en même temps, car il suffit de mettre à niveau le beacon et pas chaque proxy.
  • La taille maximale du contrat est de 24 kilo-octets pour les modèles Transparent, UUPS et Beacon.
  • Le modèle Diamond permet à chaque facette d'atteindre une taille maximale de 24 kilo-octets, ce qui permet de prendre en charge des fonctionnalités beaucoup plus importantes.
  • Tous les modèles ont une complexité de mise en œuvre moyenne et il existe des bibliothèques bien établies pour les modèles Transparent, UUPS et Beacon.

FAQ

#proxy patterns
#smart contract upgradeability
#blockchain security
BDS

Pionniers de l'avenir de la technologie blockchain avec des solutions innovantes qui renforcent les entreprises et les individus dans le monde entier.

+1 929 560 3730 (USA)
+44 2045 771515 (Royaume-Uni)
+372 603 92 65 (Estonie)
Comté de Harju, Tallinn, Lasnamäe, Katusepapi tn 6-502, 11412, Estonie

Restez informé

Recevez les dernières actualités blockchain directement dans votre boîte mail.