Generics + Refletion - Isso funciona?

5 respostas
Marcelo_Magalhaes

Caros amigos,

Estou com uma dúvida se o código abaixo funciona. Posso garantir que o objeto entity SEMPRE terá um método getId().
public void save(T entity)
    {
    	try
    	{
			Method method = type.getMethod("getId", Object.class);
			
			if (method.invoke(entity) == null)
			{
				em.persist(entity);
			}
			else
			{
				em.merge(entity);
			}
		}
    	catch (Exception e)
    	{
			e.printStackTrace();
		}
    }

O que estou tentando fazer é juntar o persist com o merge em um só método no DAO, usando o Id como verificador se o objeto é novo (persist) ou uma alteração (merge).

Abraços a todos.

5 Respostas

nel

Isso no meu ponto de vista chama-se “lambança” (para não dizer outra coisa).
A sua camada abstrata DAO não deve ter preocupação com regra de negócio.
Ela não pode se preocupar em saber se deve dar um persist ou um merge.

Isso é algo que tu deve ter conhecimento a nível de serviço e não de DAO.
O DAO tem por objetivo único trabalhar com as tuas entidades, buscar em base, persistir, atualizar e não efetuar if´s e else´s da vida.
Sem falar que tu deveria buscar exemplos de AbstractDAO no google da vida, vai abrir tua cabeça sobre isso ok?

Abraços.

Marcelo_Magalhaes

nel:
Isso no meu ponto de vista chama-se “lambança” (para não dizer outra coisa).
A sua camada abstrata DAO não deve ter preocupação com regra de negócio.
Ela não pode se preocupar em saber se deve dar um persist ou um merge.

Isso é algo que tu deve ter conhecimento a nível de serviço e não de DAO.
O DAO tem por objetivo único trabalhar com as tuas entidades, buscar em base, persistir, atualizar e não efetuar if´s e else´s da vida.
Sem falar que tu deveria buscar exemplos de AbstractDAO no google da vida, vai abrir tua cabeça sobre isso ok?

Abraços.

Ok, concordo… mas quero saber se funciona??? Eu não sei nem se este método vai ficar no DAO ou no Service… ou qualquer lugar. Quero saber se funciona?

E

A resposta é “teste”.

Hebert_Coelho

A resposta é “teste”. +1

Outra coisa, uma entity precisa ter um campo com @Id mas esse campo não precisa de get/set.

sergiotaborda

Marcelo Magalhaes:
Caros amigos,

Estou com uma dúvida se o código abaixo funciona. Posso garantir que o objeto entity SEMPRE terá um método getId().
public void save(T entity)
    {
    	try
    	{
			Method method = type.getMethod("getId", Object.class);
			
			if (method.invoke(entity) == null)
			{
				em.persist(entity);
			}
			else
			{
				em.merge(entity);
			}
		}
    	catch (Exception e)
    	{
			e.printStackTrace();
		}
    }

O que estou tentando fazer é juntar o persist com o merge em um só método no DAO, usando o Id como verificador se o objeto é novo (persist) ou uma alteração (merge).

Respondendo estritamente à sua pergunta, vc cria uma interface (Entity, por exemplo) com getId() e faz assim

public DAO<T extends Entity> {

 public void save(T entity) { 
         if (entity.getId() == null ){
         // la la la la
          }
} 

}

(pode usar uma classe em vez de interface também)
Isto é a forma de usar generics para dizer que métodos existem em T. Reflection pode funcionar, mas pode não funcionar ( se o cara passar save(new Object()) vai dar erro).
Com extends o compilador garante para vc que apenas classes que herdam de entity podem ser usadas em save(), o que é muito melhor.

Agora, uma nota: testar se o id é ou não nulo não é uma regra de negocio ( o id não é um atributo de negocio) , é válido e comum fazer este teste. Aliás é o que o hibernate faz no saveOrUpdate.

Vc deveria usar um DomainStore diretamente ( o entitymanager) e não este tipo de codigo que vc está tentando fazer. Se passar para o entitymanager ele irá saber o que fazer sem precisar do getId porque ele têm o modelo do objeto e sabe se ele é do domínio ou não. Isto simplifica muito o codigo das suas entidades que não tem que herdar de ninguem.

Criado 4 de dezembro de 2012
Ultima resposta 4 de dez. de 2012
Respostas 5
Participantes 5