2010-06-10 2 views
2

У меня странная проблема с сеансами php. Я использую их для авторизации на моем сайте. Я храню две переменные - в настоящее время вошел в систему идентификатор пользователя и имя пользователя в сеансе. Когда я вхожу в систему с одним именем пользователя, а затем выхожу из системы и снова вхожу в систему с другим именем пользователя, идентификатор предыдущего пользователя возвращается с использованием переменной сеанса вместо текущего пользователя.Задача кэширования сеанса

Самое странное, что это происходит только тогда, когда требуется вставить некоторые данные в базу данных. Когда я непосредственно эхо повторяю эту переменную, отображается правильный идентификатор, но когда я вставляю новую запись в базу данных, эта переменная отправляет неверный идентификатор.

Вот код PHP я использую для отправки данных в базу данных:

<?php 
session_start(); 
//connect database 
require_once 'dbc.php'; 

$authorID = $_SESSION['user_id']; 
if ($authorID != 0) { 
     $content = htmlentities($_POST["answ_content"],ENT_COMPAT,'UTF-8'); 
     $dro = date('Y-m-d H:i:s'); 
     $qID = $_POST["question_ID"]; 
     $author = 'avtori'; 


     $sql="INSERT INTO comments (comment_ID, comment_post_ID, comment_author, comment_date, comment_content, user_id) 
      VALUES 
      (NULL, '$qID', '$author', '$dro', '$content', '$authorID')"; 

     $result = mysql_query($sql); 

} else { 
    echo 'error'; 
} 

?> 

Может кто-нибудь пожалуйста помочь?

Вот функция выхода из системы:

function logout() 
{ 
global $db; 
session_start(); 

if(isset($_SESSION['user_id']) || isset($_COOKIE['user_id'])) { 
mysql_query("update `users` 
      set `ckey`= '', `ctime`= '' 
      where `id`='$_SESSION[user_id]' OR `id` = '$_COOKIE[user_id]'") or die(mysql_error()); 
}   

/************ Delete the sessions****************/ 
unset($_SESSION['user_id']); 
unset($_SESSION['user_name']); 
unset($_SESSION['user_level']); 
unset($_SESSION['HTTP_USER_AGENT']); 
session_unset(); 
session_destroy(); 

/* Delete the cookies*******************/ 
setcookie("user_id", '', time()-60*60*24*COOKIE_TIME_OUT, "/"); 
setcookie("user_name", '', time()-60*60*24*COOKIE_TIME_OUT, "/"); 
setcookie("user_key", '', time()-60*60*24*COOKIE_TIME_OUT, "/"); 

header("Location: index.php"); 
} 

Вот скрипт аутентификации:

include 'dbc.php'; 

$err = array(); 

foreach($_GET as $key => $value) { 
    $get[$key] = filter($value); //get variables are filtered. 
} 

if ($_POST['doLogin']=='Login') 
{ 

foreach($_POST as $key => $value) { 
    $data[$key] = filter($value); // post variables are filtered 
} 


$user_email = $data['usr_email']; 
$pass = $data['pwd']; 


if (strpos($user_email,'@') === false) { 
    $user_cond = "user_name='$user_email'"; 
} else { 
     $user_cond = "user_email='$user_email'"; 

} 


$result = mysql_query("SELECT `id`,`pwd`,`full_name`,`approved`,`user_level` FROM users WHERE 
      $user_cond 
      AND `banned` = '0' 
      ") or die (mysql_error()); 
$num = mysql_num_rows($result); 

    // Match row found with more than 1 results - the user is authenticated. 
    if ($num > 0) { 

    list($id,$pwd,$full_name,$approved,$user_level) = mysql_fetch_row($result); 

    if(!$approved) { 
    //$msg = urlencode("Account not activated. Please check your email for activation code"); 
    $err[] = "Account not activated. Please check your email for activation code"; 

    //header("Location: login.php?msg=$msg"); 
    //exit(); 
    } 

     //check against salt 
    if ($pwd === PwdHash($pass,substr($pwd,0,9))) { 
    // this sets session and logs user in 
     session_start(); 
     session_regenerate_id (true); //prevent against session fixation attacks. 

     // this sets variables in the session 
     $_SESSION['user_id']= $id; 
     $_SESSION['user_name'] = $full_name; 
     $_SESSION['user_level'] = $user_level; 
     $_SESSION['HTTP_USER_AGENT'] = md5($_SERVER['HTTP_USER_AGENT']); 

     //update the timestamp and key for cookie 
     $stamp = time(); 
     $ckey = GenKey(); 
     mysql_query("update users set `ctime`='$stamp', `ckey` = '$ckey' where id='$id'") or die(mysql_error()); 

     //set a cookie 

     if(isset($_POST['remember'])){ 
        setcookie("user_id", $_SESSION['user_id'], time()+60*60*24*COOKIE_TIME_OUT, "/"); 
        setcookie("user_key", sha1($ckey), time()+60*60*24*COOKIE_TIME_OUT, "/"); 
        setcookie("user_name",$_SESSION['user_name'], time()+60*60*24*COOKIE_TIME_OUT, "/"); 
        } 
     if(empty($err)){    
      header("Location: myaccount.php"); 
     } 
     } 
     else 
     { 
     //$msg = urlencode("Invalid Login. Please try again with correct user email and password. "); 
     $err[] = "Invalid Login. Please try again with correct user email and password."; 
     //header("Location: login.php?msg=$msg"); 
     } 
    } else { 
     $err[] = "Error - Invalid login. No such user exists"; 
     }  
} 
+0

Пожалуйста, покажите нам, как вы выполните выход из системы. – Palantir

+0

'htmlentities' не подходит для защиты повторных SQL-инъекций (если это то, для чего вы его используете). Используйте 'mysql_real_escape_string', подготовленные инструкции для созданного параметризованного построителя запросов. – Gumbo

+0

О, и как вы аутентифицируете своих пользователей? – Gumbo

ответ

3

Это убивает меня, сколько людей размещать код уязвим для SQL injection!

<?php 
$content = htmlentities($_POST["answ_content"],ENT_COMPAT,'UTF-8'); 
     //^Attack vector 
$dro = date('Y-m-d H:i:s'); 
$qID = $_POST["question_ID"]; 
    //^Attack vector 
$author = 'avtori'; 

$sql="INSERT INTO comments (comment_ID, comment_post_ID, comment_author, comment_date, comment_content, user_id) 
     VALUES 
     (NULL, '$qID', '$author', '$dro', '$content', '$authorID')"; 
?> 

Sanitize your database inputs!

0

Вы можете использовать session_regenerate_id, чтобы убедиться, что использовать новый идентификатор сеанса и уничтожить старую:

session_start(); 
if ($userIsAuthentic) { 
    session_regenerate_id(true); 
} 

Если вы не используете PHP 5.1.0 или выше, вы можете использовать этот эквивалент т заменить недостающие delete_old_session параметры:

session_start(); 
if ($userIsAuthentic) { 
    $_SESSION = array(); 
    session_destroy(); 
    session_write_close(); 
    session_start(); 
    session_regenerate_id(); 
} 
+0

Что такое переменная $ userIsAuthentic? –

+0

'$ userIsAuthentic' предназначен для переменной, которая содержит состояние, является ли текущий пользователь аутентичным или нет. – Gumbo

+0

session_regenerate_id, похоже, не является решением ... –

0

Попробуйте удаление содержимого диска сеанс с орбиты: session_destroy

Называйте это, Nuke их куки сессии, немедленно положить конец сценарий, и направить пользователя на страницу входа , Они получат новую сессию и войдут в систему должным образом.

Смежные вопросы