A Oracle liberou o release da versao 1.0 do OEPE (Oracle Enterprise Pack for Eclipse), que nada mais é do que um conjunto de plugins para o Eclipse. Segundo o post no site TheServerSide.com, alguns dos recursos que o OEPE fornece são:
In addition to capabilities provided by Eclipse and Web tools platform, OEPE provides the following features:
- Fastswap - Java Class Redefinition support for WebLogic Server
- Develop, debug and deploy to Oracle WebLogic Server 10gR3, and multiple previous versions
- Remote deployment and debugging, JSP Debugging for WebLogic Server 9.x and higher
- Virtual EAR technology that improves WebLogic Server deployment performance for large applications
- Leverage WebLogic Shared J2EE Libraries to make packaging of Enterprise Java Applications easier and faster
- Deployment descriptor editors for weblogic.xml and weblogic-application.xml
- Oracle Database Plug-in for Eclipse Data Tools Platform
- JSF Facelets Tools Project (Incubator)
Realizei pequenos testes utilizando o plugin com o Oracle Weblogic Server 10gR3 e tudo funcionou muito bem, não deixou o Eclipse pesado como alguns plugins fazem. Mas o que mais me agradou neste pack e que pelo menos no meu dia-a-dia fazia muita falta, foi o auto-complete para páginas xhtml (JSF + Facelets).
O OEPE possui versões para o Eclipse 3.3 (Europa) e 3.4 (Ganymede) e está disponivel para download aqui.
Você pode obter mais informações, no próprio site da Oracle.
Antigamente a forma mais comum para se criar uma forma de verificar a autorização das requisições feitas para determinado recurso de uma aplicação web era utilizando um filtro (Filter). Porém em Java Server Faces (JSF), podemos realizar esta tarefa de uma outra forma mais integrada, utilizando a interface PhaseListener.
Esta interface disponibiliza 3 métodos:
1
2
3
void afterPhase(PhaseEvent event);
void beforePhase(PhaseEvent event);
PhaseId getPhaseId();
No exemplo, irei demonstrar como utilizar o método afterPhase que tem por finalidade fazer o tratamento de uma notificação assim que o processamento de uma determinada fase acabar de ser concluída.
A idéia principal do listener será verificar se existe um atributo de sessão chamado “currentUser” que será uma instância de um objeto User e este representará o usuário logado na aplicação. Caso este atributo exista, o listener deixa o ciclo da pagina seguir, mas caso o atributo não exista o ciclo será interrompido e redirecionado para a página de login.
Também terá uma verificação para não fazer nenhuma verificação caso a página atual da requisição seja a página de login.
Aqui temos o código do PhaseListener:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
package com.rodrigolazoti.filter;
import javax.faces.application.NavigationHandler;
import javax.faces.context.FacesContext;
import javax.faces.event.PhaseEvent;
import javax.faces.event.PhaseId;
import javax.faces.event.PhaseListener;
import javax.servlet.http.HttpSession;
public class AuthorizationListener implements PhaseListener {
public void afterPhase(PhaseEvent event) {
FacesContext facesContext = event.getFacesContext();
String currentPage = facesContext.getViewRoot().getViewId();
boolean isLoginPage = (currentPage.lastIndexOf("login.jsf") > -1);
HttpSession session = (HttpSession) facesContext.getExternalContext().getSession(true);
Object currentUser = session.getAttribute("currentUser");
if (!isLoginPage && currentUser == null) {
NavigationHandler nh = facesContext.getApplication().getNavigationHandler();
nh.handleNavigation(facesContext, null, "loginPage");
}
}
public void beforePhase(PhaseEvent event) {
}
public PhaseId getPhaseId() {
return PhaseId.RESTORE_VIEW;
}
}
Note que o redirecionamento é feito por uma navegação configurada no arquivo faces-config.xml. Esta configuração é algo como:
1
2
3
4
5
6
7
<navigation-rule>
<from-view-id>/*</from-view-id>
<navigation-case>
<from-outcome>loginPage</from-outcome>
<to-view-id>/login.xhtml</to-view-id>
</navigation-case>
</navigation-rule>
Também deve-se incluir o listener no faces-config.xml:
1
2
3
<lifecycle>
<phase-listener>com.rodrigolazoti.filter.AuthorizationListener</phase-listener>
</lifecycle>
E com isso já se tem um PhaseListener funcionando e filtrando as requisições da aplicação.
Já mostrei como utilizar javascript de uma forma mais OO (orientada a objetos) nestes dois posts:
Agora irei mostrar uma forma de separar o código javascript em pacotes de uma forma parecida com a feita pela framework Yahoo! User Interface (YUI) Library, porém existem outras formas de se fazer isso como a feita pelo framework Dojo.
Exemplo utilizando YUI:
1
YAHOO.example.calendar.cal1 = new YAHOO.widget.Calendar("cal1", "cal1Container");
Exemplo utilizando Dojo:
1
dojo.require("dijit._Calendar");
E agora irei criar um exemplo simples, criarei uma classe chamada StringUtils que conterá um método trim e esta classe ficará no pacote br.com.rodrigolazoti.utils.
1
2
3
4
5
6
7
8
9
10
11
12
13
var br = br ? br : {}
br.com = br.com ? br.com : {}
br.com.rodrigolazoti = br.com.rodrigolazoti ? br.com.rodrigolazoti : {}
br.com.rodrigolazoti.utils = br.com.rodrigolazoti.utils ? br.com.rodrigolazoti.utils : {}
br.com.rodrigolazoti.utils.StringUtils = function() {
this.trim = function( value ) {
if (value==null) return null;
else return value.replace(/ /g, "");
}
}
Testando o código:
1
2
var stringUtils = new br.com.rodrigolazoti.utils.StringUtils();
alert( stringUtils.trim( " a b c d e f " ) );
Muitas vezes temos várias entidades em um projeto que possuem propriedades em comum como código ou nome por exemplo e que para facilitar a criação dessas entidades pode-se criar uma superclasse que não é uma entidade e que contenha as propriedades que serão herdadas pelas entidades.
Vamos criar um cenário bem simples com duas entidades Cliente e Usuário para exemplificar, conforme a representação UML a seguir:
Analisando este diagrama vemos que três propriedades são comuns entre as duas classes:
Com isso irei mudar nosso diagrama e adicionar uma nova classe que irá conter as três propriedades que serão herdadas por outras classes. O novo diagrama UML ficará da seguinte forma:
Falando um pouco sobre JPA, uma entidade pode herdar algo de uma superclasse sendo que esta superclasse é uma classe em seu modelo de domínio que não será transformada em uma entidade. Para resolver este problema temos a anotação @javax.persistence.MappedSuperclass.
Irei mostrar agora como ficará as entidades Cliente e Usuario fazendo herança das propriedades da classe Pessoa. Primeiro vou criar a superclasse Pessoa que será marcada com a anotação JPA MappedSuperclass:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import java.util.Date;
import javax.persistence.Column;
import javax.persistence.Id;
import javax.persistence.MappedSuperclass;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
@MappedSuperclass
public abstract class Pessoa {
@Id
private Long codigo;
@Column(length = 60, nullable = false)
private String nome;
@Temporal(TemporalType.DATE)
private Date dataCadastro;
//métodos get e set...
}
Agora vou criar as classes (entidades) Cliente e Usuario que herdarão as propriedades da classe Pessoa:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Table;
@Entity
@Table(name = "Usuarios")
public class Usuario extends Pessoa {
@Column(length = 20, nullable = false)
private String login;
@Column(length = 20, nullable = false)
private String senha;
//métodos get e set...
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Table;
@Entity
@Table(name="Clientes")
public class Cliente extends Pessoa {
@Column(length = 50)
private String email;
@Column(length = 100)
private String endereco;
@Column(length = 20)
private String telefone;
//métodos get e set...
}
Com isso teremos três classes, mas somente duas entidades. As classes (entidades) Cliente e Usuario vão herdar as propriedades da classe Pessoa que não é uma entidade.
É isso aí, hoje fiz a prova para a certificação SCWCD 5 (Sun Certified Web Component Developer for the Java Platform, Enterprise Edition 5) e fui aprovado com 86%, acertei 60 questões das 69 que compoem o exame.
O material que utilizei no estudo foi apenas o livro Use a Cabeça! Servlets & JSP.
Me preparei para a prova durante uns 10 dias seguidos, sendo que tinha feito uma primeira leitura do livro antes desse período, então nesses 10 dias fiz um pequena releitura fazendo um pequeno resumo e também fazendo os exercícios que acompanham cada capítulo do livro.
Os dois últimos dias deixei para fazer alguns simulados, como o JWebPlus e o simulado que acompanha o livro. Meus resultados nestes simulados ficaram entre 75% a 80%.
Na prova caiu muitas questões sobre Design patterns, EL, Listners, Tag Library, Standard Actions e segurança (bastante Deployment Descriptor sobre segurança).
Agora vou aproveitar o restante de férias da facul e depois inicio os estudos para a certificação **SCBCD **(Sun Certified Business Component Developer).