Refatorando um sistema no qual trabalho, deparei-me com uma situação semelhante a esta.
public class Genero{
private long id;
private String nome;
//gets e sets
}
public class Pessoa{
private long id;
private Genero genero;
//gets e sets
}
Onde Genero é uma entidade do meu domínio que é mapeada para uma tabela Genero no BD.
Sendo que esta tabela tinha registros com o campo NOME preenchido com o seguintes valores "MASCULINO" e "FEMININO".
Neste contexto, havia uma classe com o seguinte código:
if( "MASCULINO".equals( pessoa.getGenero().getNome()) ) ...faz alguma coisa
A saga começou com o fato da magic string "MASCULINO" me incomodar um bocado. Então resolvi criar uma constante a fim de tornar o código mais claro.
public static final NOME_GENERO_MASCULINO = "MASCULINO"
O que deixou o trecho de código da seguinte forma:
if( NOME_GENERO_MASCULINO.equals( pessoa.getGenero().getNome()) ) ...faz alguma coisa
Porém com mais algumas marteladas no código surgiu outra constante.
public static final NOME_GENERO_FEMININO = "FEMININO"
A partir do momento que havia estas duas constantes intimamente relacionadas, resolvi criar uma enumeration para encapsulá-las.
public enum NomeGenero{
MASCULINO,
FEMININO
}
Sendo que o código cliente ficou com a seguinte cara:
if( NomeGenero.MASCULINO.toString().equals( pessoa.getGenero().getNome()) ) ...faz alguma coisa
Bem ... Removi a magic string porém o código ficou maior. Mas o pior de tudo foi que, com a criação da enumeration, ficou claro que o conteúdo da coluna NOME da tabela GENERO estava replicado na enum NomeGenero. Ou seja, a mesma informação em duas "fontes de dados" distintas. BAD SMELL.
Daí contemplei a necessidade de haver somente uma "fonte de dados" e optei por manter a enumeration. As principais razões que me levaram a esta opção foram as seguintes:
1 - O código motivador de tudo isso ganharia clareza e type safety:
if( NomeGenero.MASCULINO == pessoa.getNomeGenero() ) ...faz alguma coisa
2 - Quando precisasse dos possíveis valores de gênero em vez de fazer um select na tabela Genero, o que me custaria processamento no SGBD, tráfego na rede e tudo o mais; bastaria fazer Genero.values() .
A principal razão que me afastaria da opção pela Enumeration é que quando surgisse um gênero novo eu teria que adicioná-lo na enum, para isso deveria alterar a fonte, recompilá-la e por fim realizar o deploy. Sendo que que na alternativa do BD, bastaria adicionar o registro novo na tabela GENERO. Porém, o fato de não surgir um gênero novo na raça humana corriqueiramente garante a estabilidade desta enumeration, o que praticamente anula esse trade off.
Assumindo o risco citado anteriormente, optou-se pela enumeration, o que implicou que a classe Genero e a tabela GENERO deixaram de existir e a classe Pessoa "Enumeration Powered" ficou da seguinte forma:
public class Pessoa{
private long id;
private NomeGenero nomeGenero;
//gets e sets
}
Porém para as coisas funcionarem desta forma o hibernate, que é o ORM que uso, deveria persistir o NomeGenero de Pessoa. Daí surgiram as seguintes questões; "O Hibernate persiste enumeration?"; "Como fazê-lo?"
...To be Continued
Assinar:
Postar comentários (Atom)
Nenhum comentário:
Postar um comentário