在设定的到期时间(例如5分钟)后删除数据库行

时间:2016-02-01 11:55:47

标签: php mysql session

背景:我正在设计一个在线虚拟教室管理系统......它可以在教师创建教室并将其存储在数据库中时生成随机会话密钥(md5(时间)) 。

要访问教室,学生访问唯一的教室网址,代码会将网址中的会话密钥(使用GET)与数据库中的会话密钥进行比较。如果匹配则会显示教室。

网址通常如下所示:/classroom.php?Instance = a529501db8373609f2d47a7843a461ea

需要编码帮助:我希望我的老师也能够设置会话“长度”,因此教室可以访问15分钟,25分钟或50分钟。

enter image description here

当创建教室后的时间超过例如25分钟时,会话密钥将从数据库中删除,并且无法再访问教室。

到目前为止我有什么:

当教师点击按钮创建一个classroo时,下面的PHP将会话密钥($ instance)和会话长度($ duration)存储在数据库中......

<?php
session_start();
if (isset($_SESSION['id'])) {
    if (isset($_POST['hidden'])) {

        // Connects to the database
        include_once("$_SERVER[DOCUMENT_ROOT]/classes/includes/dbconnect.php");
        mysql_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);

        // Sets the session duration
        $currentTime = time();
        $duration = $currentTime + $_POST['duration'];

        // Session variables
        $uid = $_SESSION['id'];
        $usname = $_SESSION['username'];

        // To generate the random hash from the current time
        $time = time(); // time to hash
        $instance = md5($time); // hash stored in variable

        // Stores the session hash (instance) and duration in the instance database
        $query = ("INSERT INTO `my-db-name-foo`.`instances` (`instance`, `expiry`) VALUES (`$instance`, $duration`);");
        mysql_query($query) or die(mysql_error());

        // Closes the database connection
        mysql_close();

        // Redirects the teacher header('Location:classroom.php?instance='.$instance);
    } 
} else {
    echo 'Please login';
    die();
}
?>

然后在实际的classroom.php页面上,一段代码检查会话是否已过期......如果是,则将其从数据库中删除。

<?php 

$currentTime = time();

if ($currentTime > $duration){
    // Connect to database and delete the row
} else {
    // show the classroom
}
?>

非常感谢任何帮助或建议!

更新----

感谢所有出色的答案,以下是目前这一切的工作方式......

在createclassroom.php页面上,我存储实例以及NOW()日期和时间以及持续时间为NOW()+ $ _POST ['duration']; ...

<?php
session_start();
if (isset($_SESSION['id'])) {
    if (isset($_POST['duration']) && !EMPTY($_POST['duration'])) {

        // Connects to the database
        include_once("$_SERVER[DOCUMENT_ROOT]/classes/includes/dbconnect.php");

        // Session variables
        $uid = $_SESSION['id'];
        $usname = $_SESSION['username'];

        // To generate the random hash from the current time
        $time = time(); // time to hash
        $instance = md5($time); // hash stored in variable

        // $duration = $_POST['duration'];
        $duration = $_POST['duration'];

        // Stores the hash (instance) in the instance database
        $sql = ("INSERT INTO `xxx_xxxx`.`instances` (`id`, `teacher`, `instance`, `startdate`, `expiredate`) VALUES ('$uid', '$usname', '$instance', NOW(), NOW() + $duration);");
        $query = mysqli_query($dbConnect, $sql)or die(mysql_error());

        // Redirects the teacher        
        header('Location:classroom.php?instance='.$instance);
    }  else if (isset($_POST['hidden'])) {
        echo 'Please select a duration';
    }
} else {
    echo 'Please login';
    die();
}
?>

在实际的classroom.php页面上,我只检查未过期的会话实例。

<?php 
session_start();

// Connects to the database
include_once("$_SERVER[DOCUMENT_ROOT]/classes/includes/dbconnect.php");

$instance = $_GET['instance']; // GETs instance from URL
$usname = $_SESSION['username']; // Gets teacher name

// script to retrieve all the Instances in the database and store them in a variable '$dbInstance'
$sql = "SELECT instance, expiredate FROM instances WHERE instance = '$instance' AND instances.expiredate > NOW()";
$query = mysqli_query($dbConnect, $sql);
$row = mysqli_fetch_row($query);

$dbInstance = $row[0];

if ($dbInstance == $instance){
    echo $dbInstance.'<br>';
    echo $instance;
} else {
    echo $dbInstance.'<br>';
    echo $instance.'<br>';
    die('Instance not initiated');
}
?>

现在我只需要决定如何经常清除数据库。真的,我要感谢你们的帮助,正是我需要的!

3 个答案:

答案 0 :(得分:3)

这种行到期通常按如下方式处理:

  1. 将过期DATETIME放在每一行中。 INSERT INTO tbl (id, expiration) VALUES (whatever, NOW() + INTERVAL 5 MINUTE)
  2. 查找行时,请在查询中使用AND tbl.expiration > NOW()之类的内容。这将使过期的行显得消失。
  3. 方便的时候,也许是在一夜之间的工作或每小时的EVENT,摆脱过期的行:DELETE FROM tbl WHERE tbl.expiration <= NOW()
  4. 这比在过期时尝试实际DELETE过期的行更容易且更加时间精确。它还可以抵御即时DELETE操作的失败,并且可以很好地扩展。

答案 1 :(得分:3)

expiry DATETIME添加到教室桌面,当您创建它时,请设置它到期的时间。

在课堂页面中,只需将到期时间与当前时间进行比较。

奖励:如果人们在到期后没有尝试进入教室,您的数据库可能会变大。您可以偶尔制作一个删除过期课堂的cronjob:DELETE FROM classroom WHERE expiry < NOW()

答案 2 :(得分:1)

所以说你的桌子看起来像这样:

  CREATE TABLE IF NOT EXISTS sessions (
      classroom_id int(10) unsigned NOT NULL AUTO_INCREMENT,
      session_key varchar(60) NOT NULL,
      duration tinyint(3) unsigned NOT NULL,
      created timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
      PRIMARY KEY (classroom_id)
 ) ENGINE=InnoDB  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;

并且您的持续时间始终以秒为单位,您可以通过以下查询实现您想要的效果:

SELECT  classroom_id
FROM    sessions
WHERE   session_key = :key
AND     (UNIX_TIMESTAMP(created) + (duration * 60)) > UNIX_TIMESTAMP(NOW());