DRY is probably my least favourite programming meme. There are far too many overzealous juniors who learned it and have a bee in their bonnet about creating absurd abstractions around any two lines of code (or config) that have vague or imagined similarities, locking in all sorts of annoying indirection.
For me DRY is one of the most important principles for maintainable software. Imagine having to fix a bug at two independent places or having to add or change the same conceptual functionality at two different places (which you may not even be aware, because you don't remember you copied code somewhere else once) Totally unnecessary bugs guaranteed, and ready to be thrown away after some time, because a change will b…
The problem with DRY is when abstractions with currently identical implementations are given a single interface, even though they're logically distinct.
Then, when those distinct abstractions' implementations need to diverge, you've got a rats nest of references to manually pick through and separate out.
Or worse yet , the mistakenly-shared interface becomes parameterized, leading to a horrible mixing of requirements and concepts that may never be untangled if the original intent is lost to time.
Obviously DRY is great when you can consolidate multiple implementations that are actually a single abstraction, but it can really go off the rails if the motivation for the mantra isn't understood.