Newsgroup: it.comp.java
Titolo: Jsf integrato in JBoss dà seri problemi

Salve a tutti.
Dalla versione 4 di Jboss, la casa ha dichiarato l'AS JEE5 compliant.
Da specifica ciò significa che deve gestire al suo interno jsf.
Da una serie di proteste nate da chi voleva portarsi dentro al proprio
war le librerie di jsf, jboss ha messo a disposizione un elemento di
configurazione del web.xml così fatto:
	<context-param>
		<param-name>
			org.jboss.jbossfaces.WAR_BUNDLES_JSF_IMPL
		</param-name>
		<param-value>false</param-value>
	</context-param>
Dove "false" vuol dire usare quelle di Jboss, "true" vuol dire usare
le proprie.
Fatta questa premessa, io ho un esempio di semplicissima jsp con un
<h:commandLink> all'interno di un <h:column> che non vuole sapere di
funzionare (ed ho trovato diversi esempi in cui la cosa è permessa).
Chi vuole può copiare quanto segue e fare una prova ma, ovviamente,
ancor più comodo mi farebbe se qualcuno mi indicasse una soluzione che
ci DEVE essere altrimenti sarebbe un disastro per chiunque usi JBoss.
Premettendo quindi che ho fatto le prove sulle versioni 4.0.5, 4.2.0 e
4.2.1 sia con jsf bundled che no, la situazione è la seguente:
===============
web.xml
===============
	<servlet-mapping>
		<servlet-name>Faces Servlet</servlet-name>
		<url-pattern>/faces/*</url-pattern>
	</servlet-mapping>
	<context-param>
		<param-name>
			org.jboss.jbossfaces.WAR_BUNDLES_JSF_IMPL
		</param-name>
		<param-value>false</param-value>
	</context-param>
=====================
faces-config.xml
=====================
	<application>
			<navigation-handler>mydomain.web.util.NavigationManager</navigation-
handler>
	</application>
	<navigation-rule>
		<from-view-id>/jsp/content/test/testLista.jsp</from-view-id>
		<navigation-case>
			<from-outcome>paginaDiModifica</from-outcome>
			<to-view-id>/jsp/content/test/testPaginaDiModifica.jsp</to-view-id>
		</navigation-case>
	</navigation-rule>
	<managed-bean>
		<managed-bean-name>tipologicaStandardForm</managed-bean-name>
		<managed-bean-class>mydomain.web.form.TipologicaStandardForm</
managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
	</managed-bean>
=============================
testLista.jsp
=============================
	<?xml version="1.0" encoding="ISO-8859-1" ?>
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
    pageEncoding="ISO-8859-1"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://
www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd
">
<%@ taglib uri="
http://java.sun.com/jsp/jstl/core
" prefix="c" %>
<%@ taglib uri="
http://java.sun.com/jsf/html
" prefix="h" %>
<%@ taglib uri="
http://java.sun.com/jsf/core
" prefix="f" %>
<html xmlns="
http://www.w3.org/1999/xhtml
">
<head>
<meta http-equiv="Content-Type" content="text/html;
charset=ISO-8859-1" />
<title>Insert title here</title>
</head>
<body>
	<% java.util.List list = new java.util.ArrayList();
		list.add("1");
		list.add("2");
		request.setAttribute("list",list);
	%>
	<f:view>
<h:form>
			<h:commandLink action="#{tipologicaStandardForm.paginaDiModifica}"
value="Outside table"/>
	<h:dataTable value="#{requestScope.list}" var="tipologicaStandard">
		<h:column>
			<h:commandLink action="#{tipologicaStandardForm.paginaDiModifica}">
				<h:outputText value="#{tipologicaStandard}"/>
			</h:commandLink>
		</h:column>
	</h:dataTable>
</h:form>
	</f:view>
</body>
</html>
==============================
Qual è il problema?
Come vedete, esternamente ed internamente alla tabella, ho sempre lo
stesso <h:commandLink> (cioè stessa action). A runtime ho quindi un
commandLink fuori dalla tabella e due dentro (la lista ha due
elementi). Ebbene, se io clicco su quello fuori, viene invocato il
metodo "paginaDiModifica" del mio managed bean, se clicco su quelli
dentro, invece, la chiamata va a server ma poi non viene invocato
nulla e ritorna nella stessa pagina di partenza.
Suggerimenti?
P.S.: Se volete vedere il codice formattato meglio, potete guardare
questo post:
http://www.jboss.com/index.html?module=bb&op=viewtopic&t=120622
Grazie a tutti

ciao, hai provato con la versione 5 beta (se non sbaglio si dovrebbe passare 
da myfaces alla versione rilasciata direttamente da Sun)?
- Con org.jboss.jbossfaces.WAR_BUNDLES_JSF_IMPL impostato a true (e quindi 
usi le tue librerie) funziona?
- Quando lo imposti a false togli comunque i jar dal tuo .war (.ear) file? 
(prova a toglierli comunque )
hai visto qui?:
http://wiki.jboss.org/wiki/Wiki.jsp?page=JBossWithJSFCDDL
Se trovi una soluzione facci sapere.
Ciao.

 Ciao.
Ciao

jsp e dirmi cosa succede a te?
No il problema č che io non uso al momento JBOSS sto usando tomcat, e non ho 
mai usato JSF ma struts, quindi non saprei che librerie mettere nel 
"warrettino".
Ti ho chiesto di postare la soluzione perchč vorrei provare JSF su JBOSS, ma 
se la cosa č cosě aleatoria mi sa che aspetto un altro po.
Prova a gaurdare l'HTML generato e a vedere consa manca nel link.
La tua applciazione deployata in un tomcat funziona?
Per il JBOSS 5, se non funziona neache lě, vuol dire che c'e' qualcosaa di 
sbagliato nella tua app.
Possibile che di un bug cosě comune non si sia accorto nessuno?
ciao.

 ha scritto nel messaggio 
news:1191850595.9...@k79g2000hse.googlegroups.com...
[cut]
Perche' hai dichuiarato i taglib dentro il web.xml? non servono.
Poi dovremmo vedere almeno il metodo cosa fa e sopratutto quel navigation 
handler che hai messo. 

Dalla versione 4 di Jboss, la casa ha dichiarato l'AS JEE5 compliant.
aspetta aspetta, non e' che per caso stai cercando di far girare JSF 1.2 su 
un ambiente JSP 2.0?
Controlla che versione delle JSP implementa il tuo jboss. 

 handler che hai messo.
Solo per non prendere la segnalazione di errore in compilazione sulle
jsp e farmi dare l'aiuto sulle property dei tag da eclipse.
Ho provato anche senza e il problema resta.

 Controlla che versione delle JSP implementa il tuo jboss
Posso anche controllare ma...sto usando jsf di Jboss e Servlet
Container (che poi è Tomcat) integrato dentro Jboss. Se non si
conoscono loro...

 handler che hai messo.
Nulla...il navigationhandler l'ho tolto.

 ciao.
Me lo chiedo anch'io...solo che ovviamente sul forum di JBoss si
guardano bene dal rispondere.


L'ho deployata sia su Tomcat6 con le librerie jsf 1.2 (e quindi jsp
2.1 integrato) che su Tomcat 5.5 con le jsf 1.1 (e quindi jsp 2.0
integrato).
L'anomalia resta.

 ha scritto nel messaggio 
news:1191926311....@d55g2000hsg.googlegroups.com...


Il fatto e' che JSF 1.2 non funziona su JSP 2.0 o inferiori. Non mi sembra 
che jboss 4.05 implementi le specifiche jsp 2.1.
Controlla...


http://digilander.libero.it/crfi_si/hellojsf.war
allora l'ho scariato e l'ho provato con jboss 4.2.1 GA, ho provato sia la 
tua versione (jsf 1.1) che una modificata da me (jsf1.2 - ho solo tolto i 
jar da dentro /lib e modificato un po web.xml e faces-config.xml)
Se mi dici dove mandartela te la mando (sono solo 5K)
in entrambi i casi il primo link funziona (da success) e gli altri due no.
Quando chiamo il primo link (fuori dalla tabella) jboss mi da il log: 
"inside my action" qundo clicco gli altri due non mi fa nemmeno il log. 
(cosa significa?)
Il fatto che non funzioni nè in jboss nè in tomcat nè con diverse versioni 
di jsf mi fa pensa che ci sia un errore semantico da quialche parte (ti 
ripeto non so molto di jsf ma il fatto del log mi insospettisce)
Puoi fare una prova?
Ho il dubbio che da dentro il tag <h:commandLink value="#{item}" 
action="#{testBean.myAction}"/>
 il bean "testBean" sia null, metti il metodo "myAction" dentro "item" a 
questo punto dovrebbe vederlo per forza.
ciao e fammi sapere.

 ha scritto nel messaggio 
news:1191850595.9...@k79g2000hse.googlegroups.com...
[cut]
Ho beccato l'errore. E' un tuo errore, ma devo dire che e' anche piuttosto 
comune.
In sostanza la lista non deve stare in request, ma in session.
Quando clicchi un link dentro il dataTable, JSF tenta di impostare l'oggetto 
corrente (in questo caso la stringa "1" o "2") a seconda della riga 
cliccata.
Purtroppo in questa seconda richiesta la lista non esiste piu' perche' e' 
sparita dopo la prima richiesta. Quindi JSF va in errore e non invoca il 
metodo.
C'e' da domandarsi piuttosto perche' non visualizza un qualche errore (ho 
provato anche con h:messages ma niente, e i log restano puliti).
Meglio se segnali il problema al team, un messsaggio di errore in questo 
caso mi sembra il minimo. 

 ciao e fammi sapere.
Scusa ma non ho capito cosa dovrei fare.
Ad ogni modo non credo che la tua ipotesi sia valida. A parte il fatto
che è jsf che istanzia i managed bean, poi sarebbe null su entrambi i
commandLink

commandLink
La mia ipotesi (che deriva solo dal fatto che non conosco jsf) è che 
l'action <commandLink ..> dentro il tag <h:dataTable ..> abbia uno scoping 
ridotto e possa avere accesso solo al bean definito nel parametro "var" del 
dataTable.
Ma a quanto pare è una fesseria, inquanto il problema è stato risolto (vedi 
messaggi in basso) impostando a session (invece che a request) lo scope 
della lista degli elementi.
Ma questa non l'ho capita, perchè lo scope deve essere session  (lo so, mi 
manca il ciclo di vita delle JSF...)?
ciao. 


Non l'ho capita nemmeno io tanto più che l'esempio che ho postato era
semplificato.
Adesso arriviamo a quello standard:
Ho una prima jsp che ha un <commandLink> così fatto:
<f:view>
	<h:form>
		<h:commandLink action="#{tipologicaStandardForm.lista}"
value="Proviamo và" id="tipologicaStandardForm_"/>
	</h:form>
</f:view>
Dove ricordo che tipologicStandardForm è l'alias di un mio managed
bean.
Cliccando sul link, si invoca il metodo lista, che va a db e popola un
attributo della managed bean che è una Collection chiamata
"elencoRecord", dopodichè tramite le impostazioni di navigazione viene
chiamata quest'altra jsp
	<f:view>
<h:form>
			<h:commandLink action="#{tipologicaStandardForm.paginaDiModifica}"
value="Fuori dalla tabella"/>
	<h:dataTable value="#{tipologicaStandardForm.elencoRecord}"
var="tipologicaStandard">
		<h:column>
			<h:commandLink action="#{tipologicaStandardForm.paginaDiModifica}">
				<h:outputText value="#{tipologicaStandard.codice}"/>
			</h:commandLink>
		</h:column>
	</h:dataTable>
</h:form>
	</f:view>
Quest'altra jsp ha "in canna" elencoRecord e difatti giustamente il
datatable mi presenta tanti "codici" quanti oggetti ci sono nella
collection lato server.
Che poi quando ho la jsp davanti la collection che è stata iterata non
esiste più in request è dato per scontato ma...a che serve al
commandLink sapere "chi lo ha scritto"? Per inciso, il problema resta
anche se come valore del commandLink metto una stringa fissa anzichè
l'outputText che vedete.
E comunque, ripeto, quello che nell'esempio semplificato era "list" e
che qui è elencoRecord è un attributo del managed bena su cui non
posso (via jsf) regolare lo scope.

 collection lato server.
M'è venuto in dubbio ed ho verificato.
Prima: la prima jsp chiama il metodo lista del managedBean che fa
public String lista(){
//Ottiene dati dal db
setElencoRecord(datiDalDb)
return "lista"
}
nella seconda ho   <h:dataTable
value="#{tipologicaStandardForm.elencoRecord}"  che quindi invoca il
public Collection getElencoRecord(){
return elencoRecord;
}
così facendo ho l'anomalia che sappiamo.
Se invece io ho
public Collection getElencoRecord(){
lista();
return elencoRecord();
}
Ossia, se l'invocazione al db e la generazione di elencoRecord viene
fatta quando la pagina "si carica" allora funziona tutto. Immagino
quindi che sia jsf stesso a lavorare con la session e a mettere
elencoRecod in sessione.
Allora la mia domanda è questa: ma se questo dovesse essere il modo di
procedere (ossia, ogni campo di output viene "caricato dal db" al
caricamento della pagina), non avrei N chiamate al db (=N chiamate EJB
session) per ogni campo di output anzichè (come facevo io) una sola
che caricava tutto quello che serviva una sola volta?

posso (via jsf) regolare lo scope.
Come gia' detto il managed-bean deve avere session scope, e di conseguenza 
anche le sue property avranno lo stesso scope ovviamente.

anche se come valore del commandLink metto una stringa fissa anzichè
l>'outputText che vedete.
evidentemente il problema si verifica prima dell'OutputText nel bean 
"tipologicaStandardForm".
Comunque prova a commenatre ogni accesso al database nel bean e fatti 
restituire direttamente una collezione diqualcosa generata a runtime nel 
bean (per minimizzare la possibilità di errori esterni), se il "caricamento" 
dei dati nella collection avviene una volta sola, assicurati che avvenga nel 
costruttore del bean.
ciao


Era per semplificare l'esempio. Ovviamente il command link sarà
specifico del record (devo ancora pensare bene come): ossia, fai
"paginaDiModifica" per il record sulla riga in cui sei (pensavo di
usare un campo hidden)


Affatto. Il metodo viene chiamato dalla prima jsp (guarda il
commandLink che sta dentro) il quale "popola" elencoRecord ed effettua
il  forward. La collezione non è affatto vuota e difatti io vedo i
valori nel datatable

 ciao
Il primo esempio che avevo postato creava la collection direttamente
nella jsp proprio per questo.
Non posso usare il costruttore perchè il bean si occupa di diverse
cose e non è che posso mettere nel costruttore le chiamate a tutti i
suoi metodi

application, anzichè per risolvere un problema applicativo?
Ma scusa, stiamo parlando della solita HttpSession eh!