Atenção: Com as evoluções do Java e práticas modernas, existem alternativas mais seguras e eficientes para lidar com serialização/desserialização. Mas como estamos estudando o livro vamos considerar para aprender. VER NO TÓPICO FINAL SOBRE SERIALIZAÇÃO
Problema do Singleton e Serialização
- Um singleton pode perder sua unicidade se for declarado como Serializable.
- A serialização cria uma nova instância ao desserializar, quebrando a restrição do singleton.
- O método readResolve pode ser usado para substituir a instância desserializada pela instância original.
Vulnerabilidade do readResolve
- Se um singleton tiver campos não transientes, um invasor pode capturar uma referência à instância antes da execução do readResolve.
- Isso permite criar múltiplas instâncias do singleton, contornando a restrição de instância única.
- O ataque pode ser feito utilizando uma classe "ladra" que explora a desserialização circular para obter uma cópia do singleton antes que ele seja resolvido.
Solução mais segura: Usar enum para Singletons
- Enums são implicitamente serializáveis e garantem que só existe uma única instância.
- O Java impede a criação de novas instâncias além das constantes declaradas no enum.
Exemplo seguro:
public enum Elvis {
INSTANCE;
public void sing() { System.out.println("Love me tender"); }
}
Quando ainda usar readResolve?
- Se a classe não pode ser um enum e precisa ser controlada por instância.
- Deve garantir que todos os campos de referência sejam transientes.
- O readResolve deve ter a acessibilidade adequada (privado em classes final).
Conclusão
- Prefira enum para singletons, pois é seguro e simples.
- Se precisar usar readResolve, tome precauções para evitar ataques.
Exemplos de códigos do livro:
Top comments (0)