Alguém pode esclarecer como podemos usar em geral, ou um exemplo do mundo real, esse trecho?
<f:metadata>
<f:viewParam id="id" value="#{bean.id}" />
<f:viewAction action="#{bean.init}" />
</f:metadata>
Alguém pode esclarecer como podemos usar em geral, ou um exemplo do mundo real, esse trecho?
<f:metadata>
<f:viewParam id="id" value="#{bean.id}" />
<f:viewAction action="#{bean.init}" />
</f:metadata>
Respostas:
O <f:viewParam>
gerencia a configuração, conversão e validação dos parâmetros GET. É como o <h:inputText>
, mas depois para os parâmetros GET.
O exemplo a seguir
<f:metadata>
<f:viewParam name="id" value="#{bean.id}" />
</f:metadata>
faz basicamente o seguinte:
id
.required
, validator
e converter
atributos, e aninhar um <f:converter>
e <f:validator>
nele como em <h:inputText>
)#{bean.id}
valor ou, se o value
atributo estiver ausente, configure-o como atributo de solicitação no nome, id
para que fique disponível #{id}
na visualização.Portanto, quando você abre a página foo.xhtml?id=10
, o valor do parâmetro 10
é definido no bean dessa maneira, imediatamente antes da exibição da renderização.
Quanto à validação, o exemplo a seguir define o parâmetro como required="true"
e permite apenas valores entre 10 e 20. Qualquer falha na validação resultará na exibição de uma mensagem.
<f:metadata>
<f:viewParam id="id" name="id" value="#{bean.id}" required="true">
<f:validateLongRange minimum="10" maximum="20" />
</f:viewParam>
</f:metadata>
<h:message for="id" />
Você pode usar o <f:viewAction>
para isso.
<f:metadata>
<f:viewParam id="id" name="id" value="#{bean.id}" required="true">
<f:validateLongRange minimum="10" maximum="20" />
</f:viewParam>
<f:viewAction action="#{bean.onload}" />
</f:metadata>
<h:message for="id" />
com
public void onload() {
// ...
}
No <f:viewAction>
entanto, isso é novo desde o JSF 2.2 (o <f:viewParam>
já existe desde o JSF 2.0). Se você não puder atualizar, sua melhor aposta será usar <f:event>
.
<f:event type="preRenderView" listener="#{bean.onload}" />
No entanto, isso é invocado em cada solicitação. Você precisa verificar explicitamente se a solicitação não é uma postagem:
public void onload() {
if (!FacesContext.getCurrentInstance().isPostback()) {
// ...
}
}
Quando você também quiser pular os casos "Falha na conversão / validação", faça o seguinte:
public void onload() {
FacesContext facesContext = FacesContext.getCurrentInstance();
if (!facesContext.isPostback() && !facesContext.isValidationFailed()) {
// ...
}
}
Usar <f:event>
esta maneira é, em essência, uma solução alternativa / hack, é exatamente por isso que <f:viewAction>
foi introduzido no JSF 2.2.
Você pode "passar" pelos parâmetros de exibição nos links de navegação, definindo o includeViewParams
atributo true
ou adicionando o includeViewParams=true
parâmetro de solicitação.
<h:link outcome="next" includeViewParams="true">
<!-- Or -->
<h:link outcome="next?includeViewParams=true">
que gera com o <f:metadata>
exemplo acima basicamente o seguinte link
<a href="next.xhtml?id=10">
com o valor do parâmetro original.
Essa abordagem requer apenas que tambémnext.xhtml
tenha um no mesmo parâmetro, caso contrário, ela não será repassada.<f:viewParam>
O <f:viewParam>
também pode ser usado em combinação com formulários GET "HTML simples".
<f:metadata>
<f:viewParam id="query" name="query" value="#{bean.query}" />
<f:viewAction action="#{bean.search}" />
</f:metadata>
...
<form>
<label for="query">Query</label>
<input type="text" name="query" value="#{empty bean.query ? param.query : bean.query}" />
<input type="submit" value="Search" />
<h:message for="query" />
</form>
...
<h:dataTable value="#{bean.results}" var="result" rendered="#{not empty bean.results}">
...
</h:dataTable>
Com basicamente esse @RequestScoped
bean:
private String query;
private List<Result> results;
public void search() {
results = service.search(query);
}
Observe que o <h:message>
é para o <f:viewParam>
HTML, e não para o HTML <input type="text">
! Observe também que o valor de entrada é exibido #{param.query}
quando #{bean.query}
está vazio, porque, caso contrário, o valor enviado não seria exibido quando houvesse um erro de validação ou conversão. Observe que essa construção é inválida para os componentes de entrada JSF (isso já está "oculto").