Adapter Pattern
Make incompatible interfaces work together through translation
Pattern Overview
🔗 The Adapter Pattern - Interface Compatibility
Allows incompatible interfaces to work together by providing a wrapper that translates one interface to another. Perfect for integration!
- Core Problem Solved:
- Integrate incompatible interfaces without modifying existing code
- Wrap third-party libraries with consistent APIs
- Bridge legacy systems with modern applications
- Enable code reuse across different interface requirements
- Object Adapter: Composition-based adapter using existing objects
- Class Adapter: Inheritance-based adapter (less common in JS/TS)
- Function Adapter: Simple function-based interface translation
- Real-World Applications:
- API wrappers and gateway adapters
- Database ORM adapters for different databases
- Payment gateway integration layers
- Legacy code integration with modern systems
- Third-party library wrapper implementations
- File system adapters across platforms
- Modern Usage Examples:
- React component wrappers for different UI libraries
- GraphQL adapters for REST APIs
- Node.js stream adapters
- Cloud provider SDK adapters
Examples:
Legacy printer integration
Input:
new PrinterAdapter(legacyPrinter).print('Hello World')Output:
LEGACY PRINT: HELLO WORLD (with job counting)Weather API adaptation
Input:
weatherAdapter.getWeatherData()Output:
{ temperature: 75, description: 'sunny', humidity: 60, timestamp: Date }Payment gateway unification
Input:
stripeAdapter.processPayment(10.00, 'USD')Output:
{ success: true, transactionId: 'stripe_abc123' }Concepts
interface translationwrapper patterncompatibility layer
Complexity Analysis
Time:O(1)
Space:O(1)
Implementation
object-adapter
Time: O(1) | Space: O(1)
// Target interface our application expects
interface ModernPrinter {
print(document: string): void;
isReady(): boolean;
getJobCount(): number;
}
// Legacy class we need to adapt
class LegacyPrinter {
public printOldWay(text: string): void {
console.log(`LEGACY PRINT: ${text.toUpperCase()}`);
}
public getStatus(): string {
return "READY_TO_PRINT";
}
}
// Adapter that makes legacy printer work with modern interface
class PrinterAdapter implements ModernPrinter {
private jobCount: number = 0;
constructor(private legacyPrinter: LegacyPrinter) {}
public print(document: string): void {
// Translate modern call to legacy method
this.legacyPrinter.printOldWay(document);
this.jobCount++;
}
public isReady(): boolean {
// Translate legacy status to boolean
return this.legacyPrinter.getStatus() === "READY_TO_PRINT";
}
public getJobCount(): number {
return this.jobCount;
}
}
// Usage
const legacyPrinter = new LegacyPrinter();
const adapter = new PrinterAdapter(legacyPrinter);
adapter.print("Hello World"); // Works with modern interface
console.log(adapter.isReady()); // true
console.log(adapter.getJobCount()); // 1