Principes SOLID en TypeScript : théorie et pratique de A à Z

Formateur Python en ligne pour débutants

Apprenez Python facilement sans surcharge théorique. Résolvez des tâches pratiques avec vérification automatique et écrivez du code directement dans le navigateur.

Start Course

Introduction : Pourquoi SOLID est important pour le développeur TypeScript

SOLID — ce sont cinq principes fondamentaux de la programmation orientée objet, formulés par Robert Martin (Oncle Bob). Dans le contexte de TypeScript, qui combine le typage statique et la flexibilité de JavaScript, l'application des principes SOLID permet de créer des applications évolutives, testables et facilement maintenables. Dans cet article, nous analyserons chaque principe avec une base théorique et des exemples pratiques en TypeScript.



1. Single Responsibility Principle (SRP) — Principe de responsabilité unique

Théorie

Une classe ne doit avoir qu'une seule raison de changer. Cela signifie que chaque module, classe ou fonction est responsable d'exactement une fonctionnalité.



Pratique en TypeScript

Considérons une violation du SRP avec l'exemple d'une classe qui gère les utilisateurs et l'envoi de notifications :



// ❌ Violation du SRPclass UserManager {  constructor(private name: string, private email: string) {}

saveUser(): void { console.log(`Utilisateur ${this.name} sauvegardé en BD`); }

sendWelcomeEmail(): void { console.log(`Email de bienvenue envoyé à ${this.email}`); }}


Version corrigée avec séparation des responsabilités :



// ✅ Respect du SRPclass User {  constructor(public name: string, public email: string) {}}

class UserRepository { save(user: User): void { console.log(`Utilisateur ${user.name} sauvegardé en BD`); }}

class EmailService { sendWelcomeEmail(user: User): void { console.log(`Email de bienvenue envoyé à ${user.email}`); }}


2. Open/Closed Principle (OCP) — Principe d'ouverture/fermeture

Théorie

Les entités logicielles doivent être ouvertes à l'extension, mais fermées à la modification. En d'autres termes, vous devez pouvoir ajouter de nouvelles fonctionnalités sans modifier le code existant.



Pratique en TypeScript

Exemple avec le calcul de réductions pour différents types de clients :



// ❌ Violation du OCPclass DiscountCalculator {  calculateDiscount(customerType: string, amount: number): number {    if (customerType === 'regular') {      return amount * 0.1;    } else if (customerType === 'premium') {      return amount * 0.2;    } else if (customerType === 'vip') {      return amount * 0.3;    }    return 0;  }}


// ✅ Respect du OCP via polymorphismeinterface DiscountStrategy {  calculate(amount: number): number;}

class RegularDiscount implements DiscountStrategy { calculate(amount: number): number { return amount * 0.1; }}

class PremiumDiscount implements DiscountStrategy { calculate(amount: number): number { return amount * 0.2; }}

class DiscountCalculator { constructor(private strategy: DiscountStrategy) {}

calculate(amount: number): number { return this.strategy.calculate(amount); }}


3. Liskov Substitution Principle (LSP) — Principe de substitution de Barbara Liskov

Théorie

Les objets d'un programme doivent être remplaçables par des instances de leurs sous-types sans altérer la correction du programme. En termes simples : si vous avez une classe de base, tout héritier doit fonctionner correctement partout où la classe de base est utilisée.



Pratique en TypeScript

Exemple classique avec les figures géométriques :



// ❌ Violation du LSPclass Rectangle {  constructor(protected width: number, protected height: number) {}

setWidth(width: number): void { this.width = width; }

setHeight(height: number): void { this.height = height; }

getArea(): number { return this.width * this.height; }}

class Square extends Rectangle { setWidth(width: number): void { this.width = width; this.height = width; // Violation ! }

setHeight(height: number): vo

Blogs

Book Recommendations