Документация Laravel 10.x
Здесь ты найдешь сниппеты по Laravel и полезные советы по веб-разработке.
Класс Illuminate\Http\Request
Laravel предоставляет объектно-ориентированный способ взаимодействия с текущим HTTP-запросом, обрабатываемым вашим приложением, а также получение вводных данных, куки и файлов, отправленных с запросом.
Чтобы получить экземпляр текущего HTTP-запроса с помощью внедрения зависимости, вы должны задать тип Illuminate\Http\Request
на вашем маршруте или методе контроллера. Экземпляр входящего запроса будет автоматически внедрен Laravel контейнером служб:
<?php namespace App\Http\Controllers; use Illuminate\Http\RedirectResponse;use Illuminate\Http\Request; class UserController extends Controller{ /** * Сохранить нового пользователя. */ public function store(Request $request): RedirectResponse { $name = $request->input('name'); // Сохранить пользователя... return redirect('/users'); }}
Как упоминалось ранее, вы также можете использовать тип-подсказку класса Illuminate\Http\Request
в замыкании маршрута. Контейнер служб автоматически внедрит входящий запрос в замыкание при его выполнении:
use Illuminate\Http\Request; Route::get('/', function (Request $request) { // ...});
Если в вашем методе контроллера также ожидается ввод от параметра маршрута, вы должны указать параметры маршрута после других зависимостей. Например, если ваш маршрут определен следующим образом:
use App\Http\Controllers\UserController; Route::put('/user/{id}', [UserController::class, 'update']);
Вы все равно можете использовать тип-подсказку класса Illuminate\Http\Request
и получить доступ к параметру маршрута id
, определив метод контроллера следующим образом:
<?php namespace App\Http\Controllers; use Illuminate\Http\RedirectResponse;use Illuminate\Http\Request; class UserController extends Controller{ /** * Обновить указанного пользователя. */ public function update(Request $request, string $id): RedirectResponse { // Обновить пользователя... return redirect('/users'); }}
Экземпляр Illuminate\Http\Request
предоставляет различные методы для изучения входящего HTTP-запроса и расширяет класс Symfony\Component\HttpFoundation\Request
. Ниже мы рассмотрим несколько наиболее важных методов.
Метод path
возвращает информацию о пути запроса. Таким образом, если входящий запрос направлен на http://example.com/foo/bar
, метод path
вернет foo/bar
:
$uri = $request->path();
Метод is
позволяет проверить, соответствует ли путь входящего запроса заданному шаблону. При использовании этого метода можно использовать символ *
в качестве подстановочного знака:
if ($request->is('admin/*')) { // ...}
С использованием метода routeIs
вы можете определить, соответствует ли входящий запрос именованному маршруту:
if ($request->routeIs('admin.*')) { // ...}
Для получения полного URL входящего запроса вы можете использовать методы url
или fullUrl
. Метод url
вернет URL без строки запроса, в то время как метод fullUrl
включает строку запроса:
$url = $request->url(); $urlWithQueryString = $request->fullUrl();
Если вы хотите добавить данные строки запроса к текущему URL, вы можете вызвать метод fullUrlWithQuery
. Этот метод объединяет данный массив переменных строки запроса с текущей строкой запроса:
$request->fullUrlWithQuery(['type' => 'phone']);
Если вы хотите получить текущий URL без указанного параметра строки запроса, вы можете воспользоваться методом fullUrlWithoutQuery
:
$request->fullUrlWithoutQuery(['type']);
Вы можете получить "хост" входящего запроса с помощью методов host
, httpHost
и schemeAndHttpHost
:
$request->host();$request->httpHost();$request->schemeAndHttpHost();
Метод method
вернет HTTP-глагол для запроса. Вы можете использовать метод isMethod
для проверки того, соответствует ли HTTP-глагол заданной строке:
$method = $request->method(); if ($request->isMethod('post')) { // ...}
Вы можете получить заголовок запроса из экземпляра Illuminate\Http\Request
с помощью метода header
. Если заголовок отсутствует в запросе, будет возвращено значение null
. Однако метод header
принимает второй необязательный аргумент, который будет возвращен, если заголовок отсутствует в запросе:
$value = $request->header('X-Header-Name'); $value = $request->header('X-Header-Name', 'default');
Метод hasHeader
можно использовать для определения, содержит ли запрос заданный заголовок:
if ($request->hasHeader('X-Header-Name')) { // ...}
Для удобства метод bearerToken
можно использовать для извлечения маркера авторизации из заголовка Authorization
. Если такого заголовка нет, будет возвращена пустая строка:
$token = $request->bearerToken();
Метод ip
может использоваться для извлечения IP-адреса клиента, сделавшего запрос к вашему приложению:
$ipAddress = $request->ip();
Laravel предоставляет несколько методов для изучения запрашиваемых типов контента входящего запроса через заголовок Accept
. Во-первых, метод getAcceptableContentTypes
вернет массив, содержащий все принятые запросом типы контента:
$contentTypes = $request->getAcceptableContentTypes();
Метод accepts
принимает массив типов контента и возвращает true
, если хотя бы один из типов контента принят запросом. В противном случае будет возвращено false
:
if ($request->accepts(['text/html', 'application/json'])) { // ...}
Вы можете использовать метод prefers
для определения того, какой тип контента из заданного массива типов контента наиболее предпочтителен для запроса. Если ни один из предоставленных типов контента не принят запросом, будет возвращено null
:
$preferred = $request->prefers(['text/html', 'application/json']);
Поскольку многие приложения обслуживают только HTML или JSON, вы можете использовать метод expectsJson
для быстрого определения того, ожидает ли входящий запрос ответ в формате JSON:
if ($request->expectsJson()) { // ...}
Стандарт PSR-7 определяет интерфейсы для HTTP-сообщений, включая запросы и ответы. Если вы хотите получить экземпляр PSR-7 request вместо запроса Laravel, вам сначала нужно установить несколько библиотек. Laravel использует компонент Symfony HTTP Message Bridge, чтобы преобразовать типичные запросы и ответы Laravel в совместимые с PSR-7 реализации:
composer require symfony/psr-http-message-bridgecomposer require nyholm/psr7
После установки этих библиотек вы можете получить запрос PSR-7, указав интерфейс запроса в замыкании маршрута или методе контроллера:
use Psr\Http\Message\ServerRequestInterface; Route::get('/', function (ServerRequestInterface $request) { // ...});
Примечание Если вы возвращаете экземпляр PSR-7 response из маршрута или контроллера, он автоматически будет преобразован обратно в экземпляр Laravel response и отображен фреймворком.
Вы можете получить все входящие данные запроса в виде массива с помощью метода all
. Этот метод может быть использован независимо от того, является ли входящий запрос HTML-формой или является XHR-запросом:
$input = $request->all();
С помощью метода collect
вы можете получить все входящие данные запроса в виде коллекции:
$input = $request->collect();
Метод collect
также позволяет получить подмножество входящих данных запроса в виде коллекции:
$request->collect('users')->each(function (string $user) { // ...});
С помощью нескольких простых методов вы можете получить доступ ко всем вводным данным пользователя из вашего экземпляра Illuminate\Http\Request
, не беспокоясь о том, какой HTTP-глагол был использован для запроса. Независимо от HTTP-глагола, вы можете использовать метод input
для получения вводных данных пользователя:
$name = $request->input('name');
Вы можете передать значение по умолчанию вторым аргументом методу input
. Это значение будет возвращено, если запрошенного значения ввода не существует в запросе:
$name = $request->input('name', 'Sally');
При работе с формами, содержащими массивные входы, используйте нотацию "точка" для доступа к массивам:
$name = $request->input('products.0.name'); $names = $request->input('products.*.name');
Вы можете вызвать метод input
без аргументов, чтобы получить все значения ввода в виде ассоциативного массива:
$input = $request->input();
В то время как метод input
извлекает значения из всей полезной нагрузки запроса (включая строку запроса), метод query
извлекает значения только из строки запроса:
$name = $request->query('name');
Если запрошенные данные строки запроса отсутствуют, будет возвращено второе значение этого метода:
$name = $request->query('name', 'Helen');
Вы можете вызвать метод query
без аргументов, чтобы получить все значения строки запроса в виде ассоциативного массива:
$query = $request->query();
При отправке JSON-запросов в ваше приложение вы можете получить доступ к данным JSON с использованием метода input
, при условии, что заголовок запроса Content-Type
правильно установлен в application/json
. Вы можете даже использовать синтаксис "точка" для получения значений, вложенных в массивы / объекты JSON:
$name = $request->input('user.name');
Вместо извлечения данных ввода запроса как примитивной string
, вы можете использовать метод string
для извлечения данных запроса в виде экземпляра Illuminate\Support\Stringable
:
$name = $request->string('name')->trim();
При работе с HTML-элементами, такими как флажки, ваше приложение может получать "истинные" значения, которые фактически являются строками. Например, "true" или "on". Для удобства вы можете использовать метод boolean
для извлечения этих значений как булевых. Метод boolean
возвращает true
для 1, "1", true, "true", "on" и "yes". Все остальные значения вернут false
:
$archived = $request->boolean('archived');
Для удобства значения ввода, содержащие даты/время, могут быть извлечены как экземпляры Carbon с использованием метода date
. Если в запросе отсутствует значение ввода с указанным именем, будет возвращено null
:
$birthday = $request->date('birthday');
Второй и третий аргументы, принимаемые методом date
, могут использоваться для указания формата и часового пояса даты соответственно:
$elapsed = $request->date('elapsed', '!H:i', 'Europe/Madrid');
Если значение ввода присутствует, но имеет недопустимый формат, будет сгенерировано исключение InvalidArgumentException
. Поэтому рекомендуется проверять ввод перед вызовом метода date
.
Значения ввода, соответствующие перечислениям PHP, также могут быть извлечены из запроса. Если в запросе отсутствует значение ввода с указанным именем или перечисление не имеет значений, соответствующих значению ввода, будет возвращено null
. Метод enum
принимает имя значения ввода и класс перечисления в качестве своих первого и второго аргументов соответственно:
use App\Enums\Status; $status = $request->enum('status', Status::class);
Вы также можете получать ввод пользователя с использованием динамических свойств на экземпляре Illuminate\Http\Request
. Например, если в одной из форм вашего приложения есть поле name
, вы можете получить доступ к значению поля таким образом:
$name = $request->name;
При использовании динамических свойств Laravel сначала будет искать значение параметра в полезной нагрузке запроса. Если его нет, Laravel будет искать поле в параметрах совпадающего маршрута.
Если вам нужно получить подмножество входных данных, вы можете использовать методы only
и except
. Оба этих метода принимают единственный аргумент в виде array
или динамического списка аргументов:
$input = $request->only(['username', 'password']); $input = $request->only('username', 'password'); $input = $request->except(['credit_card']); $input = $request->except('credit_card');
Внимание Метод
only
возвращает все ключи / значения, которые вы запрашиваете; однако он не вернет ключи / значения, которых нет в запросе.
Вы можете использовать метод has
, чтобы определить, присутствует ли значение в запросе. Метод has
возвращает true
, если значение присутствует в запросе:
if ($request->has('name')) { // ...}
При передаче массива метод has
определит, присутствуют ли все указанные значения:
if ($request->has(['name', 'email'])) { // ...}
Метод hasAny
возвращает true
, если присутствует хотя бы одно из указанных значений:
if ($request->hasAny(['name', 'email'])) { // ...}
Метод whenHas
выполнит предоставленное замыкание, если значение присутствует в запросе:
$request->whenHas('name', function (string $input) { // ...});
К методу whenHas
может быть передано второе замыкание, которое будет выполнено, если указанное значение отсутствует в запросе:
$request->whenHas('name', function (string $input) { // Значение "name" присутствует...}, function () { // Значение "name" отсутствует...});
Если вы хотите определить, присутствует ли значение в запросе и не является ли оно пустой строкой, вы можете использовать метод filled
:
if ($request->filled('name')) { // ...}
Метод anyFilled
возвращает true
, если любое из указанных значений не является пустой строкой:
if ($request->anyFilled(['name', 'email'])) { // ...}
Метод whenFilled
выполнит предоставленное замыкание, если значение присутствует в запросе и не является пустой строкой:
$request->whenFilled('name', function (string $input) { // ...});
К методу whenFilled
может быть передано второе замыкание, которое будет выполнено, если указанное значение не является "filled":
$request->whenFilled('name', function (string $input) { // Значение "name" заполнено...}, function () { // Значение "name" не заполнено...});
Чтобы определить, отсутствует ли данный ключ в запросе, можно использовать методы missing
и whenMissing
:
if ($request->missing('name')) { // ...} $request->whenMissing('name', function (array $input) { // Значение "name" отсутствует...}, function () { // Значение "name" присутствует...});
Иногда вам может потребоваться вручную объединить дополнительные вводы существующих входных данных запроса. Для этого можно использовать метод merge
. Если данный ключ ввода уже существует в запросе, его значения будут перезаписаны данными, предоставленными методу merge
:
$request->merge(['votes' => 0]);
Метод mergeIfMissing
можно использовать для объединения ввода в запрос, если соответствующие ключи еще не существуют во входных данных запроса:
$request->mergeIfMissing(['votes' => 0]);
Laravel позволяет сохранять ввод из одного запроса на следующий запрос. Эта функция особенно полезна для повторного заполнения форм после обнаружения ошибок валидации. Однако, если вы используете встроенные возможности валидации Laravel, возможно, вам не потребуется явно использовать эти методы миграции ввода сеанса, так как некоторые встроенные средства валидации Laravel будут вызывать их автоматически.
Метод flash
в классе Illuminate\Http\Request
поместит текущий ввод в сеанс, чтобы он был доступен при следующем запросе пользователя к приложению:
$request->flash();
Также вы можете использовать методы flashOnly
и flashExcept
для миграции подмножества данных запроса в сеанс. Эти методы полезны для хранения конфиденциальной информации, такой как пароли, вне сеанса:
$request->flashOnly(['username', 'email']); $request->flashExcept('password');
Поскольку часто требуется поместить ввод в сеанс и затем выполнить перенаправление на предыдущую страницу, вы можете легко объединить миграцию ввода с перенаправлением, используя метод withInput
:
return redirect('form')->withInput(); return redirect()->route('user.create')->withInput(); return redirect('form')->withInput( $request->except('password'));
Чтобы получить мигрированный ввод из предыдущего запроса, вызовите метод old
у экземпляра Illuminate\Http\Request
. Метод old
извлечет ранее мигрированные данные ввода из сеанса:
$username = $request->old('username');
Laravel также предоставляет глобальный вспомогательный old
. Если вы отображаете старый ввод в шаблоне Blade, удобнее использовать вспомогательный old
для заполнения формы. Если для данного поля не существует старого ввода, будет возвращено null
:
<input type="text" name="username" value="{{ old('username') }}">
Все файлы cookie, созданные фреймворком Laravel, зашифрованы и подписаны аутентификационным кодом, что означает, что они будут считаться недействительными, если их изменит клиент. Чтобы получить значение cookie из запроса, используйте метод cookie
на экземпляре Illuminate\Http\Request
:
$value = $request->cookie('name');
По умолчанию Laravel включает средства промежуточной обработки App\Http\Middleware\TrimStrings
и Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull
в глобальный стек промежуточной обработки вашего приложения. Эти средства промежуточной обработки перечислены в глобальном стеке промежуточной обработки в классе App\Http\Kernel
. Эти средства промежуточной обработки автоматически обрезают все поступающие строки в запросе, а также преобразовывают любые пустые строки в null
. Это позволяет вам не беспокоиться о таких нормализационных вопросах в ваших маршрутах и контроллерах.
Если вы хотите отключить это поведение для всех запросов, вы можете удалить два средства промежуточной обработки из стека промежуточной обработки вашего приложения, удалив их из свойства $middleware
вашего класса App\Http\Kernel
.
Если вы хотите отключить обрезку строк и преобразование пустых строк для подмножества запросов в вашем приложении, вы можете использовать метод skipWhen
, предлагаемый обоими средствами промежуточной обработки. Этот метод принимает замыкание, которое должно возвращать true
или false
, чтобы указать, следует ли пропустить нормализацию ввода. Обычно метод skipWhen
следует вызывать в методе boot
вашего AppServiceProvider
приложения.
use App\Http\Middleware\TrimStrings;use Illuminate\Http\Request;use Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull; /** * Инициализировать все службы приложения. */public function boot(): void{ TrimStrings::skipWhen(function (Request $request) { return $request->is('admin/*'); }); ConvertEmptyStringsToNull::skipWhen(function (Request $request) { // ... });}
Вы можете получить загруженные файлы из экземпляра Illuminate\Http\Request
с использованием метода file
или с использованием динамических свойств. Метод file
возвращает экземпляр класса Illuminate\Http\UploadedFile
, который расширяет класс PHP SplFileInfo
и предоставляет различные методы для взаимодействия с файлом:
$file = $request->file('photo'); $file = $request->photo;
Вы можете определить, присутствует ли файл в запросе, используя метод hasFile
:
if ($request->hasFile('photo')) { // ...}
Помимо проверки наличия файла, вы можете проверить, не было ли проблем с загрузкой файла с помощью метода isValid
:
if ($request->file('photo')->isValid()) { // ...}
Класс UploadedFile
также содержит методы для доступа к полному квалифицированному пути файла и его расширению. Метод extension
попытается угадать расширение файла на основе его содержимого. Это расширение может отличаться от расширения, предоставленного клиентом:
$path = $request->photo->path(); $extension = $request->photo->extension();
Существует множество других методов, доступных в экземплярах UploadedFile
. Проверьте документацию API по классу для получения дополнительной информации об этих методах.
Для сохранения загруженного файла вы обычно будете использовать одну из ваших настроенных файловых систем. У класса UploadedFile
есть метод store
, который переместит загруженный файл на один из ваших дисков, который может быть расположен в каталоге вашей локальной файловой системы или в облачном хранилище, таком как Amazon S3.
Метод store
принимает путь, по которому файл должен быть сохранен относительно корневого каталога настроенной файловой системы. Этот путь не должен содержать имени файла, так как автоматически будет сгенерирован уникальный идентификатор для использования в качестве имени файла.
Метод store
также принимает дополнительный необязательный второй аргумент для указания имени диска, который должен использоваться для сохранения файла. Метод вернет путь к файлу относительно корня диска:
$path = $request->photo->store('images'); $path = $request->photo->store('images', 's3');
Если вы не хотите, чтобы автоматически генерировалось имя файла, вы можете использовать метод storeAs
, который принимает путь, имя файла и имя диска в качестве аргументов:
$path = $request->photo->storeAs('images', 'filename.jpg'); $path = $request->photo->storeAs('images', 'filename.jpg', 's3');
Примечание Для получения более подробной информации о хранении файлов в Laravel, ознакомьтесь с полным руководством по хранению файлов.
При работе с приложениями через балансировщик нагрузки, завершающий сертификаты TLS / SSL, вы можете заметить, что ваше приложение иногда не генерирует HTTPS-ссылки при использовании вспомогательного url
. Обычно это происходит потому, что ваше приложение получает трафик от балансировщика на порт 80 и не знает, что должно генерировать безопасные ссылки.
Для решения этой проблемы вы можете использовать промежуточное ПО App\Http\Middleware\TrustProxies
, включенное в ваше приложение Laravel, что позволяет быстро настраивать балансировщики или прокси, которым можно доверять вашему приложению. Ваши доверенные прокси должны быть перечислены в виде массива в свойстве $proxies
этого промежуточного ПО. Кроме того, помимо настройки доверенных прокси, вы можете настроить $headers
прокси, которым можно доверять:
<?php namespace App\Http\Middleware; use Illuminate\Http\Middleware\TrustProxies as Middleware;use Illuminate\Http\Request; class TrustProxies extends Middleware{ /** * Доверенные прокси для этого приложения. * * @var string|array */ protected $proxies = [ '192.168.1.1', '192.168.1.2', ]; /** * Заголовки, которые должны использоваться для обнаружения прокси. * * @var int */ protected $headers = Request::HEADER_X_FORWARDED_FOR | Request::HEADER_X_FORWARDED_HOST | Request::HEADER_X_FORWARDED_PORT | Request::HEADER_X_FORWARDED_PROTO;}
Примечание Если вы используете балансировку нагрузки AWS Elastic Load Balancing, ваше значение
$headers
должно бытьRequest::HEADER_X_FORWARDED_AWS_ELB
. Для получения дополнительной информации о константах, которые могут использоваться в свойстве$headers
, ознакомьтесь с документацией Symfony по доверию прокси.
Если вы используете Amazon AWS или другого провайдера "облачного" балансировщика нагрузки, вам может не быть известны IP-адреса ваших фактических балансировщиков. В этом случае вы можете использовать *
, чтобы доверять всем прокси:
/** * Доверенные прокси для этого приложения. * * @var string|array */protected $proxies = '*';
По умолчанию Laravel будет реагировать на все запросы, которые он получает, независимо от содержимого заголовка Host
HTTP-запроса. Кроме того, значение заголовка Host
будет использоваться при создании абсолютных URL для вашего приложения во время веб-запроса.
Обычно вы должны настроить свой веб-сервер, такой как Nginx или Apache, чтобы он отправлял запросы в ваше приложение, которые соответствуют заданному имени хоста. Однако, если у вас нет возможности настроить ваш веб-сервер напрямую и вам нужно указать Laravel отвечать только на определенные имена хостов, вы можете сделать это, включив промежуточное ПО App\Http\Middleware\TrustHosts
для вашего приложения.
Промежуточное ПО TrustHosts
уже включено в стек промежуточного ПО $middleware
вашего приложения; однако его следует раскомментировать, чтобы оно стало активным. В методе hosts
этого промежуточного ПО вы можете указать имена хостов, на которые ваше приложение должно отвечать. Входящие запросы с другими значениями заголовков Host
будут отклонены:
/** * Получить шаблоны хостов, которым можно доверять. * * @return array<int, string> */public function hosts(): array{ return [ 'laravel.test', $this->allSubdomainsOfApplicationUrl(), ];}
Метод-вспомогатель allSubdomainsOfApplicationUrl
вернет регулярное выражение, соответствующее всем поддоменам значения конфигурации app.url
вашего приложения. Этот метод-вспомогатель обеспечивает удобный способ разрешить все поддомены вашего приложения при построении приложения, использующего поддомены-шаблоны.