Acyclic dependencies principle
"The dependency structure between packages must be a Directed Acyclic Graph ( DAG)." http://ifacethoughts.net
The Acyclic dependencies principle states that when traversing the package dependency graph, there should be no path from a package back to that package. If there is a path back to the original package, there is a cycle in the graph (ie it is not Acyclic). This occurs when package A depends on package B, and package B depends on package A. This is a transitive relationship, so if package B depends on package C, then package C must not depend on package A or B.
This is important from a deployment point of view, as well as from a maintenance perspective. If the dependency structure is a DAG, then building the application is trivially a traversal of the dependency graph. A cyclic dependency graph can result in problems when building the system. (If package A needs package B, but package B needs package A, which should you build first?).
Also, a system with no package cyclic dependencies will be easier to maintain. It will be obvious which packages may be affected by making changes to a specific package; simply traverse the dependency graph from the package that was changed.
The Visitor pattern contains a cyclic dependency. Here, the concrete visitor depends on the interface of the concrete elements it visits. Similarly, the concrete elements must be familiar with interface of all visiting concrete visitors.
- Where a visitor pattern is necessary, the ill effects of cyclic dependency can be mitigated by ensuring that cyclically dependent classes are deployed within the same package.
- Bob Martin suggests a solution to this problem in his paper Acyclic Visitor.
The Acyclic dependencies principle is well suited to Automation. The package structure can be modelled as a directed graph, and can then be tested for cycles using a topological sort algorithm.