Интеграция OpenID в ваш сайт
OpenID – несомненно, полезный механизм как для пользователей, так и для владельцев сетевых ресурсов.
Пользователям он даёт:
- Возможность запомнить один логин и один пароль и использовать его везде
- Не нужно каждый раз вводить одни и те же данные. В идеале каждый сайт будет требовать только ввода данных, специфичных именно для этого сайта
- Не нужно регистрироваться. Хотя часто это недолго (несколько минут), но регистрироваться на каждом сайте напрягает
Для владельцев сайтов тоже есть преимущества:
- Т.к. это удобнее пользователю, больше пользователей будет регистрироваться
- Возможность получить данные пользователя, которые в другом случае он поленился бы вводить (хотя и не скрывает)
- В перспективе – возможность обновления данных о пользователе (как контактной информации, так и информации о его связях, вкусах и т.д. и т.п.)
Благо, сейчас достаточно хороших библиотек для работы с OpenID и достаточно OpenID-провайдеров (в том числе многие социальные сети), чтобы эта фича была востребована на сайте.
Сейчас я расскажу и покажу, как за пару часов добавить поддержку OpenID к существующему сайту. Я не рассматриваю случаи, когда сайты построены на основе популярных движков (вроде WordPress или Drupal), для которых существуют плагины, делающие за вас всю работу. Речь будет идти о сайте в самом общем случае.
Эту статью я решил написать после подключения OpenID к своему сайту maskas.ru, на котором можно посмотреть рабочую версию того, что я сейчас покажу.
Работать это, как и сам сайт, будет на PHP с использованием библиотеки PHP OpenID Library.
Предполагается, что на сайте уже есть таблица с пользователями, которая используется как основное хранилище данных о них.
Архив со всеми скриптами, которые будут использоваться, можно скачать с меня: здесь.
Итак, приступим.
1
Для начала скачайте библиотеку и перенесите папочку Auth туда, где php-скрипты смогут найти её при использовании include.
2
Теперь создадим таблицу связей OpenID-идентификаторов с пользователями.
CREATE TABLE `openid_user_ref` (
`openid` varchar(255) NOT NULL,
`user_id` int(11) NOT NULL,
PRIMARY KEY (`openid`)
)
3
Нужно добавить куда-нибудь на сайт (скорее всего, туда же, где находится форма логина) форму с одним полем ввода для OpenID-идентификатора, перенаправляющую нас на страницу, на которой будет происходить проверка подлинности идентификатора. Выглядеть это будет примерно так:
<form method="get" action="openid_verify.php">
OpenID: <input name="openid_url" type="text" />
</form>
Для лучшей узнаваемости можно добавить к полю ввода картинку вроде
такой.
4
Переписываем файлы из моего примера в корень своего сайта (потом вы сможете их поместить куда нужно, придётся только кое-где поменять пути). Файл openid_verify.php вам трогать, скорее всего, не придётся – он занимается тем, что проверяет правильность введённого OpenID-идентификатора и перенаправляет пользователя на сайт OpenID-провайдера для проверки. В нём вам может понадобиться изменить только список запрашиваемых данных пользователя здесь:
$sreg_request = Auth_OpenID_SRegRequest::build(
// Required
array('nickname'),
// Optional
array('fullname', 'email','gender'));
Файл openid_complete.php уже интереснее. На него пользователь попадает после проверки провайдером и здесь совершаются все необходимые действия по добавлению пользователя в базу или логину. Я написал просты заглушки на нужные функции (создания пользователя, его логина в систему), которые вам нужно будет заменить на что-то более подходящее.
В моём примере логика такая: если OpenID-идентификатор нам неизвестен, мы автоматически создаём нового пользователя с данными, предоставленными OpenID-провайдером. Если идентификатор известен – логиним пользователя.
При создании пользователя используется ник, полученный от OpenID-провайдера. Если ник не получен или полученный ник не подходит (что проверяется функцией check_nickname), то он генерируется из OpenID-идентификатора.
Список данных о пользователе, которые теоретически можно получить от провайдера, достаточно скромен (т.к. используется расширение SRE, описанное в статье обмен пользовательскими данными в OpenID), но все основные данные получить можно.
Для начала вы можете просто распаковать пример в какую-либо папку на сервере и запустить – он работоспособен и сам по себе (особенно если указать правильные параметры для подключения к MySQL в файле openid_common.php). После замените заглушки по созданию пользователя и логину на подходящие для вашего сайта функции и готово – пользователи могут регистрироваться и заходить на ваш сайт при помощи OpenID.
Примечания:
Если вы используете библиотеку под Windows, то вам, скорее всего, нужно установить переменную Auth_OpenID_RAND_SOURCE из файла CryptUtil.php в null.
Не забывайте чистить директорию со временными файлами (путь к ней указывается при создании объекта Auth_OpenID_FileStore). Если ваш сайт достаточно посещаемый, то через время она может начать занимать заметное место на диске.
Я не рассматривал здесь вопрос прикрепления OpenID-идентификаторов к существующим пользователям и объединения OpenID-идентификаторов в одного пользователя. Всё это можно дописать на основе вышеизложенного.
Метки: OpenID
декабря 28, 2007 at 8:28 пп
Полезно. Сейчас сам периодически покуриваю в том-же направлении.
Но на мой вкус я бы почитал про ее внутренее устройство и особенности реализации протоколов. К примеру для чего там нужен GMP/bcmath. По крайне мере это меня в этой библиотеке интерисует прямо в данный момент :)
декабря 28, 2007 at 9:22 пп
Математические функции здесь используются для шифрованных переговоров между клиентом и сервером. В частности, используется протокол Diffie-Hellman (это я в исходниках нарыл при беглом осмотре)
декабря 29, 2007 at 7:42 дп
Неужто в стандарте обязательно идет шифрование такого уровня, что требует поддержку длинных чисел? Или это в библиотеке специально используется усиленное шифрование?
декабря 29, 2007 at 10:34 дп
В спецификации предусмотрены разные типы шифрования. OpenID-провайдер может потребовать более сильного, поэтому библиотека должна его поддерживать.
Но создание ключей обычно таки предусматривает работу с длинными числами. Особенно когда эти ключи на лету создаются как здесь.
декабря 29, 2007 at 11:32 дп
c помощью ЖЖ спокойно авторизовался на Вашем сайте.
с мойкругом, после того, как я нажал в нём на кнопочку “подтвердить”, вышло так: ваш сайт сказал, что-то типа “Bad Blah-Blah-Blah”… в чём ошибка должна быть?
декабря 29, 2007 at 12:52 пп
Вы имеете в виду на блоге? Тогда с moikrug могут быть проблемы. Они довольно странно отдают OpenID-идентификатор, а в плагине для WordPress используется старая версия библиотеки, которая это не обрабатывает.
На maskas.ru регистрация с moikrug работает нормально.
января 7, 2008 at 3:09 пп
Блин, как-то сложно все. Может подскажите, где можно найти более подробную информацию по данному аспекту?
января 7, 2008 at 3:32 пп
Пытался сделать всё как можно проще :)
Через 2 дня я буду появляться онлайн – можно позадавать мне вопросы о том, что не понятно по почте или ICQ.
января 13, 2008 at 8:56 пп
Спасибо! Правдо немножко не догнал.. потом разберусь..
января 17, 2008 at 5:21 пп
У меня вопрос, OpenID сервер может сделать любой разработчик… а как же тогда быть с уникальностью.. или есть сервер, на котором хранится инфа?
января 18, 2008 at 12:12 дп
Одного глобального сервера нет. Уникальность OpenID-идентификатора – это уникальность URI. Т.е. веб-странички. OpenID только удостоверяет ваше “владение” этой страничкой.
января 18, 2008 at 12:35 пп
так… хорошо, а как другие сайты, на которых есть поддержка OpenID будут принимать пользователей, которым я выдам OpenID?
января 25, 2008 at 8:53 пп
а так же, как вы только что комментарий оставили :)
июня 2, 2008 at 2:21 пп
Сорри.
Дайте, плиз рабочую ссылку на
openid_test.zip
указанная в статье
http://daeq.ru/openid/openid_test.zip
не работает :(
июня 2, 2008 at 2:47 пп
Спасибо!
июня 11, 2008 at 4:36 пп
[...] що хочуть додати OpenID на свій сайт: PHP OpenID Library Интеграция OpenID в ваш сайт [...]
августа 23, 2008 at 2:12 пп
Сработало. А уменя на хостинге yandex не работает, а ЖЖ нормально. В чем трюк?
января 19, 2009 at 7:35 дп
А у меня никак не получается прикрутить :((, постоянно выдается return_to does not match return URL , хотя урлы, написанные после одинаковые. Как такое может быть? Кто-нибудь сталкивался?