Praćenje isteka sesije u pregledniku

Dakle, postoji ta složena heterogena web aplikacija, s AJAX dijelovima koji se rade ručno i pomoću okvira, više iskačućih prozora itd. Veliki ugledni klijent vam se obraća sa zahtjevom da onesposobi, zatvori ili izvrši neke druge aktivnosti na cijelom webu prozori programa jednom kada HTTP sesija istekne. Nadamo se da znate kako kontrolirati interval isteka HTTP sesije, za web-aplikaciju koja je kompatibilna s J2EE to se radi iz datoteke web.xml (međutim, na većini poslužitelja aplikacija to nije na standardni način). Za 10-minutni time-out je:

  10  

Zahtjev klijenta uopće nije apsurdan i ima savršenog smisla iz perspektive krajnjeg korisnika, ali za razvojnog programera može postati užasna muka jer: 1. Ne možete jednostavno pokrenuti odbrojavanje u prozoru preglednika svaki put kad se stranica učita zatvoriti prozor nakon isteka vremena. Ovaj je pristup funkcionirao u svijetu koji nije AJAX-ov kada je svaka interakcija preglednika i poslužitelja rezultirala ponovnim učitavanjem prozora preglednika. 2. Ne možete postaviti upit poslužitelju da provjeri je li HTTP sesija istekla ili nije, jer će se svaki takav upit tretirati kao interakcija preglednika i poslužitelja koji produžuje sesiju. To će dovesti do sesije koja nikada ne ističe. 3. Možete stvoriti zasebnu web-aplikaciju koja je svjesna HTTP sesije primarne web-aplikacije i presijeca se s njom. Ali to je pretjerano,a šanse da se takvo rješenje prihvati izuzetno su malene zbog problema s integracijom koji će se vjerojatno pojaviti. 4. Možete pokušati presresti sve interakcije preglednika i poslužitelja AJAX nekim naprednim kodom sličnim hakanju, a to će vam pomoći da se nosite sa svojim trenutnim prozorom. Ali to ne funkcionira u slučaju s više otvorenih prozora - jednostavno ne možete komunicirati između prozora preglednika. Jedini način za razgovor s nekim otvorenim prozorom iz primarnog jest korištenje JavaScript reference drugog prozora, a nakon što se primarni prozor ponovo učita ili usmjeri na drugo mjesto, on gubi sve JavaScript reference na drugi prozor. 5. Najrealniji pristup je postavljanje povremenih JavaScript XMLHTTP zahtjeva (iz svakog otvorenog prozora) prema poslužitelju svaki {maks. Neaktivni interval sesije} +10 sekundi. Ovo će na kraju zatvoriti sve prozore,ali može rezultirati minutama zatvorenim (ili čak satima, ovisno o postavci vremenskog ograničenja sesije web-aplikacije) nakon uništavanja HTTP sesije, npr. nakon što se korisnik odjavi iz primarnog prozora. Nema više mogućnosti, frustrirani ste i mislite da je pravo vrijeme da sutra uzmete tatin pištolj i pucate u školske kolege. Ne, još nisam dijete - još uvijek postoji izlaz! Izlaz nije vrlo jednostavan, ali je vrlo elegantan. Kolačići će nam pomoći. Moglo bi se pomisliti da će vrijeme isteka kolačića učiniti trik. Nažalost, kako je opisano upravo je vrijeme da sutra uzmeš tatin pištolj i pucaš u školske kolege. Ne, još nisam dijete - još uvijek postoji izlaz! Izlaz nije vrlo jednostavan, ali je vrlo elegantan. Kolačići će nam pomoći. Moglo bi se pomisliti da će vrijeme isteka kolačića učiniti trik. Nažalost, kako je opisano upravo je vrijeme da sutra uzmeš tatin pištolj i pucaš u školske kolege. Ne, još nisam dijete - još uvijek postoji izlaz! Izlaz nije vrlo jednostavan, ali je vrlo elegantan. Kolačići će nam pomoći. Moglo bi se pomisliti da će vrijeme isteka kolačića učiniti trik. Nažalost, kako je opisano u

ovaj

U članku se ne možete osloniti na vrijeme isteka kolačića jer ga mjeri klijentski preglednik i nitko ne može jamčiti da sat klijentskog sustava ne kasni godinu dana. Dakle, ovdje je sustav i metoda za praćenje HTTP sesije u heterogenim web aplikacijama. Na svaki zahtjev upućen iz preglednika na poslužitelj, dva kolačića postavlja se filtrom servleta. Jedna drži trenutno vrijeme poslužitelja, a druga vrijeme isteka sesije. Trenutno vrijeme poslužitelja potrebno je samo za izračunavanje odstupanja između klijenta i poslužitelja. Zatim se povremeno provjerava vrijeme isteka sesije u odnosu na _računato_ tekuće vrijeme poslužitelja (sjetite se pomaka). Svaki put kada se _ bilo koji_ zahtjev uputi poslužitelju, kolačić s vremenom isteka ažurira se i cijela stvar jednostavno funkcionira. U praksi se ova metoda realizira u samo tri koraka: 1.Stvorite filtar servleta koji će filtrirati svaki zahtjev za vašu web-aplikaciju. Konfigurirajte ga u web.xml ovako:

  SessionTimeoutCookieFilter some.package.SessionTimeoutCookieFilter   SessionTimeoutCookieFilter /*  

Ne brinite zbog performansi svoje web-aplikacije - ovaj je filtar VRLO primitivan, samo dodaje odgovoru dva kolačića:

 public void doFilter(ServletRequest req, ServletResponse resp, FilterChain filterChain) throws IOException, ServletException { HttpServletResponse httpResp = (HttpServletResponse) resp; HttpServletRequest httpReq = (HttpServletRequest) req; long currTime = System.currentTimeMillis(); long expiryTime = currTime + session.getMaxInactiveInterval() * 1000; Cookie cookie = new Cookie("serverTime", "" + currTime); cookie.setPath("/"); httpResp.addCookie(cookie); if (httpReq.getRemoteUser() != null) { cookie = new Cookie("sessionExpiry", "" + expiryTime); } else { cookie = new Cookie("sessionExpiry", "" + currTime); } cookie.setPath("/"); httpResponse.addCookie(cookie); filterChain.doFilter(req, resp); } 

Put postavljanja (u našem slučaju na "/") je vrlo važan. Ako izostavite postavku puta, preglednik će je automatski izračunati iz URL-a što će rezultirati kaosom unutar pohrane kolačića vašeg preglednika. 2. Potreban nam je mali JavaScript na svakom prozoru da bismo izračunali odmak između vremena poslužitelja i klijenta. Treba ga pokrenuti samo jednom, ali ne bi škodilo pokrenuti ga pri svakom učitavanju stranice:

 function calcOffset() { var serverTime = getCookie('serverTime'); serverTime = serverTime==null ? null : Math.abs(serverTime); var clientTimeOffset = (new Date()).getTime() - serverTime; setCookie('clientTimeOffset', clientTimeOffset); } window.onLoad = function() { calcOffset(); }; 

3. I na kraju trebamo funkciju koja bi zapravo provjerila je li sesija istekla. Potrebno ga je izvršavati povremeno, u našem slučaju svakih 10 sekundi (ili 10000 milisekundi):

 function checkSession() { var sessionExpiry = Math.abs(getCookie('sessionExpiry')); var timeOffset = Math.abs(getCookie('clientTimeOffset')); var localTime = (new Date()).getTime(); if (localTime - timeOffset > (sessionExpiry+15000)) { // 15 extra seconds to make sure window.close(); } else { setTimeout('checkSession()', 10000); } } 

Zapravo, zatvaranje prozora preglednika po isteku sesije čista je brutalnost, a može i treba biti popraćeno porukom upozorenja koja će se pojaviti oko 1 minute prije isteka sesije. Stvarno me zanima vaš

kritičke povratne informacije

na moju metodu.

Ovu je priču "Praćenje isteka sesije u pregledniku" izvorno objavio JavaWorld.