Аутентификация пользователя
В прошлый раз мы делали регистрацию пользователя, теперь сделаем аутентификацию (авторизацию) на своём сайте.
Создадим файл tpl/auth.tpl - форму аутентификации.
<form action="login.php?go=ok" class="form" method="post">
<?=$content["error"] ?>
<input name="login" placeholder="Логин" value="<?=$content["login"] ?>"><br/>
<input type="password" name="password" placeholder="Пароль"><br/>
<input type="submit" value="Авторизоваться">
<a href="login.php?go=pass">Забыл пароль</a>
</form>
Она похожа на форму регистрации, в ней нет поля электронной почты и добавлена ссылка Забыл пароль.
В корневой папке сайта создадим файл авторизации login.php.
<?php
//подключаем класс
include_once 'PHPTemplate.php';
//подключаем функции
include_once 'function.php';
//Доступ к БД
define($config['unicod'] , true);
include_once 'config.php';
include_once 'db.php';
// Подключение к БД
$connection = @mysqli_connect($dbsettings['server'], $dbsettings['user'], $dbsettings['pass'], $dbsettings['name']);
mysqli_set_charset ( $connection , "utf8" );
if ($connection == false){
print("Ошибка: Невозможно подключиться к MySQL " . mysqli_connect_error());
}
//получаем данные
$go = valid($_GET['go']);
//присоединяем шаблон
$tpl = new PHPTemplate('./tpl/page.tpl');
//присоединяем блок пользователя
include_once 'user.php';
//присоединяем форму авторизации
$tplForm = new PHPTemplate('./tpl/auth.tpl');
if($go=="ok"){
//авторизуем пользователя
$content["login"]=valid($_POST['login']);
$content["password"]=valid($_POST['password']);
//проверка заполнености полей
if (!$content["password"]) {
$err="Введите пароль!";
}
else if (preg_match("/[^(\w)|(\x7F-\xFF)|(\s)]/",$content["password"])) {
$err="Используйте только буквы и цифры в Пароле!";
}
else if(strlen($content["password"]) < 6 or strlen($content["password"]) > 30){
$err = "Длинна Пароля должна быть не менее 6 знаков и не более 15 знаков";
}
if (!$content["login"]) {
$err="Введите логин!";
}
else if (preg_match("/[^(\w)|(\x7F-\xFF)|(\s)]/",$content["login"])) {
$err="Используйте только буквы и цифры в Логине!";
}
else if(strlen($content["login"]) < 3 or strlen($content["login"]) > 30){
$err = "Длинна Логина должна быть не менее 3 знаков и не более 15 знаков";
}
// проверяем логин
$sql = "SELECT Password, UniId FROM `Users` ";
$sql .= "WHERE Login='".mysqli_real_escape_string($connection, $content[\"login\"])."' LIMIT 1";
$result = mysqli_query($connection, $sql);
$data = mysqli_fetch_assoc( $result );
// Сравниваем пароли
if($data['Password'] != md5($content["password"])) {
$err="Не верный логин или пароль!";
}
//авторизация или вывод ошибки
if($err !=""){
//ошибка авторизации
$content["error"]=" <div style='background-color: red;color: #fff;padding: 5px;margin: 15px'>".$err."</div>";
}else{
//авторизация
$timer=time()+60*60*24*30;
setcookie($conf['cookie'], $data['UniId'],$timer, "/");
header('location: /');
exit();
}
}
if($go=="exit"){
setcookie($conf['cookie'],0,0);
header('location: /');
exit();
}
$content["title"]="Аутентификация пользователя";
$content["horizontal_menu"]="Аутентификация пользователя";
if($go=="cabinet"){
$content["title"]="Ваш профиль";
$content["horizontal_menu"]="Ваш профиль";
//присоединяем форму профиля
$tplForm = new PHPTemplate('./tpl/profile.tpl');
$sql = "SELECT Email FROM `Users` ";
$sql .= "WHERE UniId='".$_COOKIE[$conf['cookie']]."' LIMIT 1";
$result = mysqli_query($connection, $sql);
$dataUser = mysqli_fetch_assoc( $result );
$content["email"]=$dataUser["Email"];
}
if($go=="save"){
//достаём данные
$sql = "SELECT Email, UniId, Password FROM `Users` ";
$sql .= "WHERE UniId='".$_COOKIE[$conf['cookie']]."'";
$result = mysqli_query($connection, $sql);
$dataUser = mysqli_fetch_assoc($result);
//проверяем, изменился ли Email
$Email=$_POST['email'];
if($dataUser['Email'] != $Email){
// Проверим валидность мыла
if(!preg_match("/^(?:[a-z0-9]+(?:[-_.]?[a-z0-9]+)?@[a-z0-9]+(?:\.?[a-z0-9]+)?\.[a-z]{2,5})$/i",$Email))
{
$err="Не корректный формат почты!";
}
// проверяем, не сущестует ли емайла
$sql = "SELECT COUNT(*) as count FROM `Users` ";
$sql .= "WHERE (Email='".$content["email"]."' AND UniId != '".$_COOKIE[$conf['cookie']]."')";
$result = mysqli_query($connection, $sql);
$row = mysqli_fetch_assoc( $result );
if ($row['count'] > 0) {
$err="Такой емайл уже зарегистрирован ранее!";
}
}
//проверяем пароль
$password=$_POST['password'];
if($password !=""){
if (preg_match("/[^(\w)|(\x7F-\xFF)|(\s)]/",$password)) {
$err="Используйте только буквы и цифры в Пароле!";
}else{
//кодируем новый пароль
$password=md5($password);
}
}else{
$password=$dataUser['Password'];
}
//если нет ошибок - сохраняем изменения.
if($err == ""){
$User = "UPDATE Users SET";
$User .= " Password='".$password."',";
$User .= " Email='".$Email."'";
$User .= " where (UniId='".$_COOKIE[$conf['cookie']]."')";
mysqli_query($connection,$User) or die("MySQL Error: ".mysql_error()."");
header('location: /');
exit();
}else{
$tplForm = new PHPTemplate('./tpl/profile.tpl');
$content["email"]=$Email;
$content["error"]=" <div style='background-color: red;color: #fff;padding: 5px;margin: 15px'>".$err."</div>";
}
}
if($go=="pass"){
$content["title"]="Востановления пароля";
$content["horizontal_menu"]="Востановления пароля";
$tplForm = new PHPTemplate('./tpl/input.tpl');
$content["url"]="login.php?go=retpass";
$content["message"]="Введите зарегистрированную почту";
$content["input"]="Эл.почта";
$content["button"]="Запросить пароль";
}
if($go=="retpass"){
$email=valid($_POST['input']);
// проверяем, не сущестует ли емайла
$sql = "SELECT COUNT(*) as count FROM `Users` ";
$sql .= "WHERE (Email='".$email."')";
$result = mysqli_query($connection, $sql);
$row = mysqli_fetch_assoc( $result );
if ($row['count'] == 0) {
$err="Такой емайл не зарегистрирован!";
}
// Проверим валидность мыла
if (!preg_match("/^(?:[a-z0-9]+(?:[-_.]?[a-z0-9]+)?@[a-z0-9]+(?:\.?[a-z0-9]+)?\.[a-z]{2,5})$/i",$email))
{
$err="Не корректный формат почты!";
}
if($err != ""){
//ошибка регистрации
$tplForm = new PHPTemplate('./tpl/input.tpl');
$content["url"]="login.php?go=retpass";
$content["message"]="Введите зарегистрированную почту";
$content["input"]="Эл.почта";
$content["button"]="Запросить пароль";
$content["result"]=$email;
$content["error"]=" <div style='background-color: red;color: #fff;padding: 5px;margin: 15px'>".$err."</div>";
}else{
//генерируем пароль
$newPass=generateCode(6);
//отправляем письмо
$text='Ваш новый пароль: '.$newPass;
$url=str_replace("https://", "", $conf['url']);
$themes="Востановление пароля на ".$conf['url'];
$email_site='Robot_password@'.$url;
$headers = 'Content-type: text/html; charset=utf-8 ' . "\r\n"; //как раз эти заголовки что то вроде тегов meta на html странице.
$headers .= 'From: '.$email_site.' ' . "\r\n"; // Вот в заголовке From указал (без него иногда не отсылается письмо).
// Вышлем письмо
$ath = mail ($email, $themes, $text, $headers);
// Проверим успешность отправки
if (!$ath)
{
//Ошибка при отправке письма
$passText="Не удалось отправить сообщение на Вашу почту.";
}else{
$passText="Новый пароль выслан на Вашу почту.";
}
//создаём сообщение
$tplForm = new PHPTemplate('./tpl/message.tpl');
$content["url"]="login.php";
$content["message"]="Генерация пароля
".$passText;
$content["button"]="Закрыть";
}
}
$tplForm->set('content', $content);
$content["text"]=$tplForm->fetch();
$tpl->set('content', $content);
//показываем страницу
echo $tpl->fetch();
?>
$go=="ok" получает данные, проверяет существование логина в БД, сравнивает пароль. Если всё в порядке, записывает cookie с именем вашего сайта и содержимым уникального индификатора для определения авторизации пользователя.
Там есть переменная $conf['cookie'] которую пропишем в файле config.php.
<?php
if(!defined($config['unicod'])){ die('attemp hacking');}
$conf = Array(
'url' => '...',
'year' => '...',
'cookie' => '[Ваш сайт(без точки) или другое название]',
'no_user_comment' => 'yes');
?>
Изначально мы не прописали её при настройке базы данных, чтобы текст не переписывать, я добавил вручную.
$go=="exit" обнуляет cookie для отмены аутентификации.
$go=="cabinet" показывает данные профиля.
$go=="save" сохраняет данные профиля.
$go=="pass" показывает форму восстановления пароля.
$go=="retpass" генерирует новый пароль.
Создадим файл tpl/input.tpl - форма восстановления пароля.
<form action="login.php?go=ok" class="form" method="post">
<?=$content["error"] ?>
<?=$content["message"] ?>
<input name="input" placeholder="<?=$content["input"] ?>" value="<?=$content["result"] ?>"><br/>
<input type="submit" value="<?=$content["button"] ?>">
</form>
И файл tpl/profile.tpl - форма профиля.
<form action="login.php?go=ok" class="form" method="post">
<?=$content["error"] ?>
<input name="email" placeholder="Эл. почта" value="<?=$content["email"] ?>"><br/>
<input name="password" placeholder="Пароль"><br/>
<input type="submit" value="Сохранить">
</form>
Осталось добавить форму user.tpl которая будет выводиться после аутентификаци пользователя.
<div class="block" style="text-align: center; width:100%">
<b>Здравствуйте <br/><?=$dataUser['Login'] ?></b><br/>
<a href="login.php?go=cabinet">Профиль</a><br/>
<?=$dataUser['Admin'] ?>
<a href="login.php?go=exit" style="color: red">Выход</a>
</div>
В <?=$dataUser['Admin'] ?> будет выводиться ссылка на админку, если пользователь - администратор.
Осталось переписать файл user.php.
<?php
//проверка cookie
if (isset($_COOKIE[$conf['cookie']]) ){
$sql = "SELECT Login, Rang FROM `Users` ";
$sql .= "WHERE UniId='".$_COOKIE[$conf['cookie']]."' LIMIT 1";
$result = mysqli_query($connection, $sql);
$dataUser = mysqli_fetch_assoc( $result );
}
if($dataUser['Login']!=''){
$tplUser = new PHPTemplate('./tpl/user.tpl');
if($dataUser['Rang']=='Administrator'){
$dataUser['Admin']='<a href="admin.php">АДМИНКА</a><br/>';
}
$tplUser->set('dataUser', $dataUser);
}else{
$tplUser = new PHPTemplate('./tpl/login.tpl');
}
$content["user"]=$tplUser->fetch();
?>
Читаем cookie, если они есть, выводим блок пользователя или блок входа и регистрации .
Получится так.
