Private readResolve Breaks Inheritance

ID

java.serial_readresolve_must_be_protected

Severity

high

Remediation Complexity

trivial

Remediation Risk

low

Remediation Effort

low

Resource

Reliability

Language

Java

Tags

CWE:1066, reliability

Description

Reports a readResolve() method declared private inside a non-final, non-private class that implements Serializable.

Rationale

readResolve() lets a Serializable class post-process an object right after deserialization, for example to enforce a singleton or validate invariants. If the method is private, it is not inherited: any subclass deserialized through the JVM’s own logic never runs the parent’s resolution step, and the intended custom behavior is silently skipped.

Classes that cannot be subclassed — because they are final or private themselves — are unaffected by this concern and are not reported.

// Bad - subclasses of Session cannot see this method
public class Session implements Serializable {
    private static final long serialVersionUID = 1L;

    private Object readResolve() throws ObjectStreamException {
        return this;
    }
}

Remediation

Declare readResolve() as protected so it remains part of the inherited contract.

// Good
public class Session implements Serializable {
    private static final long serialVersionUID = 1L;

    protected Object readResolve() throws ObjectStreamException {
        return this;
    }
}

© 2026 Xygeni. All rights reserved