Вступление
Поскольку приложения, управляемые HTTP, не сохраняют состояния, сеансы предоставляют способ хранения информации о пользователе по нескольким запросам. Laravel поставляется с различными сессиями, доступ к которым осуществляется через выразительный унифицированный API. Поддержка популярных бэкэндов, таких как Memcached , Redis и базы данных, включена в комплект поставки.
Конфигурация
Файл конфигурации сеанса хранится в . Обязательно ознакомьтесь с опциями, доступными вам в этом файле. По умолчанию Laravel настроен на использование драйвера сеанса, который будет хорошо работать для многих приложений. В производственных приложениях вы можете рассмотреть возможность использования драйверов или для еще большей производительности сеанса.config/session.php
file
memcached
redis
Параметр driver
конфигурации сеанса определяет, где будут храниться данные сеанса для каждого запроса. Laravel поставляется с несколькими отличными водителями из коробки:
file
- сеансы хранятся в .storage/framework/sessions
cookie
- сеансы хранятся в безопасных, зашифрованных куки.database
- сеансы хранятся в реляционной базе данных.memcached
/redis
- сессии хранятся в одном из этих быстрых хранилищ на основе кэша.array
- сеансы хранятся в массиве PHP и не будут сохраняться.
Драйвер массива используется во время тестирования и предотвращает сохранение данных, хранящихся в сеансе.
Необходимые условия для водителя
База данных
При использовании database
драйвера сеанса вам нужно будет создать таблицу, содержащую элементы сеанса. Ниже приведен пример Schema
объявления для таблицы:
Schema::create('sessions', function ($table) {
$table->string('id')->unique();
$table->unsignedInteger('user_id')->nullable();
$table->string('ip_address', 45)->nullable();
$table->text('user_agent')->nullable();
$table->text('payload');
$table->integer('last_activity');
});
Вы можете использовать команду Artisan для генерации этой миграции:session:table
php artisan session:table
php artisan migrate
Redis
Перед использованием сеансов Redis с Laravel вам необходимо установить пакет (~ 1.0) через Composer. Вы можете настроить подключения Redis в файле конфигурации. В файле конфигурации эта опция может использоваться, чтобы указать, какое соединение Redis используется сеансом.predis/predis
database
session
connection
Использование сессии
Извлечение данных
Существует два основных способа работы с данными сеанса в Laravel: глобальный session
помощник и Request
экземпляр. Во-первых, давайте посмотрим на доступ к сеансу через Request
экземпляр, который может быть подсказан типом в методе контроллера. Помните, зависимости метода контроллера автоматически вводятся через сервисный контейнер Laravel :
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
class UserController extends Controller
{
/**
* Show the profile for the given user.
*
* @param Request $request
* @param int $id
* @return Response
*/
public function show(Request $request, $id)
{
$value = $request->session()->get('key');
//
}
}
Когда вы извлекаете элемент из сеанса, вы также можете передать значение по умолчанию в качестве второго аргумента get
метода. Это значение по умолчанию будет возвращено, если указанный ключ не существует в сеансе. Если вы передадите a Closure
в качестве значения по умолчанию get
методу, а запрошенный ключ не существует, Closure
он будет выполнен и его результат будет возвращен:
$value = $request->session()->get('key', 'default');
$value = $request->session()->get('key', function () {
return 'default';
});
Глобальный Помощник Сессии
Вы также можете использовать глобальную session
функцию PHP для извлечения и хранения данных в сеансе. Когда session
помощник вызывается с одним строковым аргументом, он возвращает значение этого сеансового ключа. Когда помощник вызывается с массивом пар ключ / значение, эти значения будут сохранены в сеансе:
Route::get('home', function () {
// Retrieve a piece of data from the session...
$value = session('key');
// Specifying a default value...
$value = session('key', 'default');
// Store a piece of data in the session...
session(['key' => 'value']);
});
Существует небольшая практическая разница между использованием сеанса через экземпляр HTTP-запроса и использованием глобального
session
помощника. Оба метода тестируются с помощьюassertSessionHas
метода, который доступен во всех ваших тестовых случаях.
Получение всех данных сеанса
Если вы хотите получить все данные в сеансе, вы можете использовать all
метод:
$data = $request->session()->all();
Определение, существует ли элемент в сеансе
Чтобы определить, присутствует ли элемент в сеансе, вы можете использовать has
метод. has
Метод возвращает , true
если элемент присутствует и не null
:
if ($request->session()->has('users')) {
//
}
Чтобы определить, присутствует ли элемент в сеансе, даже если его значение равно null
, вы можете использовать exists
метод. exists
Метод возвращает , true
если элемент присутствует:
if ($request->session()->exists('users')) {
//
}
Хранение данных
Для хранения данных в сеансе вы обычно будете использовать put
метод или session
помощника:
// Via a request instance...
$request->session()->put('key', 'value');
// Via the global helper...
session(['key' => 'value']);
Нажатие на массив значений сеанса
Этот push
метод может использоваться для помещения нового значения в значение сеанса, которое является массивом. Например, если ключ содержит массив имен команд, вы можете вставить новое значение в массив следующим образом:user.teams
$request->session()->push('user.teams', 'developers');
Извлечение и удаление предмета
pull
Метод извлечения и удаления элемента из сессии в одном заявлении:
$value = $request->session()->pull('key', 'default');
Flash-данные
Иногда вы можете захотеть хранить элементы в сеансе только для следующего запроса. Вы можете сделать это, используя flash
метод. Данные, сохраненные в сеансе с использованием этого метода, будут доступны только во время последующего HTTP-запроса, а затем будут удалены. Данные Flash в первую очередь полезны для кратковременных сообщений о состоянии:
$request->session()->flash('status', 'Task was successful!');
Если вам необходимо хранить данные флэш-памяти для нескольких запросов, вы можете использовать reflash
метод, который сохранит все данные флэш-памяти для дополнительного запроса. Если вам нужно только сохранить определенные данные флэш-памяти, вы можете использовать keep
метод:
$request->session()->reflash();
$request->session()->keep(['username', 'email']);
Удаление данных
forget
Метод будет удалить часть данных из сеанса. Если вы хотите удалить все данные из сеанса, вы можете использовать flush
метод:
// Forget a single key...
$request->session()->forget('key');
// Forget multiple keys...
$request->session()->forget(['key1', 'key2']);
$request->session()->flush();
Восстановление идентификатора сеанса
Регенерация идентификатора сеанса часто выполняется для того, чтобы предотвратить использование атакой фиксации сеанса в вашем приложении злонамеренными пользователями .
Laravel автоматически восстанавливает идентификатор сеанса во время аутентификации, если вы используете встроенный LoginController
; однако, если вам нужно вручную восстановить идентификатор сеанса, вы можете использовать этот regenerate
метод.
$request->session()->regenerate();
Добавление пользовательских драйверов сеансов
Реализация драйвера
Ваш пользовательский драйвер сеанса должен реализовать SessionHandlerInterface
. Этот интерфейс содержит всего несколько простых методов, которые нам нужно реализовать. Описанная реализация MongoDB выглядит примерно так:
<?php
namespace App\Extensions;
class MongoSessionHandler implements \SessionHandlerInterface
{
public function open($savePath, $sessionName) {}
public function close() {}
public function read($sessionId) {}
public function write($sessionId, $data) {}
public function destroy($sessionId) {}
public function gc($lifetime) {}
}
Laravel не поставляется с каталогом, содержащим ваши расширения. Вы можете разместить их где угодно. В этом примере мы создали
Extensions
каталог для размещенияMongoSessionHandler
.
Поскольку цель этих методов не совсем понятна, давайте быстро рассмотрим, что делает каждый из методов:
- Этот
open
метод обычно используется в файловых системах хранения сеансов. Поскольку Laravel поставляется сfile
драйвером сеанса, вам почти никогда не нужно ничего добавлять в этот метод. Вы можете оставить это как пустую заглушку. Фактом плохого дизайна интерфейса (о котором мы поговорим позже) является то, что PHP требует от нас реализации этого метода. close
Метод, какopen
метод, можно также , как правило , можно пренебречь. Для большинства водителей это не нужно.read
Метод должен возвращать версию строки данных сеанса , связанные с данными$sessionId
. При извлечении или сохранении данных сеанса в вашем драйвере нет необходимости выполнять сериализацию или другую кодировку, поскольку Laravel выполнит сериализацию за вас.write
Метод должен написать данную$data
строку , связанную с$sessionId
какой - то постоянной системой хранения, такими как MongoDB, Динамо и т.д. Опять же , вы не должны выполнять какую - либо сериализации - Laravel будет уже обработан , что для вас.destroy
Метод должен удалить данные , связанные с$sessionId
от постоянного хранения.gc
Метод должен уничтожить все данные сеанса, которое старше , чем данные$lifetime
, который является меткой времени UNIX. Для самодействующих систем, таких как Memcached и Redis, этот метод можно оставить пустым.
Регистрация водителя
Как только ваш драйвер был реализован, вы готовы зарегистрировать его в фреймворке. Чтобы добавить дополнительные драйверы в бэкэнд сессии Laravel, вы можете использовать extend
метод на Session
фасаде . Вы должны вызывать extend
метод из boot
метода поставщика услуг . Вы можете сделать это из существующего AppServiceProvider
или создать совершенно нового поставщика:
<?php
namespace App\Providers;
use App\Extensions\MongoSessionHandler;
use Illuminate\Support\Facades\Session;
use Illuminate\Support\ServiceProvider;
class SessionServiceProvider extends ServiceProvider
{
/**
* Register bindings in the container.
*
* @return void
*/
public function register()
{
//
}
/**
* Bootstrap any application services.
*
* @return void
*/
public function boot()
{
Session::extend('mongo', function ($app) {
// Return implementation of SessionHandlerInterface...
return new MongoSessionHandler;
});
}
}
После того, как драйвер сеанса был зарегистрирован, вы можете использовать mongo
драйвер в вашем файле конфигурации.config/session.php
0 комментариев