Momenteel maak ik gebruik van het Zend Framework inclusief een custom session_save_handler() zodat mijn sessies netjes in een database worden opgeslagen.
Alleen zit ik nu met de volgende vraag:
Op het moment dat er een Session ID gezet wordt door PHP, wordt er aan de kant van de browser een cookie aangemaakt met het Sessie ID.
Stel dat ik dat sessie ID verander, dan accepteert PHP dit ID als zijnde het nieuwe Sessie ID tijdens een session_start().
Hoe kan ik er nu voor zorgen dat PHP alleen maar sessie ID's accepteert die serverside gegenereerd zijn (a la Microsoft IIS)?
Het probleem zat hem namelijk in de write-functie van mijn session_save_handler.
Hier schrijf ik het sessie_id tezamen met de sessie-data weg in de sessie-tabel van de database.
In die tabel heb ik een veld: sessie_id gedefinieerd van VARCHAR(32).
Dat komt dus overeen met de standaard lengte van een PHP5 server side gegeneerde session_id().
Maar als ik het cookie nu manipuleer, en ik maak van die sessie-id gewoon een heel lange string, dan krijg ik in mijn output een vage foutmelding te zien, naar aanleiding van de write actie in mijn session_save_handler class.
Dus ik wil eigenlijk weten wat hier nu best practise is.
Moet ik bijvoorbeeld tijdens de write-actie checken of de session_id wel 32 karakters lang is in onderstaande functie?
Of is er nog een andere betere manier?
B.t.w., dit probleem geldt waarschijnlijk gewoon voor de manier waarop PHP met sessies omgaat,
in dit (http://www.acros.si/papers/session_fixation.pdf) document noemen ze het namelijk een "permissive session management":
Alleen zit ik nu met de volgende vraag:
Op het moment dat er een Session ID gezet wordt door PHP, wordt er aan de kant van de browser een cookie aangemaakt met het Sessie ID.
Stel dat ik dat sessie ID verander, dan accepteert PHP dit ID als zijnde het nieuwe Sessie ID tijdens een session_start().
Hoe kan ik er nu voor zorgen dat PHP alleen maar sessie ID's accepteert die serverside gegenereerd zijn (a la Microsoft IIS)?
Het probleem zat hem namelijk in de write-functie van mijn session_save_handler.
Hier schrijf ik het sessie_id tezamen met de sessie-data weg in de sessie-tabel van de database.
In die tabel heb ik een veld: sessie_id gedefinieerd van VARCHAR(32).
Dat komt dus overeen met de standaard lengte van een PHP5 server side gegeneerde session_id().
Maar als ik het cookie nu manipuleer, en ik maak van die sessie-id gewoon een heel lange string, dan krijg ik in mijn output een vage foutmelding te zien, naar aanleiding van de write actie in mijn session_save_handler class.
Dus ik wil eigenlijk weten wat hier nu best practise is.
Moet ik bijvoorbeeld tijdens de write-actie checken of de session_id wel 32 karakters lang is in onderstaande functie?
Of is er nog een andere betere manier?
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
| // deze write functie komt uit mijn custom save_handler klasse: /** * Write Session - commit data to resource * * @param string $id The session ID * @param mixed $data The session data * @return bool */ public function write($id, $data) { // Hier dan checken of $id wel 32 karakters is????? $dbSelect = $this->_zendDb->select(); $dbSelect->from($this->_tableName, 'COUNT(session_id)'); $dbSelect->where($this->_zendDb->quoteIdentifier('session_id') . ' = ?', $id); $result = (int) $this->_zendDb->fetchOne($dbSelect); if ($result) { $tblData = array( 'last_update' => new Zend_Db_Expr('NOW()'), 'expiry' => new Zend_Db_Expr($this->_zendDb->quoteInto('DATE_ADD(NOW(), INTERVAL ? SECOND)', $this->_lifeTime)), 'hits' => new Zend_Db_Expr($this->_zendDb->quoteIdentifier('hits') . ' + 1'), 'value' => $data ); $where = $dbSelect->getPart(Zend_Db_Select::WHERE); $affectedRows = $this->_zendDb->update($this->_tableName, $tblData, $where); } else { $tblData = array( 'session_id' => $id, 'created' => new Zend_Db_Expr('NOW()'), 'last_update' => new Zend_Db_Expr('NOW()'), 'expiry' => new Zend_Db_Expr($this->_zendDb->quoteInto('DATE_ADD(NOW(), INTERVAL ? SECOND)', $this->_lifeTime)), 'value' => $data ); $affectedRows = $this->_zendDb->insert($this->_tableName, $tblData); } return $affectedRows; } |
B.t.w., dit probleem geldt waarschijnlijk gewoon voor de manier waarop PHP met sessies omgaat,
in dit (http://www.acros.si/papers/session_fixation.pdf) document noemen ze het namelijk een "permissive session management":
We can classify session management mechanisms on web servers in two classes:
a) “Permissive”: those that accept arbitrary session IDs, and create a new session
with proposed session ID if one doesn’t exist yet (e.g., Macromedia JRun
server, PHP).
b) “Strict”: those that only accept known session IDs, which have been locally
generated at some point in the past (e.g., Microsoft Internet Information
Server).
[ Voor 10% gewijzigd door DPLuS op 18-06-2007 18:36 ]