A apresentação está carregando. Por favor, espere

A apresentação está carregando. Por favor, espere

Entity beans BMP Persistência explícita Ricardo Cavalcanti Jobson Ronan

Apresentações semelhantes


Apresentação em tema: "Entity beans BMP Persistência explícita Ricardo Cavalcanti Jobson Ronan"— Transcrição da apresentação:

1 Entity beans BMP Persistência explícita Ricardo Cavalcanti roc3@cin.ufpe.br Jobson Ronan jrjs@cin.ufpe.br

2 2 Introdução  Entity beans são objetos persistentes  Sincronizam seu estado através um mecanismo de persistência  Dois tipos de gerenciamento de persistência  Bean Managed Persistence  Container Managed Persistence

3 3 Persistência  Serialização  Facilidade de leitura e gravação  Dificuldade de consultas à base  Alternativas  Bancos de dados relacionais (JDBC)  Bancos de dados Orientados a objeto  Mapeamento Objeto relacional

4 4 O/R Mapping  Decompor os objetos em campos de uma tabela ISBNAutorTitulo 0471208310MARINESCU, FLOYDEJB DESIGN PATTERNS 0321278658BECK, KENTEXTREME PROGRAMMING EXPLAINED - EMBRACE CHANGE 8575220470TELES, VINICIUS MANHAES EXTREME PROGRAMMING Classe Livro String ISBN String autor String titulo instância: Livro ISBN = 0321278658 Autor = “BECK, KENT” Titulo = “EXTREME PROGRAMMING...”

5 5 Entity bean  Session beans modelam tarefas realizadas pelo sistema  Entity beans modelam as entidades  Representam dados  Session beans stateful não representam dados!  Independente da forma de armazenamento  Dois termos distintos  Entity bean instance: os dados na memória (instância da classe do Entity Bean)  Entity bean data: os dados fisicamente armazenados no banco

6 6 Mais diferenças entre Session e Entity  Entity beans  têm ciclo de vida independente da aplicação cliente  têm identidade e estado visível para o cliente  são concorrentes

7 7 Componentes do Entity bean  Além de: interface Home ou LocalHome, interface Remote ou Local, deployment descriptor, classe EJB  Mapeamento da classe à uma definição de entidade de um esquema de banco de dados  métodos especiais que lidam com a sincronização do EntityBean com o banco de dados  Um entity bean tem uma classe Primary Key que permite identificar sua instância

8 8 Primary Key  Identifica o entity bean unicamente  Uma classe PK deve ser serializável e têm  Pelo menos um construtor público sem argumentos  Atributos públicos que formam a chave  Métodos equals e hashcode  String e Wrapper classes podem ser usados

9 9 Exemplo: Primary Key public class AccountPK implements java.io.Serializable { public String accountID; public AccountPK(String id) { this.accountID = id; } public AccountPK() { } public String toString() { return accountID; } public int hashCode() { return accountID.hashCode(); } public boolean equals(Object account) { return ((AccountPK) account).accountID.equals(accountID); }

10 10 Características do Entity bean  Tolerante a falhas  Podem ser reconstituídos após a queda do servidor  Basta ler os dados novamente!  Ciclo de vida muuuuuito longo  Antes mesmo da aplicação pensar em ser feita já existem Entity beans  Dados legados

11 11 Sincronia  A sincronia com a base permite pensar instance e data com um só.  Container controla a sincronia  Todas as classes implementam métodos que realizam essa atualização  void ejbLoad()  lê os dados da base para dentro do entity bean  void ejbStore()  grava os dados do entity bean na base

12 12 ejbLoad e ejbStore Container/Server Instância de Entity bean 1:ejbLoad() 4:ejbStore() 2:Lê da base5: grava na base 3: Métodos de negócio Base de dados

13 13 Concorrência  Entity beans são concorrentes  Múltiplas instâncias podem representar o mesmo dado  Melhorar performance  O Container controla a sincronia através de transações

14 14 Pooling  Para otimizar recursos  Economizar tempo de criação  ejbActivate()  Adquirir recursos  ejbPassivate()  Largar recursos cliente Free Pool

15 15 Pooling e sincronismo Container Instância do bean 1:ejbStore() 2:ejbPassivate() 1:ejbLoad() 2:ejbActivate()

16 16 Tipo de persistência  Bean-managed persistence (BMP)  UPDATE no ejbStore, SELECT no ejbLoad e INSERT no ejbCreate (com um BD relacional)  Container-managed persistence (CMP)  O container gera código para garantir a sincronia com a base

17 17 Criando e removendo beans  Entity beans são dados, portanto  Criar um bean = inserir dados na base  Remover um bean = remover dados  Se você tiver o seguinte ejbCreate() no bean public AccountPK ejbCreate(String id, String owner)...  Você deve ter o seguinte create() na Home public Account create(String id, String owner)...  O bean retorna a chave primária para o container, que acha o dado utilizando-a e entrega ao cliente um objeto que implementa a Component interface.  Para destruir um bean: remove() na Home ou na Component interface  ejbRemove() é o correspondente no bean. Ele destrói o dado, mas preserva o bean para ser reciclado

18 18 Localizando entity beans  Entity Beans podem ser localizados quando já existirem  Todo bean pode ser localizado através de sua chave primária  Métodos find() adicionais podem ser criados para localizar beans de acordo com outros critérios  Finder methods na home interface  No home: EJBObject findXXX(...)  No EJB: PK ejbFindXXX(...)  Deve existir pelo menos o findByPrimaryKey()

19 19 Métodos find  Todos devem declarar que lançam FinderException  Métodos de retorno simples devem retornar uma referência de EJBObject ou EJBLocalObject, na interface Home  Lançam ObjectNotFoundException, caso não encontrem o EJB  Métodos com retorno múltiplo devem retornar uma Collection de chaves primárias  Retornam a Collection vazia caso não encontre nada

20 20 Modificando sem EJB  Você pode mudar diretamente na base  As mudanças serão refletidas no Entity bean, porém...  Problemas de cache podem ocorrer: evite!

21 21 Entity Context  Estende EJBContext  Através dele pode-se  Obter o EJBObject ou o EJBLocalObject associado  Obter a chave primária  getPrimaryKey() é essencial em ejbLoad() e ejbRemove() para descobrir qual a instância que será carregada ou removida, respectivamente PK EJBObjec t EJBLocal Object EntityContext

22 22 Classe do bean  Métodos da interface Home  Para cada create () da Home, um par ejbCreate / postCreate com a mesma assinatura  Para cada find da remote um ejbFind correspondente  Para cada “home method” xxx () um ejbHomeXxx  Métodos da Component interface  Todos os criados por você  Métodos da interface EntityBean  ejbActivate e ejbPassivate  ejbLoad e ejbStore  ejbRemove  setEntityContext e unsetEntityContext

23 23 Métodos da interface Home  PK ejbCreate  Atua como construtor do bean, inserindo na base de dados  Tipo de retorno deve ser a PK  void ejbPostCreate  Chamado pelo container após o ejbCreate  Pode ser utilizado para passar referências de outros beans para o seu bean  Pode ser vazio  ejbFindXXX  Localiza os beans  Retorna a Component interface ou Collection, para retornar múltiplos beans  Pode haver vários, apenas o ejbFindByPrimaryKey é obrigatório  ejbHomexxx  Um método da interface home

24 24 Métodos da interface EntityBean  ejbLoad  Deve conter query SELECT ou equivalente e em seguida atualizar os atributos do bean com os dados recuperados  Use context.getPrimaryKey() para saber qual a chave primária do bean a ser lido  ejbStore  Deve conter query UPDATE ou equivalente e gravar no banco o estado atual dos atributos do objeto  ejbRemove  Chamado antes que os dados sejam removidos do banco  Deve conter query DELETE ou equivalente  Use context.getPrimaryKey() para saber qual a chave primária do bean a ser removido

25 25 Métodos da interface EntityBean  ejbPassivate  Chamado antes da passivação do bean  ejbActivate  Chamado logo após a ativação do bean  setEntityContext  Chamado após a criação da instância no pool.  O contexto passado deve ser gravado em variável de instância pois pode ser usado para obter a chave primária da instância atual  unsetEntityContext  Destrói a instância (será recolhida pelo GC). Isto destrói o objeto, mas não o entity bean (os dados)

26 26 Exemplo: Interface do Componente public interface Account extends EJBObject { public void deposit(double amt) throws AccountException, RemoteException; public void withdraw(double amt) throws AccountException, RemoteException; public double getBalance() throws RemoteException; public String getOwnerName() throws RemoteException; public void setOwnerName(String name) throws RemoteException; public String getAccountID() throws RemoteException; public void setAccountID(String id) throws RemoteException; }

27 27 Exemplo: Interface Home public interface AccountHome extends EJBHome { Account create(String accountID, String ownerName) throws CreateException, RemoteException; public Account findByPrimaryKey(AccountPK key) throws FinderException, RemoteException; public Collection findByOwnerName(String name) throws FinderException, RemoteException; public double getTotalBankValue() throws AccountException, RemoteException; }

28 28 Exemplo: Classe do Bean public class AccountBean implements EntityBean { protected EntityContext ctx; private String accountID; // PK private String ownerName; private double balance; // Getters e Setters public String getAccountID() {...}... // Métodos de negócio public void deposit(double amount) {...}... // Métodos do ciclo de vida public void ejbActivate() {...}... // Métodos de Home public AccountPK findByPrimaryKey(AccountPK pk) {} // Métodos de persistência public void ejbLoad() {...}... }

29 29 Exemplo: Acesso via DataSource private Connection getConnection() throws Exception { try { Context ctx = new InitialContext(); javax.sql.DataSource ds =(javax.sql.DataSource) ctx.lookup("java:comp/env/jdbc/ejbPool"); return ds.getConnection(); } catch (Exception e) { System.err.println("Could not locate datasource:"); e.printStackTrace(); throw e; }

30 30 Exemplo: Ciclo de vida public void setEntityContext(EntityContext ctx) { System.out.println("setEntityContext called"); this.ctx = ctx; } public void unsetEntityContext() { System.out.println("unsetEntityContext called"); this.ctx = null; } public void ejbPassivate() { System.out.println("ejbPassivate () called."); } public void ejbActivate() { System.out.println("ejbActivate() called."); }

31 31 Exenplo: Métodos de negócio public void deposit(double amt) throws AccountException { balance += amt; } public void withdraw(double amt) throws AccountException { if (amt > balance) { throw new AccountException("Cannot withdraw "+amt+"!"); } balance -= amt; } // Getter/setter methods on Entity Bean fields public double getBalance() { return balance; } public void setOwnerName(String name) { ownerName = name; } public String getOwnerName() { return ownerName; }

32 32 Exemplo: ejbFindByPrimaryKey public AccountPK ejbFindByPrimaryKey(AccountPK key) throws FinderException { PreparedStatement pstmt = null; Connection conn = null; try { conn = getConnection(); pstmt = conn.prepareStatement ( "select id from accounts where id = ?"); pstmt.setString(1, key.toString()); ResultSet rs = pstmt.executeQuery(); rs.next(); return key; } catch (Exception e) { throw new FinderException(e.toString()); } finally { con.close();... } }

33 33 Exemplo: ejbCreate public AccountPK ejbCreate(String accountID, String ownerName) throws CreateException { PreparedStatement pstmt = null; Connection conn = null; try { this.accountID = accountID; this.ownerName = ownerName; this.balance = 0; conn = getConnection(); pstmt = conn.prepareStatement("insert into accounts "+ "(id, ownerName, balance) values (?, ?, ?)"); pstmt.setString(1, accountID); pstmt.setString(2, ownerName); pstmt.setDouble(3, balance); pstmt.executeUpdate(); return new AccountPK(accountID); } catch (Exception e) { throw new CreateException(e.toString()); } finally { con.close();... } } public void ejbPostCreate(String accountID, String ownerName) { }

34 34 Exemplo: ejbFindByOwnerName public Collection ejbFindByOwnerName(String name) throws FinderException { PreparedStatement pstmt = null; Connection conn = null; Vector v = new Vector(); try { conn = getConnection(); pstmt = conn.prepareStatement ("select id from accounts where ownerName = ?"); pstmt.setString(1, name); ResultSet rs = pstmt.executeQuery(); while (rs.next()) { String id = rs.getString("id"); v.addElement(new AccountPK(id)); } return v; } catch (Exception e) { throw new FinderException(e.toString()); } finally { con.close();... } }

35 35 Exemplo: ejbHomeGetTotalBankValue public double ejbHomeGetTotalBankValue() throws AccountException{ PreparedStatement pstmt = null; Connection conn = null; try { conn = getConnection(); pstmt = conn.prepareStatement ("select sum(balance) as total from accounts"); ResultSet rs = pstmt.executeQuery(); if (rs.next()) { return rs.getDouble("total"); } } catch (Exception e) { e.printStackTrace(); throw new AccountException(e); } finally {...} throw new AccountException("Error!"); }

36 36 Exemplo: ejbRemove public void ejbRemove() throws RemoveException AccountPK pk = (AccountPK) ctx.getPrimaryKey(); String id = pk.accountID; PreparedStatement pstmt = null; Connection conn = null; try { conn = getConnection(); pstmt = conn.prepareStatement ("delete from accounts where id = ?"); pstmt.setString(1, id); if (pstmt.executeUpdate() == 0) { throw new RemoveException("..."); } } catch (Exception ex) { throw new EJBException("...", ex); } finally {...conn.close()... } }

37 37 Exemplo: ejbStore public void ejbStore() { PreparedStatement pstmt = null; Connection conn = null; try { conn = getConnection(); pstmt = conn.prepareStatement ("update accounts set ownerName = ?, balance = ? where id = ?"); pstmt.setString(1, ownerName); pstmt.setDouble(2, balance); pstmt.setString(3, accountID); pstmt.executeUpdate(); } catch (Exception ex) { throw new EJBException("...", ex); } finally {...conn.close()... } } Sempre lance EJBException quando algo sair errado em ejbStore() e ejbLoad()

38 38 Exemplo: ejbLoad public void ejbLoad() { AccountPK pk = (AccountPK) ctx.getPrimaryKey(); accountID = pk.accountID; PreparedStatement pstmt = null; Connection conn = null; try { conn = getConnection(); pstmt = conn.prepareStatement ("select ownerName, balance from accounts where id = ?"); pstmt.setString(1, accountID ); ResultSet rs = pstmt.executeQuery(); rs.next(); ownerName = rs.getString("ownerName"); balance = rs.getDouble("balance"); } catch (Exception ex) { throw new EJBException("...", ex); } finally {...conn.close()... } }

39 39 Exemplo: ejb-jar.xml Account examples.AccountHome examples.Account examples.AccountLocalHome examples.AccountLocal examples.AccountBean Bean examples.AccountPK False jdbc/ejbPool javax.sql.DataSource Container Account * Required

40 40 Exemplo: jboss.xml Account account/AccountHome jdbc/ejbPool java:/DefaultDS

41 41 Patterns e Entity beans  DAO  Abstrai e encapsula o acesso a fontes de dados  Transfer Object  Antes chamado de Value Object  Encapsula dados de negócio

42 42 DAO – Data Access Object  Contexto  acesso a dados persistentes.  Problema  acoplamento entre lógica de negócios e lógica de acesso a dados  Código SQL junto do código de negócios

43 43 DAO – Data access object // all imports required // exceptions not handled in the sample code public class UserAccountEJB implements EntityBean { // All EJB methods like ejbCreate, ejbRemove go here // Business methods start here public UserDetails getUserDetails(String userId) { // A simple query for this example String query = "SELECT id, name, phone FROM userdetails WHERE name = " + userId; InitialContext ic = new InitialContext(); datasource = (DataSource)ic.lookup("java:comp/env/jdbc/DataSource"); Connection dbConnection = datasource.getConnection(); Statement stmt = dbConnection.createStatement(); ResultSet result = stmt.executeQuery(queryStr); // other processing like creation of UserDetails object result.close(); stmt.close(); dbConnection.close(); return(details); } }

44 44 DAO – Data access object  Forças  Componentes necessitam obter dados de uma fonte persistente  A portabilidade dos componentes é afetada quando um mecanismo específico de persistência é incluído nele  Os componentes devem ser transparentes quanto à persistência para prover uma migração simples para outro tipo de armazenamento

45 45 DAO – Data access object  Solução  Data access object para abstrair e encapsular todo o acesso a dados.  O DAO gerencia a conexão com a fonte de dados além de armazenar e obter os dados Fonte:Core J2EE Patterns

46 46 DAO – Data access object Fonte:Core J2EE Patterns

47 47 DAO – Data Access object  Pode ser associado com AbstractFactory  DAOFactory  Conceqüências  Transparêcnia  Migração simples  Reduz complexidade dos objetos de negócio  Centraliza acesso a dados numa nova camada  Não é interessante com CMP  Cria uma nova camada  Quando usado com AbstractFactoru exige mais design Pode-se evoluir de um factory method para uma abstract factory

48 48 Transfer Object  Contexto  Clientes necessitam trocar dados com enterprise beans  Problema  Muitas chamadas de métodos remotos para conseguir todos os atributos  Forças  Quantidade de chamadas remotas pode ter impacto na performance da rede  Geralmente o cliente necessita de mais de um atributo  Em geral, o cliente lê mais do que altera os dados

49 49 Transfer Object  Solução  Use um Transfer Object para encapsular os dados de negócio.  Apenas um método para obter todo o objeto.  O bean preenche o objeto com os atributos e envia Fonte:Core J2EE Patterns

50 50 Transfer Object Fonte:Core J2EE Patterns

51 51 Transfer Object  Conseqüências  Reduz o tráfico da rede  Simplifica o objeto remoto e a component interface  Transfere mais dados em menos chamadas  Reduz duplicação de código  Cópia do cliente pode ficar desatualizada  Aumenta complexidade de sincronização Objeto alterado enviado de volta ao servidor

52 52 Quando usar BMP  Quando você precisa de controle sobre o esquema, ou precisa trabalhar com uma base legado específico.  Quando a aplicação necessita de “sintonia fina”  Quando portabilidade não é um problema. Mesmo nesse caso, recomenda-se utilizar DAOs.  DAOs facilitam uma futura adaptação do bean para um novo esquema  Quando sua consulta excede a capacidade da EJB-EL  Quando sua base de dados não é suportada pelo CMP.


Carregar ppt "Entity beans BMP Persistência explícita Ricardo Cavalcanti Jobson Ronan"

Apresentações semelhantes


Anúncios Google