Different kinds of compatibility
By abuckley on Mar 19, 2007
Given version 1.0 of an interface, adding a method to produce version 1.1 is:
- a binary-compatible change
- Pre-existing binaries (i.e. clients compiled against interface 1.0) continue to link against the changed type (i.e. interface 1.1).
- a behavior-compatible change
- Pre-existing binaries (i.e. clients compiled against interface 1.0) do not use the new method so do not rely on its return values or side-effects.
- not a source-compatible change
- Pre-existing sources (i.e. implementations of interface 1.0) will not compile against the changed type (i.e. interface 1.1).
- not a migration-compatible change
- Sources that migrate to the new type (i.e. to use interface 1.1) will not link against the old type (i.e. interface 1.0).
Migration compatibility is the least understood and the most interesting. It concerns how a type is used, and is discussed in JLS 4.7 in the context of generics. It essentially means that:
- if a library is updated, pre-existing clients should continue to link with it
- if a client is updated, pre-existing libraries should continue to link with it
Adding a method to an interface is not migration-compatible because a client updated to use interface 1.1 will receive a NoSuchMethodError if it calls a 1.1-only method on a class that implements 1.0.