RFR: 8145461 changes to @Deprecated annotation
Stuart Marks
stuart.marks at oracle.com
Wed Mar 30 01:44:08 UTC 2016
On 3/29/16 3:54 PM, Stephen Colebourne wrote:
> I am pleased to see the simpler form of the API move forward.
Great! Thanks for the quick review.
> However, I feel that condemed() as a boolean does not provide the key
> piece of information necessary - the expected version of removal. I
> would counter-propose that condemed() be replaced by
> expectedDeletion(), a String with the same version semantics as
> since(). While occasionally, the deletion version will be wrong or
> need to be pushed back, in most cases it will be correct. What it does
> do is provides a much better sense to users as to what is going to
> happen.
>
> @Deprecated(since="9", expectedDeletion="11)
> public void myBadBadMethod() {...}
Yes, this came up in the discussion after the JEP was initially posted in the
Autumn of last year. We considered this, and in some draft APIs there was an
element called "until" with semantics similar to what you suggest. Unfortunately
it didn't make the cut. It turns out there are a bunch of problems with
specifying and using such a thing in practice.
One issue is, how does one talk about the future? Two obvious answers are in
terms of calendar dates and version numbers.
Martin's reply illustrates one issue with calendar dates.
Another issue with calendar dates is that, for the JDK, and many other projects,
there are sustaining lines of development that overlap in time with
feature-oriented lines of development. APIs would most likely be removed in the
feature line, but not in a sustaining line, but you can't tell that by looking
at a date. Or maybe it would be both, but you'd need more information to specify
that.
The more likely alternative is to specify some kind of version string, either
the first version where the removal is to occur, or the last version through
which the condemned API is supported. This seems sensible enough, but I don't
agree with the statement that "in most cases it will be correct."
Let's consider some "revisionist" history. :-)
Suppose we're working on JDK 1.6, we have the annotation with an
expectedDeletion element, and we have an API we need to get rid of because it's
incompatible with Jigsaw. We might therefore annotate the API as follows
(remember, this is in JDK 1.6):
@Deprecated(since="1.6", expectedDeletion="1.7")
There did end up being a 1.7 release ("Java 7") but didn't have Jigsaw in it as
originally planned. [1] So we might decide to revise the annotation in 1.7 as
follows:
@Deprecated(since="1.6", expectedDeletion="1.8")
If this thing really conflicts with Jigsaw, which clearly didn't ship in 1.8,
this would be wrong again. So in 1.8 we'd revise it once again:
@Deprecated(since="1.6", expectedDeletion="1.9")
And now maybe this time it really will be removed. But the version number is
wrong again; it's not "1.9" but instead according to JEP 223 [2] the version is
now "9".
The changing of the expectedDeletion value undoubtedly will cause some temporary
confusion. However, the main problem is that we've now littered the historical
record with a bunch of misinformation. This has the potential to cause confusion
for an indefinite period of time.
In addition, there is a general policy at Oracle against making any definite
statements about future versions of products.
So, maybe this an Oracle-specific thing about not talking about the future, and
maybe it's a JDK-specific thing that things change around so much from release
to release. Shouldn't there be some provision for other libraries to specify
information about the expected deletion version?
We considered that too. The problem is, as a matter of policy, the JDK wouldn't
use it at all! For all deprecated APIs in the JDK, the expectedDeletion value
would be the empty string. Now the problem is that the JDK is trying to define
some attribute that it won't use itself, for external libraries to use. It might
make sense if there were some clear consensus across different libraries about
what could be put here, but I don't think there is. Should it be the first
version where removal is expected? Or the last version there the API is
guaranteed present? Or should be a date instead of a version?
Now the attribute is reduced to being a string in a library-specific format
specifying some information with library-specific semantics. At that point it's
adding so little value that it no longer belongs in the JDK.
If external libraries really want this, they can put this information in the
javadoc text, or they can define their own annotations.
s'marks
[1] http://mreinhold.org/blog/rethinking-jdk7
[2] http://openjdk.java.net/jeps/223
More information about the jdk9-dev
mailing list