in packages/metro/src/DeltaBundler/traverseDependencies.js [410:468]
function removeDependency<T>(
parentModule: Module<T>,
absolutePath: string,
graph: Graph<T>,
delta: Delta,
// We use `canBeRemovedSafely` set to keep track of visited
// module(s) that we're sure can be removed. This will skip expensive
// inverse dependency traversals.
canBeRemovedSafely: Set<string> = new Set(),
): void {
const module = graph.dependencies.get(absolutePath);
if (!module) {
return;
}
module.inverseDependencies.delete(parentModule.path);
// Even if there are modules still using parentModule, we want to ensure
// there is no circular dependency. Thus, we check if it can be safely removed
// by tracing back the inverseDependencies.
if (!canBeRemovedSafely.has(module.path)) {
if (
module.inverseDependencies.size &&
!canSafelyRemoveFromParentModule(
module.inverseDependencies,
module.path,
graph,
canBeRemovedSafely,
delta,
)
) {
return;
}
}
delta.deleted.add(module.path);
// Now we need to iterate through the module dependencies in order to
// clean up everything (we cannot read the module because it may have
// been deleted).
Array.from(module.dependencies.values())
.filter(
dependency =>
!delta.deleted.has(dependency.absolutePath) &&
dependency.absolutePath !== parentModule.path,
)
.forEach(dependency =>
removeDependency(
module,
dependency.absolutePath,
graph,
delta,
canBeRemovedSafely,
),
);
// This module is not used anywhere else!! we can clear it from the bundle
graph.dependencies.delete(module.path);
}