Welcome Guest, Not a member yet? Register   Sign In
Sessions Performance Issue (php7.1, CI 3.1.5)
#1

Currently, within the Session library when using file  - we see `CI_Session_files_driver::read` taking up to 20s to process. We have tried using Redis, and see the same thing on `CI_Session_files_driver::_lock`.

I've done the following:
1) Add `session_write_close();` to Sessions.php anytime I touch the session object before returning
2) Added `php_value session.gc_probability 10 php_value session.gc_divisor 100` to my `.htaccess`  to kick off garabage collection.
3) Use my own folder for `session_save`, and put it outside the web directory, and gave `www-data` access as the owner.

Sessions are pouring in, and getting removed so I know GC is working, but I see still see these performance issues on requests tracked in NewRelic where it takes 13-20s at some times to read the file (open it for lock).

An `ls -l` shows the following on the sessions folder:

drwxrwxrwx  2 www-data root 1126400 Aug 23 04:34 session

I assume this is a IO issue, where the file is being written and read from the same time, but 1) should address this. Anytime a session is touched (read or write) I add `session_write_close();`. I applied this on:
- `public function sess_destroy()`
- `public function userdata($key = NULL)`
- `public function set_userdata($data, $value = NULL)`
- `public function unset_userdata($key)`

All these function do  a `session_write_close()` before return.

Any other ideas on performance issues or this is a bug?
Reply
#2

This solved my problems - wish this would be documented better with CI: https://ma.ttias.be/php-session-locking-...-requests/
Reply
#3

It's been documented all over the forums here but maybe it should be pinned some place.
What did you Try? What did you Get? What did you Expect?

Joined CodeIgniter Community 2009.  ( Skype: insitfx )
Reply
#4

(08-23-2017, 10:10 PM)gregavola Wrote: This solved my problems - wish this would be documented better with CI: https://ma.ttias.be/php-session-locking-...-requests/

https://www.codeigniter.com/user_guide/l...oncurrency

Quote:A note about concurrency
Unless you’re developing a website with heavy AJAX usage, you can skip this section. If you are, however, and if you’re experiencing performance issues, then this note is exactly what you’re looking for.

Sessions in previous versions of CodeIgniter didn’t implement locking, which meant that two HTTP requests using the same session could run exactly at the same time. To use a more appropriate technical term - requests were non-blocking.

However, non-blocking requests in the context of sessions also means unsafe, because modifications to session data (or session ID regeneration) in one request can interfere with the execution of a second, concurrent request. This detail was at the root of many issues and the main reason why CodeIgniter 3.0 has a completely re-written Session library.

Why are we telling you this? Because it is likely that after trying to find the reason for your performance issues, you may conclude that locking is the issue and therefore look into how to remove the locks ...

DO NOT DO THAT! Removing locks would be wrong and it will cause you more problems!

Locking is not the issue, it is a solution. Your issue is that you still have the session open, while you’ve already processed it and therefore no longer need it. So, what you need is to close the session for the current request after you no longer need it.

Long story short - call session_write_close() once you no longer need anything to do with session variables.
Reply
#5

I just want to point out while the documentation it simply does not work. There are tons of articles and documentation, but a clear answer:

According to CI docs you should do this:
Long story short - call session_write_close() once you no longer need anything to do with session variables.

However, adding this to the Session Lib doesn't work, where are they supposed to go?
Reply
#6

(09-21-2017, 11:29 AM)gregavola Wrote: I just want to point out while the documentation it simply does not work. There are tons of articles and documentation, but a clear answer:

According to CI docs you should do this:
Long story short - call session_write_close() once you no longer need anything to do with session variables.

However, adding this to the Session Lib doesn't work, where are they supposed to go?

eg.

PHP Code:
class Musterclass extends CI_Controller {
    public function 
mister_long_method()
    {
        
//add/delete/read the session
        
session_write_close();
        
$this->bigmodel->getVeryLongQuery('i am very slow');
    }

Reply
#7

You can read from sessions after calling session_write_close( ); but you can't write to them. In every controller method either call this first inside your method or immediately after the last session write call. This is assuming you're auto-loading the session library. If you aren't you can call close in the places you do use sessions after you're done writing to them.
Reply
#8

(This post was last modified: 12-11-2019, 02:00 PM by blasto333.)

I have the following code below and even in the view method, it can still get locked (With redis or database driver). I want to be able to run the view method parallel. It doesn't seem to do this all the time.

Code:
<?php
class App_files extends MY_Controller
{
    function __construct()
    {
        parent::__construct();    
    }
    
    //$extra_file_name can be used for SEO purposes but is not acutally used in function
    function view($file_id,$extra_file_name = FALSE)
    {
        //cast to index in case we have extension
        $file_id = (int)$file_id;
        //Don't allow images to cause hangups with session
        session_write_close();
        $this->load->model('Appfile');
        $file = $this->Appfile->get($file_id);
        $file_name = $file->file_name;
        $this->load->helper('file');
        header("Cache-Control: max-age=2592000");
        header('Expires: '.gmdate('D, d M Y H:i:s', strtotime('+1 month')).' GMT');
        header('Pragma: cache');
        header('Content-Disposition: inline; filename="'.$file_name.'"');
        header("Content-type: ".get_mime_by_extension($file->file_name));
        
        if (function_exists('header_remove'))
        {
          foreach(headers_list() as $header)
            {
                if (strpos($header, 'Set-Cookie') === 0)
                {
                 header_remove('Set-Cookie');
                }
            }
        }
        echo $file->file_data;
    }
}
?>
Reply




Theme © iAndrew 2016 - Forum software by © MyBB