Вставить конкретные куки, не используя sessionStorage или любые функции HTML5
Я заинтересован в том, чтобы пользователи могли входить в систему и выходить из системы с помощью нескольких cookie сеансов пользователя в моем веб-приложении. В настоящее время аутентификация выполняется стандартно, и уникальный идентификатор позволяет мне аутентифицировать пользователя, когда они посещают наш сайт, если они представляют токен аутентификации, доступный в их файле cookie. Типичные варианты использования применяются в том случае, если пользователь выходит из одной вкладки, он выводит их из другой вкладки. Прямо сейчас для этого требуется наличие имени пользователя из двух уникальных экземпляров браузера, чтобы иметь возможность входа в систему с двумя разными учетными записями.
Есть ли способ, отличный от HTML5 (с использованием стандартных куки файлов javascript), чтобы иметь идентификаторы файлов cookie, специфичные для табуляции? Я предполагаю, что нет четкого пути для этого, и для этого потребуется какой-то хак + сотрудничество с бэкэндом. Если есть решение, которое имеет смысл без использования HTML5, это было бы идеально.
Ответы
Ответ 1
Вы не можете.
Есть способы справиться с этим условием, но ни один из них не прост.
Если вы хотите, вы должны сказать пользователю сделать так: Как выродок
Из документации: Данные, сохраненные с помощью sessionStorage
не сохраняются между вкладками браузера, даже если две вкладки оба содержат веб-страниц из одного домена происхождения. Другими словами, данные внутри sessionStorage
ограничивается не только домен и каталог страницы вызывающем, а вкладки браузера, в котором страница содержится. Contrast, что сессионные куки, которые делают сохраняются данные вкладки на вкладку.
Ответ 2
Я некоторое время назад добился подобного поведения. Итак, что я делаю, это примерно так:
- Чтобы это сработало, вам нужно перенести sessionId в URL-адрес или как часть содержимого страницы.
- Когда загружается страница входа в систему, удалите файл cookie sessionId.
- Когда отправляется логин для входа, сервер предоставляет страницу входа в систему вместе с sessionId в URL-адресе или как часть тела ответа html.
- С этого момента, перед каждым вызовом сервера, установите cookie сеанса в том, что у вас есть в URL-адресе или содержимом страницы.
- Итак, каждая вкладка установит свой собственный файл cookie перед любым вызовом сервера, который заставит запрос приземлиться с нужным сеансом на сервере.
Ответ 3
Прежде всего, это решение работает, если вы используете только относительные URL-адреса! (для изображений, ссылок и даже вызовов Ajax)
Используйте сеансы, как в любом обычном сценарии, с одним небольшим изменением. Вместо идентификации пользователей с каждым идентификатором сеанса каждый идентификатор сеанса идентифицирует машину (браузер). Поэтому, когда запросы поступают на сервер, он идентифицирует группу пользователей, которые используют ваш веб-сайт на этом компьютере. Каждый пользователь будет иметь свой собственный под-идентификатор (это может быть последовательный счетчик или случайное число). Проще говоря, ваши данные сеанса (идентифицированные идентификатором сеанса в файлах cookie) содержат ассоциативный массив. Каждая запись этого массива содержит данные сеанса для одного конкретного пользователя, идентифицированного под-идентификатором. Например, в PHP, если ваш под-идентификатор пользователя user0
, вы можете получить доступ к этим данным сеанса пользователя, например:
<?php
session_start();
$user_data = $_SESSION['user0'];
Далее описано, как передать пользовательский под-идентификатор.
Вы можете использовать перезапись URL-адреса веб-сервера. Вам нужно придумать шаблон, который можно рассматривать как обычное имя папки, в то время как нет такой папки. Например:
RewriteEngine On
RewriteRule ^user(\d+)\/(.*)$ $2?sub_id=$1 [QSA,L]
В этом примере вам не разрешено иметь такие папки, как user0
, user1
и т.д. Если какой-либо запрос запрашивает http://domain.com/user0/index.php
, он будет переписан на http://domain.com/index.php?sub_id=user0
. Теперь в index.php
у вас будет:
<?php
session_start();
$user_data = $_SESSION[$_REQUEST['sub_id']];
И вы должны использовать $user_data
вместо $_SESSION
с этого момента. Остается только, как сгенерировать под-идентификатор в первый раз. Это относительно легко, вы можете:
<?php
session_start();
if (!isset($_REQUEST['sub_id'])) {
$sub_id = 0;
while (isset($_SESSION["user{$sub_id}"])) {
$sub_id++;
}
$_SESSION["user{$sub_id}"] = array();
header("Location: /user{$sub_id}".$_SERVER['REQUEST_URI']);
die();
}
else {
$user_data = $_SESSION[$_REQUEST['sub_id']];
}
В конце все будет работать, только если все ваши URL-адреса являются относительными! Каждый абсолютный URL-адрес, который не начинается с /user0/
, будет считаться новым пользователем и приведет к новой записи в сеансе.
Преимущество такого подхода заключается в том, что ваш текущий код будет работать с минимальными усилиями, если URL уже рассмотрены относительно.
Ответ 4
Это простой пример того, как вы можете создать систему, в которой пользователь может войти в несколько учетных записей. Это не проверка безопасности и должна быть добавлена. Этот код можно гораздо лучше писать и оптимизировать.
inc.php
https://github.com/maksa9/multiple-user-login/blob/master/inc.php
Этот файл включен в каждый php script.
Эта часть проверяет, какой пользователь зарегистрирован и какая учетная запись активна. Вот функции, которые создают правильный путь к php-скриптам в соответствии с активной учетной записью
// check which user is logged and which account is active
if(isset($_GET['user'])) $id_user = (int)$_GET['user'];
if($id_user > 0)
{
if(isset($_SESSION['user'][$id_user]))
{
$user_name = $_SESSION['user'][$id_user]['name'];
$user_email = $_SESSION['user'][$id_user]['email'];
}
else
gotToLoginForm();
}
// If the user id is not specified and there is a user session, finds another id
if($id_user == 0 and isset($_SESSION['user']))
{
$sess = $_SESSION['user'];
$id_user = (int)key($sess);
if(isset($_SESSION['user'][$id_user]))
{
$user_name = $_SESSION['user'][$id_user]['name'];
$user_email = $_SESSION['user'][$id_user]['email'];
define('ID_USER',$id_user);
gotToIndex();
}
else
gotToLoginForm();
}
define('ID_USER',$id_user);
LoginForm.php
https://github.com/maksa9/multiple-user-login/blob/master/loginform.php
Простая форма для входа с методом post.
login.php
https://github.com/maksa9/multiple-user-login/blob/master/login.php
Вход пользователя. имитирует запрос к базе данных.
if(isset($_POST['email']))
if(isset($_POST['pass']))
{
$email = $_POST['email'];
$pass = $_POST['pass'];
$id_user = 0;
// simulates a query to the database
if($email === '[email protected]' and $pass === '111')
{
$id_user = 1;
$name='John Doe';
}
if($email === '[email protected]' and $pass === '222')
{
$id_user = 2;
$name = 'Doe John';
}
// login user
if($id_user > 0)
{
// checks if the user is already logged
if( !isset($_SESSION['user'][$id_user]))
{
$_SESSION['user'][$id_user] = array('email'=>$email, 'name'=>$name);
}
//go to main page
$page = ROOT.'user/'.$id_user.'/index.php';
header('Location: '.$page);
exit;
}
}
index.php
https://github.com/maksa9/multiple-user-login/blob/master/index.php
Главная страница приложения.
<div>
<h1>Welcome: <?php echo $user_name ?> (<?php echo $user_email ?>) [<?php echo $id_user ?>]</h1>
<p><a href="<?php echo returnUrl('swap.php',$id_user) ?>">Choose an account</a></p>
<p><a href="<?php echo returnUrl('loginform.php',$id_user) ?>">Login with the another account</a></p>
<p><a href="<?php echo returnUrl('logout.php',$id_user) ?>">Log out</a></p>
</div>
swap.php
https://github.com/maksa9/multiple-user-login/blob/master/swap.php
Позволяет пользователю выбирать учетную запись.
foreach($_SESSION['user'] as $idus => $userA)
{
echo '<p><a href="'.returnUrl('index.php',$idus).'">'.$userA['name'].' ('.$userA['email'].') ['.$idus.']</a></p>';
}
logout.php
https://github.com/maksa9/multiple-user-login/blob/master/logout.php
Выход из системы. Проверяйте активные учетные записи пользователей и перенаправляйте их, если они есть.
unset($_SESSION['user'][ID_USER]);
if(count($_SESSION['user']) == 0)
unset($_SESSION['user']);
// checks for active user accounts and redirects them if any
if(isset($_SESSION['user']))
{
$sess = $_SESSION['user'];
$id_user = (int)key($sess);
if(isset($_SESSION['user'][$id_user]))
{
$page = ROOT.'user/'.$id_user.'/index.php';
header('Location: '.$page);
exit;
}
}
.htaccess
https://github.com/maksa9/multiple-user-login/blob/master/.htaccess
Options +FollowSymlinks
RewriteEngine On
RewriteRule ^user\/([0-9]*)\/index.php$ index.php?user=$1 [NC,L]
RewriteRule ^user\/([0-9]*)\/logout.php$ logout.php?user=$1 [NC,L]
RewriteRule ^user\/([0-9]*)\/login.php$ login.php?user=$1 [NC,L]
RewriteRule ^user\/([0-9]*)\/loginform.php$ loginform.php?user=$1 [NC,L]
RewriteRule ^user\/([0-9]*)\/swap.php$ swap.php?user=$1 [NC,L]
RewriteRule ^user\/$ index.php [NC,L]
RewriteRule ^user$ index.php [NC,L]
Ответ 5
Вы не можете
Когда создается файл cookie, можно контролировать его видимость, установив его "корневой домен". Затем он будет доступен для любого URL-адреса, принадлежащего этому корню. Например, root может быть установлен в "example.com", и cookie будет доступен для сайтов в "www.example.com" или "xyz.example.com" или "example.com". Это может использоваться, чтобы позволить связанным страницам "общаться" друг с другом. Невозможно установить корневой домен для доменов верхнего уровня, таких как ".com" или ".co.uk", поскольку это позволит широко распространять доступ к файлу cookie.
По умолчанию куки файлы видны всем путям в своих доменах, но во время создания они могут быть отнесены к указанному подпуту - например, "www.example.com/images".
поэтому любая вкладка, имеющая тот же корневой домен, может получить доступ к этому файлу cookie.
Ответ 6
Файлы cookie сеанса являются специфичными для сервера AFAIK, поэтому вы можете настроить разные DNS-имена для одного и того же сервера, например. субдомены типа: session1.myserver.com, session2.myserver.com, session3.myserver.com
Ответ 7
Ну, @dm4web ответ правильный, но вы должны обратить внимание на свои предупреждения о безопасности. Лучшее, что вы можете сделать, это использовать двунаправленный подход.
Направление 1
Regular Login.
Create a Unique session ID and pass it via the URL.
Направление два
Check Session via i) Logged In User and ii) Check Session ID via URL Param
Теперь возьмем пример:
$usrname: Fool
$psswd: dm4web
Код PHP
session_start();
//all inputs should be sanitized
$sql = "SELECT * FROM `users` WHERE `usrname`='".$usrname."' AND `psswd` = '".$psswd."'":
$dbh = new PDO('odbc:db', 'db2inst1', 'ibmdb2');
$count = $dbh->exec($sql);
if($count > 0){
//Guy is logged in
$a = session_id();
//**Use this $a in every URL parameter under current session**
}
else {
//Go f**k yourself >> to the user ;)
}
Но вы должны заметить, что вы не можете напрямую перейти в эту схему соответствия пользователя/пароля. Сначала вы должны убедиться, что вы узнали, что пользователь уже вошел в систему или нет. Кроме того, на основе SESSION Cookie от PHP вы обнаружите, что
- Если на компьютере активен вход в систему
- Если есть активный логин в URL-адресе [см. $a из файла session_id]
Вы сопоставляете параметр URL при любых обстоятельствах, перекрестно ссылаетесь на файл cookie SESSION и продолжаете!
Удачи!
Дайте мне знать, если у вас есть еще вопросы!