olá pessoal,
estou desenvolvendo uma aplicação web utilizando JSF e Rich Faces e estou com um problema referente a sessão.
configurei a sessão no DD
<session-config>
<session-timeout>30</session-timeout>
</session-config>
qnd este tempo expira e o usuario tenta utilizar algum recurso o container lanca uma javax.faces.application.ViewExpiredException.
ate aqui td bem… porem eu quero fazer o seguinte…
qnd expirar a sessão e o usuario tentar fazer um request… alem de aparecer a tela de erro ele seja redirecionado para tela de login…
eu não estou conseguindo fazer isto… ja tentei fazer filtro… ja tentei capturar a exception…
e nada…
eu gostaria da ajuda de vcs!!!
como devo proceder para implementar corretamente a sessão?
como consigo redirecionar para a pagina de login?
agradeço desde ja…
at.,
Jeferson
Olha, pelo menos no ajax4jsf era só você sobreescrever uma função javascript que estava tudo dominado
A4J.AJAX.onExpired = function(loc,expiredMsg){
if(window.confirm("A sua sessão expirou! Deseja recarregar a página?!")){return loc;}else{return undefined;}
};
Onde loc é a página que você estava, você pode colocar a URL da tua página de login!
dae, faz o seguinte usa o FhaseListener
coloca no seu Faces-Config - apontando para a pasta que esta a classe
br.com.simct.util.AutorizadorPhaseListener
cria uma classe PhaseListener
public class AutorizadorPhaseListener implements PhaseListener {
//Chama a pagina que quer direcionar após a sessa expirar
public static final String loginPage = "/template.jsf";
public void afterPhase(PhaseEvent event) {
try {
FacesContext fc = event.getFacesContext();
if(fc.getViewRoot().getViewId().equals(loginPage)){
return;
}
ELResolver elr = fc.getApplication().getELResolver();
NavigationHandler nav = fc.getApplication().getNavigationHandler();
nav.handleNavigation(fc, null, "login");
} catch (Exception e) {
// Não há necessidade de informar erro
}
}
public void beforePhase(PhaseEvent arg0) {
ExternalContext context = FacesContext.getCurrentInstance().getExternalContext();
HttpServletRequest request = (HttpServletRequest) context.getRequest();
if(!request.getRequestURL().toString().endsWith(loginPage) && context.getSession(false) == null){
try {
context.redirect(request.getContextPath() + loginPage);
} catch (IOException e) {
// Não há necessidade de informar erro
}
}
}
public PhaseId getPhaseId() {
return PhaseId.RESTORE_VIEW;
}
}
hum…
gostei! parece ser simples =)
porem nunca fiz algo assim =)
vc me disse pra sobrescrever a função… como faço isso?
tipo… onde devo colocar esse trecho q vc me passou?
em um .properties, no DD, faces-config?
dai como ficaria na minha pagina?
suponhamos q eu tenho as seguintes paginas…
login.jsp e uma outra pagina tipo show.jsp…
fiquei 40 min na show.jsp e minha sessão expirou…
como eu faria?
=)
t+ abraços
iaew surfzera blz?
tenho um listener parecido com esse porem não implementei o beforePhase…
eu utilizo para não deixar alguem tentar acessar qlq pagina sem estar logado no sitema…
bom… eu implementei o beforePhase mais começou a dar erro…
java.lang.RuntimeException: Cannot find FacesContext
da uma olhada no meu listener:
[code]
public class AutorizarUsuario implements PhaseListener {
private static final long serialVersionUID = 1L;
public static final String LOGIN_PAGE = "/login/index.jsp";
@Override
public void afterPhase(PhaseEvent event) {
FacesContext facesContext = event.getFacesContext();
// Verifica se é a pagina de login
if ( facesContext.getViewRoot().getViewId().equals( LOGIN_PAGE ) ) {
return;
}
// Obtem uma referencia para o autenticador na sessão
ELResolver elResolver = facesContext.getApplication().getELResolver();
LoginHandler login = (LoginHandler) elResolver.getValue( facesContext.getELContext(), null, "loginHandler" );
if ( login == null || ! login.isLogado() ) {
System.out.println( "Não esta Logado" );
// Redireciona para o Login
NavigationHandler navigationHandler = facesContext.getApplication().getNavigationHandler();
navigationHandler.handleNavigation( facesContext, null, "login" );
// Renderiza a Pagina
facesContext.renderResponse();
}
}
@Override
public void beforePhase(PhaseEvent event) {
// aqui utilizei oq vc me passou
ExternalContext context = FacesContext.getCurrentInstance().getExternalContext();
HttpServletRequest request = (HttpServletRequest) context.getRequest();
if(!request.getRequestURL().toString().endsWith(LOGIN_PAGE) && context.getSession(false) == null){
try {
context.redirect(request.getContextPath() + LOGIN_PAGE);
} catch (IOException e) {}
}
}
@Override
public PhaseId getPhaseId() {
return PhaseId.RESTORE_VIEW;
}
}[/code]
oq sera q estou fazendo de errado?
da uma forcinha ai =)
vlw
cara não entendi do modo que eu fiz funciona perfeitamente para qualquer aplicacao. Não entendi ainda porque do cheito que você implementou esta dando erro… 
iaew galera!
esse problema de java.lang.RuntimeException: Cannot find FacesContext eu consegui resolver…
fiz um mapeamento para *.faces portanto meu loginPage aparece assim /login/index.faces…
a solução foi criar uma costante com o falor de login page assim “/login/index.faces” e funcionou…
porem surgiu 2 problema…
1 - qnd a sessão expira na pagina de login da erro (ViewExpiredException)… =(
não entendi…
2 - este não e um erro e sim um WARRING… porem todo aviso pode virar um erro…
qnd estou em qlq pagina (menos a de login) e expira a sessão ele redireciona pra pagina de login… perfeito!
porem percebi q ele gera um WARRING… no console…
segue:
17/06/2009 12:08:23 com.sun.faces.lifecycle.Phase handleAfterPhase
WARNING: JSF1053: (Listener: br.com.corpus.controller.listener.AutorizarUsuario.afterPhase(), Phase ID: RESTORE_VIEW 1, View ID: ) Exception thrown during phase-listener execution: java.lang.NullPointerException
17/06/2009 12:08:23 com.sun.faces.lifecycle.Phase handleAfterPhase
WARNING: br.com.corpus.controller.listener.AutorizarUsuario.afterPhase(AutorizarUsuario.java:28)
com.sun.faces.lifecycle.Phase.handleAfterPhase(Phase.java:175)
com.sun.faces.lifecycle.Phase.doPhase(Phase.java:114)
com.sun.faces.lifecycle.RestoreViewPhase.doPhase(RestoreViewPhase.java:103)
com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)
javax.faces.webapp.FacesServlet.service(FacesServlet.java:265)
org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
org.ajax4jsf.webapp.BaseXMLFilter.doXmlFilter(BaseXMLFilter.java:178)
org.ajax4jsf.webapp.BaseFilter.handleRequest(BaseFilter.java:290)
org.ajax4jsf.webapp.BaseFilter.processUploadsAndHandleRequest(BaseFilter.java:390)
org.ajax4jsf.webapp.BaseFilter.doFilter(BaseFilter.java:517)
org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
br.com.corpus.model.database.filter.HibernateSessionFilter.doFilter(HibernateSessionFilter.java:39)
org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:128)
org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:286)
org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:845)
org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583)
org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447)
java.lang.Thread.run(Unknown Source)
este negocio ta me dando quebrando…
ah… segue meu listener novamente:
public class AutorizarUsuario implements PhaseListener {
private static final long serialVersionUID = 1L;
public static final String LOGIN_PAGE = "/login/index.jsp";
public static final String LOGIN_PAGE_FACES = "/login/index.faces";
@Override
public void afterPhase(PhaseEvent event) {
FacesContext facesContext = event.getFacesContext();
// Verifica se é a pagina de login
if ( facesContext.getViewRoot().getViewId().equals( LOGIN_PAGE ) ) {
return;
}
// Obtem uma referencia para o autenticador na sessão
ELResolver elResolver = facesContext.getApplication().getELResolver();
LoginHandler login = (LoginHandler) elResolver.getValue( facesContext.getELContext(), null, "loginHandler" );
if ( login == null || ! login.isLogado() ) {
System.out.println( "Não esta Logado" );
// Redireciona para o Login
NavigationHandler navigationHandler = facesContext.getApplication().getNavigationHandler();
navigationHandler.handleNavigation( facesContext, null, "login" );
// Renderiza a Pagina
facesContext.renderResponse();
}
}
@Override
public void beforePhase(PhaseEvent event) {
ExternalContext context = FacesContext.getCurrentInstance().getExternalContext();
HttpServletRequest request = (HttpServletRequest) context.getRequest();
if(!request.getRequestURL().toString().endsWith(LOGIN_PAGE_FACES) && context.getSession(false) == null){
try {
context.redirect(request.getContextPath() + LOGIN_PAGE_FACES);
} catch (IOException e) {}
}
}
@Override
public PhaseId getPhaseId() {
return PhaseId.RESTORE_VIEW;
}
}
tenta tirar essa parte porque automaticamente já estara apontando para tela de login caso a session va pro bebeleu…
if ( login == null || ! login.isLogado() ) {
System.out.println( "Não esta Logado" );
// Redireciona para o Login
NavigationHandler navigationHandler = facesContext.getApplication().getNavigationHandler();
navigationHandler.handleNavigation( facesContext, null, "login" );
// Renderiza a Pagina
facesContext.renderResponse();
}
ops nao vi sua resposta anterior…vou tentar aqui pra ver se o meu da erro tambem que vc falou.