Clean Code en C# : principes et exemples pratiques
Le code propre (Clean Code) n'est pas qu'un terme à la mode, c'est une compétence fondamentale pour tout développeur professionnel. Dans l'écosystème .NET et C#, où les projets vivent souvent des années et sont maintenus par des dizaines de programmeurs, savoir écrire un code compréhensible et facilement modifiable devient crucial. Dans cet article, nous allons détailler les principes essentiels du Clean Code appliqués à C# et examiner des exemples concrets de leur mise en œuvre.
Pourquoi le code propre est-il important en C# ?
C# est un langage fortement typé, orienté objet, avec un écosystème riche. Cependant, sa puissance peut se transformer en chaos si l'on ne suit pas une certaine discipline. Le code propre réduit le nombre de bugs, accélère l'intégration des nouveaux développeurs et diminue le coût de maintenance. Comme le disait Robert Martin : « La seule façon d'écrire du code rapidement est de bien l'écrire ».
Principe 1 : Des noms explicites
Les noms des variables, méthodes et classes doivent révéler l'intention. N'économisez pas les caractères — un mauvais code nécessite plus de temps pour être compris.
Mauvais exemple
int d; // temps depuis la modificationList<int> lst = new List<int>();void Proc(int a, int b) { ... }Bon exemple (Clean Code)
int elapsedTimeInDays;List<int> customerIds = new List<int>();void CalculateDiscount(decimal basePrice, decimal taxRate) { ... }Règle : Si un nom nécessite un commentaire, c'est qu'il est mauvais. Utilisez camelCase pour les variables et PascalCase pour les méthodes et les classes.
Principe 2 : Des fonctions courtes (SRP au niveau des méthodes)
Chaque fonction doit faire exactement une chose et la faire bien. Si une méthode contient plus de 20 à 30 lignes ou a une imbrication de plus de deux niveaux, c'est un signal pour un refactoring.
Mauvais exemple : la fonction couteau suisse
public void ProcessOrder(Order order){ // Validation if (order == null || order.Items.Count == 0) throw new ArgumentException("Commande invalide");
// Calcul de la remise decimal discount = 0; if (order.Total > 1000) discount = 0.1m; else if (order.Total > 500) discount = 0.05m;
// Sauvegarde en base de données using var db = new AppDbContext(); db.Orders.Add(order); db.SaveChanges();
// Envoi d'email SendEmail(order.CustomerEmail, "Commande reçue");}Bon exemple : séparation des responsabilités
public void ProcessOrder(Order order){ Validate(order); var discount = CalculateDiscount(order.Total); ApplyDiscount(order, discount); SaveOrder(order); SendConfirmationEmail(order);}
private void Validate(Order order){ if (order == null || order.Items.Count == 0) throw new ArgumentException("Commande invalide");}
private decimal CalculateDiscount(decimal total){ if (total > 1000) return 0.1m; if (total > 500) return 0.05m; return 0;}
private void SaveOrder(Order order){ using var db = new AppDbContext(); db.Orders.Add(order); db.SaveChanges();}Principe 3 : Évitez la duplication (DRY)
Le code répétitif est la racine de tous les maux. Si vous copiez un bloc de code plus d'une fois, extrayez-le dans une méthode ou une classe.
Exemple : duplication de logique
// Dans le contrôleur utilisateurif (user.Role == "Admin" || user.Role == "Manager") GrantAccess();
// Dans le contrôleur de rapportsif (user.Role == "Admin" || user.Role == "Manager") ShowReport();Refactoring : encapsulation de la vérification
public static class UserExtensions{ public static bool HasElevatedPermissions(this User user) { return user.Role == "Admin" || user.Role == "Manager"; }}
// Utilisationif (user.HasElevatedPermissions()) GrantAccess();