Páginas

sexta-feira, 22 de novembro de 2013

HIBERNATE

Sobre o Hibernate : 
O Hibernate é um framework ORM - Object Relational Mapping. É uma ferramenta que nos ajuda a persistir objetos Java em um banco de dados relacional. O trabalho do desenvolvedor é definir como os objetos são mapeados nas tabelas do banco e o Hibernate faz todo o acesso ao banco, gerando inclusive os comandos SQL necessários. O Hibernate não cuida apenas do mapeamento desde às classes de Java até as mesas de banco de dados (e de tipos de dados Java até tipos de dados da SQL), mas também proporciona a consulta de dados e facilidades de recuperação que pode significativamente reduzir o tempo de desenvolvimento. Do contrário, consumido com o manual de dados executados em SQL e JDBC.

O presente artigo tem por finalidade apenas apresentar o Framework Hibernate, portanto não foi utilizado nenhuma ferramenta, mas caso queiram realizar alguma aplicação estamos disponibilizando três links que serão uteis. O primeiro corresponde ao Framework Hibernate, o segundo a um banco de dados e o último a um servidor. Espero que gostem, bom aprendizado.

Ferramentas:
Hibernate 4.1
H2 DataBase
Apache Tomcat 6.0


Principais anotações para mapeamento:

O mapeamento objeto relacional utilizando Hibernate pode ser feito a partir de anotações. As anotações podem ser definidas como metadados que aparecem no código fonte e são ignorados pelo compilador. Qualquer símbolo em um código Java que comece com uma @ (arroba) é uma anotação.

@Entity : define uma entidade, e deve ser utilizada em todas as classes que forem mapeadas pelo hibernate.

@Id : define o campo que será o primary key no banco de dados.

@GeneratedValue(strategy = GenerationType.IDENTITY) : indica que deve ser gerado um valor quando for salvar um novo produto. A estratégia utilizada é a IDENTITY,onde o  sequenciamento usa colunas de identidade especial no banco de dados para permitir que o banco de dados atribua automaticamente um id para o objeto quando sua linha é inserida.

@Table(name = "paciente") : permite que você especifique os detalhes da tabela que será usado para manter a entidade no banco de dados. E nos fornece quatro atributos, que lhe permite substituir o nome da tabela, o seu catálogo, e seu esquema, e impor restrições exclusivas em colunas na tabela. Serve para indicar em qual tabela iremos salvar os dados. Se você não usar essa anotação, o Hibernate usa o nome da classe para a tabela. O atributo name refere-se ao nome da tabela.

@Column(name = "cod_paciente") / @Column(name = "cpf", nullable = false, unique = true): é utilizado para especificar os detalhes da coluna à qual um campo ou propriedade será mapeada. Utilizamos para especificar uma coluna da tabela do banco de dados. Se você não mapear a coluna, o nome da propriedade será usado como nome da coluna. Você pode usar anotação coluna com os seguintes atributos mais comumente utilizados: 
name: permite que o nome da coluna a ser especificado explicitamente.
length: permite o tamanho da coluna usada para mapear um valor particular para um valor de cadeia.
unique: permite que a coluna a ser marcado como contendo apenas os valores originais.
nullable: permite que a coluna a ser marcado NOT NULL quando o esquema é gerado.

@Temporal : Informações que representam instantes de tempo são comuns. Em alguns casos há interesse em persistir todo um instante, o que inclui a hora, o minuto e o segundo corrente, juntamente com o dia, mês e ano. Em outros, apenas a data contendo o dia, o mês e o ano. Em outros, tem-se interesse apenas na hora, no minuto e no segundo corrente.
Cada uma das três opções apresentadas acima são representadas, respectivamente, pelos tipos TemporalType.TIMESTAMP,TemporalType.DATE e, por último, TemporalType.TIME. Estes tipos são fornecidos como argumentos para a anotação @Temporal. Convém ressaltar que, por padrão, quando nenhuma anotação é fornecida, é empregada o tipo "mais completo", contendo a data e a hora, ou seja, o equivalente à anotação @Temporal(TemporalType.TIMESTAMP).

@Embedded / 
@Embeddable : Uma entidade pode ser incorporado em outra entidade. Os atributos de uma entidade podem ser atributos comuns de mais de uma entidade. Nesse caso pode haver uma entidade nivelado. E esta entidade embutido pode ser incorporado em mais do que uma entidade. Objetos são sempre gerenciados dentro do ciclo de vida de seus pais. Se o pai é atualizado ou excluído, eles estão atualizados ou excluídos também.
Ex:
Na Classe Java usamos: 
@Embeddable
public class Endereco {
 
 @Column(name="rua")
 private String rua;

E no atributo da outra classe colocamos: 
@Embedded
private Endereco endereco;

@Enumerated(EnumType.STRING) : às vezes pode ser desejável ter um tipo de enumeração Java para representar uma coluna particular numa base de dados. JPA suporta a conversão de dados de banco de dados para tipos enum Java.
Ex:
No atributo da  classe colocamos:
@Enumerated(EnumType.STRING)
 @Column(name="nome")
 private NomePlano nome;


Na classe Enum colocamos:
public enum NomePlano {
 
 UNIMED("Unimed"), AMIL("Amil"), AMS("Ams"), GOLDENCROSS("Golden Cross"), DIX("DIX"), ASSIM("Assim"), SEMPLANO("Sem Plano");
  


@ManyToOne(fetch = FetchType.EAGER) :
Define uma associação de valor único para outra entidade de classe que tem multiplicidade muitos-para- um. Normalmente não é necessário especificar a entidade visada explicitamente , uma vez que geralmente pode ser inferida a partir do tipo de objeto que está sendo referenciado. Você pode usar os seguintes atributos mais comumente utilizados:
fetch: (Opcional) Defini como a associação deve ser carregada . A estratégia EAGER é uma exigência na execução provedor de persistência que a entidade associada deve ser ansiosamente buscada, ou seja, quando você usa o EAGER e dá um get num objeto, ele traz tudo que está dentro do objeto, ou seja, se há um relacionamento 1 para N, no objeto será carregado todas as referências(N) dele. A estratégia LAZY é uma dica para o tempo de execução do provedor de persistência, quando acessamos o objeto ele não traz instantaneamente todas as dependências. Somente quando precisamos do atributo dependente é que a pesquisa (select ou JOIN) é feita, economizando memória.
cascade: As operações que devem ser em cascata para o alvo da associação, por padrão, nenhuma operação é em cascata. Os mais usados são o cascadetype.ALL que é equivalente a cascade = {persistirem, MERGE, remover REFRESH, retire},Cascata todas as operações; e encotramos bastante també o cascadetype.REMOVE que Cascata a operação de remoção.
mappedBy: O campo que possui o relacionamento. Usada para relação bidirecional.

@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, orphanRemoval = true) :
Define uma associação polivalente com multiplicidade um-para-muitos. Se a coleção é definida usando os genéricos para especificar o tipo de elemento, o tipo de entidade de destino associado não precisa ser especificada, caso contrário a classe entidade de destino deve ser especificado. Se a relação é bidirecional, o elemento mappedBy deve ser utilizado para especificar a relação de campo ou a propriedade da entidade que é o dono da relação. Você pode usar os seguintes atributos mais comumente utilizados(Além do fetch, cascade e mappedBy já citados anteriormente):
orphanRemoval: (Opcional) Se aplica à operação de remoção de entidades que tenham sido removidos da relação e cascata a operação de remoção para essas entidades. Quando uma entidade alvo em um-para-um ou um-para-muitos é removido a partir da relação, é muitas vezes desejável a cascata a operação de remoção para a entidade alvo. Essas entidades alvo são considerados "órfãos", e o orphanRemoval atributo pode ser usado para especificar que as entidades órfãs devem ser removidos.

@JoinColumn(name = "paciente_fk") : Especifica uma coluna para juntar uma associação entidade ou coleção de elementos. Usado nas relações um para muitos e muitos para um.
Ex:
@ManyToOne
 @JoinColumn(name = "paciente_fk")
 private Paciente paciente;

@OneToMany(cascade = CascadeType.ALL, orphanRemoval = true)
 @JoinColumn(name = "paciente_fk")
 private List<Plano> planos = new ArrayList<Plano>();


Para ver as classes completas que usei como exemplo clique aqui.


Principais comandos:
persist vs save: O método persist(), não garante que será atributo um id à instância imediatamente, sendo que a associação ocorrerá quando o flush ocorrer. Além disso, ele garante que só irá executar um insert se estiver dentro do contexto de uma transaction. Já o save(), atribui a chave imediatamente, não importando se isso exige um insert (no caso do identity generator) ou se existe um contexto de transação. Isso explica também porque o save() retorna o Id gerado e o persist() é void.

update vs merge: Use update() se você tiver certeza de que a sessão não contém uma instância já persistente com o mesmo identificador e merge( ) se você quiser mesclar suas modificações a qualquer momento, sem levar em conta o estado da sessão.

remove : Remova a instância da entidade.
Ex:
manager.remove(paciente);

find: Localizar por chave primária. Procure uma entidade da classe especificada pela chave primária. Se a instância de entidade está contido no contexto de persistência, ele é retornado de lá.
Ex:
return (Paciente) manager.find(Paciente.class, Long.valueOf(id));

HQL(Hibernate Query Language):
O Hibernate vem com uma poderosa linguagem de consulta (HQL) que é muito parecida com o SQL. No entanto, comparado com o SQL o HQL é totalmente orientado à objetos, e compreende noções de herança, polimorfismo e associações. O HQL oferece ao desenvolvedor todo recurso necessário para trabalhar com um nível de abstração tão alto que fica quase transparente a manipulação com um banco de dados relacional, isso porque o HQL é um “SQL com capa”, ou seja, ao realizar a busca através de um Bean do Java, automaticamente o HQL é transformado em um SQL equivalente, de forma transparente ao desenvolvedor.
Usando HQL: Antes de começar, é importante que você tenha em mente que é necessário ter todo mapeamento do hibernate.cfg.xml pronto, pois o HQL faz consulta a ele para transformar sua Classe em Tabela.
Ex:
Retorna todos os registro da classe Paciente:
select p from Paciente p


Retorna apenas o objeto que satisfaz a condição do cpf:
Query query = manager.createQuery("select p from Paciente p where p.cpf = :cpf");
  query.setParameter("cpf", cpf);

  return (Paciente) query.getSingleResult();



Espero que tenham gostado da nossa pequena explicação. Qualquer dúvida entrem em contato.
Preparamos um pequeno tutorial com uma Aplicação Simples do uso do Framework Hibernate.
Espero que tenham gostado. Até breve.


Bibliografia:
http://www.h2database.com/html/main.html
http://tomcat.apache.org/download-60.cgi
http://www.hibernate.org/
http://www.caelum.com.br/apostila-vraptor-hibernate/persistindo-os-dados-com-o-hibernate/#4-2-sobre-o-hibernate
http://docs.jboss.org/hibernate/core/3.5/reference/pt-BR/pdf/hibernate_reference.pdf
http://docs.jboss.org/hibernate/orm/3.5/reference/pt-BR/html/preface.html
http://docs.jboss.org/hibernate/core/4.0/quickstart/en-US/html_single/
http://docs.jboss.org/hibernate/orm/3.5/reference/pt-BR/html/persistent-classes.html
http://www.javaframework.org/portal/2010/03/17/iniciando-com-hibernate-3-utilizando-annotations/
http://www.futurepages.org/wiki/lib/exe/fetch.php?media=quickstart:hibernate_anotacoes.pdf
http://docs.jboss.org/hibernate/annotations/3.5/reference/en/html_single/
http://www.tutorialspoint.com/hibernate/hibernate_annotations.htm
http://docs.doctrine-project.org/en/2.0.x/reference/annotations-reference.html
https://code.google.com/p/exemplos/wiki/jpaDezenove
http://www.concretepage.com/hibernate/example-embeddable-embedded-hibernate-annotation
http://tomee.apache.org/examples-trunk/jpa-enumerated/
http://docs.oracle.com/javaee/6/api/javax/persistence/ManyToOne.html
http://spigandoeaprendendo.wordpress.com/2012/11/29/quando-usar-o-fetch-lazy-e-o-fetch-eager/
http://uaihebert.com/jpa-onetomany-e-manytoone-unidirecional-e-bidirecional/
http://docs.jboss.org/hibernate/orm/3.6/reference/pt-BR/html/collections.html
https://www.ibm.com/developerworks/community/blogs/fd26864d-cb41-49cf-b719-d89c6b072893/entry/como_criar_relacionamento_onetomany_com_hibernate?lang=en
http://docs.oracle.com/javaee/6/api/javax/persistence/OneToMany.html
http://docs.oracle.com/javaee/6/api/javax/persistence/CascadeType.html
http://docs.jboss.org/hibernate/core/3.5/reference/pt-BR/html/queryhql.html
http://www.devmedia.com.br/introducao-ao-hql-hibernate-query-language/28950
http://docs.oracle.com/javaee/6/api/javax/persistence/EntityManager.html
http://www.linkedin.com/groups/What-is-difference-between-merge-4183182.S.101844747

Nenhum comentário:

Postar um comentário