What you may not know about PHP session

Summary

PHP's default session management settings, specifically session.gc_maxlifetime and session.cookie_lifetime, are often unreliable for robust user session control. The garbage collector for gc_maxlifetime runs probabilistically and uses file modification time instead of last access time, leading to potential premature session deletion or persistence. Meanwhile, cookie_lifetime only affects the client-side cookie, not the server-side session validity. A more reliable approach involves implementing a custom session timeout by storing a 'LAST_ACCESSED' timestamp within the session data. This timestamp should be updated on every request, allowing developers to accurately check for inactivity and manually destroy sessions when the defined timeout is exceeded.

When we access one website, the site usually should have a mechanism to keep track of the status of the user on the site. There are a few mechanisms supported by many server side languages to help track user status such as session and cookie.

Today we will talk about session, when creating a session, we need to keep track of many data, besides user data, we also need to tell the server what is the timeout of the session so that we can garbage collect the session data which should not be stored anymore. How do we implement a reliable session mechanism?

In PHP, we are often told that we can change the value of session.gc_maxlifetime and session.cookie_lifetime in php.ini or by setting ini_set('session.gc-maxlifetime', time) and ini_set('session.cookie_lifetime',time) if you cannot edit php.ini. But the truth is these settings are not reliable. Instead we should implement the session timeout ourselves. The reasons are:

First for session.gc_maxlifetime, from the PHP manual:

session.gc_maxlifetime
session.gc_maxlifetime specifies the number of seconds after which data will be seen as 'garbage' and cleaned up. Garbage collection occurs during session start.

But the garbage collector starts only with a probability of session.gc_probability divided by session.gc_divisor as specified in php.ini. If you use the default values for these options), the chance of the garbage collection is only at 1%.

Of course you can adjust these values so that the garbage collector can start garbage collection more often. But when the garbage collector is started, it will check the validity for every registered session, if there are many sessions on the server at the moment, the cost is very high.

Furthermore, when using PHP’s default session save handler files, the session data is stored in files in a path specified in session.save_path. With that session handler the age of the session data is calculated on the file’s last modification date and not the last access date:

The reason why using modification time is that on Windows, we cannot access the access time of a file, so to make it cross platform compatible, after PHP 4.2.3, the modification time of the file is used to check the session validity.

The drawback of using modification time is that it additionally might occur that a session data file is deleted while the session itself is still considered as valid because the session data may not be updated within the session timeout.

Second for session.cookie_lifetime, from the PHP manual:

session.cookie_lifetime
session.cookie_lifetime specifies the lifetime of the cookie in seconds which is sent to the browser. […]

This does only affect the cookie lifetime and the session itself may be still valid. But it’s the server’s task to invalidate a session, not the client’s. So this doesn’t help anything.

The best solution is to implement a session timeout on our own. Use a simple time stamp that denotes the time of the last page request:

if(isset($_SESSION['LAST_ACCESSED'])&&(time()- $_SESSION['LAST_ACCESSED']>1800)){// last request was more than 30 minutes ago
    session_unset();// unset $_SESSION variable
    session_destroy();// destroy session data in storage
}
$_SESSION['LAST_ACCESSED']= time();// update this on every page request

Updating the session data with every request does also change the session file’s modification date so that the session is not removed by the garbage collector prematurely.

This solution can be also used in other languages.

EXAMPLE PHP SESSION SESSION TIMEOUT

  RELATED

  COMMENTS

0

No comment for this article.