32

How can I set session expiration time dynamically in codeigniter?

For example, if a user logs in and has the role of admin, the expiration time should be longer than if a user logs in who does not have an admin role.

Thanks.

Brad Bird
  • 737
  • 1
  • 11
  • 30
Siregar
  • 321
  • 1
  • 3
  • 3

12 Answers12

33

You can update your session expiration time by increasing this variable in config file:

$config['sess_expiration'] = 'somevalue'.

Set $config['sess_expiration'] = 0, if you want it to never expire.

Here's a good discussion on CI forums:

Dynamically set configuration on session expire doesn’t work

Firze
  • 3,939
  • 6
  • 48
  • 61
talha2k
  • 24,937
  • 4
  • 62
  • 81
  • 7
    People keep upvoting this, but I think by reading the description this is not what the OP was asking for. He says "manually" which would be accomplished by this answer (a constant value in the config), but if you read what he's actually trying to do he means "dynamically" based on which user role is logged in. So setting the value in the config file will not help, because it will be the same value no matter the user role. – solidau Aug 10 '11 at 06:51
  • 1
    yeah, I agree. After figuring out this step he's going to ultimately want to set it dynamically to accomplish what he's really asking for. So that's why my answer earlier would really help his cause. Upvote that one for the foresight :). – Chamilyan Aug 10 '11 at 07:41
  • @Juventus 18, yeah..that's what i mean – Siregar Aug 11 '11 at 00:19
  • I find that setting sess_expiration doesn't prevent expiration of the session and my session data is stored in the database. – Martin Oct 31 '12 at 15:12
  • I have made an edit to the original post to make it more clear what the questioner is asking for. – Brad Bird Aug 12 '15 at 08:39
  • What to fill if I dont want the session expiration to be activated? All this time, I make it expired after 1 week logged in – Attaroqqi Feb 11 '20 at 03:40
  • @Attaroqqi Set $config['sess_expiration'] = 0, if you want it to never expire. – talha2k Feb 11 '20 at 11:13
14
$data = array(
'username' => $this->input->post('username'),
'ADMIN_is_logged_in' => true
);

$this->session->sess_expiration = '14400';// expires in 4 hours
$this->session->set_userdata($data);// set session
2

None of these solutions address doing this dynamically or require another variable to be added to the session. The solution I came up with for CI 3.0.4 is to extend Session.php.

  1. Create file application/libraries/Session/MY_Session.php

  2. Put the following into the file and modify for your logic of setting the $expiration variable. In my case I am pulling the value from a database. NOTE: If you have different expiration values per user type; there is a chance they could get garbage collected and expire unexpectedly due to different expirations with the same session. In this case I do NOT recommend this approach.

    <?php
    class MY_Session extends CI_Session 
    {
        public function __construct(array $params = array())
        {
            parent::__construct($params);
        }
    
        /**
         * Configuration
         *
         * Handle input parameters and configuration defaults
         *
         * @param   array   &$params    Input parameters
         * @return  void
         */
        protected function _configure(&$params)
        {
            $CI =& get_instance();
            $phppos_session_expiration = NULL;
    
            $CI->db->from('app_config');
            $CI->db->where("key", "phppos_session_expiration");
            $row = $CI->db->get()->row_array();
            if (!empty($row))
            {
                if (is_numeric($row['value']))
                {
                    $phppos_session_expiration = (int)$row['value'];
                }
            }
    
            $expiration = $phppos_session_expiration !== NULL ? $phppos_session_expiration : config_item('sess_expiration');
    
            if (isset($params['cookie_lifetime']))
            {
                $params['cookie_lifetime'] = (int) $params['cookie_lifetime'];
            }
            else
            {
                $params['cookie_lifetime'] = ( ! isset($expiration) && config_item('sess_expire_on_close'))
                    ? 0 : (int) $expiration;
            }
    
            isset($params['cookie_name']) OR $params['cookie_name'] = config_item('sess_cookie_name');
            if (empty($params['cookie_name']))
            {
                $params['cookie_name'] = ini_get('session.name');
            }
            else
            {
                ini_set('session.name', $params['cookie_name']);
            }
    
            isset($params['cookie_path']) OR $params['cookie_path'] = config_item('cookie_path');
            isset($params['cookie_domain']) OR $params['cookie_domain'] = config_item('cookie_domain');
            isset($params['cookie_secure']) OR $params['cookie_secure'] = (bool) config_item('cookie_secure');
    
            session_set_cookie_params(
                $params['cookie_lifetime'],
                $params['cookie_path'],
                $params['cookie_domain'],
                $params['cookie_secure'],
                TRUE // HttpOnly; Yes, this is intentional and not configurable for security reasons
            );
    
            if (empty($expiration))
            {
                $params['expiration'] = (int) ini_get('session.gc_maxlifetime');
            }
            else
            {
                $params['expiration'] = (int) $expiration;
                ini_set('session.gc_maxlifetime', $expiration);
            }
    
            $params['match_ip'] = (bool) (isset($params['match_ip']) ? $params['match_ip'] : config_item('sess_match_ip'));
    
            isset($params['save_path']) OR $params['save_path'] = config_item('sess_save_path');
    
            $this->_config = $params;
    
            // Security is king
            ini_set('session.use_trans_sid', 0);
            ini_set('session.use_strict_mode', 1);
            ini_set('session.use_cookies', 1);
            ini_set('session.use_only_cookies', 1);
            ini_set('session.hash_function', 1);
            ini_set('session.hash_bits_per_character', 4);
        }
    
    }
    
Chris Muench
  • 17,444
  • 70
  • 209
  • 362
1

In Codeigniter 4 Go to the file App=>Config=>App.php Find the var $sessionExpiration The default value for this var is 7200 Change it to the value as you want your session to be alive. The complete config for the session is given below:

 public $sessionDriver = 'CodeIgniter\Session\Handlers\FileHandler';
public $sessionCookieName = 'ci_session';
public $sessionExpiration = 7200;
public $sessionSavePath = WRITEPATH . 'session';
public $sessionMatchIP = false;
public $sessionTimeToUpdate = 300;
public $sessionRegenerateDestroy = false;
Kapil Kumar
  • 143
  • 3
1

You can handle this with a custom controller. When a user logs in, set a session variable with the time of login. Create custom controller that contains a function in the constructor to check if the user is not admin user and if the timeout has expired. If it has, call $this->session->destroy(); Now, make all your controllers extend that controller instead of the CI base controller.

solidau
  • 4,021
  • 3
  • 24
  • 45
  • When the code arrives to a custom controller the session has already started, so it won't work. It's probably needed to extend the Session file class. – giovannipds Mar 21 '18 at 20:51
  • @giovannipds You would need a session started to decide whether to destroy it, correct? cant decide on null/unknown data... – solidau Nov 28 '18 at 03:53
0

Session will expire in 10 seconds

$config['sess_expiration']= 10;

Session will not expire

$config['sess_expiration']= 0;
Abd Abughazaleh
  • 4,615
  • 3
  • 44
  • 53
0

In Codeigniter 4, I do it the other way.

Set the session expiration time to maximal value (for example month for everybody) then in your controller or libraries, if the user is not admin, check the last active time, if time is more than what you need, destroy session and require log in.

hery
  • 49
  • 6
-1

use something like this:

$user_type = $this->input->post('user_type');
if ($user_type == 'admin')
{
    //set session to non-expiring
    $this->session->sess_expiration = '32140800'; //~ one year
    $this->session->sess_expire_on_close = 'false';
}
else
{
    //set session expire time, after that user should login again
    $this->session->sess_expiration = '1800'; //30 Minutes
    $this->session->sess_expire_on_close = 'true';
}

//set session and go to Dashboard or Admin Page
$this->session->set_userdata(array(
    'id' => $result[0]['id'],
    'username' => $result[0]['username']
));
Reza Amya
  • 89
  • 1
  • 10
-1

At codeigniter go to applications/config.php and find the below configuration.

$config['sess_expiration'] = 14400; //in seconds
abilash kumar
  • 179
  • 1
  • 9
-1

In your login functionality just after user credentials have been verified you can check if user is admin and set different sessions accordingly. Something along these lines

<?php
/*
 *Assuming user is successfully veriefied and you've verified id user is admin*/

if($isAdmin==true){
$this->session->sess_expiration = 14400; // 4 Hours

}else{

// For ordinary users
$this->session->sess_expiration = 1800; // 30 minutes 
   

}
$this->session->sess_expire_on_close = FALSE;
Cengkuru Michael
  • 4,590
  • 1
  • 33
  • 33
  • No, changing the session expiration time after it has already been initiated doesn't and won't work, I've tested this today. – giovannipds Mar 21 '18 at 20:51
-1

I think the most better chooice is using session temp_data and always you can change is dynamically and it is not depended your 'sess_expiration' in config file:

$this->session->set_tempdata('admin_session', true, 72000);
$this->session->set_tempdata('user_session', true, 14400);

where you check admin or user login state, like 'ADMIN_is_logged_in?' check the remained 'tempdata' lifetime by:

 if($this->session->tempdata('admin_session')){
//do something }
else{ 
//session timeout and is time to destroy all sessions
session_destroy();
}
ganji
  • 752
  • 7
  • 17
-3

You can solve the session issue by replacing this:

$config['sess_use_database'] = TRUE;
$config['sess_encrypt_cookie'] = TRUE;

with this:

$config['sess_use_database'] = FALSE;
$config['sess_encrypt_cookie'] = FALSE;
Adi Inbar
  • 12,097
  • 13
  • 56
  • 69