Hoe laat ik een PHP-sessie na 30 minuten verlopen?

Ik moet een sessie 30 minuten in leven houden en dan vernietigen.


Antwoord 1, autoriteit 100%

U moet zelf een sessietime-out implementeren. Beide opties genoemd door anderen (session.gc_maxlifetimeen sessie. cookie_lifetime) zijn niet betrouwbaar. Ik zal de redenen daarvoor uitleggen.

Eerst:

session.gc_maxlifetime
session.gc_maxlifetimespecificeert het aantal seconden waarna gegevens als ‘vuilnis’ worden gezien en opgeschoond. Het ophalen van huisvuil vindt plaats tijdens het starten van de sessie.

Maar de garbage collector wordt alleen gestart met een kans van session.gc_probabilitygedeeld door session.gc_divisor. En als we de standaardwaarden voor die opties gebruiken (respectievelijk 1 en 100), is de kans slechts 1%.

Nou, je kunt deze waarden gewoon aanpassen zodat de garbage collector vaker wordt gestart. Maar wanneer de garbage collector wordt gestart, controleert deze de geldigheid van elke geregistreerde sessie. En dat is kostenintensief.

Bovendien, bij gebruik van PHP’s standaard sessie .Save_Handler -bestanden, de sessiegegevens worden opgeslagen in bestanden in een pad dat is opgegeven in session.save_path . Met die sessiehandler wordt de leeftijd van de sessiegegevens berekend op de laatste modificatiedatum van het bestand en niet de laatste toegangsdatum:

Opmerking: Als u de standaardbestand-gebaseerde sessiehandler gebruikt, moet uw bestandssysteem toegangstijden bijhouden (ATIME). Windows-vet doet niet, dus je zult een andere manier moeten bedenken om afval te hanteren dat je sessie verzamelt als je vasthoudt met een vetbestandssysteem of een ander bestandssysteem waar Atime-tracking niet beschikbaar is. Sinds PHP 4.2.3 heeft het MMTime (gewijzigde datum) gebruikt in plaats van ATIME. U hebt dus geen problemen met bestandssystemen waar Atime-tracking niet beschikbaar is.

Dus het kan bovendien optreden dat een sessiedatabestand wordt verwijderd terwijl de sessie zelf nog steeds wordt beschouwd als geldig omdat de sessiegegevens niet recent zijn bijgewerkt.

en tweede:

session.cookie_lifetime
session.cookie_lifetime Specificeert de levensduur van de cookie in seconden die naar de browser wordt verzonden. […]

Ja, dat klopt. Dit heeft alleen invloed op de levensduur van de cookie en de sessie zelf kan nog steeds geldig zijn. Maar het is de taak van de server om een sessie ongeldig te maken, niet de client. Dit helpt dus niets. Als session.cookie_lifetimeop 0staat, zou de cookie van de sessie zelfs een echte sessiecookiedie alleen geldig is totdat de browser wordt gesloten.

Conclusie / beste oplossing:

De beste oplossing is om zelf een sessietime-out te implementeren. Gebruik een eenvoudige tijdstempel die de tijd van de laatste activiteit (d.w.z. verzoek) aangeeft en update deze bij elk verzoek:

if (isset($_SESSION['LAST_ACTIVITY']) && (time() - $_SESSION['LAST_ACTIVITY'] > 1800)) {
    // last request was more than 30 minutes ago
    session_unset();     // unset $_SESSION variable for the run-time 
    session_destroy();   // destroy session data in storage
}
$_SESSION['LAST_ACTIVITY'] = time(); // update last activity time stamp

Door de sessiegegevens bij elk verzoek bij te werken, wordt ook de wijzigingsdatum van het sessiebestand gewijzigd, zodat de sessie niet voortijdig door de vuilnisman wordt verwijderd.

Je kunt ook een extra tijdstempel gebruiken om de sessie-ID periodiek opnieuw te genereren om aanvallen op sessies zoals te voorkomen sessie fixatie:

if (!isset($_SESSION['CREATED'])) {
    $_SESSION['CREATED'] = time();
} else if (time() - $_SESSION['CREATED'] > 1800) {
    // session started more than 30 minutes ago
    session_regenerate_id(true);    // change session ID for the current session and invalidate old session ID
    $_SESSION['CREATED'] = time();  // update creation time
}

Opmerkingen:

  • session.gc_maxlifetimemoet ten minste gelijk zijn aan de levensduur van deze aangepaste expiratie-handler (1800 in dit voorbeeld);
  • als u de sessie wilt laten verlopen na 30 minuten activiteitin plaats van na 30 minuten sinds de start, moet u ook setcookiemet een vervaldatum van time()+60*30om de sessiecookie actief te houden.

Antwoord 2, autoriteit 8%

Eenvoudige manier om een PHP-sessie binnen 30 minuten te laten verlopen.

Opmerking: als je de tijd wilt wijzigen, verander dan de 30 met de gewenste tijd en verander niet * 60: dit geeft de minuten.


In minuten : (30 * 60)
In dagen : (n * 24 * 60 * 60 ) n = aantal dagen


Login.php

<?php
    session_start();
?>
<html>
    <form name="form1" method="post">
        <table>
            <tr>
                <td>Username</td>
                <td><input type="text" name="text"></td>
            </tr>
            <tr>
                <td>Password</td>
                <td><input type="password" name="pwd"></td>
            </tr>
            <tr>
                <td><input type="submit" value="SignIn" name="submit"></td>
            </tr>
        </table>
    </form>
</html>
<?php
    if (isset($_POST['submit'])) {
        $v1 = "FirstUser";
        $v2 = "MyPassword";
        $v3 = $_POST['text'];
        $v4 = $_POST['pwd'];
        if ($v1 == $v3 && $v2 == $v4) {
            $_SESSION['luser'] = $v1;
            $_SESSION['start'] = time(); // Taking now logged in time.
            // Ending a session in 30 minutes from the starting time.
            $_SESSION['expire'] = $_SESSION['start'] + (30 * 60);
            header('Location: http://localhost/somefolder/homepage.php');
        } else {
            echo "Please enter the username or password again!";
        }
    }
?>

HomePage.php

<?php
    session_start();
    if (!isset($_SESSION['luser'])) {
        echo "Please Login again";
        echo "<a href='http://localhost/somefolder/login.php'>Click Here to Login</a>";
    }
    else {
        $now = time(); // Checking the time now when home page starts.
        if ($now > $_SESSION['expire']) {
            session_destroy();
            echo "Your session has expired! <a href='http://localhost/somefolder/login.php'>Login here</a>";
        }
        else { //Starting this else one [else1]
?>
            <!-- From here all HTML coding can be done -->
            <html>
                Welcome
                <?php
                    echo $_SESSION['luser'];
                    echo "<a href='http://localhost/somefolder/logout.php'>Log out</a>";
                ?>
            </html>
<?php
        }
    }
?>

Uitloggen.php

<?php
    session_start();
    session_destroy();
    header('Location: http://localhost/somefolder/login.php');
?>

Antwoord 3, autoriteit 3%

Is dit om de gebruiker na een bepaalde tijd uit te loggen? Het instellen van de aanmaaktijd van de sessie (of een vervaltijd) wanneer deze is geregistreerd en vervolgens controleren of dat bij elke paginalading mogelijk is.

Bijvoorbeeld:

$_SESSION['example'] = array('foo' => 'bar', 'registered' => time());
// later
if ((time() - $_SESSION['example']['registered']) > (60 * 30)) {
    unset($_SESSION['example']);
}

Bewerken:ik heb het gevoel dat je iets anders bedoelt.

Je kunt sessies schrappen na een bepaalde levensduur door de session.gc_maxlifetimeini-instelling:

Bewerken:
ini_set(‘session.gc_maxlifetime’, 60*30);


Antwoord 4

Dit bericht laat een aantal manieren zien om de sessietime-out te beheren: http:// bytes.com/topic/php/insights/889606-setting-timeout-php-sessions

IMHO de tweede optie is een mooie oplossing:

<?php
/***
 * Starts a session with a specific timeout and a specific GC probability.
 * @param int $timeout The number of seconds until it should time out.
 * @param int $probability The probablity, in int percentage, that the garbage 
 *        collection routine will be triggered right now.
 * @param strint $cookie_domain The domain path for the cookie.
 */
function session_start_timeout($timeout=5, $probability=100, $cookie_domain='/') {
    // Set the max lifetime
    ini_set("session.gc_maxlifetime", $timeout);
    // Set the session cookie to timout
    ini_set("session.cookie_lifetime", $timeout);
    // Change the save path. Sessions stored in teh same path
    // all share the same lifetime; the lowest lifetime will be
    // used for all. Therefore, for this to work, the session
    // must be stored in a directory where only sessions sharing
    // it's lifetime are. Best to just dynamically create on.
    $seperator = strstr(strtoupper(substr(PHP_OS, 0, 3)), "WIN") ? "\\" : "/";
    $path = ini_get("session.save_path") . $seperator . "session_" . $timeout . "sec";
    if(!file_exists($path)) {
        if(!mkdir($path, 600)) {
            trigger_error("Failed to create session save path directory '$path'. Check permissions.", E_USER_ERROR);
        }
    }
    ini_set("session.save_path", $path);
    // Set the chance to trigger the garbage collection.
    ini_set("session.gc_probability", $probability);
    ini_set("session.gc_divisor", 100); // Should always be 100
    // Start the session!
    session_start();
    // Renew the time left until this session times out.
    // If you skip this, the session will time out based
    // on the time when it was created, rather than when
    // it was last used.
    if(isset($_COOKIE[session_name()])) {
        setcookie(session_name(), $_COOKIE[session_name()], time() + $timeout, $cookie_domain);
    }
}

Antwoord 5

Nou, ik begrijp dat de bovenstaande antwoorden correct zijn, maar ze zijn op toepassingsniveau, waarom gebruiken we niet gewoon het bestand .htaccessom de vervaltijd in te stellen?

<IfModule mod_php5.c>
    #Session timeout
    php_value session.cookie_lifetime 1800
    php_value session.gc_maxlifetime 1800
</IfModule>

Antwoord 6

if (isSet($_SESSION['started'])){
    if((mktime() - $_SESSION['started'] - 60*30) > 0){
        //Logout, destroy session, etc.
    }
}
else {
    $_SESSION['started'] = mktime();
}

Antwoord 7

Gebruik de session_set_cookie_paramsfunctie om dit te maken.

Moet deze functie worden aangeroepen voordat session_start()wordt aangeroepen.

Probeer dit:

$lifetime = strtotime('+30 minutes', 0);
session_set_cookie_params($lifetime);
session_start();

Zie meer in: http://php.net/manual/ function.session-set-cookie-params.php


Antwoord 8

Het is eigenlijk heel eenvoudig met een functie als de volgende. Het gebruikt de databasetabelnaam ‘sessions’ met de velden ‘id’ en ‘time’.

Telkens wanneer de gebruiker uw site of service opnieuw bezoekt, moet u deze functie gebruiken om te controleren of de geretourneerde waarde WAAR is. Als het ONWAAR is, is de gebruiker verlopen en wordt de sessie vernietigd (Opmerking: deze functie gebruikt een databaseklasse om verbinding te maken en de database te doorzoeken, u kunt dit natuurlijk ook binnen uw functie of iets dergelijks doen):

function session_timeout_ok() {
    global $db;
    $timeout = SESSION_TIMEOUT; //const, e.g. 6 * 60 for 6 minutes
    $ok = false;
    $session_id = session_id();
    $sql = "SELECT time FROM sessions WHERE session_id = '".$session_id."'";
    $rows = $db->query($sql);
    if ($rows === false) {
        //Timestamp could not be read
        $ok = FALSE;
    }
    else {
        //Timestamp was read succesfully
        if (count($rows) > 0) {
            $zeile = $rows[0];
            $time_past = $zeile['time'];
            if ( $timeout + $time_past < time() ) {
                //Time has expired
                session_destroy();
                $sql = "DELETE FROM sessions WHERE session_id = '" . $session_id . "'";
                $affected = $db -> query($sql);
                $ok = FALSE;
            }
            else {
                //Time is okay
                $ok = TRUE;
                $sql = "UPDATE sessions SET time='" . time() . "' WHERE session_id = '" . $session_id . "'";
                $erg = $db -> query($sql);
                if ($erg == false) {
                    //DB error
                }
            }
        }
        else {
            //Session is new, write it to database table sessions
            $sql = "INSERT INTO sessions(session_id,time) VALUES ('".$session_id."','".time()."')";
            $res = $db->query($sql);
            if ($res === FALSE) {
                //Database error
                $ok = false;
            }
            $ok = true;
        }
        return $ok;
    }
    return $ok;
}

Antwoord 9

Sla een tijdstempel op in de sessie


<?php    
$user = $_POST['user_name'];
$pass = $_POST['user_pass'];
require ('db_connection.php');
// Hey, always escape input if necessary!
$result = mysql_query(sprintf("SELECT * FROM accounts WHERE user_Name='%s' AND user_Pass='%s'", mysql_real_escape_string($user), mysql_real_escape_string($pass));
if( mysql_num_rows( $result ) > 0)
{
    $array = mysql_fetch_assoc($result);    
    session_start();
    $_SESSION['user_id'] = $user;
    $_SESSION['login_time'] = time();
    header("Location:loggedin.php");            
}
else
{
    header("Location:login.php");
}
?>

Controleer nu of de tijdstempel binnen het toegestane tijdvenster valt (1800 seconden is 30 minuten)

<?php
session_start();
if( !isset( $_SESSION['user_id'] ) || time() - $_SESSION['login_time'] > 1800)
{
    header("Location:login.php");
}
else
{
    // uncomment the next line to refresh the session, so it will expire after thirteen minutes of inactivity, and not thirteen minutes after login
    //$_SESSION['login_time'] = time();
    echo ( "this session is ". $_SESSION['user_id'] );
    //show rest of the page and all other content
}
?>

Antwoord 10

Gebruik het volgende codeblok in uw include-bestand dat op elke pagina is geladen.

$expiry = 1800 ;//session expiry required after 30 mins
    if (isset($_SESSION['LAST']) && (time() - $_SESSION['LAST'] > $expiry)) {
        session_unset();
        session_destroy();
    }
    $_SESSION['LAST'] = time();

Antwoord 11

Hoe PHP met sessies omgaat, is nogal verwarrend voor beginners om te begrijpen. Dit kan hen helpen door een overzicht te geven van hoe sessies werken:
hoe sessies werken(custom-session-handlers)


Antwoord 12

Gebruik deze les 30 min

class Session{
    public static function init(){
        ini_set('session.gc_maxlifetime', 1800) ;
        session_start();
    }
    public static function set($key, $val){
        $_SESSION[$key] =$val;
    }
    public static function get($key){
        if(isset($_SESSION[$key])){
            return $_SESSION[$key];
        } else{
            return false;
        }
    }
    public static function checkSession(){
        self::init();
        if(self::get("adminlogin")==false){
            self::destroy();
            header("Location:login.php");
        }
    }
    public static function checkLogin(){
        self::init();
        if(self::get("adminlogin")==true){
            header("Location:index.php");
        }
    }
    public static function destroy(){
        session_destroy();
        header("Location:login.php");
    }
}

Antwoord 13

Tijdstempel gebruiken…

<?php
if (!isset($_SESSION)) {
    $session = session_start();
} 
if ($session && !isset($_SESSION['login_time'])) {
    if ($session == 1) {
        $_SESSION['login_time']=time();
        echo "Login :".$_SESSION['login_time'];
        echo "<br>";
        $_SESSION['idle_time']=$_SESSION['login_time']+20;
        echo "Session Idle :".$_SESSION['idle_time'];
        echo "<br>";
    } else{
        $_SESSION['login_time']="";
    }
} else {
    if (time()>$_SESSION['idle_time']){
        echo "Session Idle :".$_SESSION['idle_time'];
        echo "<br>";
        echo "Current :".time();
        echo "<br>";
        echo "Session Time Out";
        session_destroy();
        session_unset();
    } else {
        echo "Logged In<br>";
    }
}
?>

Ik heb 20 seconden gebruikt om de sessie met tijdstempel te laten verlopen.

Als je 30 min nodig hebt, voeg dan 1800 toe (30 min in seconden)…


Antwoord 14

U kunt rechtstreeks een DB gebruiken om het als alternatief te doen. Ik gebruik hiervoor een DB-functie die ik chk_lgn aanroep.

Controleer inlogcontroles om te zien of ze zijn ingelogd of niet en door dit te doen, wordt de datum-tijdstempel van de controle ingesteld als het laatst actief in de db-rij/kolom van de gebruiker.

Ik doe daar ook de tijdcontrole. Dit werkt voor mij momenteel omdat ik deze functie voor elke pagina gebruik.

P.S. Niemand die ik had gezien had een pure DB-oplossing voorgesteld.


Antwoord 15

Dit was een eye-opener voor mij, wat Christopher Kramer in 2014 schreef over
https://www.php.net/manual/en/session. configuratie.php#115842

Op debian (gebaseerde) systemen heeft het veranderen van session.gc_maxlifetime tijdens runtime geen echt effect. Debian schakelt PHP’s eigen garbage collector uit door session.gc_probability=0 in te stellen. In plaats daarvan heeft het elke 30 minuten een cronjob (zie /etc/cron.d/php5) die oude sessies opruimt. Deze cronjob kijkt in feite naar je php.ini en gebruikt daar de waarde van session.gc_maxlifetime om te beslissen welke sessies moeten worden opgeschoond (zie /usr/lib/php5/maxlifetime). […]


Antwoord 16

Hier kun je de uren instellen

$lifespan = 1800;
ini_set('session.gc_maxlifetime', $lifespan); //default life time

Antwoord 17

Sla de huidige tijd op en als deze langer is dan 30 minuten door te vergelijken, vernietig dan de huidige sessie.

Other episodes