segunda-feira, 26 de abril de 2010

Um pouquinho do gigante, JPA

Uma Breve pincelada doJPA

Bom, nos conceitos mais "primários", serei bem objetivo, tentarei focar um pouco mais nos mapeamentos.

Então, vamos lá...

O que é JPA?
Java Persistence API.
Uma API de persistencia que possui amplo suporte pela maioria dos grandes players do mercado. (apache, Oracle, JBoss, etc).

ORM = Mapeamento Objeto Relacional.

E quais as principais funcionalidades do JPA?

* Padronizar o Mapeamento Objeto-Relacional
* Utilizar POJO's ao invés de Entity Beans.
* Pode ser utilizado com JSE e JEE.
* Suporta a utilização de diferentes Providers.
* Suporta herança, polimorfismo.

Tudo bem, até o momento, falamos um pouquinho de alguns conceitos relativamente importantes, e agora vamos começar colocar a "mão-na-massa".

Pequena receita de bolo que poderá ser seguida.
1) Download do JPA Provider (http://jpa.hibernate.org)
2) Preparar banco de dados e driver JDBC (http://www.mysql.com/downloads/mysql/)
3) Mapeamento Objeto-Relancional (ORM)
4) Configurar arquivo persistence.xml
5) Implementar aceso a dados via EntityManager

Modelo Relacional



Acima temos um pequeno exemplo de um modelo relacional, com 2 tabelas. Agora vamos fazer o mapeamento entre delas.


Acima, montamos um mapeamento simples entre as duas tabelas. (A classe cliente não foi criada, por isso está sublinhada de vermelho... rs)

Vamos dar "nomes aos bois", o que usamos para criar este mapeamento.

@Entity => com esta anotação (annotations) dizemos que esta classe Pedido, é uma entidade.
obs.: Entidade, é um objeto que pode ser persistido.

@Table => Especifica o nome da tabela no banco de dados. Caso fosse necessário, ainda poderíamos ter passado em qual schema esta tabela estava localizada (name = "pedido", schema = "venda")

@Column => Mapeia um atributo ou uma propriedade (getter) a um campo do banco de dados. Aceita diversas opções de validações.

@Id => Mapeia uma chave primária simples. Podemos gerar a chave automaticamente caso necessite.

@Embeddable => Define que uma classe pode fazer parte de uma entidade
Podemos imaginar a tabela, itemPedido, recebendo as chaves da tabela produto e da tabela pedido, e o mapeamento ficar assim:


Relacionamentos:

@ManyToOne , @OneToMany, @ManyToMany

Agora alguns recursos, que poderão nos ajudar bastante se usados corretamente.

@Version => Define uma coluna para armazenar a informação de versão para o controle de lock otimista. Este recurso, é interessantíssimo, pois podemos imaginar um cenário que duas pessoas estão trabalhando em um mesmo 'formulário', o de cadastro de pessoas, e coincidentemente, estão atualizando dados da mesma pessoa, o Fulano de Tal. A João terminou a sua atualização primeiro que o Pedro, como nosso mapeamento está corretinho, o Pedro irá receber uma Exception, dizendo algo do tipo: "outra transação".

Operações em Cascata:
Persist: Quando uma entidade é persistida, todas as outras nas coleções tbm são.
Merge: Quando uma entidade desconectada é atualizada, todas as outras entidades na coleção são atualizadas.
Remove: Quando uma entidade existente é removida, todas as outras na coleção tbm são.
ALL: Todas a regras anteriores.


Uma das funcionalidades que acho mais interessantes, são os métodos de Callback, quando usados corretamente, podem facilitar bastante a  vida .

> PostLoad, PostPersist, PostRemove, PostUpDate
> PrePersist, PreRemove, PreUpdate

Podem ser utilizados para adicionar funcionalidades extras, como validações, atualizações de tabelas auditadas, etc.
Em um próximo post, falaremos com mais detalhes dos tão Famosos Métodos de Callback.

Cenas para os próximos capítulos: Consultas Estáticas, Consultas Dinâmicas, Criação de Objetos, Configuração do Persistence.xml,

E para concluirmos, fica claro que o JPA nos provê uma API simples e padronizada de persistência, e o uso de annotations simplifica e muito a configuração das entidades.

Vou ficando por aqui, e espero que o Post seja de grande valia.

quinta-feira, 15 de abril de 2010

Façade/Facade [Design Pattern]

Façade

A idéia principal do Façade, é oferecer uma Interface única para o conjunto de interfaces de um subsistema.

Um problema clássico é: Em um determinado contexto, um cliente precisa saber muitos detalhes do Subsistema.


No cenário acima, o cliente tem acesso a todos os componentes do subsistema. E neste caso, o trabalho que ele teria seria absurdamente grande, pois, teria que conhecer todos os componentes, detalhadamente, e ter que controlar todos os acessos ‘no braço’, sem falar que, uma manutenção daria a maior dor de cabeça.

Com o uso do Façade, facilmente resolvemos este problema. Pois como já foi dito, ele oferece uma interface única para acesso ao subsistema, além de reduzir a complexidade da comunicação entre o cliente e as demais classes utilitárias.

Solução:


A estrutura apresentada, é bastante simples, a classe que construirá o Façade, deverá oferecer os recursos suficientes para que seus clientes possam usar o subsistema adequadamente, lembrando que, sem precisar de conhecer as interfaces de seus componentes.

Para este  padrão, existe inúmeras maneiras de representá-lo, mas o que importa mesmo, é que o cliente apenas utilize os objetos da classe façade, deixando toda a responsabilidade de acesso/manipulação aos outros componentes pra ela.

Pequeno Exemplo do Façade em Java.



Mas quais as vantagens de se utilizar este padrão?

    *  Proteger o cliente das complexidades dos componentes do subsistema
    * Acoplamento fraco, entre o subsistema e os clientes
    * Redução de dependências de compilação
    * Maior portabilidade

E para finalizar, Fachadas freqüentemente são implementadas como Singleton. (cenas para o próximo capítulo).

quarta-feira, 14 de abril de 2010

Coleções/Collections

Vamos iniciar com apenas uma prévia do que são as coleções.

Podemos definir que coleção é uma estrutura de dados na qual os objetos são armazenados. Esta coleção pode crescer ou diminuir dinamicamente.

Em java 5, a estrutura de conjuntos nos fornece listas, conjuntos, mapas e filas.Vamos detalhar um pouco mais a seguir, primeiro vamos ver como fica a estrutura das coleções e dos maps.


Vendo rapidamente estes diagramas, é possivel já fazer a nossa primeira análise:
É muito fácil confudir o Collection com Collections. Mas qual a diferença?

Collections é uma classe, possui métodos utilitários estáticos, enquanto Collection é uma Interface com as declarações dos métodos comuns à maioria dos conjuntos.

De uma forma objetiva, como ficaria este primeiro diagrama?
Collection é uma Interface, onde possui métodos como add, remove, addAll, removeAll entre outros, no nosso contexto, ela seria a Interface 'Pai'.

Tendo como filhos, temos as Interfaces Set, List e Qeue. Todas estas estendem a Interface pai.
Detalhando um pouco de cada 'Filho' do Collection.

Interface Set: Dá importância a exclusividade, não permitindo registros duplicados

Tem como seus 'descendentes':

HashSet => Conjunto Set, não classificado e não ordenado.
LinkedHashSet => Quando a ordem da iteração for importante, essa classe é a ideal para usar, é uma versão ordenada do HashSet
TreeSet => É um dos 2 conjuntos ordenados (outro TreeMap). Mantem os registros na sua ordem natural, mas você pode personalizar isso usando o Comparable ou Comparator.
 
Interface List: Ao contrário do Set, o List permite duplicatas.

ArrayList => um array, como o próprio nome diz. conjunto ordenado por indice. não classificado. Proporciona uma iteração rápida. Prefira esta lista a LinkedList, quando isso for requisito.
 Vector => semelhante ao ArrayList, mas seus métodos são sincronizados para garantirem a segurança com Threads.
LinkedList => Ordenado pela posição no índice.

Interface Qeue: FIFO, primeiro a entrar, primeiro a sair

PriorityQueue => a idéia dessa classe, é criar uma prioridade na manipulação dos elementos.

--------------------------

Interface MAP: o MAP trabalha com chave e valor. Cada chave é mapeada com um valor específico. É importante ressaltar, que tanto a chave quanto o valor, são objetos.

HashMap => Não classificado e não ordenado. a ordema na iteração não é a preocupação dessa classe.
HashTable => Permite tanto chaves e valores nulos.
TreeMap => Conjunto Map classificado. Permite a personalização na ordem  de iteração por meio do Comparable ou Comparator.

E aqui finalizamos as Coleções.

Bom, espero poder ter ajudado com algumas informações.