Безопасно ли хранить пользовательский объект в файле cookie?

У меня есть пользовательский объект, который содержит информацию о пользователе (имя пользователя, ip, страна, имя, адрес электронной почты... но НЕ пароль). Должен ли я хранить только имя пользователя в файле cookie, а затем извлекать всю информацию из БД при загрузке страницы или просто хранить весь объект пользователя в файле cookie?


person Gal    schedule 23.11.2009    source источник


Ответы (6)


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

Я предлагаю использовать сеанс PHP для хранения объекта. Таким образом, конечный пользователь имеет только идентификатор сеанса, хранящийся в файле cookie, с реальными данными на вашем сервере.

Сеанс в конечном итоге истечет, хотя... заставляя пользователя снова войти в систему.

Редактировать: Упс, я должен отметить, что сеансы действительно просты в использовании. Просто сделайте следующее:

session_start(); // This MUST be at the very top of every page that accesses the session

// Store something in the session with the key 'something'
$_SESSION['something'] = "Hi, I'm a session!"; 

// Retrieve 'something' from the session
$myString = $_SESSION['something'];
person Powerlord    schedule 23.11.2009
comment
+1 за «вы не можете доверять данным в файлах cookie». Чтобы расширить точку зрения Р. Бемроуза, файлы cookie должны содержать указатель на данные в вашей системе, не более того. Таким образом, данные cookie сами по себе не имеют смысла. - person Dave Swersky; 23.11.2009
comment
Кроме того, передача огромных объемов данных в файле cookie может отрицательно сказаться на времени загрузки страницы, поскольку файл cookie передается с каждым запросом. - person Yacoby; 23.11.2009
comment
Или это может оказать положительное влияние на время загрузки страниц, так как позволяет исключить обращение к базе данных туда и обратно. Вы узнаете, только измерив. :) - person Thom; 23.11.2009
comment
@Thom: Предполагая, что вы отвечаете Якоби; Вы сэкономите время на обмен данными с базой данных за счет отправки файла cookie с каждым запросом на ваш сервер. Сеанс аккуратно устраняет обе эти проблемы. - person Powerlord; 24.11.2009
comment
@R.Bemrose: и это происходит за счет обращения к вашему хранилищу сеансов для каждого запроса - я подозреваю, что в настройках PHP по умолчанию это означает чтение и запись файла, поэтому у вас есть дополнительные дисковые операции ввода-вывода, о которых нужно беспокоиться. Все, что я хочу сказать, это то, что хранение информации в куки-файле — это правильное решение, если оно вас устроит, и любые решения, которые вы принимаете в отношении производительности, должны основываться на измеренных вами вещах, а не на сделанных вами предположениях. :) - person Thom; 24.11.2009
comment
PHP по умолчанию использует обработчик сеанса файлов. Это связано с тем, что компиляция PHP по умолчанию не включает библиотеку общей памяти mm, необходимую для обработчика сеанса в памяти (который просто называется mm). - person Powerlord; 24.11.2009
comment
Этому ответу много лет, но обе библиотеки memcache имеют обработчики сеансов, которые вы можете использовать для хранения данных сеанса в памяти. - person Powerlord; 17.02.2011
comment
Правда ли, что настройка httpOnly может ограничить доступ к файлам cookie для пользователя? - person Ramesh Pareek; 28.02.2018

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

person JeffreyABecker    schedule 23.11.2009

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

Чтобы проверить, загружается ли страница в первый раз, я просто устанавливаю логическое значение в сеансе, если оно было загружено. Если bool не существует, ваш пользователь сначала загружает его.

Вероятно, есть лучшие способы сделать это, но это работает красиво и легко. :)

person F.P    schedule 23.11.2009

Сохраняйте только идентификатор сеанса! Никогда не значимые данные, такие как идентификатор пользователя. Представьте, что у вас есть сайт с 10 000 пользователей. Скорее всего, у вас есть хотя бы один пользователь с именем супермен и бэтмен — если вы разорвали имя пользователя в файле cookie для доступа к информации о сеансе — я потенциально могу манипулировать этим файлом cookie, чтобы изменить сохраненную информацию с моего имени пользователя на Бэтмен и получить доступ на учетную запись Бэтмена, если его сессия все еще жива. Если вы храните какой-то случайно сгенерированный идентификатор сеанса, мне практически невозможно определить номер сеанса, который будет работать для другого пользователя, чтобы захватить этот сеанс.

person konung    schedule 23.11.2009

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

person Thom    schedule 23.11.2009

@ ApoY2k - я думаю, что проголосовал против (это был не я :), потому что вы не можете предположить, что имя пользователя, передаваемое из файла cookie, является фактическим именем пользователя, которое вы записали в файл cookie. Вот почему они предложили использовать sessionID. Используя идентификатор сеанса, вы можете получить имя пользователя, и, как он сказал, он подходит только на 20 минут или на то, что вы установили для тайм-аута сеанса. SessionID не раскрывает никаких личных данных. У меня была такая же мысль, прежде чем я нашел этот пост.

person mokumaxCraig    schedule 16.02.2011