Я создаю основанный на сеансе механизм входа в систему без базы данных для однофайлового приложения PHP. Я осознаю, что безопасность является базовой только для такой установки, но для создаваемого приложения это приемлемо (иными словами, мне не нужны долгие головоломки по поводу безопасности на уровне отрасли). У меня есть два вопроса, связанных с оптимизацией основного механизма входа в систему, но я не знаю, добавляю ли я слои ненужной сложности. Мой простой механизм входа в систему выглядит примерно так:
$username = 'someone';
$password = '$2y$10...'; // encrypted with password_hash();
$login_hash = md5('randomkey' . $password);
session_start();
if(isset($_SESSION['login']) && $_SESSION['login'] === $login_hash){
// already logged in
} else if(isset($_POST['username']) && isset($_POST['username'])){
if($_POST['username'] === $username && password_verify($_POST['password'], $password)){
// login success
$_SESSION['login'] = $login_hash;
} else {
// incorrect login, display login <form>
}
} else {
// display login <form>
}
Вопрос 1 Насколько я вижу, одна уязвимость заключается в том, что cookie-файл входа в систему, сохраненный в браузере пользователя, может утечь, ив свою очередь, используется другим пользователем для прослушивания сессии. В таком случае, не имеет ли смысла сохранять значение, специфичное для пользователя / браузера, в $login_hash
, чтобы сеанс мог использоваться только браузером / пользователем, запустившим сеанс? Например:
$login_hash = md5($IP . $HTTP_USER_AGENT . $password);
В этом случае сеанс не может быть хай-джек, если не были подделаны IP и user-agent. Имеет ли это смысл или я глупый?
Вопрос 2 Имеет ли смысл включать скрытый ввод session_ID в форму входа в систему и проверять, совпадает ли он с идентификатором сеанса при входе в систему? Это предотвратит попытки входа в систему, которые не имеют предварительного SID для предварительного входа в систему из формы входа. Или это просто бесполезно? Например:
// login form contains:
<input type="hidden" name="sid" value="<?php echo session_id(); ?>">
// check credentials
if($_POST['sid'] === session_id() && $_POST['username'] === $username && password_verify($_POST['password'], $password)){
Подумал, что я опубликую и посмотрю, не было ли у меня мышления и / или, может быть, я смогу чему-то научиться.