Simplify essential complexity; diminish accidental complexity.
Essential complexity represents the difficulty inherent in any problem. For example, photosynthesis is complex by itself; it is inherently complex. Conversely, accidental complexity grows from the things we feel we must build to mitigate essential complexity. Many frameworks and vendor "solutions" are the symptoms of the accidental complexity disease. Frameworks that solve specific problems are useful. Over-engineered frameworks add more complexity than they relieve.
Developers are drawn to complexity like moths to flame, frequently with the same result. Puzzle solving is fun, and developers are problem solvers. Who doesn't like the rush of solving some incredibly complex problem? In large-scale software, though, removing accidental complexity while retaining the solution to the essential complexity is challenging.
How do you do this? Prefer frameworks derived from working code rather than ones cast down from ivory towers. Look at the percentage of code you have in a solution that directly addresses the business problem vs. code that merely services the boundary between the application and the users. Cast a wary eye on vendor driven solutions. They may not be inherently bad, but vendors are the pushers of accidental complexity. Make sure that the solution fits the problem.
It’s the duty of the architect to solve the problems inherent in essential complexity without introducing accidental complexity.