Статьи

Как создать собственную охрану аутентификации в Laravel

В этой статье мы рассмотрим систему аутентификации в рамках Laravel. Основная цель этой статьи — создать пользовательскую защиту аутентификации путем расширения базовой системы аутентификации.

Laravel обеспечивает очень надежную систему аутентификации в ядре, которая делает реализацию базовой аутентификации быстрым. На самом деле, вам просто нужно выполнить несколько кустарных команд, чтобы настроить каркас системы аутентификации.

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

Система аутентификации Laravel состоит из двух основных элементов — охранников и провайдеров.

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

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

Далее в этой статье мы реализуем средство защиты, которое проверяет определенные параметры JSON в заголовках запросов и извлекает действительного пользователя из серверной части MongoDB.

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

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

В нашем примере мы реализуем поставщик аутентификации MongoDB, который выбирает учетные данные пользователя из серверной части MongoDB.

Так что это было базовое введение в охранников и провайдеров в системе аутентификации Laravel. Начиная со следующего раздела, мы сосредоточимся на разработке индивидуальной защиты аутентификации и провайдера!

Давайте кратко рассмотрим список файлов, которые мы реализуем на протяжении всей этой статьи.

  • config/auth.php : это файл конфигурации аутентификации, в который мы добавим запись нашего пользовательского сторожа.
  • config/mongo.php : это файл, который содержит конфигурацию MongoDB.
  • app/Services/Contracts/NosqlServiceInterface.php : это интерфейс, который реализует наш пользовательский класс базы данных Mongo.
  • app/Database/MongoDatabase.php : это основной класс базы данных, который взаимодействует с MongoDB.
  • app/Models/Auth/User.php : это класс модели User, который реализует Authenticable контракт.
  • app/Extensions/MongoUserProvider.php : Это реализация поставщика аутентификации.
  • app/Services/Auth/JsonGuard.php : Это реализация драйвера защиты аутентификации.
  • app/Providers/AuthServiceProvider.php : это существующий файл, который мы будем использовать для добавления привязок нашего контейнера служб.
  • app/Http/Controllers/MongoController.php : это демонстрационный файл контроллера, который мы реализуем для проверки нашей специальной защиты.

Не беспокойтесь, если список файлов пока не имеет особого смысла, так как мы обсудим все подробно, когда будем его изучать.

В этом разделе мы рассмотрим реализацию необходимых файлов.

Первое, что нам нужно сделать, это сообщить Laravel о нашей таможенной охране. Идите вперед и введите подробные данные о config/auth.php файле config/auth.php как показано.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
‘guards’ => [
    ‘web’ => [
        ‘driver’ => ‘session’,
        ‘provider’ => ‘users’,
    ],
 
    ‘api’ => [
        ‘driver’ => ‘token’,
        ‘provider’ => ‘users’,
    ],
     
    ‘custom’ => [
      ‘driver’ => ‘json’,
      ‘provider’ => ‘mongo’,
    ],
],

Как вы можете видеть, мы добавили нашу собственную охрану под пользовательским ключом.

Далее нам нужно добавить соответствующую запись провайдера в разделе провайдеров .

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
‘providers’ => [
    ‘users’ => [
        ‘driver’ => ‘eloquent’,
        ‘model’ => App\User::class,
    ],
    ‘mongo’ => [
        ‘driver’ => ‘mongo’
    ],
 
    // ‘users’ => [
    // ‘driver’ => ‘database’,
    // ‘table’ => ‘users’,
    // ],
],

Мы добавили запись нашего провайдера под ключом Монго .

Наконец, давайте изменим защиту аутентификации по умолчанию с веб на кастом.

1
2
3
4
5
6
7
8
‘defaults’ => [
    ‘guard’ => ‘custom’,
    ‘passwords’ => ‘users’,
],

Конечно, это пока не сработает, так как мы еще не реализовали необходимые файлы. И это то, что мы обсудим в следующих нескольких разделах.

В этом разделе мы реализуем необходимые файлы, которые взаимодействуют с базовым экземпляром MongoDB.

Давайте сначала создадим файл config/mongo.php который содержит настройки соединения по умолчанию с MongoDB.

1
2
3
4
5
6
7
8
<?php
return [
  ‘defaults’ => [
    ‘host’ => ‘{HOST_IP}’,
    ‘port’ => ‘{HOST_PORT}’,
    ‘database’ => ‘{DB_NAME}’
  ]
];

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

Вместо непосредственного создания класса, который взаимодействует с MongoDB, мы в первую очередь создадим интерфейс.

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

Создайте файл интерфейса app/Services/Contracts/NosqlServiceInterface.php со следующим содержимым.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
<?php
// app/Services/Contracts/NosqlServiceInterface.php
namespace App\Services\Contracts;
 
Interface NosqlServiceInterface
{
  /**
   * Create a Document
   *
   * @param string $collection Collection/Table Name
   * @param array $document Document
   * @return boolean
   */
  public function create($collection, Array $document);
  
  /**
   * Update a Document
   *
   * @param string $collection Collection/Table Name
   * @param mix $id Primary Id
   * @param array $document Document
   * @return boolean
   */
  public function update($collection, $id, Array $document);
 
  /**
   * Delete a Document
   *
   * @param string $collection Collection/Table Name
   * @param mix $id Primary Id
   * @return boolean
   */
  public function delete($collection, $id);
  
  /**
   * Search Document(s)
   *
   * @param string $collection Collection/Table Name
   * @param array $criteria Key-value criteria
   * @return array
   */
  public function find($collection, Array $criteria);
}

Это довольно простой интерфейс, который объявляет основные методы CRUD, которые должен определить класс, который реализует этот интерфейс.

Теперь давайте определим реальный класс в app/Database/MongoDatabase.php .

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
<?php
// app/Database/MongoDatabase.php
namespace App\Database;
 
use App\Services\Contracts\NosqlServiceInterface;
 
class MongoDatabase implements NosqlServiceInterface
{
  private $connection;
  private $database;
     
  public function __construct($host, $port, $database)
  {
    $this->connection = new MongoClient( «mongodb://{$host}:{$port}» );
    $this->database = $this->connection->{$database};
  }
  
  /**
   * @see \App\Services\Contracts\NosqlServiceInterface::find()
   */
  public function find($collection, Array $criteria)
  {
    return $this->database->{$collection}->findOne($criteria);
  }
 
  public function create($collection, Array $document) {}
  public function update($collection, $id, Array $document) {}
  public function delete($collection, $id) {}
}

Конечно, я предполагаю, что вы установили MongoDB и соответствующее расширение MongoDB PHP.

Метод __construct создает экземпляр класса MongoClient с необходимыми параметрами. Другой важный метод, который нас интересует, — это метод find , который извлекает запись на основе критериев, представленных в качестве аргументов метода.

Это была реализация драйвера MongoDB, и я старался сделать его как можно более простым.

Придерживаясь стандартов системы аутентификации, нам необходимо реализовать модель User, которая должна реализовывать Illuminate\Contracts\Auth\Authenticatable .

app/Models/Auth/User.php создайте файл app/Models/Auth/User.php со следующим содержимым.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
<?php
// app/Models/Auth/User.php
namespace App\Models\Auth;
 
use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
use App\Services\Contracts\NosqlServiceInterface;
 
class User implements AuthenticatableContract
{
  private $conn;
  
  private $username;
  private $password;
  protected $rememberTokenName = ‘remember_token’;
 
  public function __construct(NosqlServiceInterface $conn)
  {
    $this->conn = $conn;
  }
 
  /**
   * Fetch user by Credentials
   *
   * @param array $credentials
   * @return Illuminate\Contracts\Auth\Authenticatable
   */
  public function fetchUserByCredentials(Array $credentials)
  {
    $arr_user = $this->conn->find(‘users’, [‘username’ => $credentials[‘username’]]);
     
    if (! is_null($arr_user)) {
      $this->username = $arr_user[‘username’];
      $this->password = $arr_user[‘password’];
    }
 
    return $this;
  }
 
  /**
   * {@inheritDoc}
   * @see \Illuminate\Contracts\Auth\Authenticatable::getAuthIdentifierName()
   */
  public function getAuthIdentifierName()
  {
    return «username»;
  }
  
  /**
   * {@inheritDoc}
   * @see \Illuminate\Contracts\Auth\Authenticatable::getAuthIdentifier()
   */
  public function getAuthIdentifier()
  {
    return $this->{$this->getAuthIdentifierName()};
  }
 
  /**
   * {@inheritDoc}
   * @see \Illuminate\Contracts\Auth\Authenticatable::getAuthPassword()
   */
  public function getAuthPassword()
  {
    return $this->password;
  }
 
  /**
   * {@inheritDoc}
   * @see \Illuminate\Contracts\Auth\Authenticatable::getRememberToken()
   */
  public function getRememberToken()
  {
    if (! empty($this->getRememberTokenName())) {
      return $this->{$this->getRememberTokenName()};
    }
  }
 
  /**
   * {@inheritDoc}
   * @see \Illuminate\Contracts\Auth\Authenticatable::setRememberToken()
   */
  public function setRememberToken($value)
  {
    if (! empty($this->getRememberTokenName())) {
      $this->{$this->getRememberTokenName()} = $value;
    }
  }
 
  /**
   * {@inheritDoc}
   * @see \Illuminate\Contracts\Auth\Authenticatable::getRememberTokenName()
   */
  public function getRememberTokenName()
  {
    return $this->rememberTokenName;
  }
}

Вы должны были уже заметить, что App\Models\Auth\User реализует Illuminate\Contracts\Auth\Authenticatable .

Большинство методов, реализованных в нашем классе, говорят сами за себя. Сказав это, мы определили метод fetchUserByCredentials , который извлекает пользователя из доступной серверной части. В нашем случае это будет класс MongoDatabase который будет вызываться для получения необходимой информации.

Так что это реализация модели User.

Как мы обсуждали ранее, система аутентификации Laravel состоит из двух элементов — охранников и провайдеров.

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

Создайте файл app/Extensions/MongoUserProvider.php как показано ниже.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
<?php
// app/Extensions/MongoUserProvider.php
namespace App\Extensions;
 
use Illuminate\Support\Str;
use Illuminate\Contracts\Auth\UserProvider;
use Illuminate\Contracts\Auth\Authenticatable;
 
class MongoUserProvider implements UserProvider
{
  /**
   * The Mongo User Model
   */
  private $model;
 
  /**
   * Create a new mongo user provider.
   *
   * @return \Illuminate\Contracts\Auth\Authenticatable|null
   * @return void
   */
  public function __construct(\App\Models\Auth\User $userModel)
  {
    $this->model = $userModel;
  }
 
  /**
   * Retrieve a user by the given credentials.
   *
   * @param array $credentials
   * @return \Illuminate\Contracts\Auth\Authenticatable|null
   */
  public function retrieveByCredentials(array $credentials)
  {
      if (empty($credentials)) {
          return;
      }
 
    $user = $this->model->fetchUserByCredentials([‘username’ => $credentials[‘username’]]);
 
      return $user;
  }
  
  /**
   * Validate a user against the given credentials.
   *
   * @param \Illuminate\Contracts\Auth\Authenticatable $user
   * @param array $credentials Request credentials
   * @return bool
   */
  public function validateCredentials(Authenticatable $user, Array $credentials)
  {
      return ($credentials[‘username’] == $user->getAuthIdentifier() &&
    md5($credentials[‘password’]) == $user->getAuthPassword());
  }
 
  public function retrieveById($identifier) {}
 
  public function retrieveByToken($identifier, $token) {}
 
  public function updateRememberToken(Authenticatable $user, $token) {}
}

Опять же, вам нужно убедиться, что пользовательский поставщик должен реализовать Illuminate\Contracts\Auth\UserProvider .

В дальнейшем он определяет два важных метода — retrieveByCredentials и validateCredentials.

Метод retrieveByCredentials используется для получения учетных данных пользователя с использованием класса модели User, который обсуждался в предыдущем разделе. С другой стороны, метод validateCredentials используется для проверки пользователя по заданному набору учетных данных.

И это была реализация нашего пользовательского поставщика аутентификации. В следующем разделе мы продолжим создание защиты, взаимодействующей с MongoUserProvider аутентификации MongoUserProvider .

Как мы уже говорили ранее, защита в системе аутентификации Laravel обеспечивает аутентификацию пользователя. В нашем случае мы проверим наличие параметра запроса jsondata, который должен содержать строку учетных данных в кодировке JSON.

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

Создайте файл app/Services/Auth/JsonGuard.php со следующим содержимым.

001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
027
028
029
030
031
032
033
034
035
036
037
038
039
040
041
042
043
044
045
046
047
048
049
050
051
052
053
054
055
056
057
058
059
060
061
062
063
064
065
066
067
068
069
070
071
072
073
074
075
076
077
078
079
080
081
082
083
084
085
086
087
088
089
090
091
092
093
094
095
096
097
098
099
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
<?php
// app/Services/Auth/JsonGuard.php
namespace App\Services\Auth;
 
use Illuminate\Http\Request;
use Illuminate\Contracts\Auth\Guard;
use Illuminate\Contracts\Auth\UserProvider;
use GuzzleHttp\json_decode;
use phpDocumentor\Reflection\Types\Array_;
use Illuminate\Contracts\Auth\Authenticatable;
 
class JsonGuard implements Guard
{
  protected $request;
  protected $provider;
  protected $user;
 
  /**
   * Create a new authentication guard.
   *
   * @param \Illuminate\Contracts\Auth\UserProvider $provider
   * @param \Illuminate\Http\Request $request
   * @return void
   */
  public function __construct(UserProvider $provider, Request $request)
  {
    $this->request = $request;
    $this->provider = $provider;
    $this->user = NULL;
  }
 
  /**
   * Determine if the current user is authenticated.
   *
   * @return bool
   */
  public function check()
  {
    return !
  }
 
  /**
   * Determine if the current user is a guest.
   *
   * @return bool
   */
  public function guest()
  {
    return !
  }
 
  /**
   * Get the currently authenticated user.
   *
   * @return \Illuminate\Contracts\Auth\Authenticatable|null
   */
  public function user()
  {
    if (! is_null($this->user)) {
      return $this->user;
    }
  }
     
  /**
   * Get the JSON params from the current request
   *
   * @return string
   */
  public function getJsonParams()
  {
    $jsondata = $this->request->query(‘jsondata’);
 
    return (!empty($jsondata) ? json_decode($jsondata, TRUE) : NULL);
  }
 
  /**
   * Get the ID for the currently authenticated user.
   *
   * @return string|null
  */
  public function id()
  {
    if ($user = $this->user()) {
      return $this->user()->getAuthIdentifier();
    }
  }
 
  /**
   * Validate a user’s credentials.
   *
   * @return bool
   */
  public function validate(Array $credentials=[])
  {
    if (empty($credentials[‘username’]) || empty($credentials[‘password’])) {
      if (!$credentials=$this->getJsonParams()) {
        return false;
      }
    }
 
    $user = $this->provider->retrieveByCredentials($credentials);
       
    if (! is_null($user) && $this->provider->validateCredentials($user, $credentials)) {
      $this->setUser($user);
 
      return true;
    } else {
      return false;
    }
  }
 
  /**
   * Set the current user.
   *
   * @param Array $user User info
   * @return void
   */
  public function setUser(Authenticatable $user)
  {
    $this->user = $user;
    return $this;
  }
}

Прежде всего, наш класс должен реализовать интерфейс Illuminate\Contracts\Auth\Guard . Таким образом, нам нужно определить все методы, объявленные в этом интерфейсе.

Здесь важно отметить, что функция __construct требует реализации Illuminate\Contracts\Auth\UserProvider . В нашем случае мы передадим экземпляр App\Extensions\MongoUserProvider , как мы увидим в следующем разделе.

Далее есть функция getJsonParams которая получает учетные данные пользователя из параметра запроса с именем jsondata . Ожидается, что мы получим строку с учетными данными пользователя в кодировке JSON, мы использовали функцию json_decode для декодирования данных JSON.

В функции validate первое, что мы проверяем, — это наличие аргумента $credentials . Если его нет, мы getJsonParams метод getJsonParams для получения учетных данных пользователя из параметров запроса.

Затем мы вызываем метод MongoUserProvider поставщика MongoUserProvider , который извлекает пользователя из серверной части базы данных MongoDB. Наконец, это метод MongoUserProvider поставщика MongoUserProvider , который проверяет действительность пользователя.

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

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

Как вы уже знаете, поставщик услуг Laravel — это правильное место для реализации необходимых привязок.

Откройте файл app/Providers/AuthServiceProvider.php который позволяет нам добавлять привязки контейнера службы аутентификации. Если он не содержит никаких пользовательских изменений, вы можете просто заменить его следующим содержимым.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
<?php
// app/Providers/AuthServiceProvider.php
namespace App\Providers;
 
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Gate;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
use App\Services\Auth\JsonGuard;
use App\Extensions\MongoUserProvider;
use App\Database\MongoDatabase;
use App\Models\Auth\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Config;
 
class AuthServiceProvider extends ServiceProvider
{
  /**
   * The policy mappings for the application.
   *
   * @var array
   */
  protected $policies = [
    ‘App\Model’ => ‘App\Policies\ModelPolicy’,
  ];
 
  /**
   * Register any authentication / authorization services.
   *
   * @return void
   */
  public function boot()
  {
    $this->registerPolicies();
     
    $this->app->bind(‘App\Database\MongoDatabase’, function ($app) {
      return new MongoDatabase(config(‘mongo.defaults.host’), config(‘mongo.defaults.port’), config(‘mongo.defaults.database’));
    });
     
    $this->app->bind(‘App\Models\Auth\User’, function ($app) {
      return new User($app->make(‘App\Database\MongoDatabase’));
    });
 
    // add custom guard provider
    Auth::provider(‘mongo’, function ($app, array $config) {
      return new MongoUserProvider($app->make(‘App\Models\Auth\User’));
    });
 
    // add custom guard
    Auth::extend(‘json’, function ($app, $name, array $config) {
      return new JsonGuard(Auth::createUserProvider($config[‘provider’]), $app->make(‘request’));
    });
  }
 
  public function register()
  {
    $this->app->bind(
      ‘App\Services\Contracts\NosqlServiceInterface’,
      ‘App\Database\MongoDatabase’
    );
  }
}

Давайте рассмотрим метод boot который содержит большинство привязок провайдера.

Для начала создадим привязки для элементов App\Database\MongoDatabase и App\Models\Auth\User .

1
2
3
4
5
6
7
$this->app->bind(‘App\Database\MongoDatabase’, function ($app) {
  return new MongoDatabase(config(‘mongo.defaults.host’), config(‘mongo.defaults.port’), config(‘mongo.defaults.database’));
});
 
$this->app->bind(‘App\Models\Auth\User’, function ($app) {
  return new User($app->make(‘App\Database\MongoDatabase’));
});

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

Мы использовали метод провайдера Auth Facade для добавления нашего провайдера аутентификации под ключом mongo . Напомним, что ключ отражает настройки, которые были добавлены ранее в файле auth.php .

1
2
3
Auth::provider(‘mongo’, function ($app, array $config) {
  return new MongoUserProvider($app->make(‘App\Models\Auth\User’));
});

Аналогичным образом, мы добавим нашу собственную реализацию защиты, используя метод Auth фасада.

1
2
3
Auth::extend(‘json’, function ($app, $name, array $config) {
  return new JsonGuard(Auth::createUserProvider($config[‘provider’]), $app->make(‘request’));
});

Далее, есть метод register который мы использовали для привязки интерфейса App\Services\Contracts\NosqlServiceInterface к реализации App\Database\MongoDatabase .

1
2
3
4
$this->app->bind(
  ‘App\Services\Contracts\NosqlServiceInterface’,
  ‘App\Database\MongoDatabase’
);

Поэтому, когда возникает необходимость разрешить зависимость App\Services\Contracts\NosqlServiceInterface , Laravel отвечает реализацией адаптера App\Database\MongoDatabase .

Преимущество использования этого подхода состоит в том, что можно легко заменить данную реализацию пользовательской реализацией. Например, скажем, кто-то хотел бы заменить реализацию App\Database\MongoDatabase адаптером CouchDB в будущем. В этом случае им просто нужно добавить соответствующую привязку в методе register.

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

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

Давайте быстро реализуем довольно простое app/Http/Controllers/MongoController.php файл контроллера app/Http/Controllers/MongoController.php как показано ниже

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
<?php
// app/Http/Controllers/MongoController.php
namespace App\Http\Controllers;
 
use App\Http\Controllers\Controller;
use Illuminate\Contracts\Auth\Guard;
 
class MongoController extends Controller
{
  public function login(Guard $auth_guard)
  {
    if ($auth_guard->validate()) {
      // get the current authenticated user
      $user = $auth_guard->user();
     
      echo ‘Success!’;
    } else {
      echo ‘Not authorized to access this page!’;
    }
  }
}

Внимательно рассмотрите зависимость метода входа в систему, которая требует реализации Illuminate\Contracts\Auth\Guard guard. Так как мы установили настраиваемую охрану в качестве защиты по умолчанию в файле auth.php , именно App\Services\Auth\JsonGuard будет введена на самом деле!

Затем мы вызвали метод validate класса App\Services\Auth\JsonGuard , который, в свою очередь, инициирует серию вызовов методов:

  • Он вызывает метод retrieveByCredentials класса App\Extensions\MongoUserProvider .
  • Метод retrieveByCredentials вызывает метод fetchUserByCredentials класса User App\Models\Auth\User .
  • Метод fetchUserByCredentials вызывает метод find из App\Database\MongoDatabase для получения учетных данных пользователя.
  • Наконец, метод find из App\Database\MongoDatabase возвращает ответ!

Если все работает должным образом, мы должны получить аутентифицированного пользователя, вызвав метод user нашей охраны.

Чтобы получить доступ к контроллеру, вы должны добавить связанный маршрут в файл routes/web.php .

1
Route::get(‘/custom/mongo/login’, ‘MongoController@login’);

Попробуйте получить доступ к URL-адресу http: // your-laravel-site / custom / mongo / login без передачи каких-либо параметров, и вы должны увидеть сообщение «не авторизовано».

С другой стороны, попробуйте что-то вроде http: // your-laravel-site / custom / mongo / login? Jsondata = {«username»: «admin», «password»: «admin»}, и это должно вернуть сообщение об успехе если пользователь присутствует в вашей базе данных.

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

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

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

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

Я надеюсь, что это упражнение дало вам представление о процессе аутентификации Laravel, и теперь вы должны чувствовать себя более уверенно относительно его внутренней работы.

Для тех из вас, кто только начинает работать с Laravel или хочет расширить свои знания, сайт или приложение с помощью расширений, у нас есть множество вещей, которые вы можете изучить на Envato Market .

Я хотел бы услышать ваши отзывы и предложения, так что громко кричите, используя канал ниже!