Most developers are familiar with circular dependencies - when module A depends on module B, and module B depends on module A. Build systems catch these easily, and we know to avoid them. However, there's a more subtle form of circular dependency that builds successfully but creates the same architectural problems: conceptual circular dependencies.
Note
This article is adapted from my contribution to LY Corporation's internal "Review Committee Report" series, where we share knowledge gathered from code reviews to maintain high development productivity. I've rewritten it here to share with the broader software engineering community.


