Активная сессия. Подводные камни использования сессий в PHP

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

В случае необходимости вы можете завершить сеанс работы выбранного пользователя.

Модуль «Активные сессии»

Просмотр информации о текущих подключениях

  • Id сессии - уникальный номер, идентифицирующий сеанс работы с панелью управления. По умолчанию информация отображается в таблице в течение 60 минут.
  • Пользователь - имя пользователя, подключенного к системе в настоящее время.
  • Доступ - уровень доступа данного пользователя к панели управления (например, суперпользователь, администратор сервера, пользователь и др.).
  • IP-адрес - удалённый IP-адрес, с которого осуществляется доступ.
  • Ожидание - время, прошедшее с момента, когда панель управления получила последнюю команду от пользователя.
  • Активных запросов - количество активных запросов.

Завершение сеанса

Чтобы завершить тот или иной сеанс работы с панелью управления, выделите нужные строки в списке активных сеансов и нажмите кнопку "Завершить".

Для предотвращения случайных удалений панель управления попросит подтвердить или отменить ваше действие. Если в окне подтверждения вы нажмёте "Ок", то выделенные сеансы будут завершены.

Если сеанс был завершен, для дальнейшей работы с панелью управления пользователь должен снова авторизоваться.

Эта форма - не обращение в поддержку.
Мы не можем идентифицировать вас и ответить на ваше сообщение.

To properly display this page you need a browser with JavaScript support.

Сессии авторизации пользователей

Для доступа к нему необходимо перейти по ссылке Активные пользователи в разделе Администрирование – Домашняя страница в блоке Пользователи (рис. 2); по ссылке Активные пользователи в разделе Администрирование – Система – Лицензии в строке Конкурентных лицензий (рис. 3) – такой вариант возможен, только если в системе ELMA используется тип конкурентных лицензий ; нажав кнопку Активные пользователи в разделе Администрирование – Пользователи (рис. 4).

Рис. 2. Раздел "Администрирование - Пользователи". Кнопка "Активные пользователи"

Рис. 3. Раздел "Администрирование – Система – Лицензии". Ссылка "Активные пользователи"

Рис. 4. Раздел "Администрирование – Домашняя страница". Ссылка "Активные пользователи"

Имя пользователя – это поле содержит Ф.И.О. пользователя в системе ELMA. Кнопка рядом с именем пользователя позволяет прервать (выполнить выход из системы для соответствующего пользователя) и удалить информацию обо всех сессиях этого пользователя из списка.

IP адрес – это поле содержит IP-адрес пользователя, с которого была выполнена авторизация в системе . В том случае, если для работы используется веб-ферма ELMA , для каждого из активных пользователей будут отображены их реальные IP-адреса.

Кнопка рядом с IP-адресом позволяет прервать соответствующую сессию и удалить информацию о ней из списка.

Значок рядом с IP-адресом означает, что в настоящий момент текущий пользователь авторизован в системе. По истечении определенного времени с момента последнего отклика пользователя активная сессия приостанавливается. Приостановленные сессии отмечены значком . Период времени ожидания, после которого активная сессия приостанавливается, определяется в разделе Администрирование – Система – Настройки системы – Настройки Безопасности .

Последний отклик – это поле содержит информацию о последнем совершенном пользователем действии в системе либо о последнем успешно отправленном со страницы запросе на сервер (один раз в минуту с открытой в браузере страницы на сервер ELMA отправляется веб-запрос с целью проверки соединения и сбора статистики).

Последнее действие пользователя – это поле содержит информацию о последнем совершенном пользователем действии в системе в формате Дата – Время – Ссылка на последнюю посещенную пользователем страницу . Эта ссылка является относительной. Для получения полной ссылки необходимо добавить к ней адрес сервера (рис. 5).

Рис. 5. Формирование полного адреса ссылки на последнюю посещенную пользователем страницу

При отсутствии активности пользователя в течении определённого времени текущая сессия прерывается автоматически. Настройки длительности хранения сессий настраиваются в разделе

Раздел Активные сессии на странице «Настройки безопасности» показывает список последних случаев доступа к Вашей учетной записи на Facebook .

Каждая запись содержит дату и время входа в систему, примерное местоположение из которого происходила авторизация, и тип устройства, используемого для входа в аккаунт . Справа от каждой записи появится также возможность завершения сеанса.

Примечание : Указывается местоположение определяемое на основе IP-адреса, с которого был получен доступ к учетной записи. Если вы хотите узнать точные данные, касающиеся IP-адреса входа в систему, просто установите указатель мыши над информацией о местоположении сессии.

Что значит ситуация, когда я не узнаю места входа

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

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

Пароль приложения Facebook

Что такое пароль для приложений

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

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

Чтобы получить пароль к приложению:

Подтверждение входа на Facebook

Что такое функция подтверждения входа в систему

Подтверждение входа в систему – это дополнительная защита аккаунта Facebook, связанная с функцией Уведомление о входе , но с дополнительным этапом процедуры безопасности.

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

После входа в систему вы будете иметь возможность дать этому устройству имя и сохранить его в вашем аккаунте. Ввод кода не потребуется при входе в систему с одного из официальных устройств.

Чтобы включить функцию подтверждения входа в систему:


Примечание :Чтобы иметь возможность включить Подтверждение входа необходимо сохранить в данных счета номер телефона .

Как закрыть доступ к Facebook без кода

Если вы не хотите, чтобы любой человек имел возможность войти в ваш аккаунт с любого места, вы можете включить Подтверждение регистрации .

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

Что будет если я попытаюсь зайти с другого компьютера

Когда вы попытаетесь войти в систему с неопознанного устройства, появится сообщение с просьбой ввести код для входа в систему.

Если вы установили приложение Генератор кодов, откройте приложение Facebook для Android и получите код.

Если приложение не установлено, проверьте защитный код на телефоне, введите его и воспользуйтесь службой. В случае возникновения проблем с получением защитного кода подождите несколько минут и запросите новый код с помощью ссылки Отправить код еще раз . Для получения дополнительной информации по устранению проблем, нажмите на ссылку Я не могу получить код .

Как получить код подтверждения

Если вы включили Подтверждение входа , вы получите сообщение SMS с кодом входа в систему каждый раз, когда он вам понадобится. Если же вы используете приложение для Android, вы можете скачать программу Генератор кодов.

Мне вводить код при каждом входе в систему

После ввода защитного кода и входа в систему необходимо присвоить компьютеру или телефону условное имя и сохранить его (если устройство необходимо Вам). Если вы будете продолжать получать запросы на ввод кода при входе в систему с помощью одного из сохраненных (официальных) устройств, может потребоваться настройка параметров браузера.

В случае использование Вами функции подтверждения входа, система должна сохранить данные Вашего компьютера и браузера, чтобы они могли быть распознаны при следующем входе в систему.

Некоторые функции браузера не позволяют этого. Если вы используете функцию приватного просмотра или ваш браузер настроен так, чтобы очищать историю использования при закрытии.

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

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

В принципе, довольно несложно сделать собственный аналог сессий, не такой функциональный, как встроенный в PHP, но похожий по сути. На куках и базе данных.
При запросе скрипта смотрим, пришла ли кука с определенным именем. Если куки нет, то ставим ее и записываем в базу новую строку с данными пользователя. Если кука есть, то читаем из базы данные. Еще одним запросом удаляем из базы старые записи и вот у нас готов механизм сессий. Совсем несложно. Но есть некоторые нюансы, которые делают предпочтительным использование именно встроенного механизма сессий.

Если включена только первая, то при старте сессии (при каждом вызове session_start () ) клиенту устанавливается кука. Браузер исправно при каждом следующем запросе эту куку возвращает и PHP имеет идентификатор сессии. Проблемы начинаются, если браузер куки не возвращает. В этом случае, не получая куки с идентификатором, PHP будет все время стартовать новую сессию, и механизм работать не будет.

Если включена только вторая, то кука не выставляется. А происходит то, ради чего, в основном, собственно, и стоит использовать встроенный механизм сессий. После того, как скрипт выполняет свою работу, и страница полностью сформирована, PHP просматривает ее всю и дописывает к каждой ссылке и к каждой форме передачу идентификатора сессии. Это выглядит примерно так:
Index превращается в
Index
а к формам добавляется скрытое поле

И браузер при клике на любую ссылку, или при нажатии на кнопку в форме, пошлет в запросе нужную нам переменную - идентификатор сессии!
По очевидным причинам идентификатор добавляется только к относительным ссылкам.

Теоретически, в наших с вами самодельных сессиях на куках и базе, можно самому, руками приписать ко всем ссылками передачу ид - и тогда наши собственные сессии будут работать независимо от кук. Но, согласитесь - приятнее, когда эту работу делает кто-то другой? ;-)

По умолчанию в последних версиях PHP включены обе опции. Как PHP поступает в этом случае? Кука выставляется всегда. А ссылки автодополняются только если РНР не обнаружил куку с идентификатором сессии. Когда пользователь в првый раз за этот сеанс заходит на сайт, ему ставится кука, и дополняются ссылки. При следующем запросе, если куки поддерживаются, PHP видит куку и перестает дополнять ссылки. Если куки не работают, то PHP продолжает исправно добавлять ид к ссылкам, и сессия не теряется.
Пользователи, у которых работают куки, увидят длинную ссылку с ид только один раз.

Фух. С передачей идентификатора закончили.
Теперь осталось привязать к нему файл с данными на стороне сервера.
PHP это сделает за нас. Достаточно просто написать
session_start ();
$_SESSION [ "test" ]= "Hello world!" ;

И PHP запишет в файл, связанный с этой сессией, переменную test.
Здесь очень важное замечание.
Массив $_SESSION - особенный.
В нем, собственно, и находятся переменные, которые мы ходим сделать доступными в различных скриптах.
Чтобы поместить переменную в сессию, достаточно присвоить ее элементу массива $_SESSION.
Чтобы получить ее значение - достаточно обратиться к тому же элементу. Пример будет чуть ниже.

Cборкой мусора - удалением устаревших файлов PHP тоже занимается сам. Как и кодированием данных и кучей всяких других нужных вещей. В результате этой заботы работа с сессиями оказывается очень простой.
Вот мы, собственно, и подошли к примеру работы сессий.
Пример очень маленький:
session_start ();

echo "Вы обновили эту страницу " . $_SESSION [ "counter" ]++. " раз. " ;
echo "
обновить" ;
?>

Мы проверяем, есть ли у нас в сессии переменная counter, если нет, то создаем ее со значением 0, а дальше выводим ее значение и увеличиваем на единицу. Увеличенное значение запишется в сессию, и при следующем вызове скрипта переменная будет иметь значение 1, и так далее.
Все очень просто.

Для того, чтобы иметь доступ к переменным сессии на любых страницах сайта, надо написать ТОЛЬКО ОДНУ(!) строчку в самом начале КАЖДОГО файла, в котором нам нужны сессии:
session_start ();
И далее обращаться к элементам массива $_SESSION. Например, проверка авторизации будет выглядеть примерно так:
session_start ();
if ($_SESSION [ "authorized" ]<> 1 ) {
header ("Location: /auth.php" );
exit;
}

Удаление переменных из сессии.
Если у вас register_globals=off , то достаточно написать
unset($_SESSION [ "var" ]);
Если же нет, то тогда рядом с ней надо написать
session_unregister ("var" );

Самыми распространенными ошибками, которые выдает РНР при попытке работать с сессиями, являются такие:
Две из них,
Warning: Cannot send session cookie - headers already sent
Warning: Cannot send session cache limiter - headers already sent

вызваны одной и той же причиной, решение описано в этом факе
Третья,
Warning: open(/tmp\sess_SID, O_RDWR) failed: No such file or directory (2) in full_script_path on line number (ранее она выглядела, как Warning: Failed to write session data (files). Please verify that the current setting of session.save_path is correct (/tmp) ),
если перевести ее с английского, подробно объясняет проблему: недоступен указанный в php.ini путь к каталогу, в который пишутся файлы сессий. Эту ошибку исправить проще всего. Просто прописать каталог, который существует, и доступен на запись, например,
session.save_path = c:\windows\temp
И не забыть перезагрузить апач после этого.

Как выясняется, сообразительность людская не имеет пределов, и поэтому я вынужден пояснить:
сообщение о третьей ошибке (невозможно найти каталог) НЕИЗБЕЖНО приведет к появлению первых двух, поскольку сообщение об ошибке - это вывод в браузер и после него заголовками пользоваться нельзя. Поэтому не спешите искать преждевременный вывод, а сначала пропишите правильный путь!

Следующей по распространенности проблемой при работе с сессиями является тяжелое наследие register_globals. НЕ давайте переменным скрипта имена, совпадающие с индексами массива $_SESSION!
При register_globals=on значения будут перезаписывать друг друга, и вы запутаетесь.
А при register_globals=off появится другая ошибка: "Your script possibly relies on a session side-effect which existed until PHP 4.2.3.", в случае, если в скрипте есть переменная сессии не имеющая значения, и глобальная переменная с тем же именем. Чтобы от неё избавиться, надо всегда инициализировать переменные перед использованием (или хотя бы проверять на существование) и не давать глобальным переменным имена, совпадающие с индексами массива $_SESSION.

Если не работает, но и никаких сообщений не выводится, то добавьте в самое начало скрипта две строчки, отвечающие за вывод ВСЕХ ошибок на экран - вполне возможно, что ошибки есть, но вы их просто не видите.
ini_set ("display_errors" , 1 );
error_reporting (E_ALL );

или смотрите ошибки в error_log. Вообще, тема отображения сообщений об ошибках выходит за рамки данной статьи, поэтому просто убедитесь хотя бы, что вы можете их видеть. Чуть продробнее о поиске ошибок можно прочитать в этом разделе .

Если вы уверены, что ошибок нет, но приведенный пример не работает все равно, то, возможно, в PHP не включена передача ид через урл, а куки по каким-то причинам не работают .
Смотрите, что у вас с куками.
Вообще, если у вас "не работают" сессии, то сначала попробуйте передать идентификатор сессии руками, то есть, сделать ссылку и приписать к ней идентификатор:
session_start ();
if (!isset($_SESSION [ "counter" ])) $_SESSION [ "counter" ]= 0 ;
echo "Вы обновили эту страницу " . $_SESSION [ "counter" ]++. " раз.

обновить" ;
?>

При этом следует убедиться, что не включена директива session.use_only_cookies , которая запрещает PHP принимать идентификатор сессии, если он был передан через URL

Если этот пример не заработает, то проблема либо в банальных опечатках (половина "проблем" с сессиями происходит от неправильно написанного имени переменной), либо в слишком старой версии PHP: поддержка сессий появилась в версии 4.0, а массив $_SESSION - в 4.1 (До этого использовался $HTTP_SESSION_VARS ).
Если же заработает - то проблема в куках. Отслеживайте - что за куку ставит сервер браузеру, возвращает ли браузер ее. Искать очень полезно, просматривая просматривая обмен HTTP-заголовками между браузером и сервером.
Объяснение принципа работы кук выходит за рамки этого и так уж слишком большого текста, но хотя бы убедитесь, что сервер куку с идентификатором посылает, а браузер - возвращает. И при этом идентификаторы совпадают друг с другом =)
Установка куки должна выглядеть, как
Set-Cookie: PHPSESSID=prlgdfbvlg5fbsbshch6hj0cq6;
или как
Set-Cookie: PHPSESSID=prlgdfbvlg5fbsbshch6hj0cq6; path=/
(если вы запрашиваете скрипт не из корневого каталога)
Ответ сервера должен выглядеть, как
Cookie: PHPSESSID=prlgdfbvlg5fbsbshch6hj0cq6
либо
Cookie: PHPSESSID=prlgdfbvlg5fbsbshch6hj0cq6; b=b
если браузер возвращает другие куки, кроме идентификатора сессии.

Если браузер куки не возвращает - проверьте, работают ли куки вообще.
Убедитесь, что домен, к которому вы обращаетесь, имеет нормальное имя (в котором есть хотя бы одна точка и не содержится запрещенных символов, например подчеркивания) и почистите кэш браузера - это две основные причины, по которм куки могут не работать.

Если пример отсюда работает, а ваш собственный код - нет, то проблема, очевидно, не в сессиях, а в алгоритме. Ищите, где потеряли переменную, по шагам переносите пример отсюда, отлаживайте свой скрипт.

Еще одна проблема может возникнуть, если вы используете перенаправление через header или навигацию с помощью JavaScript.
Дело в том, что РНР автоматически дописывает идентификатор сессии только к ссылкам вида
, но не делает этого для header-ов, яваскрипта, мета-тегов.
Поэтому надо добавлять идентификатор руками, например, так:
header ("Location: /script.php?" . session_name (). "=" . session_id ());

Так же, весьма редкая, и совершенно непонятно, откуда появляющаяся, проблема бывает в том, что настройка session.save_handler имеет значение, отличное от files. Если это не так - исправляйте.

Безопасность
Безопасность сессий - тема обширная. Поэтому остановлюсь на нескольких основных моментах.
Самый хрестоматийный - не передавать идентификатор через адресную строку. Об этом написано даже в php.ini, но это ограничивает функциональность сессий. Если вы решите последовать этому совету, то кроме session.use_trans_sid = 0 не забудьте session.use_only_cookies = 1
Желательно привязывать сессию к IP адресу: таким образом, если идентификатор будет украден, то злодей все равно не сможет им воспользоваться в большинстве случаев.
Рекомендуется пользоваться директивой session.save_path, с помощью которой задать собственный каталог для сохранения файлов сессий. Это более безопасно, чем когда они хранятся в общем временном каталоге сервера по умолчанию.

Дополнительная информация:

  • Кроме кук, механизм сессий посылает еще и заголовки, запрещающие кэширование страниц (тот самый cache limiter). Для html это правильно и необходимо. Но вот когда вы пытаетесь скриптом, проверяющим авторизацию, отдать файл, то интернет эксплорер отказывается его скачивать. Именно из-за этого заголовка. Вызов
    session_cache_limiter ("private" );
    перед стартом сессии должен решить проблему.
  • Как это ни кажется странным, но в массиве $_SESSION нельзя использовать числовые индексы - $_SESSION [ 1 ], $_SESSION [ "10" ] - cессии работать не будут.
  • Где-то между версиями 4.2 и 5.0 невозможно было установить session.use_trans_sid с помощью ini_set () . Начиная с 5.0 уже можно снова.
  • До версии 4.3.3 куку PHP отправлял куку только если при старте сессии в запросе отсутстввал идентификатор. Теперь же кука посылается при каждом вызове session_start ()

    Пример авторизации с помощью сессий
    Проиллюстрируем все вышенаписанное небольшим примером:
    создадим файл auth.php:
    if (isset($_POST [ "auth_name" ]))
    {
    $sql = "SELECT * FROM users WHERE name=?s" ;
    $row = $db -> getRow ($sql , $_POST [ "auth_name" ]);
    if ($row && password_verify ($_POST [ "auth_pass" ], $row [ "pass" ])) {
    $_SESSION [ "user_id" ] = $row [ "id" ];
    }
    header ("Location: http://" . $_SERVER [ "HTTP_HOST" ]. $_SERVER [ "REQUEST_URI" ]);
    exit;
    }

    if (isset($_GET [ "action" ]) AND $_GET [ "action" ]== "logout" ) {
    session_start ();
    session_destroy ();
    header ("Location: http://" . $_SERVER [ "HTTP_HOST" ]. "/" );
    exit;
    }

    if (!isset($_SESSION [ "user_id" ])) {
    ?>








    exit;
    }

    Теперь достаточно написать во всех защищаемых скриптах строчку
    require "auth.php" ;
    В данном примере предполагается, что сессия уже стартовала и соединение с БД создано, с использованием Класс для безопасной и удобной работы с MySQL . Также предполагается, что пароль хэширован с использованием рекомендованной функции password_hash .
    Пример защищаемого файла:

    session_start ();
    include "safemysql.class.php" ;
    $db = new safemysql ([ "db" => "test" ]);
    include "auth.php" ;
    ?>
    secret

    logout

    ОПС! Очень Полезные Ссылки:
    http://www.php.net/manual/ru/ref.session.php - самая последняя и свежая информация о поддержке сессий в PHP в официальной документации, плюс многочисленные комментарии пользователей. Настоятельно рекомендуется к прочтению.
    http://phpclub.ru/manrus/f/ref.session.html - ВЕСЬМА устаревший перевод этой главы на русский, из документации в переводе Александра Пирамидина.
    http://phpclub.ru/detail/article/sessions
    Статья с пафосным названием "Правда о сессиях". Двойственное впечатление оставляет. Вначале автор ОЧЕНЬ доступно рассказывает о механизме сессий, но методы, которые он предлагает к концу статьи - совершенно мутные.

    Хрестоматийная статья Дмитрия Бородина с сайта
    http://php.spb.ru/ настоятельно НЕ рекомендуется.
    Ребята, она страшно устарела. Мало того, что в ней есть фактические неточности, так с сессиями в PHP уже давно просто не работают.
    Огромное Диме спасибо за нее, это была первая статья по сессиям на русском языке, я сам по ней учился, но сейчас надо ее отправить на заслуженный отдых.
    Так же, устарели к сожалению, и многие другие статьи, лежащие в интернете и не обновлявшиеся годами.

  • Модуль сессии не гарантирует, что хранимая сессионная информация доступна только пользователю, который создал сессию. Необходимо принять дополнительные меры по защите конфиденциальности сессии, основываясь на связанных с ней данных.

    Оценка важности данных, передаваемых в рамках сессии, важна для выбора мер по защите этой информации; все имеет свою цену и обычно дополнительные меры защиты приводят к ухудшению удобства для конечного пользователя. Например, если необходимо защитить пользователя от простейших методов социальной инженерии, следует включить session.use_only_cookies . В данном случае со стороны пользовательского ПО обязательна поддержка cookie, иначе механизм сессий не будет работать.

    Существует несколько способов утечки существующего идентификатора сессии третьим лицам. Например инъекции JavaScript, передача идентификатора сесии в URL, перехват пакетов, физический доступ к устройству и т.д. Перехваченный идентификатор сессии позволит третьим лицам получить доступ ко всем ресурсам, связанным с данной сессией. Во-первых, передача идентификатора сессии в URL. При переходе на внешний сайт идентификатор сессии пользователя и адрес ресурса могут попасть в статистику переходов данного сайта. Во-вторых, при более активной атаке возможно прослушивание сетевого трафика злоумышленником. Если канал передачи данных не зашифрован, идентификаторы сессии будут переданы в виде простого текста. В таком случае решением является обязательное использование SSL/TLS пользователями при доступе к сайту. Для этих целей следует применять HSTS.

    Замечание : Даже HTTPS иногда может не защитить конфиденциальные данные. Например, уязвимости типа CRIME, BEAST могут позволить злоумышленнику получить доступ к данным. Многие сети используют прокси HTTPS MITM для аудита. Атакующие также могут настроить такие прокси.

    Неадаптивное управление сессиями

    В настоящее время PHP использует адаптивное управление сессиями по умолчанию. Адаптивное управление сессиями несет дополнительные риски.

    С версии PHP 5.5.2 доступна опция session.use_strict_mode . При её включении и при условии, что обработчик сохранения сессий её поддерживает, неинициализированный сессионный ID отвергается и создается новый. Это защищает от атак, которые принуждают пользователя использовать заранее извесный ID. Ататкующий может размещать ссылки или отправлять письма, которые содержат сессионный ID. Например http://example.com/page.php?PHPSESSID=123456789 . Если опция session.use_trans_sid включена, то жертва откроет сессию с этим идентификатором. Опция session.use_strict_mode уменьшает этот риск.

    Внимание

    Определённый пользователем обработчик сохранения также может поддерживать строгий сессионный режим, путем реализации функции/метода проверки корректности идентификатора сессии. Все определённые пользователем обработчики сохранения обязаны его реализовывать.

    Cookie с сессионным ID должна устанавливаться с указанием параметров domain, path, httponly, secure и, начиная с PHP 7.3, аттрибут SameSite. Их приоритетность определяется браузерами. Опираясь на эту приоритетность, атакующий может может установить сессионный ID, который будет использоваться бесконечно. Применение session.use_only_cookies не решает эту проблему. session.use_strict_mode уменьшает риск. session.use_strict_mode =On, не допускает использование неинициализированных сессионных ID.

    Замечание : Даже при уменьшении риска с помощью session.use_strict_mode атакующий все ещё может заставить пользователя использовать уже инициализированную сессию, созданную атакующим. Например JavaScript-инъекция. Эта атака может быть смягчена, если следовать рекомендациям этого руководства. Если вы следуете этому руководству, вы должны включить session.use_strict_mode , использовать управление сессиями на основе временных меток и пересоздавать идентификатор сессии с помощью session_regenerate_id() , как рекомендуется. Если вы всё это сделаете, идентификатор сессии злоумышленника в итоге будет удален. Если произошел доступ к истекшей сессией, вы должны сохранить все данные активных сессий пользователя. Это позволит для дальнейшего расследования причин произошедшего. После этого, принудительно заставьте пользователя выйти из всех активных сессий, то есть потребуйте от пользователей переавторизации. Это позволит предотвратить атаку с использованием краденной сессии.

    Внимание

    Доступ к истекшей сессии не всегда означает атаку. Нестабильное сетевое соединение и/или немедленное удаление активной сессии может повлечь за собой подобное поведение.

    С PHP 7.1.0 добавлена функция session_create_id() . Эта функция может быть полезна для создания идентификатора сессии с использованием идентификатора пользователя в качестве префикса для достижения большей управляемости. При её использовании крайне важно разрешать session.use_strict_mode . В противном случае недобросовестные пользователи смогут устанавливать поддельные идентификаторы сессий для других пользователей.

    Замечание : В версиях PHP до 7.1.0 необходимо использовать CSPRNG, то есть /dev/urandom или random_bytes() и функции хеширования для генерации нового идентификатора сессии. session_create_id() имеет встроенный функционал обнаружения коллизий и генерирует идентификатор основываясь на INI-настройках. Использование session_create_id() является предпочтительной практикой.

    Пересоздание идентификатора сессии

    Внимание

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

    Управление сессиями на базе временных меток является обязательным для определения устаревших сессий. Если обнаружена попытка доступа к устаревшей сессии, необходимо сбросить флаги авторизации для всех активных сессий пользователя.

    Сессии и автоматический вход

    Разработчики НЕ ДОЛЖНЫ использовать долгоживущие сессии для реализации автоматического входа в систему, потому что это резко повышает вероятность кражи сессии. Автоматический вход в систему должен реализовываться разработчиком самостоятельно.

    Устанавливайте безопасные хешированные одноразовые ключи в качестве ключей автологина с помощью setcookie() . Используйте безопасное хеширование, посильнее чем SHA-2, например SHA-256 или выше со случайными данными из random_bytes() или /dev/urandom.

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

    Ключ автологина - это очень долгоживущий ключ авторизации. Его надо защищать по максимуму. Используйте параметры path/httponly/secure/SameSite при установке cookie для его защиты. Никогда не передавайте ключ автологина, кроме случаев, когда это необходимо.

    Разработчик должен реализовать функционал, который отключает автоматический вход в систему и удаляет ненужные "cookie", установленные для его реализации.

    CSRF (Межсайтовая подделка запроса)

    output_add_rewrite_var() может быть использована для защиты от CSRF. Читайте руководство для подробностей.

    Замечание : До PHP 7.2.0 использовался один и тот же буфер вывода и INI-настройки для "trans sid". Так что использование output_add_rewrite_var() с PHP более ранних версий не рекомендуется.

    Многие фреймворки поддерживают защиту от CSRF. Обратитесь к документации своего фреймворка для более подробной информации.

    Начиная с PHP 7.3, для сессионной cookie можно установить атрибут SameSite. Это обеспечит дополнительную защиту против CSRF.

    Похожие статьи

    • Как цитировать, чтобы пройти антиплагиат

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

    • Программы для просмотра ТВ через интернет: лучшие приложения для стационарных и мобильных систем

      Подключение телеприемника к интернету дает множество преимуществ и удобств: возможность смотреть ролики на YouTube, а не только телеканалы, подписываться на сервисы потокового мультимедиа и др. В рамках статьи мы опишем все варианты, как...

    • Как настроить бесплатные каналы на Smart TV

      Приветствую всех на страницах блога сайт. Наконец добрался я до своего блога и решил написать о том, как настроить и подключить телевизор Самсунг к интернету? Думаю многим это будет интересно. И сразу же перейдем к делу. Подключить...

    • Три способа подключения «Мобильного банка» от Сбербанка

      Мобильный банк — такой же важный инструмент управления своими деньгами, как и сервис Сбербанк онлайн. Тем более, второй без первого практически не работает! Пакет «Эконом» берет с клиента 15 рублей за проверку последней операции на карте и...

    • Что такое яндекс директ и как он работает

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

    • Управление ставками Яндекс

      В этой статье вы узнаете, что такое Яндекс Директ и как он работает в интернете. Также я дам советы и кейсы, которые помогут вам повысить эффективность и увеличить прибыль от контекстной рекламы. Для владельцев сайтов — это...