Newsgroup: it.comp.lang.javascript
Titolo: javascript che modifica form in un frameset

Ho gia' postato questa richiesta su un paio di forum internazionali (di 
javascript e di firefox) ma senza ricevere nulla di particolare. Spero 
che qualcuno qui mi sappia dire di piu' !
Ho (da diversi anni) un arrangiamento di un frameset che contiene un 
form nella frame superiore, la cui action e' una servlet java. Questa 
servlet interroga via JDBC un database mysql e (in un paio di passi) 
scrive nella frame inferiore del codice javascript che modifica il 
contenuto del form (il codice invoca delle function che stanno nella 
HEAD del frameset).
Tutto questo ha sempre funzionato col mio vecchio firefox (inserendo gli 
opportuni permessi in user.js). Da quanto sono passato a firefox 3.6 ha 
smesso di funzionare.
Si direbbe un problema di timing, come se il DOM del frameset non fosse 
ancora completo quando il javascript nella frame inferiore viene 
generato.
Ho fatto un tot di esperimenti (verifica W3C, test sostituendo la 
servlet con dell'HTML statico o dei CGI) che mostrano come il codice 
javascript (che ho usato per anni) sia sano, e che il problema si 
presenta solo con la servlet.
E' inutile che racconti qui dettagli, che ho invece gia' scritto nella 
pagina che presenta i test cases
http://sax.iasf-milano.inaf.it/~lucio/temp/prova/
Ringrazio chiunque mi dara' delle dritte !
-- 
----------------------------------------------------------------------
nos...@mi.iasf.cnr.it
 is a newsreading account used by more persons to
avoid unwanted spam. Any mail returning to this address will be rejected.
Users can disclose their e-mail address in the article if they wish so.

 smesso di funzionare.
[CUT]
Non entro in merito della cosa perché non sono competente, ma giusto ieri 
sera un amico mi diceva che ha installato firefox 3.6 (su ubuntu, ma 
immagino sia irrilevante) e la virtual machine non funzionava più.
Dopo ricerche in rete, ha scoperto che hanno cambiato la virtual machine, 
e che, se ricordo bene quello che mi hanno detto, ha cambiato path ... 
dice che ci ha messo parecchio per trovare la soluzione, una volta 
trovata è bastato puntare il plug-in al path corretto e ha riniziato a 
funzionare tutto... vedi se può servirti come spunto, a naso pare la 
stessa problematica.

 path ...
Dovrebbe essere una cosa del tutto diversa da QUESTO mio caso. Nel mio 
caso la servlet java gira su una altra macchina, quindi non ha niente a 
che fare col browser. Potrebbe essere un cgi o un altro http server che 
"scrive" dell'HTML. O no ?
Diverso sarebbe il caso se fosse un applet. ALLORA girerebbe nella 
virtual machine del browser. Been there done that ! Di fatto su Suse il 
plugin java di firefox che viene su di default e' quello di openjdk, che 
ha una resa grafica schifosa. Mi hanno consigliato di sostituirlo col 
java della Sun, cosa che ho fatto (e lo yast2 di Suse ha ripuntato i 
path come si deve ... cosa che non ha fatto [non poteva fare] per 
openoffice - che ho scoperto a posteriori dipendere da java - dato che 
il path sta in un file xml nella user config :-( )


 "scrive" dell'HTML. O no ?
No, il problema è quasi sicuramente lato client: lanciando gli script a 
pagina completata tutti gli elementi e le funzioni compaiono correttamente.
Sono riuscito facilmente a riprodurre l'errore che segnali ma non è 
banale capire quale ne sia l'origine: supponendo che sulla suse tu abbia 
un firefox 1.0 o 1.5 tra gecko 1.7 e 1.9 di modifiche ne son state fatte 
parecchie, anche riguardo alla gestione della creazione del DOM [1].
Di soluzioni ce ne sono due, IMO:
- seguire la seconda parte del consiglio di Cristiano, ossia togliere i 
frame (ovviamente non la servlet :-) ) e usare AJAX;
- provare ad aggiungere dei timeout (meglio ancora: debuggare con 
firebug mettendo dei breakpoint) prima dei "changeItem" e vedere se 
trovi il punto critico.
Personalmente consiglierei la prima, visto che è anche il mio abituale 
approccio alla creazione di pagine con questo tipo di funzionalità. Di 
fatto è molto più semplice gestire, debuggare, modificare una pagina con 
"due" funzioni AJAX che non n pagine su vari frame (soluzione che tu 
stesso definisci un accrocchio).
La seconda soluzione potrebbe inoltre essere "ingannevole" perché 
abilitare il debug degli script in firebug altera l'ordine di rendering 
della pagina (i thread che possono, procedono; gli altri aspettano il 
via libera dall'utente).
Buon lavoro! ;-)
[1] ad esempio, abbastanza radicale, il nuovo thread manager:
https://developer.mozilla.org/en/The_Thread_Manager

 abilitare il debug degli script in firebug altera l'ordine
Per alterare l'ordine o il timing basta anche meno. P.es. il codice 
javascript che uso per verificare il permesso di modificare le cose 
anche contro la "same-origin-policy"). Nel caso di pagine locali (non 
generate dalla servlet), il javascript va DOPO la prima occorrenza in 
cui gli dico di ricordare per sempre il permesso. Se invece lascio che 
esca il popup ogni volta, il timing nella generazione del DOM e' diverso 
(si ferma uno statement PRIMA di quando lo fa con le servlet, sul reset 
del form)
Il workaround che ho trovato e implementato e' il seguente. La servlet
NON scrive piu' il codice javascript nella frame di sotto, ma in un file 
html temporaneo. Dopo di che fa un sendRedirect a quello.
(incidentalmente a posteriori mi rendo conto che questo eliminerebbe 
anche la necessita' di configurare i permessi per derogare alla same 
origin policy ... la servlet gira su hosta:8080 mentre la pagina 
rediretta sarebbe su hosta e basta, dove stanno anche frameset e frame)
Comunque, prima di fare un sendRedirect, ho provato anche a fare 
scrivere alla servlet nella frame di sotto un singolo statement 
(this.location='....vattelapesca.html') e questo aveva lo stesso effetto 
favorevole.
Ossia introdurre quel minimo delay che basta !


 Ossia introdurre quel minimo delay che basta !
Sì, come avevamo intuito.
Permettimi però una "critica" a questo approccio: ora con l'aggiunta 
artificiosa di un "rallentatore" riesci ad aggirare il problema ma non 
hai nessuna garanzia su quanto questa soluzione sia stabile e duratura.
Ad esempio hai problemi con Chrome? Il suo motore JavaScript è più 
veloce, sarebbe un test interessante.
IMHO sostituire l'attuale codice JavaScript con altro codice che carichi 
in modo asincrono (cosa che ti darebbe la garanzia citata poc'anzi) 
quanto ti serve ti permetterebbe di semplificare e rendere più robusto 
il tutto.
Tra l'altro vi sono una miriade di librerie Java per generare e gestire 
automaticamente chiamate AJAX: 
http://ajaxpatterns.org/Java_Ajax_Frameworks
In alternativa anche lavorare sull'evento onload dei documenti potrebbe 
essere una soluzione più solida, senza stravolgere il tutto.

 ancora completo quando il javascript nella frame inferiore viene generato.
Fammi capire. La form sta nel frame superiore, e la action chiama una
servlet java. Quindi l'esecuzione avviene nel submit della form, ergo la
pagina viene ricaricata. Ora, il target della form mi pare di capire si
a quello inferiore. Ma in tal caso, solo quello viene ricaricato. Ergo,
il DOM del parent non viene rigenerato e ci� che si trovava prima vi si
trova tutt'ora. Differente sarebbe se tutta la pagina venisse nuovamente
ricaricata.
Installa Firebug, fai un po' di debug, vedi cosa accade quando provi a
chiamare la funzione nel frameset, e qual'� il valore di "parent" in
quel momento.
Puoi anche fare un semplice - sempre con firebug - console.dir(parent)
dal frame - quindi lo generer� la servlet - per vedere che valore ha.
Prova eventualmente a cambiare "parent" con "top".
Il consiglio � quello di debuggare comunque e vedere cosa accade. Facci
sapere!
-- 
"When you have eliminated the impossible, whatever remains, however
improbable, must be the truth."

 
https://developer.mozilla.org/en/DOM/window.postMessage
fico! (oddio, non mi viene in mente un momento in cui ne abbia avuto 
bisogno, però, al bisogno ... :-))

 bisogno, però, al bisogno ... :-))
I casi sono molteplici. Se I browser implementassero tutti correttamente
le richieste cross domain, ce ne sarebbe meno bisogno probabilmente.
Con postMessage puoi far comunicare due siti con stesso dominio e porte
differenti, o protocolli differenti, o subdomain differenti. Gli esempi
si sprecano, ma uno eclatante potrebbe essere l'invio di informazioni
sensibili senza dover mettere tutto il sito in HTTPS, e senza cambio
della pagina. Puoi esporre solo le API server side di autenticazione in
HTTPS, mentre il resto del sito / applicazione è in HTTP.
