[RESOLVIDO] - JSF2 - Passar objeto por parâmetro

Fala galera, estou treinando JSF 2.0 e gostaria de saber se tem como eu passar o objeto que está na linha do meu datatable para um método de edição?

Mais ou meno isso:

package s2.bean;

import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.SessionScoped;
import s2.dao.CdDAO;
import s2.model.Cd;

@ManagedBean(name = "ListaCdBean")
@SessionScoped
public class ListaCdBean {
    public List<Cd> getAll() {
        try {
            return CdDAO.getAll();
        } catch (Exception ex) {
            Logger.getLogger(CdBean.class.getName()).log(Level.SEVERE, null, ex);
        }

        return null;
    }

    public String EditCd(Cd cd){
        CdBean cdBean = new CdBean();
        cdBean.setCd(cd);
        return "cd";
    }
}
<?xml version='1.0' encoding='UTF-8' ?>
<!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">
    <h:head>
        <title>Facelet Title</title>
    </h:head>
    <h:body>
        <f:view>
            <h:form>
                <h:dataTable value="#{ListaCdBean.all}" var="cd">
                    <h:column>
                        <h:form>
                            <h:commandLink action="#{ListaCdBean.EditCd}" value="Editar">
                                <f:param name="cd" value="cd"/>
                                <f:ajax execute="@this" render="@form"/>
                            </h:commandLink>
                        </h:form>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            Cantor
                        </f:facet>
                        #{cd.cantor}
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            Preço
                        </f:facet>
                        #{cd.preco}
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            Ano
                        </f:facet>
                        #{cd.anoLancamento.anoLancamento}
                    </h:column>
                </h:dataTable>
            </h:form>
        </f:view>
    </h:body>
</html>

Tem um commandlink na primeira coluna do datatable e gostaria de passar a variável cd (var=“cd”) do meu datatable para o método EditCd do Bean.

Tem como fazer isso?

Obrigado…

AFF, eu estava viajando…

É só passar como se fosse uma chamada de método normal e não com a tag <f:param/>…

Então:

<?xml version='1.0' encoding='UTF-8' ?>
<!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">
    <h:head>
        <title>Facelet Title</title>
    </h:head>
    <h:body>
        <f:view>
            <h:form>
                <h:dataTable value="#{ListaCdBean.all}" var="cd">
                    <h:column>
                        <h:form>
                            <h:commandLink action="#{ListaCdBean.EditCd(cd)}" value="Editar">
                                <f:ajax execute="@this" render="@form"/>
                            </h:commandLink>
                        </h:form>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            Cantor
                        </f:facet>
                        #{cd.cantor}
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            Preço
                        </f:facet>
                        #{cd.preco}
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            Ano
                        </f:facet>
                        #{cd.anoLancamento.anoLancamento}
                    </h:column>
                </h:dataTable>
            </h:form>
        </f:view>
    </h:body>
</html>

O que voce pode fazer é o seguinte:


<h:commandLink action="#{ListaCdBean.EditCd}" value="Editar">
     <f:setPropertyListener value="#{cd}" target="#{ListaCdBean.cd}"/>
</h:commandLink>

onde “ListaCdBean.cd” é uma variavel do mesmo tipo que o “cd”;

@edit

ops… não vi que voce resolveu…

Valeu pela dica Caio, pode ser uma outra forma de se fazer também.

Pessoal, desculpem reabrir o tópico mas estou com o mesmo problema para envio de um objeto por parametros utilizando a forma de no faces-config.

Tenho uma tela list e quero editar um registro do datatable conforme abaixo:

lista.xhtml

...
<p:dataTable value="#{carrosMB.listarTodos}" var="carro">
  <p:column headerText="#{msgs.carroId}" width="80">
	<h:outputText value="#{carro.id}" />
  </p:column>
					
   <p:column headerText="#{msgs.carroNome}">
	<h:outputText value="#{carro.nome}" />
   </p:column>
</p:dataTable>

<h:link outcome="edit" value="editar" >
	<f:param name="carroId" value="#{carro.id}"/>							
</h:link>

edit.xhtml

<f:metadata>
   	<f:viewParam name="carroId" value="#{carroMB.carro.id}" />
</f:metadata>
...
<h:link outcome="edit" value="editar" >
	<f:param name="carroId" id="carroId" value="#{consorcio.id}"/>								
</h:link>

Fazendo desta forma consigo receber o id do objeto carro com redirect normal. Mas como faço para enviar o objeto inteiro da pagina list para edit e então poder usar os seus elementos na tela edit? Tentei de fato enviar <f:param name=“carro” value="#{carro}"/> mas é lançado apenas um Servlet.service() for servlet Faces Servlet threw exception: java.lang.NullPointerException.

Tentei da forma que o and.rds fez mas algo deve estar errado no meu MB.
Estou empenhado nisso e parece tão simples :roll:

[quote=kdashu]Pessoal, desculpem reabrir o tópico mas estou com o mesmo problema para envio de um objeto por parametros utilizando a forma de no faces-config.

Tenho uma tela list e quero editar um registro do datatable conforme abaixo:

lista.xhtml

...
<p:dataTable value="#{carrosMB.listarTodos}" var="carro">
  <p:column headerText="#{msgs.carroId}" width="80">
	<h:outputText value="#{carro.id}" />
  </p:column>
					
   <p:column headerText="#{msgs.carroNome}">
	<h:outputText value="#{carro.nome}" />
   </p:column>
</p:dataTable>

<h:link outcome="edit" value="editar" >
	<f:param name="carroId" value="#{carro.id}"/>							
</h:link>

edit.xhtml

<f:metadata>
   	<f:viewParam name="carroId" value="#{carroMB.carro.id}" />
</f:metadata>
...
<h:link outcome="edit" value="editar" >
	<f:param name="carroId" id="carroId" value="#{consorcio.id}"/>								
</h:link>

Fazendo desta forma consigo receber o id do objeto carro com redirect normal. Mas como faço para enviar o objeto inteiro da pagina list para edit e então poder usar os seus elementos na tela edit? Tentei de fato enviar <f:param name=“carro” value="#{carro}"/> mas é lançado apenas um Servlet.service() for servlet Faces Servlet threw exception: java.lang.NullPointerException.

Tentei da forma que o and.rds fez mas algo deve estar errado no meu MB.
Estou empenhado nisso e parece tão simples :roll:

[/quote]

tentou usar : <f:setPropertyActionListener></> ?

Olá renlih,

Tentei sim, funciona normalmente se eu faço o metodo pagefoward. Informo um <h:inputHidden value="#{carroMB.carro.id}"/> e sem o redirect no faces-config vai.

Mas preciso atualizar a url de list para edit quando entrar nesta tela, além de que meu filtro na tela listagem só funciona a edição de um registro se usar redirect. Senão ao clicar no editar do registro ele permanece na mesma tela.

Obrigado

Bom, resolvido.

Bastava na view list.xhtml informar um <f:param id=“id” value="#{bean.id}"> da vida, na view edit.xhtml algo como <f:viewParam name=“id” value=“meuManageBean.bean.id”> no topo da página.

E no metodo init do ManageBean usar um @postConstruct, chamando um método localizar que pegasse esse id pelo FacesContext e inicializasse o objeto. Depois eu posto o código.
Agora ficou praticamente como no seam.

Valeu!