Oprettet ons. d. 10. marts 2010 kl. 17:37:45

steffen
steffen (44.427 point. Point ude: 400)

Parallel afvikling af requests i den samme session i PHP?

Jeg vil gerne høre om der er nogen har en opskrift til at tillade at to scripts kan udføres simultant i den samme session?

Det ser ud til at PHP har implicit session locking pr. default, og jeg synes ikke jeg har held af at implementere nogle af de metoder der burde kunne slå denne sessionslåsning fra.

Men for at demonstrere hvad jeg er ude efter, så prøv at 1) oprette dette script (det udskriver 60 lodrette streger med et sekunds mellemrum):

<?php
print "[";

for($i = 0; $i < 100; $i++){
  $spaces.="<!-- bufferme -->";
} // for

//and then

for($i = 0; $i < 60; $i++){
  for($ii = 0; $ii < 200000; $ii++){
    //do something slow here
  } // for
  sleep(1);
  print "$spaces|";
  flush();
} // for

print "]";

?>

Dernæst, 2) åbn to browsertabs i din browser og 3) kald scriptet fra begge.

Hvis det virker som jeg håber at kunne demonstrere, så køres kun ét af scriptene ad gangen.

Jeg har prøvet forskellige ting, fx at overskrive save_handler med session_set_save_handler (http://theserverpages.com/ (...)), men det giver ikke rigtigt nogen effekt, låsningen synes effektiv lige meget hvad jeg gør. Dvs. scriptet to browsertabs bliver afviklet "i serie" - først den ene, og når den så er færdig, så først dernæst påbegynder den anden.

Jeg har fundet et par sider på nettet der tilsyneladende omhandler problemet:

http://thwartedefforts.org/ (...)

http://www.tonymarston.co.uk/ (...)

http://blog.perplexedlabs.com/ (...)

Men altså ingen af dem med en opskrift jeg har været heldig med at kunne få til at du.

Så mit spørgsmål er egentligt bare: Hvilke linier mangler i mit script for at jeg kan køre to instanser af scriptet samtidigt, i to tabs i min browser (dvs. i samme session)?

Skrevet ons. d. 10. marts 2010 kl. 18:21:02| #1

kimsey0
kimsey0 (23.154 point)
jacobbundgaard.dk
Hmm... Jeg har aldrig stødt på dette problem før, men kan forestille mig, at det faktisk er en funktion ("It's a feature, not a bug"). Ellers kunne to scripts jo prøve at modificere samme sessionsvariabel på samme tid, og derved skabe fejl og sikkerhedsproblemer.

if($isadmin) { $_SESSION['userlevel']++}

Den eneste måde at afhjælpe det på, jeg lige kan finde er, selv at lave en session handler med alt hvad der hører med, men det er besværligt og helt ligeså usikkert som PHPs sessions ville have været med funktionen indbygget.

Skrevet ons. d. 10. marts 2010 kl. 19:34:05| #2

steffen
steffen (44.427 point)
"Den eneste måde at afhjælpe det på, jeg lige kan finde er, selv at lave en session handler ..."

Super! Det lyder spændende - hvordan gjorde du?

Selv om jeg overrider phps default session handler med session_set_save_handler(), gør det ikke rigtigt nogen forskel for mig. Og jeg har efterhånden prøvet en hel del forskellige måder, skulle jeg hilse at sige :-)

Kan du lokkes til at paste det kode du fik til at køre i parallel, i samme session?

Skrevet ons. d. 10. marts 2010 kl. 21:19:20| #3

kimsey0
kimsey0 (23.154 point)
jacobbundgaard.dk
Jeg tror ikke PHP's session-handle er muligt at manipulere til dette, lige meget hvor meget man prøver (med mindre man selvfølgelig er C++-hacker, men så kan man jo alt).
Til gengæld kan man lave sin helt egen session handler, selvom det er besværligt. Jeg har desværre ikke lavet en kode til dette, men kan da hurtigt forklare en grundlæggende model:

1) Definer funktioner til læsning og skrivning af sessioner, samt  i database
2)Tjek om brugeren har sat en session-cookie og:
2a) Tjek om dette id er udløbet. Hvis ikke, læs id'ets variabler fra databasen eller
2b) Opret et nyt, ubrugt session-id
3) Send en session cookie til brugeren. Dette gøres under alle omstændigheder for at sikre, at den ikke udløber
4) Fyld en global variabel med sessionsvariablerne
5) Brug de prædefinerede funktioner til at ændre på sessionsvariablerne

Skrevet ons. d. 10. marts 2010 kl. 22:52:00| #4

steffen
steffen (44.427 point)
Som jeg lige læser din kommentar #3, så handler den om at implementere en session handler fra scratch.

Men jeg vil i egentligt bare gerne se helt bort fra sessioner, dvs. se væk fra cookies, headers, synkroniseret tilgang til variable, http-protokol-spindsfindigheder osv osv .... alt det man normalt skal vride hovedet af led for at tage højde for :-)

Mit spørgsmål handler stadig bare om noget parallel afvikling af noget php-kode, så simpelt som muligt, i to tabs i en browser.

Skrevet ons. d. 10. marts 2010 kl. 23:31:54| #5

kimsey0
kimsey0 (23.154 point)
jacobbundgaard.dk
Jeg forstår ikke helt dit spørgsmål, og især ikke, hvorfor sleep() skal blandes ind i det. Sleep laver netop en masse rod med (klient)sessioner. I praksis vil du heller aldrig have brug for funktionen.

Ønsker du alligevel at få dit script til at virke, kan du prøve at indsætte funktionskaldet session_write_close(); før dit sleep-kald. Det burde fjerne den sammenhæng du ser.

Skrevet ons. d. 10. marts 2010 kl. 23:43:08| #6

steffen
steffen (44.427 point)
Jeg har også læst at session_write_close(); skulle virke mange steder, men jeg har ikke haft held af det - har du en kodestump du har kunnet få til at du?

For mig gør det ingen forskel om jeg erstatter sleep med andre konstruktioner heller - har du kunnet konstatere en forskel?

Skrevet tor. d. 11. marts 2010 kl. 09:31:24| #7

Du har jo egentlig allerede i dine artikler fundet svaret; race conditions giver ballade og der skal derfor tages højde for dem.
Det eneste du opnår ved at implementere en af de strukturer som er nævnt i artiklen er en 'løsere' form for kontrol at tilgangen til en session. Det er jo ikke nødvendigvis en god ting - udover at det aldrig vil kunne løse dit 'problem', for fuldstændig som kimsey0 er inde på, så er det en feature - ikke en bug. Det er en feature som sikrer dig at du ikke laver race conditions i dine applikationer.

For at tage udgangspunkt i dit eget script, så sker der faktisk det at i det samme du starter scriptet (i din første tab), session_start() initialiseres, så låses din session til den pågældende tråd (script). Den resource frigives først i det øjeblik scriptet afsluttes. Når den resource er frigivet vil du opleve at scriptet (fra den anden tab) starter. Meget logisk og ganske korrekt.

Skrevet tor. d. 11. marts 2010 kl. 10:29:41| #8

steffen
steffen (44.427 point)
Jeg kan nu godt lide "friheden til at vælge selv" - jeg har ikke nogen session_start() i mit script - og hvis du antyder at den fyres af automatisk, så vil jeg egentligt bare gerne vide hvordan jeg overtaler php til at lade være :-)

Skrevet tor. d. 11. marts 2010 kl. 10:38:32| #9

Du misser pointen lidt... udgangspunktet var dit eget script; selvom du ikke bruger sessions i scriptet vil sessions fungere som jeg beskriver.

Det du oplever med at dit specifikke script ikke vil eksekvereres af flere processer samtidig kan jeg ikke nikke genkendende til.
Jeg kan have adskille 'tabs' åbne og se at scriptet kører som forventet - altså samtidig uden jeg skal vente på at nogle af processerne bliver færdige for at den næste proces kan startes.

Dit spørgsmål gik mere på behandlingen af sessions; i tilfælde af du ville anvende sessions i scriptet måtte du vente på at din session blev frigivet til at blive skrevet i på ny.

Skrevet tor. d. 11. marts 2010 kl. 10:40:39| #10

Og for lige at knytte en kommentar til konceptet om "friheden til at vælge selv" i forhold til race conditions, så hænger verden jo sammen på den måde at selvom jeg godt kan lide idéen om at flyve som supermand, så er der nogle naturlove der gør at jeg ret basalt ikke er i stand til det. Samme koncept gør sig også gældende inden for programmering; der er nogle ting du ikke kan, grundet det omkringliggende miljøs begrænsninger.

Skrevet tor. d. 11. marts 2010 kl. 11:05:41| #11

steffen
steffen (44.427 point)
"Det du oplever med at dit specifikke script ikke vil eksekvereres af flere processer samtidig kan jeg ikke nikke genkendende til."

Ydrk - det lyder rigtigt spændende! Er det på en php-instans jeg kan nå fra nettet? Et php-info dump fra den ville jeg helt sikkert sætte meget pris på hvis du vil af med det.

Ang. "friheden til at vælge selv" tænker jeg mere på at jeg bare gerne selv vil have lidt indflydelse på hvor jeg gerne vil have mutual exclusiveness og jeg ikke vil, ikke andet. Og at høre at du har en opsætning der kører i to tabs samtidigt, giver allerede temmeligt meget blod på tanden i den retning :-)

Skrevet tor. d. 11. marts 2010 kl. 11:26:23| #12

Du kan se scriptet eksekveres på min server her:
http://err0r.dk/ (...)

En video af min test her:
http://rapidshare.com/ (...)

Min phpinfo() kan ses her:
http://err0r.dk/ (...)

Skrevet tor. d. 11. marts 2010 kl. 13:25:31| #13

steffen
steffen (44.427 point)
Øijs, det var jo lækkerier.

Fik afprøvet scriptet på et par hosts mere, og fandt en der opførte sig ligesådan (yay!). Og det viser sig at forskellen lå i en php setting - om "session.auto_start" er sat til "on".

Den er nu slået fra ... og nu virker det søreme :-)

- i ie, safari og andre - men ikke i firefox. Heller ikke mod dit site, herfra. Og det er tilsyneladende lige meget om jeg har pipelining settings slået til eller fra osv.

Hvilken opførsel får du i firefox? (Mange tak for den fine video i øvrigt, det var jo luksus at gå videre på :-)).

Skrevet tor. d. 11. marts 2010 kl. 13:27:17| #14

steffen
steffen (44.427 point)
Er gået i google-mode på firefox'en - har fundet et par links der lyder lidt til at det er en opførsel andre er stødt i på firefox før - men har ingen forklaring/løsning endnu:

http://www.bigresource.com/ (...)

http://www.bigresource.com/ (...)

Skrevet tor. d. 11. marts 2010 kl. 13:50:36| #15

Videoen jeg havde lavet var optaget fra Firefox (findes der andre? ;) )

Som du selv konstaterer, så opstår 'problemet' først når der er tale om brugen af sessions. De to artikler du har fundet omhandler også race conditions i session handling - hvis man lige læser mellem linierne...

At din firefox så ikke behandler min test som jeg selv oplevede den, kan jeg ikke svare dig på. Det kan have noget at gøre med den måde Firefox håndterer sin forbindelse på. Jeg anvender Firefox 3.6.

Skrevet tor. d. 11. marts 2010 kl. 14:24:35| #16

steffen
steffen (44.427 point)
Hmmm, dumdidum - hvad i alverden kan det nu være, der gør forskellen der, det vil jeg sgu gerne lige holde fast i ...

Jeg har lige prøvet i både firefox 3.5.8 og 3.6 på Windows, men  uden held. Har prøvet både med og uden safemode. Med "gamle"  indstillinger og med "rene" (oprettede en ny bruger i Windows for hver version og prøvede med den).

"c:\Program Files\Mozilla Firefox\firefox.exe" --safe-mode

Har du noget i din prefs.js der kunne afsløre om du har en speciel magisk setting der et sted? Dvs. i

c:\Users\<user>\AppData\Roaming\Mozilla\Firefox\Profiles\<profile>.default\prefs.js

respektivt

c:\Documents and Settings\<user>\Application Data\Mozilla\Firefox\Profiles\<profile>.default\prefs.js ?

Eller måske et plugin der skubber på? (FasterFox eller lign).

Jeg kører selv med nedenstående indstillinger lige nu, mest fordi pipelining netop skulle medføre at requests blev parallelle - men "nr. 2" tab opretter ikke engang en tcp-forbindelse til serveren når den bliver sat i gang :-/

user_pref("network.http.keep-alive", false);
user_pref("network.http.max-connections", 60);
user_pref("network.http.max-connections-per-server", 30);
user_pref("network.http.max-persistent-connections-per-proxy", 12);
user_pref("network.http.max-persistent-connections-per-server", 12);
user_pref("network.http.pipelining", true);
user_pref("network.http.pipelining.maxrequests", 30);
user_pref("network.http.pipelining.ssl", true);
user_pref("network.http.proxy.pipelining", true);

Hvad for noget Windows afvikler du i øvrigt i? Har prøvet ovenstående eksperimenter i XP og i 64 bit win 7, uden forskel.

Skrevet tor. d. 11. marts 2010 kl. 14:41:19| #17

Jeg har adskillige udvidelser i min firefox, men ikke nogen der skal øge perfomance. Som udgangspunkt har jeg aldrig cache slået til (det er livet sq for kort til), men det er nok også det eneste jeg kunne forestille mig kunne have det mindste at sige.

Kører Win 7 x64 UK Pro.

Jeg er ikke sikker på at jeg forstår hvorfor du vil fokusere på netop det at klienterne ikke behandler kaldet ens; laveste fællesnævner er jo netop nu at det ikke altid kan lade sig gøre, selvom forholdene - serverside - er til det. Burde det så ikke være dit udgangspunkt? Du kan jo på ingen måde bestemme over klienten alligevel, ej heller være sikker på om problemet er det samme hos alle klienter?

Skrevet tor. d. 11. marts 2010 kl. 14:45:45| #18

steffen
steffen (44.427 point)
Tjoe, det kan vi godt blive enige om, at der er flere måder at komme til Mekka på her. Men derfor er det nu alligevel interessant for mig, om ikke andet så af princip for bare at prøve at forstå browserforskellene nu.

Virker de to tabs simultant når du kører safe mode?

"c:\Program Files\Mozilla Firefox\firefox.exe" --safe-mode

Kom til at tænke på, hvis ikke du har alt for hemmelige ting i din prefs.js (eller kan genskabe "evnen" for en ny bruger / ny profil), kan du måske lokkes til at uploade sådan en virkende en?

Skrevet tor. d. 11. marts 2010 kl. 15:43:56| #19

steffen
steffen (44.427 point)
Øijs, det viser sig at min udgave af firefox serializerer requests mod det samme url internt, og at det faktisk bare er det der driller nu:

Dvs. at hvis bare jeg ændrer lidt i url'erne:

http://err0r.dk/ (...)
http://err0r.dk/ (...)
http://err0r.dk/ (...)

osv, så kan jeg køre alle dem jeg vil nu.

Med andre ord "Jubiiii!! :-)"

Sæføli er jeg nu lidt nysgerrig efter om ikke jeg kan overtale firefox til at lade være med at tænke for mig der også - hvis jeg beder om den samme url to gange, så er det jo _fordi_ jeg vil se indholdet to gange .... nu, tak! ... men det kan godt vente til en anden dag med at finde ud af om det kan overrules et sted :-)

Mange tak for tålmodig hjælp og støtte, det er meget værdsat!

Skrevet tor. d. 11. marts 2010 kl. 19:38:41| #20

Så kom jeg lige lidt tilbage igen; jamen, det var da alligevel rart at der kom lidt forklaring hvad det gik ud på - men det er jo nok firefox' måde at cache på, hvorfor jeg ikke oplevede det samme som dig, da den som udgangspunkt konsekvent er slået fra hos mig - så det må jo konsekvent være en ny forespørgsel hver gang.

Jeg har nu - til samme URL som tidligere, tilføjet nogle headere der skulle fortælle browseren den ikke må cache resultatet og at resultatet i forvejen er forældet.

Prøv lige igen, uden at rette URL'en (du skal naturligvis lige tømme din cache først).

Skrevet fre. d. 19. marts 2010 kl. 10:03:38| #21


Skriv et indlæg




Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] [img]link til billede[/img]
Web- og emailadresser omdannes automatisk til links

Log ind

   

   

Seneste spørgsmål

INNER JOIN mellem 2 tabler

Oprettet den 4. februar 2012 kl. 02.49
tobrukDk giver 15 point for svar | Giv et svar »

gøre password mere sikkert

Oprettet den 4. februar 2012 kl. 00.09
tobrukDk giver 30 point for svar | Giv et svar »

ingen bruger eller lign i database frem vise tekst

Oprettet den 3. februar 2012 kl. 20.18
tobrukDk giver 20 point for svar | Giv et svar »

Seneste guides

Den gode bruger
Adgang til NAS-server via WAN
Kollektion af Batch tutorials (FJERNET)
Tilpas din YouTube afspiller


   




Tips & Tricks fra PC World

Teaser billede

Sådan fjerner du pladskrævende metadata fra dine fotos

Det er langt fra altid, at dine billeders metadata såsom kameramodel og geografisk placering er vigtige at bevare. JPG & PNG Stripper kan luge ud i billedfilerne, så de fylder meget mindre....


Anmeldelser fra PC World

Teaser billede

Test: Superlet bærbar med mange muligheder

Toshiba har med Satellite Z830 skabt en af verdens letteste ultrabooks. Den vejer 1,1 kilo, og computeren på 13 tommer ser på papiret ud til at være en oplagt rejsekammerat. Men den lave vægt har...


Seneste blogindlæg

Teaser billede

Tvangslukke spørgsmål: Hvad er den bedste løsning?

Hej Vi har mange åbne spørgsmål på Eksperten. Vi ville gerne tvangslukke dem - så et spørgsmål efter f.eks. 6 måneder lukkes. Men der er et par uklarheder som ville være gode at få lidt input til:...


Nyheder fra PC World

Teaser billede

Samsung Galaxy S III på vej

Samsungs bedst sælgende smartphone nogensinde får en efterfølger om kort tid.


Nyheder fra Computerworld

Teaser billede

Apple retter hele 51 sikkerhedshuller i Mac OS X

Apple lukker hele 51 sårbarheder i Mac OS X, hvoraf de fleste er kritiske. Se her, hvor hullerne er.


Kurser
Samarbejdspartnere

Udgiver · © 2012 IDG Danmark A/S · Hørkær 18 · 2730 Herlev · Tlf.: 77 300 300 · Fax: 77 300 301 · Brug af personoplysninger