- Подписка на печатную версию:
- Подписка на электронную версию:
- Подшивки старых номеров журнала (печатные версии)
LXF73:PHP II
Материал из Linuxformat.
PHP аутентификация на web-сайте
Пол Хафпенни (Paul Halfpenny) рассказывает, как при помощи PHP и MySQL создать на вашем сайте закрытые области, требующие аутентификации.
Существует множество различных причин для создания закрытых областей на вашем web-сайте. Например, вы можете захотеть сделать рабочее место для администраторов, с помощью которого они смогут изменять содержимое сайта или загружать новые документы. Это позволит ввести контроль за изменением документов на сайте, а также даст возможность неспециалистам выполнять некоторые простые задачи.
Но самая популярная причина ограничения доступа к некоторым частям сайта в последнее время — это создание разделов «для своих» (Member’s Area), в которых расположена информация, доступная только зарегистрированным пользователям, возможно, по платной подписке. Согласно этой модели, владелец сайта должен быть уверен, что посетитель, входящий в раздел для своих, имеет на это право. Проще всего добиться этой цели, запросив у каждого посетителя имя и пароль. Но как же убедиться, что имя и пароль правильные?
На самом деле, есть очень много способов это сделать. Например, вы можете использовать базовую авторизацию HTTP и прописать все пары имени/пароля прямо в коде сценария. Или же держать эту информацию в базе данных. Ниже мы рассмотрим оба этих варианта
HTTP-аутентификация на PHP
Начнём с сохранения пользовательских данных в нашем сценарии. базовая HTTP-авторизация служит для аутентификации пользователей, пытающихся прочитать защищённую страницу, и построена по схеме «запрос-ответ». Первый запрос приходит, когда пользователь запрашивает файл с сервера. если файл находится в защищённой области, сервер отправляет код 401 (неавторизованный пользователь) в заголовке ответа клиенту. Web-браузер клиента распознаёт этот ответ и показывает пользователю всплывающее окно с предложением ввести имя и пароль. После того, как пользователь указал эти данные и нажал кнопку OK, браузер отправляет их серверу.
если имя пользователя и пароль были признаны правильными, защищённый файл передаётся клиенту. Подтверждение прав доступа будет происходить постоянно, пока авторизованный пользователь находится в защищённом разделе. Но если имя и пароль, набранные в диалоге браузера, сервер счёл неправильными, окно для их ввода будет показано снова, чтобы можно было повторить попытку. Этот цикл будет продолжаться до тех пор, пока не будут введены корректные данные, или пока пользователю не надоест.
При помощи простого сценария на PHP мы можем сымитировать эту систему запроса-ответа базовой авторизации HTTP, отправляя нужные заголовки браузеру, которые потребуют от него отобразить окно ввода пароля. Полученную информацию об имени и пароле затем можно будет прочитать в глобальных переменных — ($PhP_AUTh_USER, $PhP_AUTh_PW, и $PhP_AUTh_TYPE). С их помощью можно проверить имя пользователя и пароль на соответствие данным из текстового файла, из базы данных или из любого другого списка
давайте начнём не торопясь, с простого сценария, который проверяет наличие имени пользователя (любого!) в переменной $PhP_AUTh_USER. если там ничего нет, сценарий отправит клиенту сообщение «401 Unauthorized» в заголовке ответа. Этот заголовок укажет браузеру на необходимость показать окно авторизации, и на этом сценарий завершается. После того, как пользователь что-то ввёл и нажал на OK, данные будут отправлены на сервер и страница будет перезагружена. Поскольку на этот раз в переменной $PhP_AUTh_USER будет содержаться введённое имя пользователя, первая часть сценария окажется пропущена и заголовок 401 не будет отправлен.
<?php // File Name: auth01.php // Содержится ли что-нибудь в $PHP_AUTH_USER if (!isset($PHP_AUTH_USER)) { // Пусто - выдать диалог для ввода пароля header(‘WWW-Authenticate: Basic realm=”Secret Area “’); header(‘HTTP/1.0 401 Unauthorized’); echo ‘Authorization Required.’; exit; } else { // Не пусто – вывести значения переменных echo “<P>You have entered this username: $PHP_AUTH_ USER<br>You have entered this password: $PHP_AUTH_PW<br>The authorization type is: $PHP_AUTH_TYPE</p>“; } ?>
Теперь мы собираемся проверить введённые данные на совпадение с прописанными в сценарии значениями. Этот метод полезен, если у вас всего одна комбинация из имени и пароля (например, если это сценарий администрирования сайта). Второй сценарий очень похож на первый, главное отличие состоит в том, что если имя/пароль были указаны, выполняется оператор if/else: если полученные данные не совпали с требуемыми, диалог аутентификации будет показан снова. И только если и имя, и пароль совпали с указанным в сценарии значениями, в браузер будет выведено сообщение об этом.
<?php // File Name: auth02.php // Содержится ли что-нибудь в $PHP_AUTH_USER if (!isset($PHP_AUTH_USER)) { // Пусто – выдать диалог для ввода пароля header(‘WWW-Authenticate: Basic realm=”Secret Area “’); header(‘HTTP/1.0 401 Unauthorized’); echo ‘Authorization Required.’; exit; } else if (isset($PHP_AUTH_USER)) { if (($PHP_AUTH_USER != “user”) || ($PHP_AUTH_PW != “password”)) { header(‘WWW-Authenticate: Basic realm=”Secret Area”’); header(‘HTTP/1.0 401 Unauthorized’); echo ‘Authorization Required.’; exit; } else { echo “<P>You’re authorized!</p>“; } } ?>
Попробуйте ввести неправильное имя пользователя и правильный пароль, или же правильное имя пользователя и неправильный пароль, или же укажите и то и другое неверно. Вы видите, что сервер не принимает такие варианты. а теперь попробуйте ввести в поле для имени пользователя слово «user», а в поле для пароля слово «password». На этот раз вы авторизованы.
Отрицательная сторона такого метода авторизации состоит в том, что многие сайты требуют уникальные имя пользователя и пароль для каждого участника, чтобы администратор сайта мог видеть, сколько человек получило доступ в закрытый раздел. кроме того, поскольку в Интернете так легко обмениваться информацией, уникальная комбинация имени и пароля поможет избежать прекращения платежей за контент после первого же заказа.
аутентификация с помощью базы данных
Аутентификация в CGI Глобальные переменные $PhP_AUTh_USER, $PhP_AUTh_PW и $PhP_AUTh_TYPE доступны только в том случае, если PHP установлен в качестве модуля сервера Apache. если вы используете PHP как CGI-приложение, то ваши возможности ограничены аутентификацией на основе файле .htaccess, или же вам придётся использовать HTML-формы, и проверять введённую информацию на совпадение с записью из базы данных при помощи приложения на PHP.
Чтобы и вам избежать этого, можно сохранять информацию в текстовом файле или в базе данных, так как проверять по ним данные не сложнее, чем в предыдущем случае. Оба способа хороши, но при увеличении потока посетителей на вашем сайте база данных выигрывает, так как она может одновременно обрабатывать множество запросов и обновляться на лету.
давайте рассмотрим, как можно сравнивать полученные имя пользователя и пароль с данными из списка, хранящегося в таблице базы данных. В этом примере мы используем функции PHP для подключения к базе данных MySQL, но вы можете использовать вместо неё любые другие встроенные функции, что позволит вам использовать любую базу данных их числа поддерживаемых в PHP.
для хранения имён пользователей и паролей нам потребуется создать таблицу. Назовём её Users, и выглядеть она будет так:
+-------------+----------+----------+ | real_name | username | password | +-------------+----------+----------+ | Joe Smith | joe | ai890d | +-------------+----------+----------+ | Jane Smith | jane | 29hj0jk | +-------------+----------+----------+ | Mary Smith | mary | fsSS92 | +-------------+----------+----------+ | Bob Smith | bob | 2NNg8ed | +-------------+----------+----------+
Вам нужно выполнить поиск записи, поля username и password для которой совпадают с введенными пользователем. Это можно сделать при помощи следующего SQL-запроса:
SELECT * FROM users WHERE username='$PHP_AUTH_USER' AND password='$PHP_AUTH_PW'
Выполнив этот запрос, мы сразу получим результат, которым можем воспользоваться. Не обязательно читать полученные данные, достаточно просто посчитать, сколько вернулось строк — ноль (то есть такой пары имя/пароль в базе данных нет) или одна (пользователь найден).
mysql_connect(“hostname”, “username”, “password”) or die (“Unable to connect to database.”); mysql_select_db(“dev_i2ii_com”) or die (“Unable to select database.”); $sql = “SELECT * FROM users WHERE username=’$PHP_AUTH_USER’ and password=’$PHP_AUTH_PW’”; $result = mysql_query($sql); $num = mysql_numrows($result);
Всё, что нам осталось — это поместить обращение к базе данных в наш сценарий аутентификации.
<?php // File Name: auth04.php if (!isset($PHP_AUTH_USER)) { header('WWW-Authenticate: Basic realm="Secret Area "'); header('HTTP/1.0 401 Unauthorized'); exit; } else if (isset($PHP_AUTH_USER)) { // Не пусто – произвести поиск в базе данных mysql_connect("hostname", "username", "password") or die ("Unable to connect to database."); mysql_select_db("dev_i2ii_com") or die ("Unable to DB."); $sql = "SELECT * FROM users WHERE username='$PHP_AUTH_USER' and password='$PHP_AUTH_PW'"; $result = mysql_query($sql); // Посчитаем число записей в результате. 0 – авторизаци провалилась, 1 – прошла успешно. $num = mysql_numrows($result); if ($num != "0") { echo "<P>You're authorized!</p>"; exit; } else { header('WWW-Authenticate: Basic realm="Secret"'); header('HTTP/1.0 401 Unauthorized'); echo 'Authorization Required.'; exit; } } ?>
Мы с вами рассмотрели два способа аутентификации для защиты закрытых разделов вашего сайта. какой выбрать — зависит от того, что именно вы хотите защитить и скольким пользователям требуется получить имена и пароли. Принцип в обоих случаях одинаков — доступ предоставляется только тогда, когда оба введённых параметра в точности совпадают с хранящимися у вас значениями. Вам осталось только принять главное решение — кому именно вы дадите права доступа.