private ChainSpecification flatten(Resolver<ChainSpecification> allChainSpecifications,
Deque<ComponentId> path) {
path.push(componentId);
Map<String, ComponentSpecification> resultingComponents = componentsByName(componentReferences);
Map<String, Phase> resultingPhases = new LinkedHashMap<>(phases);
for (ComponentSpecification inheritedChainSpecification : inheritance.chainSpecifications) {
ChainSpecification inheritedChain =
resolveChain(path, allChainSpecifications, inheritedChainSpecification).
flatten(allChainSpecifications, path);
mergeInto(resultingComponents,
filterByComponentSpecification(
filterByName(inheritedChain.componentReferences, names(componentReferences)),
inheritance.excludedComponents));
mergeInto(resultingPhases, inheritedChain.phases);
}
path.pop();
return new ChainSpecification(componentId, inheritance.flattened(), resultingPhases.values(),
new LinkedHashSet<>(resultingComponents.values()));
}