У меня есть сайт, написанный на PHP, и я добавляю новые функции, используя Python и Django. Частью этого будет аутентификация Django с использованием стандартного пакета contribs.auth.
Когда кто-то вошел в систему, используя нашу настройку Django, когда он перейдет на сторону PHP, мне нужно убедиться, что он вошел в систему и использует информацию пользователя из базы данных).
Каков наилучший способ получения идентификатора пользователя и доказательства того, что идентификатор сеанса Django действителен из PHP, с использованием этого значения cookie сеанса Django?
Мой план заключается в создании хеш-кода идентификатора сеанса Django, моего секретного ключа Django и идентификатора пользователя при входе в систему. Это значение будет установлено как дополнительный файл cookie. Затем в PHP я извлекаю идентификатор пользователя, создаю его хеш и секретный ключ плюс значение cookie сеанса Django, и сравниваю, если они совпадают.
Я расширил представление авторизации при входе в систему, чтобы установить дополнительный файл cookie после успешной аутентификации пользователя. Вместо HttpResponseRedirect он возвращает HttpResponseSetAuthCookieAndRedirect.
HttpResponseSetAuthCookieAndRedirect получает в качестве аргумента request.session.session_id и user_id.
class HttpResponseSetAuthCookieAndRedirect(HttpResponse):
""" a cookie enhanced version of HttpResponseRedirect """
status_code = 302
def __init__(self, user_id, session_id, redirect_to):
HttpResponse.__init__(self)
self['Location'] = iri_to_uri(redirect_to)
my_hash=hashlib.sha512('{0}|-|{1}|-|{2}'.format(settings.SECRET_KEY,user_id,session_id)).hexdigest()
cookie_hash="{0}::{1}".format(user_id,my_hash[:64])
self.set_cookie('check', value=cookie_hash, max_age=172800, path='/', domain=None)
Это устанавливает cookie, который является хешем идентификатора сеанса, моего секретного ключа Django и идентифицированного идентификатора пользователя, который совпадает с идентификатором сеанса.
В PHP
$check_cookie=$_COOKIE['check'];
$django_cookie=$_COOKIE['sessionid'];
$check_cookie=str_replace('"','',$check_cookie);
$django_cookie=str_replace('"','',$django_cookie); //they have quotes for some reason
$parts=explode('::',$check_cookie);
$sent_user_id=(int)$parts[0];
$sent_hash=$parts[1];
$cookie_hash=hash('sha512',"$secret_key|-|$sent_user_id|-|$dj_cookie_sessionid");
$reconstructed_security_hash=$sent_user_id.'::'.substr($cookie_hash,0,64);
if($reconstructed_security_hash==$cookie_hash)
{
return $sent_user_id; //cookies are valid, and user id is the one set by Django for this session id.
}
return false; //cookies do not match
Пока это работает.
Звучит ли эта идея?