Безопасность аторизации/регистрации/сессиям в чистом PHP
Это скорее не вопрос как исправить то, что не работает а как защитить то, что работает. Прочитал что хранить user_id в $_SESSION небезопасно, но тогда и непонятно как его узнать после авторизации.
//Авторизация
session_start();
if(!empty($_POST['email']) && $_POST['password'])) {
$email = $_POST['email'];
$password = $_POST['password'];
}
//Проверяем есть ли такой юзер в базе по логину и паролю и совпадают ли они
$isAccount = $database->has("account", [
"email" => $email,
"password" => $password
]);
//Узнаем по email user_id и role
if ($isAccount) {
$userdata = $database->select("account", [
"user_id",
"role",
"email"
], [
"email" => $email
]);
foreach ($userdata as $user) {
}
//Записываем дату и время последнего входа
$date = date("Y-m-d H:i:s");
$database -> update("account", [
"last_login" => $date
],[
"user_id" => $user['user_id']
]);
//И вот здесь возникает вопрос, правильно ли это?
//Может будут какие рекомендации?
$_SESSION['user_logged_in'] = [
"user_id" => $user['user_id'],
"role" => $user['role']
];
}
Далее в header на страницах user_id берется так:
session_start();
if (!empty($_SESSION['user_logged_in'])) {
$user_auth = $_SESSION['user_logged_in'];
$user_id = $user_auth['user_id'];
}else{
$user_auth = false;
}
Ответы (1 шт):
При создании сессии создается уникальный идентификатор, который отправляется браузеру в виде куки и сохраняется на пользовательском компьютере: https://www.php.net/manual/ru/session.examples.basic.php Такой способ имеет потенциальные угрозы в зависимости от настроек на стороне пользователя, вот некоторые потенциальные примеры: https://habr.com/ru/post/120636/ Поэтому для защиты обычно добавляют различные дополнительные способы, например:
- сохраняют в сессии IP пользователя;
- сохраняют данные системы;
- сохраняют данные браузера;
- сессию дополняют идентификаторами сеанса, чтобы исключить повторное обращение пользователя; и т.п.
В частности в вашем примере проверка не происходит никакая, только на наличие данных в сессии.
Так же в вашем примере похоже есть ошибка: при сохранении данных сессии вы создаете массив второго уровня
$_SESSION['user_logged_in'] = [
"user_id" => $user['user_id'],
"role" => $user['role']
];
а при проверке данных обращаетесь вообще к массиву $user_auth
if (!empty($_SESSION['user_logged_in'])) {
$user_auth = $_SESSION['user_logged_in'];
$user_id = $user_auth['user_id'];
}
Т.е. в вашей сессии достаточно просто получить идентификатор сессии и можно подключаться к серверу