Alternativas ao escopo session do Managed Bean [RESOLVIDO]

4 respostas
FightSurf_George_Mai

Amigos, estou impaciente com esses escopos dos Managed Beans e com o ciclo de vida deles.

Toda vez que tento fazer algo com jsf só consigo deixando o Managed Bean com escopo session.
Se for request, eu perco os valores das variáveis toda vez que faço um submit na página.

Como posso fazer para manter o valor das minhas variáveis, por exemplo no código abaixo?
Toda vez que pressiono o botão VOLTAR da página Teste2.xhtml, eu mando imprimir o valor da variável MeuNome…

Mas vem null todas as vezes, pois o Bean sempre é criado.

Eu li a respeito do immediate=true, onde ele executaria primeiro o método antes do submit… Mas não soube como utilizá-lo.

Qual a solução para isso deixando o escopo Request e sem utilizar variáveis estáticas?

Teste1.xhtml

<body>
	
		<f:view>
			<h:form>
				
				<h:commandButton action="Teste2" value="Teste">
					<f:setPropertyActionListener value="George" target="#{teste2BEAN.meunome}" />
				</h:commandButton>
						
			</h:form>
		</f:view>
	
	</body>

Teste2.xhtml

<body>
 		<f:view>
			<h:form>
				<h:outputText value="#{teste2BEAN.meunome}" />
								
				<h:commandButton value="Voltar" action="#{teste2BEAN.botaoOKAction}" />
			</h:form>			
 		</f:view>
 	</body>

Teste2Bean.java

public class Teste2BEAN {
	
	private String meunome;

	public String getMeunome() {
		return meunome;
	}

	public void setMeunome(String meunome) {
		this.meunome = meunome;
	}
	
	
	public String botaoOKAction()
	{
		System.out.println(meunome);
		return "teste1";
	}
}

4 Respostas

marcos.junqueira

George, poste o seu faces-config.xml

O immediate você utiliza em actions como o h:commandButton ou o h:commandLink e ele vai antecipar algumas etapas que seriam executadas em outra fase do ciclo de vida do jsf para a segunda fase do ciclo de vida. Utilize ele com sabedoria. :lol:

No seu teste2.xhtml quando vc utiliza o h:outputText ele somente imprime o valor da tela, não vai existir nenhum campo no form para quando for utilizar o botão voltar. Nesse caso ele não vai popular o seu ManagedBean com esse valor a não ser que você coloque um h:inputText para fazer o submit desse valor.

renanreismartins

cara se vc estiver utilizando rich faces de um olhadinha no componente a4j:keepAlive

abrassss

FightSurf_George_Mai

Obrigado pelas duas mensagens.

Estava usando richfaces mesmo e acabei optando pelo a4j:keepalive e com todos os Managed Beans com escopo request.

Vou dar um presente para quem está aprendendo JSF com RichFaces.
Minha aplicação completa ficou assim:

faces.config.xml

<?xml version="1.0" encoding="UTF-8"?>
<faces-config version="1.2" xmlns="http://java.sun.com/xml/ns/javaee"
 xmlns:xi="http://www.w3.org/2001/XInclude"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_1_2.xsd">
 <managed-bean>
  <managed-bean-name>teste1BEAN</managed-bean-name>
  <managed-bean-class>teste.Teste1BEAN</managed-bean-class>
  <managed-bean-scope>request</managed-bean-scope>
 </managed-bean>
 <managed-bean>
  <managed-bean-name>teste2BEAN</managed-bean-name>
  <managed-bean-class>teste.Teste2BEAN</managed-bean-class>
  <managed-bean-scope>request</managed-bean-scope>
 </managed-bean>
 
 
 <navigation-rule>
  <from-view-id>/Teste1.xhtml</from-view-id>
  <navigation-case>
   <from-outcome>Teste2</from-outcome>
   <to-view-id>/Teste2.xhtml</to-view-id>
  </navigation-case>
 </navigation-rule>
 <navigation-rule>
  <from-view-id>/Teste2.xhtml</from-view-id>
  <navigation-case>
   <from-outcome>Teste1</from-outcome>
   <to-view-id>/Teste1.xhtml</to-view-id>
  </navigation-case>
 </navigation-rule>
 <application>
  <view-handler>com.sun.facelets.FaceletViewHandler</view-handler>
 </application>
</faces-config>

Teste1.xhtml

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:h="http://java.sun.com/jsf/html"
      xmlns:f="http://java.sun.com/jsf/core"
      xmlns:ui="http://java.sun.com/jsf/facelets"
      xmlns:a4j="http://richfaces.org/a4j"
      xmlns:rich="http://richfaces.org/rich">


	<body>
				<rich:dataTable id="dataTable" value="#{teste1BEAN.categoriaslista}" var="categoria">
					<rich:column>
						<h:outputText value="#{categoria.codigoCategoria}" />
					</rich:column>
					<rich:column>
						<h:outputText value="#{categoria.nomeCategoria}" />
					</rich:column>
					<rich:column>
						<a4j:form>	
							<a4j:commandLink value="#{teste1BEAN.commandLinkTitulo}" 
							action="#{teste1BEAN.commandLinkClick}" 
							id="commandLink"
							reRender="commandLink"
							disabled="#{teste1BEAN.desabilitado}">
							
								<f:setPropertyActionListener value="#{categoria}" 
								target="#{teste1BEAN.categoria}"></f:setPropertyActionListener>
							
							</a4j:commandLink>
					</a4j:form>

						
					</rich:column>
					
					
					<rich:column>
					<h:form>
						<h:commandLink action="Teste2" value="Glosar Atendimento">
								<f:setPropertyActionListener value="#{categoria}" 
								target="#{teste2BEAN.categoria}">

								</f:setPropertyActionListener>
						</h:commandLink>
					</h:form>
					</rich:column>
					
				</rich:dataTable>
	
	</body>

</html>

Teste1BEAN.java

package teste;

import java.util.List;

import categoria.Categoria;
import categoria.CategoriaDAO;

public class Teste1BEAN{
	
	private List<Categoria> categoriaslista = new CategoriaDAO().getCategorias();
	private Categoria categoria = new Categoria();
	private String commandLinkTitulo = "Título";
	private boolean desabilitado = false;
	
	
	public String commandLinkClick()
	{	
		System.out.println(categoria);
		setCommandLinkTitulo("Clicado!");
		setDesabilitado(true);
		
		return "";
	}
	
	
	public String glosarAtendimento()
	{
		return "Teste2";
	} 
	
	
	
	public List<Categoria> getCategoriaslista() {
		return categoriaslista;
	}

	public void setCategoriaslista(List<Categoria> categoriaslista) {
		this.categoriaslista = categoriaslista;
	}

	public Categoria getCategoria() {
		return categoria;
	}

	public void setCategoria(Categoria categoria) {
		this.categoria = categoria;
	}


	public String getCommandLinkTitulo() {
		return commandLinkTitulo;
	}

	public void setCommandLinkTitulo(String commandLinkTitulo) {
		this.commandLinkTitulo = commandLinkTitulo;
	}


	public boolean isDesabilitado() {
		return desabilitado;
	}

	public void setDesabilitado(boolean desabilitado) {
		this.desabilitado = desabilitado;
	}
	

}

Teste2.xhtml

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:h="http://java.sun.com/jsf/html"
      xmlns:f="http://java.sun.com/jsf/core"
      xmlns:ui="http://java.sun.com/jsf/facelets"
      xmlns:a4j="http://richfaces.org/a4j"
      xmlns:rich="http://richfaces.org/rich">

 	<body>
		
		<a4j:keepAlive beanName="teste2BEAN" />	
		<h:outputText value="#{teste2BEAN.categoria}" />
		<br />	 	
			
		
		<a4j:form>
			<a4j:commandButton value="Glosar" action="#{teste2BEAN.botaoGlosaClick}"/>
			<h:commandButton value="Cancelar e voltar"/>
		</a4j:form>
		
	</body>

</html>

Teste2BEAN.java

package teste;

import java.io.Serializable;

import categoria.Categoria;

public class Teste2BEAN implements Serializable{
	
	private Categoria categoria;

	
	
	
	public String botaoGlosaClick()
	{
		System.out.println(categoria);
		return "";
	}
	
	
	
	public Categoria getCategoria() {
		return categoria;
	}

	public void setCategoria(Categoria categoria) {
		this.categoria = categoria;
	}

}

Categoria.java

package categoria;

import java.io.Serializable;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name="CATEGORIA", schema="sistema")
public class Categoria implements Serializable{
	
	@Id
	@Column(name="CAT_CODIGO")
	private int codigoCategoria;
	@Column(name="CAT_NOME")
	private String nomeCategoria;
	
	public Categoria() {
		// TODO Auto-generated constructor stub
	}
	
	public int getCodigoCategoria() {
		return codigoCategoria;
	}
	
	public void setCodigoCategoria(int codigoCategoria) {
		this.codigoCategoria = codigoCategoria;
	}
	
	public String getNomeCategoria() {
		return nomeCategoria;
	}
	
	public void setNomeCategoria(String nomeCategoria) {
		this.nomeCategoria = nomeCategoria;
	}

	@Override
	public String toString() {
		return "Categoria [codigoCategoria=" + codigoCategoria
				+ ", nomeCategoria=" + nomeCategoria + "]";
	}

	public Categoria(int codigoCategoria, String nomeCategoria) {
		super();
		this.codigoCategoria = codigoCategoria;
		this.nomeCategoria = nomeCategoria;
	}
	
}
Laubstein_M_cio

Só um adendo, o immediate se utilizado com componentes que herdam de EditableValueHolder NÃO pularam a fase de Validação do ciclo do JSF, mantenha isto sempre em mente.

Criado 12 de novembro de 2009
Ultima resposta 14 de nov. de 2009
Respostas 4
Participantes 4