← Back to Home

Composite Pattern

Compose objects into tree structures to represent part-whole hierarchies. Composite lets clients treat individual objects and compositions uniformly.

What is it?

The Composite pattern allows you to build complex structures from simple objects, using the same interface for both leaves and composites.

Example

interface FileSystemEntity {
  getName(): string;
  display(indent?: string): string;
}

class File implements FileSystemEntity {
  constructor(private name: string) {}

  getName() {
    return this.name;
  }

  display(indent = '') {
    return `${indent}- File: ${this.name}`;
  }
}

class Folder implements FileSystemEntity {
  private children: FileSystemEntity[] = [];

  constructor(private name: string) {}

  add(child: FileSystemEntity) {
    this.children.push(child);
  }

  getName() {
    return this.name;
  }

  display(indent = '') {
    const lines = [`${indent}+ Folder: ${this.name}`];
    for (const child of this.children) {
      lines.push(child.display(indent + '  '));
    }
    return lines.join('
');
  }
}

const root = new Folder('root');
const src = new Folder('src');
const index = new File('index.tsx');
src.add(index);
root.add(src);
console.log(root.display());

Common Uses

  • File system trees
  • UI component hierarchies
  • Organization charts

When to Use

  • You want to treat individual and composite objects the same way
  • You want to represent recursive structures

Caution

  • Can make code harder to understand if hierarchy grows too large
  • Not ideal for flat or non-hierarchical data