Problemi con session e ajax

Ciao, in una applicazione rails sto sviluppando una chat e il seguente
problema mi sta facendo impazzire:
Semplificando al massimo io salvo l’id della chat aperta nella session
in una action richiamata via ajax, ma spesso l’id non viene salvato e
rimane a nil. Oppure la richiesta ajax di chiusura non elimina l’id.

Sembrerebbe quasi un problema di concorrenza tra più richieste parallele
via ajax che però… non ci sono, a meno che non entrino in gioco i
filtri dell’autenticazione. L’app usa authlogic, che salva l’autenticaz.
in un altro cookie “user_credentials” mentre la mia session salva in
“_bd_session”, il default.

Qualunque aiuto è ben accetto, non so più dove sbattere il testone.

Di solito questi sono proprio problemi di concorrenza. Se usi il cookie
session store ti basterà tracciare le chiamate http, ad esempio con
livehttpheaders (firefox) e vedere i valori dei cookie cambiare (sono
codificati, ma il cambiamento si vede lo stesso). Se usi un session
store su file system o su database devi ragionarci un po’ e tracciare le
varie chiamate. Il problema è spiegato molto bene a
http://www.paulbutcher.com/2007/05/race-conditions-in-rails-sessions-and-how-to-fix-them/
Ci ho sbattuto il testone pure io.

Paolo

Matteo F. wrote:

Ciao, in una applicazione rails sto sviluppando una chat e il seguente
problema mi sta facendo impazzire:
Semplificando al massimo io salvo l’id della chat aperta nella session
in una action richiamata via ajax, ma spesso l’id non viene salvato e
rimane a nil. Oppure la richiesta ajax di chiusura non elimina l’id.

Sembrerebbe quasi un problema di concorrenza tra più richieste parallele
via ajax che però… non ci sono, a meno che non entrino in gioco i
filtri dell’autenticazione. L’app usa authlogic, che salva l’autenticaz.
in un altro cookie “user_credentials” mentre la mia session salva in
“_bd_session”, il default.

Qualunque aiuto è ben accetto, non so più dove sbattere il testone.

Paolo M. wrote:

Di solito questi sono proprio problemi di concorrenza. Se usi il cookie
session store ti basterà tracciare le chiamate http, ad esempio con
livehttpheaders (firefox) e vedere i valori dei cookie cambiare (sono
codificati, ma il cambiamento si vede lo stesso). Se usi un session
store su file system o su database devi ragionarci un po’ e tracciare le
varie chiamate. Il problema è spiegato molto bene a
http://www.paulbutcher.com/2007/05/race-conditions-in-rails-sessions-and-how-to-fix-them/
Ci ho sbattuto il testone pure io.

Paolo

Ok. Direi proprio che abbiamo individuato il problema. E’ indubbiamente
un problema di concorrenza.
Dalla tua esperienza mi conviene passare subito le session sul db e
usare il plugin smart_session_store o ha senso cercare di aggirare il
problema continuando ad utilizzare il cookieStore ?
Una cosa che mi lascia perplesso è che nell’articolo (e nel ticket) si
dice esplicitamente che per vedere il problema bisogna usare una coppia
di mongrel, invece io ce l’ho anche con webrick.
In pratica però il session store si può usare solo per richieste non
ajax.

Riassumo le mie umili conclusioni:

Prima di tutto nell’app. chat e msg erano già risorse rest, e tutto
funzionava bene. Il problema mi sorgeva cercando di gestire molte chat
aperte su molte pagine (le chat seguono l’utente su tutto il sito), per
tenere traccia delle cose aperte utilizzavo le session, però le
richieste ajax degli aggiornamenti, delle chiusure ecc ecc si
incrociavano e quindi problemi di concorrenza come ottimamente descritto
nell’articolo citato da Paolo.

La mia soluzione è stata barbaramente gestire le informazioni relative
alle chat aperte da ciascun utente in una tabella, aggiornata via metodi
privati del controller chat. Grezzo ma efficace. Una risorsa rest mi
sembrava esagerata allo scopo (anche se sarebbe stato tranquillamente
fattibile).

L’insegnamento che ho tratto è che non posso usare le session per stati
che variano via ajax, a meno di non essere assolutamente sicuri che non
si “sovrappongano” più richieste (se le diverse richieste ajax partono
solo da stati differenti del sistema).
Per star tranquillo come mia regola non aggiornerò mai l’hash session in
action ajax. Di fatto limitando l’uso delle session ai dati di autentica
e magari qualche preferenza temporanea dell’utente.

Grazie dell’aiuto.

Piccola premessa: quando ho iniziato con Rails venivo dal mondo Java ed
usavo le session con entusiasmo tipicamente javista (javico?) per cui ho
finito presto per incorrere in questi problemi e ho usato una versione
rimaneggiata di smart session store per risolverli. Poi ho messo la
testa a posto, per così dire, ed ora in session non metto quasi più
nulla. L’approccio restful alla progettazione delle applicazioni aiuta
molto a tenere le session scarne.

Venendo a noi dovresti identificare precisamente il problema e poi
capire se puoi applicare il metodo di smart session store al cookie
store. La sensazione è che non si possa. Ho però anche la sensazione che
per quanto si transazionalizzino gli aggiornamenti della sessione non si
possa risolvere il problema in generale: potrebbero esserci due thread
di esecuzione nel browser con assunzioni completamente diverse sullo
stato della sessione e potrebbe essere impossibile riconciliarle.
L’unica cosa che penso si possa fare è risolvere il tuo problema
particolare, magari con altre soluzioni. Ad esempio: l’id della chat
aperta non si può memorizzare nell’url invece che nella session? Sembra
un approccio restful

POST /chat/1 manda un messaggio
GET /chat/1 polla per un messaggio

Ok, questa non è del tutto restful perché ritorna valori diversi ogni
volta, ma puoi leggere

e

per soluzioni alternative.

Paolo

Matteo F. wrote:

Paolo M. wrote:

Di solito questi sono proprio problemi di concorrenza. Se usi il cookie
session store ti basterà tracciare le chiamate http, ad esempio con
livehttpheaders (firefox) e vedere i valori dei cookie cambiare (sono
codificati, ma il cambiamento si vede lo stesso). Se usi un session
store su file system o su database devi ragionarci un po’ e tracciare le
varie chiamate. Il problema è spiegato molto bene a
http://www.paulbutcher.com/2007/05/race-conditions-in-rails-sessions-and-how-to-fix-them/
Ci ho sbattuto il testone pure io.

Paolo

Ok. Direi proprio che abbiamo individuato il problema. E’ indubbiamente
un problema di concorrenza.
Dalla tua esperienza mi conviene passare subito le session sul db e
usare il plugin smart_session_store o ha senso cercare di aggirare il
problema continuando ad utilizzare il cookieStore ?
Una cosa che mi lascia perplesso è che nell’articolo (e nel ticket) si
dice esplicitamente che per vedere il problema bisogna usare una coppia
di mongrel, invece io ce l’ho anche con webrick.
In pratica però il session store si può usare solo per richieste non
ajax.