Blade-компоненты: переиспользуемый UI
Blade-компоненты — современный способ собирать интерфейс из переиспользуемых кирпичиков с входными параметрами (props) и контентом (slots).
Суть: компонент — это самостоятельный элемент UI (кнопка, карточка, алерт), который вызывается как HTML-тег
<x-alert />, принимает props для настройки и slot для содержимого.
Наследование шаблонов хорошо для каркаса страницы, но для мелких повторяющихся элементов — кнопок, карточек, уведомлений — нужен инструмент гибче. Это Blade-компоненты. Они работают как собственные HTML-теги: вы описываете компонент один раз, а потом вставляете его где угодно одной строкой, настраивая через атрибуты.
Есть два вида компонентов. Анонимные — это просто шаблон в папке resources/views/components, без PHP-класса; идеальны для простого UI. Классовые имеют PHP-класс с логикой; нужны, когда внутри есть вычисления. Начинать стоит с анонимных — их проще всего понять.
Анонимный компонент
Создадим компонент-уведомление. Файл resources/views/components/alert.blade.php:
{{-- объявляем входные параметры со значениями по умолчанию --}}
@props(['type' => 'info'])
<div {{ $attributes->merge(['class' => 'alert alert-'.$type]) }}>
{{ $slot }} {{-- сюда попадёт содержимое компонента --}}
</div>Теперь используем его как тег. Имя начинается с x-, props передаются как атрибуты, а содержимое между тегами попадёт в $slot:
<x-alert type="danger" class="mb-4">
Ошибка: товар не найден!
</x-alert>
<x-alert>
Обычное информационное сообщение.
</x-alert>Как работает под капотом
Директива @props объявляет ожидаемые параметры и их значения по умолчанию. Переменная $slot хранит всё, что вы написали между открывающим и закрывающим тегом. А $attributes собирает все «лишние» HTML-атрибуты, не объявленные в props (например, class="mb-4"), и метод merge() аккуратно объединяет их с собственными классами компонента, не затирая ни те, ни другие.
Вызов: <x-alert type="danger" class="mb-4">Текст</x-alert>
type="danger" -> prop $type = 'danger'
class="mb-4" -> $attributes (не объявлен в props)
Текст -> $slot
merge: 'alert alert-danger' + 'mb-4'
= class="alert alert-danger mb-4"
Смоделируем логику компонента на Python: props со значениями по умолчанию, слияние атрибутов и подстановка слота.
Попробуй сам ▶
# Логика Blade-компонента: props + merge атрибутов + slot
def alert(slot, type='info', extra_class=''):
base = f'alert alert-{type}' # собственные классы
merged = (base + ' ' + extra_class).strip() # $attributes->merge()
return f'<div class="{merged}">{slot}</div>'
print(alert('Ошибка!', type='danger', extra_class='mb-4'))
print(alert('Просто информация')) # type по умолчанию = info
Частые ошибки
- Затирать классы вместо merge. Если присвоить
classнапрямую, переданный класс потеряется. Используйте$attributes->merge(). - Забыть
@props. Без объявления параметр окажется в$attributesи просочится в HTML как атрибут. - Не чистить кэш. После изменений иногда нужно
php artisan view:clear, чтобы увидеть результат.
Best practices
- Держите компоненты маленькими и сфокусированными на одной задаче.
- Для простого UI используйте анонимные компоненты, классовые — только при наличии логики.
- Всегда применяйте
$attributes->merge(), чтобы внешние классы и атрибуты не терялись.
Стоит чётко понимать разницу между анонимными и классовыми компонентами на практике. Анонимный компонент — это один файл-шаблон без сопровождающего PHP-класса; он идеален, когда вся логика сводится к подстановке props и вёрстке. Как только внутри появляется нетривиальная подготовка данных (например, вычисление вариантов кнопки по статусу заказа или формирование сложного набора классов), переходят к классовому компоненту: его создают командой php artisan make:component Alert, и тогда рядом с шаблоном появляется класс с публичными свойствами и методами, доступными в разметке. Ещё одна важная деталь — именованные слоты. Кроме основного $slot компонент может принимать несколько именованных областей: например, у карточки бывают слоты заголовка и подвала. Их объявляют тегами <x-slot:header> и выводят внутри компонента как переменную. Это позволяет строить богатые, но при этом аккуратные переиспользуемые блоки интерфейса, не превращая компонент в свалку условий.
Итог: Blade-компоненты превращают интерфейс в набор переиспользуемых тегов с props и slots — это современный, чистый способ строить UI. Дальше переходим к работе с базой данных: миграциям и Eloquent.