The same way you design interfaces. If you can write good interfaces then you can write good base classes, its all about the contract between methods. Inheritance gets a bad rap because most programmers used it with classes that were never written to have interface contracts and therefore they create unintended coupling. Intended coupling is a good thing though, so as long as you have the same discipline when creating base classes as you have when creating interfaces then inheritance isn't an issue.
The difference is that in one case, it is impossible to cause this error and in the other case (with contracts between methods) we now have to rely people on understanding what they are doing. Looking hat Java's hashCode&equals, I think history has shown that it is maybe not a good idea to rely on that too much.