The <code>@Deprecated</code> Annotation in Java

@Deprecated marks an API element (class, method, field, constructor) as something callers should stop using. The compiler emits a warning on every use; IDEs typically strike through the name.

Basic

@Deprecated
public void oldCompute(int x) { ... }

Java 9+ β€” since and forRemoval

@Deprecated(since = "2.0", forRemoval = true)
public void oldCompute(int x) { ... }
  • since β€” the version when deprecation was introduced (documentation).
  • forRemoval = true β€” this will disappear in a future release; the compiler warning is stronger (-Xlint:removal escalates to error).

Always explain in Javadoc

/**
 * @deprecated since 2.0. Use {@link #compute(Options)} instead β€”
 *             it accepts a full options object and validates input.
 */
@Deprecated(since = "2.0", forRemoval = true)
public void oldCompute(int x) { ... }

The annotation says "don't use". The Javadoc @deprecated tag says why and what to use instead β€” essential for callers.

Deprecation lifecycle

  1. Add @Deprecated + Javadoc in release N (soft deprecation).
  2. Update all internal callers in the same release.
  3. Add forRemoval = true in release N+1 (hard deprecation).
  4. Delete in release N+2 (major version).

Suppressing the warning

@SuppressWarnings("deprecation")
public void callOld() {
    api.oldCompute(5);
}

Suppress only at the smallest scope (a single call, a single method) and document why you haven't migrated yet.

Common mistakes

  • No Javadoc @deprecated tag β€” leaves callers guessing what to use instead.
  • Suppressing globally β€” hides the problem at scale. Leave warnings visible.
  • Removing without forRemoval first β€” breaks downstream builds with no warning cycle.

Related

Pillar: Java annotations. See also @SuppressWarnings.