Een postbode zonder geheugen
Een server is een postbode zonder geheugen. Elk verzoek is een brief, en zodra het antwoord weg is, is hij de brief vergeten. Hij weet alleen wat op de brief staat en wat in zijn schrift staat: de database. Hoe weet zo'n server dan dat jij bent ingelogd? Jullie spelen het na, in drie rondes.
Wat je nodig hebt
- Per groepje van drie: strookjes papier voor de brieven, een envelop als koekjestrommel, een schrift voor de server en een pen per persoon.
- Ongeveer 25 minuten.
De rollen
- Sam speelt de browser. Hij schrijft brieven aan de server en bewaart in de koekjestrommel wat de server hem vraagt te bewaren. Elke brief aan de server krijgt alles uit de trommel mee.
- De server leest de brief, mag in zijn schrift kijken en schrijven, en schrijft een antwoord. Daarna draait hij de brief om: hij weet niets meer.
- Alex is een andere bezoeker. Hij heeft geen wachtwoord van Sam, maar hij mag brieven schrijven met wat hij wil erop.
In het schrift van de server staat al: sam: welkom123. Een bericht slaat de
server alleen op als hij weet van wie het is. Weet hij dat niet, dan antwoordt
hij 401 Log eerst in.
Ronde 1: zonder cookies
Sam stuurt twee brieven na elkaar.
POST /inloggenmetnaam=samenwachtwoord=welkom123POST /gastenboekmetbericht=Hoi
Gok eerst: weet de server bij brief 2 dat die van Sam komt? ______
Ronde 2: een cookie met de naam
Nu antwoordt de server op een goede inlog met: "bewaar naam=sam". Sam
stopt dat in de trommel, en stuurt het bij elke brief mee. De server gelooft
de naam op de brief. Speel Sams twee brieven opnieuw. Daarna schrijft Alex
één brief: POST /gastenboek met bericht=Ik vind dit gastenboek saai, en hij schrijft er
zelf naam=sam bij.
Gok eerst: van wie komt het bericht van Alex, volgens het gastenboek? ______
Ronde 3: een sessie
Nu doet de server het anders. Bij een goede inlog gooit hij drie keer met
een dobbelsteen en schrijft hij die cijfers in zijn schrift, bijvoorbeeld
sessie 352 is van sam. Sam krijgt alleen het nummer: "bewaar
sessie_id=352". Bij een bericht zoekt de server het nummer op in zijn
schrift. Staat het er niet, dan weet hij niet van wie de brief is.
Speel Sams brieven opnieuw. Daarna probeert Alex het twee keer: één keer met
sessie_id=sam, en één keer met een nummer dat hij zelf verzint.
Gok eerst: lukt het Alex? ______
| Ronde | Brief | Mee uit de trommel | Wat de server weet | Antwoord |
|---|---|---|---|---|
| 1 | Sam: inloggen | |||
| 1 | Sam: bericht | |||
| 2 | Sam: bericht | |||
| 2 | Alex: bericht | |||
| 3 | Sam: bericht | |||
| 3 | Alex: bericht |
Bespreek na
- In ronde 1 logt Sam goed in, en toch weet de server het bij de volgende brief niet meer. Wat doet het gastenboek in de basis van de cursus daarom bij elk bericht?
- Wat ging er mis in ronde 2? Wie bepaalt wat er in een cookie staat?
- Waarom werkt ronde 3 wel? Wat zou het makkelijker maken voor Alex?
- Waarom gooit een echte server niet drie keer, maar met
secrets.token_hex(16)?
Antwoorden
| Ronde | Brief | Mee uit de trommel | Wat de server weet | Antwoord |
|---|---|---|---|---|
| 1 | Sam: inloggen | niets | naam en wachtwoord kloppen | goed ingelogd |
| 1 | Sam: bericht | niets | alleen bericht=Hoi | 401 Log eerst in |
| 2 | Sam: bericht | naam=sam | "dit is sam" | bericht van sam opgeslagen |
| 2 | Alex: bericht | naam=sam, zelf geschreven | "dit is sam" | bericht van sam opgeslagen |
| 3 | Sam: bericht | sessie_id=352 | 352 staat in het schrift: sam | bericht van sam opgeslagen |
| 3 | Alex: bericht | een verzonnen nummer | het staat niet in het schrift | 401 Log eerst in |
Zo zoekt de server in ronde 3, met een dictionary als schrift:
sessies = {"352": {"naam": "sam"}}
for sessie_id in ["352", "sam", "614"]:
mijn = sessies.get(sessie_id, {})
print(sessie_id, mijn.get("naam"))
Uitvoer:
352 sam
sam None
614 None
Bespreek na. Vraag 1: elk bericht stuurt het wachtwoord opnieuw mee: een
kleine inlog per bericht. Vraag 2: de server geloofde wat er op de brief
stond. Een cookie staat in de browser, en wat in de browser staat, kan de
bezoeker zelf schrijven. Vraag 3: het nummer zegt zelf niets; alleen het
schrift van de server weet bij wie het hoort. Met maar drie dobbelstenen zijn
er 216 nummers, en die kan Alex allemaal proberen. Vraag 4: token_hex(16)
maakt 32 tekens uit 16 mogelijkheden per teken. Dat zijn zoveel nummers dat
niemand er een raadt.
Verder op de site
- In de les: Inloggen: een wachtwoord controleren, Onthouden met een cookie, Onthouden op de server: sessies en Cookie of sessie?.
- Wat er met een sessie nog mis kan gaan, staat in de reeks Cookies afschermen.