Functions, Scope & Object Model
Object Composition
Composition builds behavior by combining smaller capabilities rather than relying on deep inheritance. JavaScript makes composition natural because objects and functions are flexible runtime values.
- Composition favors small capabilities
- Decorators wrap behavior without changing the original
- Dependency injection is composition
- Mixins are composition with sharp edges
- Composition is easier to test when boundaries are explicit
function withRetry(service, retries = 3) {
return {
async save(data) {
let lastError
for (let attempt = 0; attempt < retries; attempt++) {
try {
return await service.save(data)
} catch (err) {
lastError = err
}
}
throw lastError
},
}
}| Strategy | Strength | Weakness |
|---|---|---|
| Class inheritance | Shared API and polymorphism | Can become rigid/deep |
| Composition | Flexible behavior assembly | Needs clear boundaries |
| Decorator | Wrap behavior locally | Too many wrappers can obscure flow |
| Mixin | Reuse method groups | Name collisions and hidden assumptions |