class Node {
  
  constructor(name) {
    this.name = name;
    this.edges = [];
  }

  addEdge(node) {
    this.edges.push(node);
  }
}

const a = new Node('a');
const b = new Node('b');
const c = new Node('c');
const d = new Node('d');
const e = new Node('e');

a.addEdge(b);
a.addEdge(d);
b.addEdge(c);
b.addEdge(e);
c.addEdge(d);
c.addEdge(e);
// Circular dependency
c.addEdge(b);

function depResolve(node, resolved, visited) {
  visited.push(node);
  for (edge of node.edges) {
    if (!resolved.includes(edge)) {
      if (visited.includes(edge)) {
        throw new Error(`Circular dependency in ${node.name} -> ${edge.name}`);
      }
      depResolve(edge, resolved, visited);
    }
  }
  resolved.push(node);
}

let resolved = [];
let visited = [];

depResolve(a, resolved, visited);

for (node of resolved) {
  console.log(node.name);
}