Аутентификация пользователей при входе в систему с помощью паролей с солью sha1

У меня есть очень простой сценарий входа/регистрации пользователя, который хранит пароли с использованием sha1 и соли. У меня есть пароли и создание пользователей, которые работают нормально и прекрасно сохраняют все в базе данных, но когда я пытаюсь войти в систему с учетными данными, это не работает. По поиску в этой теме ничего не нашел.

Вот моя форма добавления пользователя:

session_start();
include("includes/resume.config.php");

// make sure form fields have a value and strip them
function check_input($data, $problem='')
{
$data = trim($data);
$data = stripslashes($data);
$data = htmlspecialchars($data);
if ($problem && strlen($data) == 0)
{
    die($problem);
}
    return $data;
}

// get form values, escape them and apply the check_input function
$name = $link->real_escape_string(check_input($_POST['name'], "Please enter a name!"));
$email = $link->real_escape_string(check_input($_POST['email'], "Please enter an email!"));
$password = $link->real_escape_string(check_input($_POST['password'], "Please enter a password!"));

// generate a random salt for converting passwords into MD5
$salt = bin2hex(mcrypt_create_iv(32, MCRYPT_DEV_URANDOM));
$saltedPW =  $password . $salt;
$hashedPW = sha1($saltedPW);

mysqli_connect($db_host, $db_user, $db_pass) OR DIE (mysqli_error());
// select the db
mysqli_select_db ($link, $db_name) OR DIE ("Unable to select db".mysqli_error($db_name));

 // our sql query
$sql = "INSERT INTO admins (name, email, password, salt) VALUES ('$name', '$email', '$hashedPW', '$salt');";

//save the updated information to the database          
mysqli_query($link, $sql) or die("Error in Query: " . mysqli_error($link));

if (!mysqli_error($link)) 
{
    header("Location: file_insert.php");
}   

А вот мой сценарий входа: Вот что не работает

function check_input($data, $problem='')
{
$data = trim($data);
$data = stripslashes($data);
$data = htmlspecialchars($data);
if ($problem && strlen($data) == 0)
{
    die($problem);
}
    return $data;
}

if(isset($_POST['submitLogin'])) { //form submitted?

// get form values, escape them and apply the check_input function
$name = $link->real_escape_string(check_input($_POST['name'], "Please enter a name!"));
$password = $link->real_escape_string(check_input($_POST['password'], "Please enter a password!"));

$saltQuery = $link->query('SELECT salt FROM admins WHERE name = "'.$name.'"');

$salt = mysqli_fetch_assoc($saltQuery);
$saltedPW =  $password . $salt;
$hashedPW = sha1($saltedPW);

mysqli_connect($db_host, $db_user, $db_pass) OR DIE (mysqli_error());
// select the db
mysqli_select_db ($link, $db_name) OR DIE ("Unable to select db".mysqli_error($db_name));

$validate_user = $link->query('SELECT id, name, password FROM admins WHERE name = "'.$name.'" AND password = "'.$hashedPW.'"');

if ($validate_user->num_rows == 1) {
    $row = $validate_user->fetch_assoc();
    $_SESSION['id'] = $row['id'];
    $_SESSION['loggedin'] = TRUE;
    Header('Location: file_insert.php');
} else {
    print "<center><p style='margin-top: 200px; font-weight: bold;'>Invalid Login Information</p>";
    print "<a href='admin-login.php'>Click here</a> to return to the login page.</center>";
}
}

person Ty Bailey    schedule 24.09.2012    source источник


Ответы (2)


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

PHP будет жаловаться на преобразование массива в строку при вызове $password . $salt, поскольку в этот момент $salt является массивом. В результате к паролю добавляется слово Array, что приводит к неправильному хешу. Если у вас display_errors отключено и/или error_reporting установлено скрытие уведомлений в php.ini, вы не увидите это сообщение.

Если вы измените:

$saltedPW =  $password . $salt;

to:

$saltedPW =  $password . $salt['salt'];

тогда это должно работать.

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

person drew010    schedule 24.09.2012
comment
так что я должен изменить $salt = mysqli_fetch_assoc($saltQuery); только на $salt = $saltQuery;? - person Ty Bailey; 25.09.2012
comment
Нет, вам все еще нужно выполнить запрос, оставьте эту часть как есть, просто измените назначение, как показано в ответе, и оно должно работать. - person drew010; 25.09.2012
comment
Кроме того, если вы выберете хэш пароля И соль в этом запросе, вам не нужно делать 2 запроса, чтобы узнать, действителен ли логин или нет. Если вы найдете совпадение, просто хешируйте пароль в PHP и сравните его с хешированным паролем, который вы уже выбрали из БД. - person drew010; 25.09.2012

Вы не сказали, получите ли вы какое-либо сообщение об ошибке, но из того, что вы публикуете, я думаю, что это проблема с подключением:

if(isset($_POST['submitLogin'])) { //form submitted?

// Here, you didn't connect to database, but you are expecting to fetch salt!
$saltQuery = $link->query('SELECT salt FROM admins WHERE name = "'.$name.'"');

$salt = mysqli_fetch_assoc($saltQuery);

Итак, вам, возможно, придется сначала подключиться к базе данных:

if(isset($_POST['submitLogin'])) { //form submitted?

mysqli_connect($db_host, $db_user, $db_pass) OR DIE (mysqli_error());
// select the db
mysqli_select_db ($link, $db_name) OR DIE ("Unable to select db".mysqli_error($db_name));

// Here, you didn't connect to database, but you are expecting to fetch salt!
$saltQuery = $link->query('SELECT salt FROM admins WHERE name = "'.$name.'"');

Во-вторых, mysqli_fetch_assoc возвращает массив с именем ключа в качестве поля того, что вы вставляете в свой запрос SELECT, окончательный код должен быть таким:

if(isset($_POST['submitLogin'])) { //form submitted?

mysqli_connect($db_host, $db_user, $db_pass) OR DIE (mysqli_error());
// select the db
mysqli_select_db ($link, $db_name) OR DIE ("Unable to select db".mysqli_error($db_name));

// Here, you didn't connect to database, but you are expecting to fetch salt!
$saltQuery = $link->query('SELECT salt FROM admins WHERE name = "'.$name.'"');
$salt = mysqli_fetch_assoc($saltQuery);
$saltedPW =  $password . $salt["salt"];
$hashedPW = sha1($saltedPW);
person SIFE    schedule 24.09.2012