Чат PHP-разработчиков
Как сделать авторизацию на сайте на PHP

Система авторизации с помощью cookie на PHP

В прошлом уроке мы изучили механизм взаимодействия с cookie в языке PHP. Теперь давайте попробуем применить эти знания на практике — создадим простейшую систему авторизации.

Техническое задание

Начнём мы это дело с описания будущей системы. Пусть у нас будут следующие компоненты:

  1. Главная страница сайта с каким-либо содержимым. Вверху страницы выводится:
    • если пользователь авторизован: Добро пожаловать, %username%.
    • если пользователь неавторизован: Авторизация — слово является ссылкой, которая ведёт на форму авторизации.
      Авторизован пользователь или нет, определяется с помощью cookie.
  2. Страница с формой авторизации. Два инпута для логина и пароля и кнопкой «Вход». Если введены правильные логин и пароль, устанавливаются cookie со значениями переданных данных, а затем пользователя автоматически редиректит (перенаправляет) на главную страницу.
  3. Страница для разлогинивания — при переходе на неё cookie будут удаляться из браузера пользователя, а затем выполняется редирект на главную страницу.

Решение

Продумываем архитектуру

Первое, о чём нам нужно подумать — это то, как будут храниться элементы этой системы, и сколько их вообще будет.

Начнем с простого — для начала у нас должно получиться 3 странички, которые мы описали в ТЗ.

Ещё нам потребуется функционал, который будет проверять, авторизован ли пользователь. Если мы перечитаем ТЗ, то поймём, что он используется в двух местах — и на главной странице и на странице авторизации. Значит, стоит вынести этот механизм в отдельный файл, и использовать его в двух местах сразу.

Ну и наконец, нам где-то нужно хранить самих пользователей, а именно — их логины и пароли. Создадим для этого простенькую «базу данных» - массив, с набором пар логин-пароль. Это ещё один файл.

Пишем код

Все исходники по данному заданию доступны здесь.

База данных

Ну вот, всё продумали, осталось только написать. Предлагаю начать с нашей базы данных. Создадим файл usersDB.php и запишем в него несколько пользователей.

Код доступен только после покупки курса PHP для начинающих.

Функции проверки авторизации

Давайте теперь напишем функцию, которая будет проверять, являются ли переданные в неё логин и пароль правильными. Для этого создадим ещё один файл auth.php. В нём нам для получения списка пользователей потребуется подключить файл с базой данных.

Код доступен только после покупки курса PHP для начинающих.

В цикле мы пробегаемся по базе данных пользователей и пытаемся найти пользователя с переданными логином и паролем. Если такой пользователь в массиве найден — возвращаем true. Иначе — false.

Давайте теперь ещё напишем функцию, которая будет возвращать логин текущего пользователя. Эта функция будет проверять текущие значения cookie с ключами login и password с помощью уже существующей функции checkAuth. При этом если пользователь найдётся, то она вернёт его login, а иначе — null. Назовём эту нашу новую функцию getUserLogin.

Код доступен только после покупки курса PHP для начинающих.

На этом всю логику проверки логина мы описали. Теперь займёмся непосредственно страничками.

Главная страница

Создадим файл index.php. Для простоты примера мы будем использовать только строку с приветствием авторизованного пользователя, либо ссылкой на авторизацию. В этой странице нам потребуется функция проверки авторизации через cookie, поэтому здесь нужно подключить файл auth.php.

Код доступен только после покупки курса PHP для начинающих.

Наша главная страничка готова. Можно зайти на неё и убедиться, что мы не авторизованы.

Главная страничка с призывом авторизации

Форма авторизации

Давайте теперь сделаем форму авторизации — создаём файл login.php и для начала набрасываем саму HTML-форму. Шаблон получился следующим.

Код доступен только после покупки курса PHP для начинающих.

Давайте теперь добавим логику проверки переданных данных.

Код доступен только после покупки курса PHP для начинающих.

Логика простейшая — если был отправлен POST-запрос, проверяем правильные ли логин и пароль были переданы.

Если нет — то создаём переменную $error, в которой пишем об ошибке авторизации. Позже в шаблоне выводим эту ошибку, если эта переменная объявлена.

Если же авторизация прошла успешно, мы устанавливаем cookie с ключами login и password, в которые помещаем значения из POST-запроса. После этого выполняем редирект на главную страницу.

Редирект делается с помощью заголовка в HTTP-ответе. Этот заголовок называется Location и выглядит следующим образом:

Код доступен только после покупки курса PHP для начинающих.

Для формирования заголовков в PHP используется функция header – ознакомиться с ней более детально вы можете здесь.

Теперь можно попробовать нашу страничку в действии. Давайте для начала введём несуществующую пару логина и пароля. Например, 123:123.

Ошибка при авторизации

Мы увидим соответствующую ошибку.

Теперь давайте зайдем под пользователем user. В нашей БД для него указан пароль 123. Пробуем...

Успешная авторизация

Успех! Нас автоматически перекинуло на главную страницу, где мы видим приветствие для данного пользователя!

Безопасная система авторизации

Однако, данная схема имеет недостаток - пароль используется в открытом виде, а это небезопасно. Всё что идёт дальше - только для ознакомления, пока это слишком сложно реализовать без хорошей архитектуры и полноценной базы данных.

Хеширование паролей

В более совершенных системах авторизации используют хеш от пароля.

Если по-простому, то это такое вычисленное значение, полученное в результате выполнения над паролем определенных манипуляций. В результате этих действий мы получаем строку, из которой нельзя восстановить исходный пароль.

Но мы можем снова повторить над паролем те же действия и сравнить получившиеся значения. То есть сравниваются хеши, а не исходные пароли. И в базе данных тоже хранят хеши, а после того как от клиента пришел пароль в открытом виде, вычисляют его хэш и сравнивают со значением в базе. Если они равны - значит от пользователя пришел верный пароль.

Для чего это делается? Да просто потому, что если сайт будет каким-то образом взломан, то злоумышленник в базе данных не найдёт паролей в открытом виде - только хеши. А так как из хеша получить пароль довольно сложно (при условии, что хеш-функция надежна и используется надёжный пароль), то пароль он не узнает. Следовательно:

  1. злоумышленник не сможет использовать пароль для входа на взломанный сайт;
  2. он также не сможет использовать этот пароль для входа под тем же логином и паролем в другие места (ведь довольно часто люди используют одинаковые пароли для всего).

Вычисляются хеши с помощью хеш-функции. Хеш-функции при этом вычисляют хеши следуя алгоритмам хеширования. Сейчас в PHP для хеширования следует использовать функцию password_hash(), а для проверки хеша - password_verify(). Если вы в каком-то уроке увидите, что для хеширования паролей используется md5 - бегите оттуда, такие хеши вскрываются за несколько минут, она устарела ещё лет 10 назад.

Авторизационные токены

Помимо хеша пароля в базе данных так же принято хранить так называемые авторизационные токены (AuthToken). Это комбинация символов (желательно подлиннее и с кучей кракозябр), которая генерируется при успешной авторизации пользователя и сохраняется в базе данных. А ещё она и пользователю отправляется.

И потом пользователь с помощью cookie передает этот токен на сервер, где он сравнивается со значением в базе данных. Если они равны, то считаем пользователя авторизованным. Для чего? Дело в том, что куки могут быть похищены злоумышленниками (очень многими способами, не будем об этом в этой статье, кому интересно - погуглите). И если злоумышленнику попадет в руки токен - он не сможет получить исходный пароль. О том, почему это так важно, я уже объяснил.

Заключение

Повторюсь, два последних параграфа здесь только для ознакомления. Реализуем мы их в дальнейших уроках, когда будем знать чуть больше вещей. Пока что - вот такая простейшая но небезопасная система авторизации.

Ах да, чуть не забыл, все исходники к каждому уроку я для вашего удобства буду выкладывать на github – вот тут.

Домашнее задание
  • Создайте страницу для разлогинивания - logout.php. При переходе на неё должны удаляться cookie с ключами login и password и выполняться редирект на главную страницу. В качестве ответа предоставьте полный код файла logout.php.
  • Сейчас при переходе авторизованного пользователя на страницу login.php открывается форма авторизации. Сделайте предварительную проверку того, что пользователь уже авторизован. И если он является авторизованным, перенаправляйте его на главную страницу. В качестве ответа на это задание предоставьте только код, который вы добавили в файл login.php.
Онлайн обучение PHP
Путь с полного нуля до джуниора!
Начать бесплатно
Читайте также
Курс программирования на PHP
Подготовка до уровня устройства на работу!
Начать бесплатно
Комментарии (68)


fantasyz

удаление

if (!empty($_COOKIE)) {
    setcookie('login', $login, -10, '/');
    setcookie('password', $password, -10, '/');
    header('Location: /cookie/index.php');
}

проверка

if (!empty($_COOKIE)) {
    header('Location: /cookie/index.php');
}
ivashkevich

Хорошо, всё норм. Только для удаления cookie можно в качестве значения вообще передать пустую строку:

setcookie('login', '', -10, '/');
ivashkevich

А нет, не норм. Проверка проверяет только наличие cookie. При этом не гарантируется, что пользователь авторизован.

fantasyz
if (!empty($_COOKIE['login'] && $_COOKIE['password'])) {
    header('Location: /cookie/index.php');
} 

вот так по идее гарантируется

ivashkevich

Нет, так гарантируется только то, что в cookie есть какие-то данные, но не гарантируется, что эти данные принадлежат какому-то пользователю.

В общем, нужно попытаться их использовать для логина, и если логин успешен, то тогда уже редиректить. Иначе - считать пользователя неавторизованным.

fantasyz
require __DIR__ . '/auth.php';

if (!empty($_COOKIE)) {
    $login = $_COOKIE['login'];
    $password = $_COOKIE['password'];
    if (checkAuth($login, $password)) {
        header('Location: /cookie/index.php');
    }
}
ivashkevich

Вот, теперь логика правильная. Единственное что не учли - в cookie может что-то лежать, но не будет ключей login и password. В таком случае будет warning.

Нужно предусмотреть такой кейс и в переменную login положить пустую строку, если $_COOKIE['login'] не существует:

$login = $_COOKIE['login'] ?? '';

С паролем аналогично.

fantasyz

понял, с горем пополам осилил дз)), точнее с вашей помощью), спасибо большое!

ivashkevich

Не за что. Главное, что вы пробуете. Это 99% успеха :)

1nSide

logout.php

<?php

setcookie('login', '$login', -10, '/');
setcookie('password' , '$password', -10, '/');
header('location: indexCookie.php' );
1nSide

Во втором задании уже была проверка

ivashkevich

При простом переходе (без отправки POST-запроса) не будет у вас никакой проверки. Задание требует выполнения проверки при любом запросе.

1nSide

а где пароли хешировать? это если пользователь вошел то сделать чтобы они хешировались?

ivashkevich

Знаете, я переборщил с этим заданием. С последними двумя параграфами пока только ознакомьтесь (я их только что подправил). Усовершенствуем систему чуть позже.

arminbuuren86@gmail.com
function getUserLogin(): ?string
{
    $loginFromCookie = $_COOKIE['login'] ?? '';
    $passwordFromCookie = $_COOKIE['password'] ?? '';

    if (checkAuth($loginFromCookie, $passwordFromCookie)) {
        return $loginFromCookie;
    }

    return null;
}

Пишет, что ошибка в ?string на знак ? указывает, почему?

ivashkevich

Версия PHP 7.1? Если ниже - то не заработает.

arminbuuren86@gmail.com

CTRL + ALT + S -> Languages & Frameworks -> PHP. Там выбрана 7.1, еще есть ниже версии и выше 7.2. Может 7.2 выбрать?

ivashkevich

PhpStorm - это только редактор. Ошибка возникает во время выполнения скрипта, значит менять нужно версию интерпретатора. Если Вы всё делаете по урокам, то версию нужно менять в настройках OpenServer. Повторите уроки как работает PHP и установка и настройка OpenServer.

arminbuuren86@gmail.com

Спасибо за ответ. Буду разбираться. И спасибо вам за ваши уроки! Отличные и реально быстро понимаешь, что да как)

ivashkevich

Спасибо за отзыв) Удачи в прохождении)

arminbuuren86@gmail.com
Parse error: syntax error, unexpected '?' in C:\OpenServer\OSPanel\domains\autorizacion.loc\www\auth.php on line 15

вот что пишет

Fox-24

Спасибо за еще один урок!)

<?php

// Создайте страницу для разлогинивания - logout.php.
// При переходе на неё должны удаляться cookie с ключами login и password и выполняться редирект на главную страницу.
// В качестве ответа предоставьте полный код файла logout.php.

if (!empty($_COOKIE['login'])) {
    // Удаляем Cookie
    setcookie('login', $login, -10, '/');
    setcookie('password', $login, -10, '/');
    header('Location: /autorization/index.php');
}

У меня php 5.4, так что..)

//Сейчас при переходе авторизованного пользователя на страницу login.php открывается форма авторизации.
//Сделайте предварительную проверку того, что пользователь уже авторизован. И если он является авторизованным, перенаправляйте его на главную страницу.
// В качестве ответа на это задание предоставьте только код, который вы добавили в файл login.php.

if (!empty($_COOKIE)) {
    require __DIR__ . '/auth.php';
    if (isset($_COOKIE['login'])) {
        $login = $_COOKIE['login'];
    } else {
        // присваиваем $login значение '' если $_COOKIE['login'] равен NULL
        $login = '';
    }
    if (isset($_COOKIE['password'])) {
        $password = $_COOKIE['password'];
    } else {
        // присваиваем $password значение '' если $_COOKIE['password'] равен NULL
        $password = '';
    }

    $password = $_COOKIE['password'];
    if (checkAuth($login, $password)) {
        header('Location: /autorization/index.php');
    }
}
ivashkevich
  1. Можно не проверять перед удалением кукисов:
    if (!empty($_COOKIE['login'])) {
  2. Вот эта строка может накидать warning-ов (которая вне условия):
    $password = $_COOKIE['password'];
Fox-24
  1. Да, спасибо:)
  2. Забыл почистить код..

    require __DIR__ . '/auth.php';
    if (isset($_COOKIE['login'])) {
        $login = $_COOKIE['login'];
    } else {
        // присваиваем $login значение '' если $_COOKIE['login'] равен NULL
        $login = '';
    }
    if (isset($_COOKIE['password'])) {
        $password = $_COOKIE['password'];
    } else {
        // присваиваем $password значение '' если $_COOKIE['password'] равен NULL
        $password = '';
    }

    if (checkAuth($login, $password)) {
        header('Location: /autorization/index.php');
    }
dom1r

В комментариях уже прочитал, что проверку куки можно опустить и в принципе unset тоже, но:

<?php
//logout.php
if (isset($_COOKIE['login'])) {
    unset($_COOKIE['login']);
    unset($_COOKIE['password']);
    setcookie('login', null, -1, '/');
    setcookie('password', null, -1, '/');
    header('Location: /index.php');
} else {
    return false;
}

Сначала просто проверял isset-ом далее редиректил, в комментариях вышел прочел, подправил:

//login.php
if (isset($_COOKIE['login']) && isset($_COOKIE['password'])) {
    require __DIR__ . '/auth.php';
    $login = $_COOKIE['login'];
    $password = $_COOKIE['password'];

    if (checkAuth($login, $password)) {
        header('Location: /index.php');
    }

}

Также не понятные языковые конструкции вроде этих:

function getUserLogin(): ?string

Понятно что возвращаемое значение должно быть строкой, но не понятен вопросительный знак.

Также и здесь:

$loginFromCookie = $_COOKIE['login'] ?? '';
ivashkevich

Вот это бессмысленно:

    unset($_COOKIE['login']);
    unset($_COOKIE['password']);

Вопросительный знак означает, что помимо строки может вернуться null.

function getUserLogin(): ?string

?? - null coalescing operator. Если перед ним null - то вернет значение из правой части, иначе - значение слева.

$loginFromCookie = $_COOKIE['login'] ?? '';
RusTaylor
if (!empty($_COOKIE['login'] && !empty($_COOKIE['password']))){
        $login = $_COOKIE['login'];
        $password = $_COOKIE['password'];
        if (checkAuth($login,$password)){
            header('Location:/index.php');
        }
    }

У меня вот такая проверка куки получилась,только при переходе в login.php всё равно требует вводить пароль, хотя куки есть

ivashkevich

Проверьте дебаггером, где ошибка.

RusTaylor

В панели разработчика пишет что не даёт куки файлам вставить пароль и логин

ivashkevich

Напиши в личку в ВК или Телеге.

ivashkevich

Ниже Вам подсказали)

Bogdan
if (!empty($_COOKIE['login'] && !empty($_COOKIE['password']))){

а здесь все ок? скобки правильно расставлены?

ivashkevich

Именно здесь ошибка)

ArtemijeKA
  1. logout.php

    setcookie('login', '', -1, '/');
    setcookie('password', '', -1, '/');
    /**
    * У меня папка этого задания называется 23 в локальном сервере webshake, то есть webshake/23
    * по этому я сначала ставлю / после logout.php а потом поднимаюсь до дирректории повыше ../ и перехожу в index.php
    */
    header("Location: " . $_SERVER['REQUEST_URI'] . "/../index.php");
  2. В начале login.php добавил:

    require __DIR__ . '/auth.php';
    if (isset($_COOKIE['login']) && isset($_COOKIE['password'])) {
        if (checkAuth($_COOKIE['login'], $_COOKIE['password'])) {
            header('Location: ' . $_SERVER['REQUEST_URI'] . '/../index.php');
        }
    }

Сначала переписал на require_once потом понял, что там еще подключается usersDB и если там данные изменятся то не получится авторизоваться и исправил этот косяк за собой.

ivashkevich

Можно просто Location: /index.php
И для первого и для второго случаев. А так - норм.

ArtemijeKA

Я забыл написать у меня локальный сервер webshake а папка с заданием 23 и того webshake/23/ по этому если я напишу "Location: /index.php" то перекинет на webshake.

Benya
<?php
setcookie('login', $login, time()-3600, '/');
setcookie('password', $password, time()-3600, '/');
header('Location: /index.php');
Benya
<?php
require __DIR__ . '/auth.php';
$login = getUserLogin();

if  ($login === null) {
    if (!empty($_POST)) {

        $login = $_POST['login'] ?? '';
        $password = $_POST['password'] ?? '';

        if (checkAuth($login, $password)) {
            setcookie('login', $login, 0, '/');
            setcookie('password', $password, 0, '/');
            header('Location: /index.php');
        } else {
            $error = 'Ошибка авторизации';
        }

    }
}else {
    header('Location: /index.php');
}
?>
SBTesla
<?php
//проверяем переданны ли данные и подключаем файл авторизации
if (!empty($_POST)) {
     require __DIR__ . '/auth.php';

     //заносим переданые данные в переменные
     $login = $_COOKIE['login'] ?? '';
     $password = $_COOKIE['password'] ?? '';

     /*проверяем попали ли данные в куки и какие, устанавливаем
     время жизни и директорию*/
     if (checkAUth($login, $password)) {
          setcookie('login', $login, 0, '/');
          setcookie('password', $password, 0, '/');
          header('location: index.php');
     } else {
          $error = 'Ошибка Авторизации';
     }

}

?>

2

<?php
/* удаление cookie , устанавливаем время 
и направляем пользователя на главную страницу
*/
setcookie('login', $login, time() -3600, '/');
setcookie('password', $password, time()-3600, '/');
header('location: /index.php');
ivashkevich
  1. нужно проверять не $_POST а $_COOKIE
  2. 100 секунд может не хватить, лучше сразу на час назад отбрасывать, если у пользователя косяки со временем
SBTesla

Ага сори поправил,а 100 секунд посоветовали на стаке поставить сказали что ставить на час это костыли, вобще в идеале говорили про -1, но я не совсем понял про -1

ivashkevich

Перечитайте домашку и посмотрите что вы делаете - проверяете наличие куки, а потом данные POST-запроса - это не имеет смысла.

antoxa

Добрый день! Спасибо за урок, возник вопрос, ответь пожалуйста с точки зрения максимальной безопасности.
Сгенерировали auth_token, записали его в базу при входе на сайт и в куки к пользователю.
Дальше при повторном посещении сайта пользователем, сравниваем этот токен и если он совпадает с тем что в базе, логинем пользователя.
Допустим этот токен крадут, вставляют себе в куки и посещают сайт. Происходит логин уже поддельного пользователя.
Как должен выглядеть алгоритм правильно и безопасно чтоб даже если украдут куки не смогли войти?

ivashkevich

Самый простой вариант - сохранять в базу еще и IP, для которого этот токен создавался. Но есть и более изощренные способы защиты. Стоит устанавливать на сайте SSL-сертификат и cookie передавать только по зашифрованному каналу. Еще стоит запретить куки для JS - всё это можно сделать с помощью setcookie - почитайте документацию по этой функции.

antoxa

Спасибо за ответ.
Проверять IP будет плохо для пользователя, он может меняться.
Целый день гуглил сегодня)
В итоге вот к чему пришел: При логине через логин пароль, генерируем токен и пишем в куки и в базу, так же пишем user agent в базу.
При повторном заходе смотрим есть ли токен в куках, если есть, ищем такой в базе, если находим, то сравниваем user agent если все совпадает, то логинем пользователя, ставим переменную в сессию и обновляем токен.
++ как Вы сказали SSL и httponly в true.

Поправьте пожалуйста если что не так)

ivashkevich

В целом - лучше. Но вообще - если будут красть куки, то подделать UserAgent - вообще не проблема. Потому что куки всегда крадутся через какой-нибудь сторонний ресурс, получить на этом ресурсе юзерагент - вообще не проблема. Продвинутые защищенные системы могут строиться на совокупности сразу нескольких характеристик - UserAgent, расширение экрана, язык и версия системы, IP, и еще куча всего.

antoxa

Тут смысл в том что при логине пользователя токен поменяется.
И куками можно воспользоваться пока токен не поменялся.
Плюс на сколько я понял при использовании SSL куки можно украсть только в зашифрованном виде, верно?

ivashkevich

Нет. Украсть куки можно не только перехватом трафика между пользователем и сайтом. Есть XSS атаки. Если интересуетесь темой безопасности, можете прочитать вот эту вводную статью =)

lordbear53@gmail.com

1)

if(!empty($_COOKIE)) {
    setcookie('login', $login, 1, '/');
    setcookie('password', $password, 1, '/');
    header('Location: login.php');
}

2)

if(!empty($_COOKIE)){
    header('Location: index.php');
}
ivashkevich
  1. Что будет, если я зайду на страничку логаута, не будучи залогиненным?
  2. Наличие куки еще не значит, что пользователь авторизован! Нужна нормальная проверка того, что в куки пришло.
demyanovpaul@yandex.ru

Создайте страницу для разлогинивания - logout.php. При переходе на неё должны удаляться cookie с ключами login и password и выполняться редирект на главную страницу. В качестве ответа предоставьте полный код файла logout.php.

<?php
setcookie('login','0',time() - 3600);
setcookie('password','0',time() - 3600);
header('Location: index.php');

Сейчас при переходе авторизованного пользователя на страницу login.php открывается форма авторизации. Сделайте предварительную проверку того, что пользователь уже авторизован. И если он является авторизованным, перенаправляйте его на главную страницу. В качестве ответа на это задание предоставьте только код, который вы добавили в файл login.php.

<?php
//Задание 2
if(!empty($_COOKIE['login']) && !empty($_COOKIE['password'])){
    header('Location: index.php');
}

if (!empty($_POST)) {
    require __DIR__ . '/auth.php';

    $login = $_POST['login'] ?? '';
    $password = $_POST['password'] ?? '';

    if (checkAuth($login, $password)) {
        setcookie('login', $login, 0, '/');
        setcookie('password', $password, 0, '/');
        header('Location: /index.php');
    } else {
        $error = 'Ошибка авторизации';
    }
}
?>
<html>
<head>
    <title>Форма авторизации</title>
</head>
<body>
<?php if (isset($error)): ?>
    <span style="color: red;">
    <?= $error ?>
</span>
<?php endif; ?>
<form action="/login.php" method="post">
    <label for="login">Имя пользователя: </label><input type="text" name="login" id="login">
    <br>
    <label for="password">Пароль: </label><input type="password" name="password" id="password">
    <br>
    <input type="submit" value="Войти">
</form>
</body>
</html>
ivashkevich

Для заголовка Location лучше указывать абсолютный путь:

Location: /index.php

Так точно перенесет на index.php в корне сайта.

if(!empty($_COOKIE['login']) && !empty($_COOKIE['password'])){
    header('Location: index.php');
}

Наличие Cookie в браузере ещё не означает, что пользователь авторизован. Если они есть, нужно их еще проверить.

demyanovpaul@yandex.ru
if(!empty($_COOKIE['login']) && !empty($_COOKIE['password'])){
    if(checkAuth($_COOKIE['login'], $_COOKIE['password'])){
        header('Location: /index.php');
    }
}

Спасибо, поправил.

ivashkevich

Хорошо. После отправки header-а location можно сразу завершить работу скрипта с помощью die().

virtual2018

Неплохое задание, единственная претензия, что используются конструкции, которые хоть и имеют общую тему с уже пройденным материалом, но я думаю требуют некоторого акцента на них:
1) такая строка кода: function checkAuth(string $login, string $password): bool
начиная с версии PHP7 позволяет указать нам тип возвращаемого значения функции (аналогичны мы использовали типизацию входных данных при изучении функций). И по аналогии при использовании _declare(stricttypes=1) мы сможем включить строгую типизацию.
2) строка: function getUserLogin(): ?string как уже отвечал автор курса, указывает что возвращаемое значение может быть или строкой или NULL.
текст ссылки
3) строка: $loginFromCookie = $_COOKIE['login'] ?? '', это еще одно нововведение 7 версии,
можно назвать другой записью тернарного оператора, но более правильно Оператор объединения с null (null coalescing), логика простая - "Выражение (expr1) ?? (expr2) вычисляется так: expr2, если expr1 равен NULL и expr1 в противном случае"
текст ссылки
1 задание

<?php
setcookie('login', '', 0, '/');
setcookie('password', '', 0, '/');
header('Location: /index.php');

2 задание

if (!empty($_COOKIE)) {
    require __DIR__ . '/auth.php'; 
    if (isset($_COOKIE['login']) && isset($_COOKIE['password'])) {
        if (checkAuth($_COOKIE['login'], $_COOKIE['password'])) {
            header('Location: /index.php');
        }
    }
}
ivashkevich

Отличное дополнение!

avansis1

Ввожу верные логин/пароль - выдается следующая ошибка:
Parse error: syntax error, unexpected '?' in C:\OSPanel\domains\myproject.loc\www\auth.php on line 14

Памагите(

ivashkevich

Переводить ошибку пробовали?

avansis1

Да, уже решил, где то выше описание было)

7vs13@inbox.ru
require __DIR__.'/authorization.php';
if (!empty($_COOKIE['login']) && !empty($_COOKIE['password']) &&
    checkInvUser($_COOKIE['login'], $_COOKIE['password']))
   {
    header('Location: /index.php');
   }
ivashkevich

Правильно.

Bogdan

Создайте страницу для разлогинивания - logout.php. При переходе на неё должны удаляться cookie с ключами login и password и выполняться редирект на главную страницу. В качестве ответа предоставьте полный код файла logout.php

setcookie('login', '', 1, '/');
setcookie('password', '', 1, '/');
header('Location: /index.php');

Сейчас при переходе авторизованного пользователя на страницу login.php открывается форма авторизации. Сделайте предварительную проверку того, что пользователь уже авторизован. И если он является авторизованным, перенаправляйте его на главную страницу. В качестве ответа на это задание предоставьте только код, который вы добавили в файл login.php.

if (isset($_COOKIE['login'])
        && isset($_COOKIE['password'])) {
        header('Location: /index.php');
    }
ivashkevich
  1. ОК
  2. Наличие cookie в браузере еще не означает, что пользователь авторизован.
Bogdan

на счет второго задания, где я мыслю не правильно. Как я видел задание. У нас есть страница авторизации, человек вводит свои данные, проходит авторизацию, куки с паролем и логином сохранились. Дальше он закрывает браузер заходит снова на нужный сайт, и я просто поднимаю его куки с паролем и логином, хотя вот тут коненчо можно повторную проверку запилить на совпадение пароля и логина с куки с теми что в базе... наверное вот эту проверку мне и стоило сделать)) Сам ответил на свой вопрос

ivashkevich

Всё именно так)

Самый понятный курс PHP
Онлайн-уроки в удобное время!
Начать бесплатно
Популярное за сутки
Онлайн-курсы PHP и MySQL
Обучение с полного нуля до уровня джуниора!
Начать бесплатно
Сейчас читают
Логические задачи с собеседований