Начало работы с Ресурсами в конструкторе панелей Filament (Panel Builder)
- Информация о материале
- Родительская категория: Конструктор панелей (Panel Builder)
- Категория: Ресурсы конструктора панелей Filament
- Обзор
- Создание ресурса
- Заголовки записей
- Формы ресурсов
- Таблицы ресурсов
- Авторизация
- Настройка метки модели
- Элементы навигации по ресурсам
- Генерация URL-адресов страниц ресурсов
- Настройка запроса Eloquent к ресурсу
- Настройка URL-адреса ресурса
- Удаление страниц ресурса
Обзор
Ресурсы — это статические классы, которые используются для построения CRUD-интерфейсов для используемых в Eloquent моделей. Они описывают, как администраторы могут взаимодействовать с данными из используемого приложения посредством таблиц и форм.
Создание ресурса
Для создания ресурса для модели App\Models\Customer используется команда Artisan:
php artisan make:filament-resource Customer
В результате в каталоге app/Filament/Resources будет создан ряд файлов:
.
+-- CustomerResource.php
+-- CustomerResource
| +-- Pages
| | +-- CreateCustomer.php
| | +-- EditCustomer.php
| | +-- ListCustomers.php
Новый класс ресурса находится в файле CustomerResource.php.
Классы в каталоге Pages используются для настройки страниц приложения, взаимодействующих с вашим ресурсом. Все они представляют собой полностраничные компоненты Livewire, которые можно настраивать по своему усмотрению.
Был создан ресурс, но он не отображается в навигационном меню? Если у вас используется политика модели, убедитесь, что метод viewAny() возвращает true.
Простые (модальные) ресурсы
Иногда модели достаточно просты, чтобы управлять записями только на одной странице, используя модалы для создания, редактирования и удаления записей. Чтобы сгенерировать простой ресурс с модалами можно использовать следующую команду Artisan:
php artisan make:filament-resource Customer --simple
На вашем ресурсе появится страница "Manage", которая представляет собой страницу List с добавленными модалами.
Кроме этого, у вашего простого ресурса не будет метода getRelations(), поскольку менеджеры связей отображаются только на страницах Edit и View, которые в простых ресурсах отсутствуют. Все остальное остается неизменным.
Автоматическая генерация форм и таблиц
Для экономии времени Filament может автоматически сгенерировать форму и таблицу на основе столбцов базы данных вашей модели, используя команду --generate:
php artisan make:filament-resource Customer --generate
Если ваша таблица содержит ENUM-колонки, то используемый пакет doctrine/dbal не сможет просканировать эту таблицу и завершится с ошибкой. Следовательно, Filament не может сгенерировать схему для вашего ресурса, если он содержит ENUM-столбец. Подробнее об этой проблеме можно прочитать здесь.
Обработка мягкого удаления
По умолчанию взаимодействие с удаленными записями в приложении невозможно. Если вы хотите добавить в свой ресурс функциональность по восстановлению, принудительному удалению и фильтрации удаленных записей, используйте флаг --soft-deletes при генерации ресурса:
php artisan make:filament-resource Customer --soft-deletes
Подробнее о мягком удалении можно узнать здесь.
Создание страницы просмотра
По умолчанию для ресурса генерируются только страницы List (Список), Create (Создание) и Edit (Редактирование). Если нужно также получить страницу View (Просмотр), используйте флаг --view:
php artisan make:filament-resource Customer --view
Заголовки записей
Для ресурса может быть задан атрибут $recordTitleAttribute, который представляет собой название колонки в модели, по которому ее можно идентифицировать среди других.
Например, это может быть название title в блоге или name клиента:
protected static ?string $recordTitleAttribute = 'name';
Это необходимо для работы таких функций, как глобальный поиск.
Если для идентификации записи недостаточно одного столбца, можно указать имя accessor Eloquent.
Формы ресурсов
Классы ресурсов содержат метод form(), который используется для построения форм на страницах Create (Создание) и Edit (Редактирование):
use Filament\Forms;
use Filament\Forms\Form;
public static function form(Form $form): Form
{
return $form
->schema([
Forms\Components\TextInput::make('name')->required(),
Forms\Components\TextInput::make('email')->email()->required(),
// ...
]);
}
Метод schema() используется для определения структуры формы. Он представляет собой массив полей и компонентов макета, расположенных в том порядке, в котором они должны появляться в форме.
Руководство по созданию форм с помощью Filament см. в документации Forms.
Скрытие компонентов с учетом выполняемой операции
Метод hiddenOn() компонентов формы позволяет динамически скрывать поля в зависимости от текущей страницы или действия.
В приведённом ниже примере поле password скрывается на странице edit:
use Livewire\Component;
Forms\Components\TextInput::make('password')
->password()
->required()
->hiddenOn('edit'),
В качестве альтернативы имеется метод быстрого доступа visibleOn(), позволяющий отображать поле только на одной странице или событии:
use Livewire\Component;
Forms\Components\TextInput::make('password')
->password()
->required()
->visibleOn('create'),
Таблицы ресурсов
Классы ресурсов содержат метод table(), который используется для построения таблицы на странице List (Список):
use Filament\Tables;
use Filament\Tables\Table;
use Illuminate\Database\Eloquent\Builder;
public static function table(Table $table): Table
{
return $table
->columns([
Tables\Columns\TextColumn::make('name'),
Tables\Columns\TextColumn::make('email'),
// ...
])
->filters([
Tables\Filters\Filter::make('verified')
->query(fn (Builder $query): Builder => $query->whereNotNull('email_verified_at')),
// ...
])
->actions([
Tables\Actions\EditAction::make(),
])
->bulkActions([
Tables\Actions\BulkActionGroup::make([
Tables\Actions\DeleteBulkAction::make(),
]),
]);
}
Ознакомьтесь с документацией Filament по таблицам, чтобы узнать, как добавить столбцы таблицы, фильтры, действия и многое другое.
Авторизация
Для авторизации Filament будет соблюдать все политики моделей, зарегистрированные в вашем приложении. При этом используются следующие методы:
viewAny()используется для полного скрытия ресурсов из навигационного меню и предотвращает доступ пользователя к любым страницам.create()используется для управления созданием новых записей.update()используется для управления редактированием записи.view()используется для управления просмотром записи.delete()используется для предотвращения удаления одной записи.deleteAny()используется для предотвращения массового удаления записей.- Filament использует метод
deleteAny(), поскольку итерация по нескольким записям и проверка политикиdelete()не очень производительна.
- Filament использует метод
forceDelete()используется для предотвращения принудительного удаления одной мягко удаленной записи.forceDeleteAny()используется для предотвращения массового принудительного удаления записей.- Filament использует метод
forceDeleteAny(), поскольку итерация по нескольким записям и проверка политикиforceDelete()не слишком производительна.
- Filament использует метод
restore()используется для предотвращения восстановления одной мягко удаленной записи.restoreAny()используется для предотвращения массового восстановления записей.- Filament использует метод
restoreAny(), поскольку итерация по нескольким записям и проверка политикиrestore()не слишком производительны.
- Filament использует метод
reorder()используется для управления переупорядочиванием записи.
Отмена авторизации
Если вы хотите пропустить авторизацию для ресурса, то можно установить свойство $shouldSkipAuthorization в true:
protected static bool $shouldSkipAuthorization = true;
Настройка метки модели
Каждый ресурс имеет "метку модели", которая автоматически генерируется из имени модели. Например, модель App\Models\Customer будет иметь метку customer.
Эта метка используется в нескольких частях пользовательского интерфейса, и вы можете настроить ее с помощью свойства $modelLabel:
protected static ?string $modelLabel = 'cliente';
В качестве альтернативы можно использовать функцию getModelLabel() для задания динамической метки:
public static function getModelLabel(): string
{
return __('filament/resources/customer.label');
}
Настройка метки множественного числа модели
Ресурсы также имеют "метку множественного числа модели", которая автоматически генерируется из метки модели. Например, метка customer будет преобразована во множественное число в customers.
Можно настроить множественный вариант метки с помощью свойства $pluralModelLabel:
protected static ?string $pluralModelLabel = 'clientes';
В качестве альтернативы можно задать динамическую метку множественного числа в методе getPluralModelLabel():
public static function getPluralModelLabel(): string
{
return __('filament/resources/customer.plural_label');
}
Элементы навигации по ресурсам
Filament автоматически сгенерирует пункт меню навигации для ресурсов с помощью метки множественного числа.
Если требуется настроить метку пункта навигации, можно воспользоваться свойством $navigationLabel:
protected static ?string $navigationLabel = 'Mis Clientes';
В качестве альтернативы можно задать динамическую навигационную метку в методе getNavigationLabel():
public static function getNavigationLabel(): string
{
return __('filament/resources/customer.navigation_label');
}
Установка иконки для навигации по ресурсам
Свойство $navigationIcon поддерживает имя любого компонента Blade. По умолчанию устанавливаются Heroicons. Однако при желании можно создать свои собственные компоненты иконок или установить альтернативную библиотеку.
protected static ?string $navigationIcon = 'heroicon-o-user-group';
В качестве альтернативы можно задать динамическую навигационную иконку в методе getNavigationIcon():
public static function getNavigationIcon(): ?string
{
return 'heroicon-o-user-group';
}
Сортировка элементов навигации по ресурсам
Свойство $navigationSort позволяет указать порядок, в котором располагаются элементы навигации:
protected static ?int $navigationSort = 2;
В качестве альтернативы можно задать динамический порядок элементов навигации в методе getNavigationSort():
public static function getNavigationSort(): ?int
{
return 2;
}
Группировка элементов навигации по ресурсам
Сгруппировать элементы навигации можно, указав свойство $navigationGroup:
protected static ?string $navigationGroup = 'Shop';
Альтернативный вариант - использовать метод getNavigationGroup() для установки динамической метки группы:
public static function getNavigationGroup(): ?string
{
return __('filament/navigation.groups.shop');
}
Генерация URL-адресов страниц ресурсов
Filament предоставляет статический метод getUrl() для классов ресурсов, позволяющий генерировать URL-адреса ресурсов и определенных страниц внутри них. Традиционно для этого требуется сформировать URL вручную или с помощью помощника Laravel route(), но эти методы зависят от знания slug ресурса или соглашений об именовании маршрутов.
Метод getUrl() без каких-либо аргументов генерирует URL на страницу List (Список) ресурса:
use App\Filament\Resources\CustomerResource;
CustomerResource::getUrl(); // /admin/customers
Можно также генерировать URL-адреса на определенные страницы ресурса. Имя каждой страницы является ключом массива getPages() ресурса. Например, для генерации URL-адреса страницы Create (Создать):
use App\Filament\Resources\CustomerResource;
CustomerResource::getUrl('create'); // /admin/customers/create
Некоторые страницы в методе getPages() используют URL-параметры типа record. Чтобы сгенерировать URL на эти страницы и передать запись, необходимо использовать второй аргумент:
use App\Filament\Resources\CustomerResource;
CustomerResource::getUrl('edit', ['record' => $customer]); // /admin/customers/edit/1
В данном примере $customer может быть объектом модели Eloquent или ID.
Если в приложении имеется несколько панелей, функция getUrl() будет генерировать URL в пределах текущей панели. Можно также указать, с какой панелью связан ресурс, передав ID панели в аргумент panel:
use App\Filament\Resources\CustomerResource; CustomerResource::getUrl(panel: 'marketing');
Настройка запроса Eloquent к ресурсу
В Filament каждый запрос к модели ресурса начинается с метода getEloquentQuery().
Благодаря этому очень легко применять собственные ограничения на запросы или области действия модели, которые влияют на весь ресурс:
public static function getEloquentQuery(): Builder
{
return parent::getEloquentQuery()->where('is_active', true);
}
Отключение глобальных возможностей
По умолчанию Filament будет отслеживать все глобальные диапазоны, зарегистрированные в вашей модели. Однако это может быть не совсем удобно, если вы хотите получить доступ, например, к мягким удаленным записям.
Чтобы решить эту проблему, можно переопределить метод getEloquentQuery(), который использует Filament:
public static function getEloquentQuery(): Builder
{
return parent::getEloquentQuery()->withoutGlobalScopes();
}
В качестве альтернативы можно удалить определенные глобальные диапазоны:
public static function getEloquentQuery(): Builder
{
return parent::getEloquentQuery()->withoutGlobalScopes([ActiveScope::class]);
}
Более подробную информацию об удалении глобальных областей видимости можно найти в документации Laravel.
Настройка URL-адреса ресурса
По умолчанию Filament генерирует URL на основе имени ресурса. Это можно настроить, задав свойство $slug для ресурса:
protected static ?string $slug = 'pending-orders';
Удаление страниц ресурса
Если требуется удалить страницу из ресурса, достаточно удалить файл страницы из каталога Pages ресурса и запись о ней в методе getPages().
Например, у вас может быть ресурс с записями, которые не могут быть никем созданы. Удалите файл страницы Create, а затем удалите его из метода getPages():
public static function getPages(): array
{
return [
'index' => Pages\ListCustomers::route('/'),
'edit' => Pages\EditCustomer::route('/{record}/edit'),
];
}
Удаление страницы не приведет к удалению действий, связанных с этой страницей. Любые действия будут открывать модальное окно, а не отправлять пользователя на несуществующую страницу. Например, действие CreateAction на странице List, действие EditAction на странице Table или View, действие ViewAction на странице Table или Edit. Если вы хотите удалить эти кнопки, необходимо удалить и действия.
Перевод с английского официальной документации Filament 3:https://filamentphp.com/docs/3.x/panels/resources/getting-started
Как установить phpMyAdmin в Docker для работы с Laravel
- Информация о материале
- Родительская категория: Программы для работы с хостингом
- Категория: phpMyAdmin
- Постановка задачи об установке phpMyAdmin в Docker под WSL
- Установка phpMyAdmin в Docker для работы с Laravel
- Проверка работы phpMyAdmin в Docker с Laravel Sail.
Постановка задачи об установке phpMyAdmin в Docker под WSL
Имеем:
- Установленную WSL2 на Windows.
- Установленный и настроенный для работы с WSL Docker.
- Установленный и запускающийся с помощью Sail Laravel.
Требуется:
- Установить phpMyAdmin так, чтобы он открывался при запуске Laravel Sail.
Установка phpMyAdmin в Docker для работы с Laravel
1. Находим файл docker-compose.yml в папке проекта.
2. В блоке services в самом его конце находим запись:
selenium:
image: selenium/standalone-chrome
extra_hosts:
- 'host.docker.internal:host-gateway'
volumes:
- '/dev/shm:/dev/shm'
networks:
- sail
3. Сразу после неё добавляем запись:
phpmyadmin:
depends_on:
- mysql
image: phpmyadmin/phpmyadmin
environment:
- PMA_HOST=mysql
- PMA_PORT=3306
networks:
- sail
ports:
- 8050:80
4. Для проверки: После этого следует блок:
networks:
sail:
driver: bridge
Проверка работы phpMyAdmin в Docker с Laravel Sail
После этого нужно либо перезапустить Docker, остановив Laravel Sail в Терминале Windows Ctrl+C, либо командой:
./vendor/bin/sail stop
если Laravel Sail был запущен в фоновом режиме.
Теперь нужно запустить заново Laravel Sail для загрузки Docker с новой конфигурацией. Запуск в фоновом режиме:
./vendor/bin/sail up -d
При первом запуске будет загружен и распакован пакет Docker с phpMyAdmin. При последующих запусках всё будет проходить быстрее и безболезненней. =)
Ну и в браузере при запущенном Laravel Sail будет открываться по адресу:
http://localhost:8050/
Порт при желании можно поменять в конфиге Docker.
Логин и пароль можно посмотреть в файле проекта .env в корне проекта. Обычно это:
DB_USERNAME=sail
DB_PASSWORD=password
Всё! Радуемся и идём пить пиво... или продолжаем работу над проектом. =D
Аутентификация
- Информация о материале
- Родительская категория: Полное руководство по Yii 2.0
- Категория: Безопасность
- Что такое аутентификация
- Аутентификация во фреймворке Yii
- Настройка [[yii\web\User]]
- Реализация [[yii\web\IdentityInterface]]
- Использование [[yii\web\User]]
- События аутентификации
Что такое аутентификация
Аутентификация — это процесс проверки подлинности пользователя. Обычно используется идентификатор (например, username или адрес электронной почты) и секретный токен (например, пароль или ключ доступа), чтобы судить о том, что пользователь именно тот, за кого себя выдаёт. Аутентификация является основной функцией формы входа.
Аутентификация во фреймворке Yii
Yii предоставляет фреймворк авторизации с различными компонентами, обеспечивающими процесс входа. Для использования этого фреймворка вам нужно проделать следующее:
- Настроить компонент приложения [[yii\web\User|user]];
- Создать класс, реализующий интерфейс [[yii\web\IdentityInterface]].
Настройка [[yii\web\User]]
Компонент [[yii\web\User|user]] управляет статусом аутентификации пользователя. Он требует, чтобы вы указали [[yii\web\User::identityClass|identity class]], который будет содержать текущую логику аутентификации. В следующей конфигурации приложения, [[yii\web\User::identityClass|identity class]] для [[yii\web\User|user]] задан как app\models\User, реализация которого будет объяснена в следующем разделе:
return [
'components' => [
'user' => [
'identityClass' => 'app\models\User',
],
],
];
Реализация [[yii\web\IdentityInterface]]
[[yii\web\User::identityClass|identity class]] должен реализовывать [[yii\web\IdentityInterface]], который содержит следующие методы:
- [[yii\web\IdentityInterface::findIdentity()|findIdentity()]]: Этот метод находит экземпляр
identity class, используя ID пользователя. Этот метод используется, когда необходимо поддерживать состояние аутентификации через сессии. - [[yii\web\IdentityInterface::findIdentityByAccessToken()|findIdentityByAccessToken()]]: Этот метод находит экземпляр
identity class, используя токен доступа. Метод используется, когда требуется аутентифицировать пользователя только по секретному токену (например в RESTful приложениях, не сохраняющих состояние между запросами). - [[yii\web\IdentityInterface::getId()|getId()]]: Этот метод возвращает ID пользователя, представленного данным экземпляром
identity. - [[yii\web\IdentityInterface::getAuthKey()|getAuthKey()]]: Этот метод возвращает ключ, используемый для основанной на
cookieаутентификации. Ключ сохраняется в аутентификационной cookie и позже сравнивается с версией, находящейся на сервере, чтобы удостоверится, что аутентификационнаяcookieверная. - [[yii\web\IdentityInterface::validateAuthKey()|validateAuthKey()]]: Этот метод реализует логику проверки ключа для основанной на
cookieаутентификации.
Если какой-то из методов не требуется, то можно реализовать его с пустым телом. Для примера, если у вас RESTful приложение, не сохраняющее состояние между запросами, вы можете реализовать только [[yii\web\IdentityInterface::findIdentityByAccessToken()|findIdentityByAccessToken()]] и [[yii\web\IdentityInterface::getId()|getId()]], тогда как остальные методы оставить пустыми.
В следующем примере, [[yii\web\User::identityClass|identity class]] реализован как класс Active Record, связанный с таблицей user.
<?php
use yii\db\ActiveRecord;
use yii\web\IdentityInterface;
class User extends ActiveRecord implements IdentityInterface
{
public static function tableName()
{
return 'user';
}
/**
* Finds an identity by the given ID.
*
* @param string|int $id the ID to be looked for
* @return IdentityInterface|null the identity object that matches the given ID.
*/
public static function findIdentity($id)
{
return static::findOne($id);
}
/**
* Finds an identity by the given token.
*
* @param string $token the token to be looked for
* @return IdentityInterface|null the identity object that matches the given token.
*/
public static function findIdentityByAccessToken($token, $type = null)
{
return static::findOne(['access_token' => $token]);
}
/**
* @return int|string current user ID
*/
public function getId()
{
return $this->id;
}
/**
* @return string current user auth key
*/
public function getAuthKey()
{
return $this->auth_key;
}
/**
* @param string $authKey
* @return bool if auth key is valid for current user
*/
public function validateAuthKey($authKey)
{
return $this->getAuthKey() === $authKey;
}
}
Как объяснялось ранее, вам нужно реализовать только getAuthKey() и validateAuthKey(), если ваше приложение использует только аутентификацию основанную на cookie. В этом случае вы можете использовать следующий код для генерации ключа аутентификации для каждого пользователя и хранения его в таблице user:
class User extends ActiveRecord implements IdentityInterface
{
......
public function beforeSave($insert)
{
if (parent::beforeSave($insert)) {
if ($this->isNewRecord) {
$this->auth_key = \Yii::$app->security->generateRandomString();
}
return true;
}
return false;
}
}
Note: Не путайте
identityклассUserс классом [[yii\web\User]]. Первый является классом, реализующим логику аутентификации пользователя. Он часто реализуется как класс Active Record, связанный с некоторым постоянным хранилищем, где лежит информация о пользователях. Второй — это класс компонента приложения, отвечающий за управление состоянием аутентификации пользователя.
Использование [[yii\web\User]]
В основном класс [[yii\web\User]] используют как компонент приложения user.
Можно получить identity текущего пользователя, используя выражение Yii::$app->user->identity. Оно вернёт экземпляр [[yii\web\User::identityClass|identity class]], представляющий текущего аутентифицированного пользователя, или null, если текущий пользователь не аутентифицирован (например, гость). Следующий код показывает, как получить другую связанную с аутентификацией информацию из [[yii\web\User]]:
// `identity` текущего пользователя. `Null`, если пользователь не аутентифицирован.
$identity = Yii::$app->user->identity;
// ID текущего пользователя. `Null`, если пользователь не аутентифицирован.
$id = Yii::$app->user->id;
// проверка на то, что текущий пользователь гость (не аутентифицирован)
$isGuest = Yii::$app->user->isGuest;
Для залогинивания пользователя вы можете использовать следующий код:
// найти identity с указанным username.
// замечание: также вы можете проверить и пароль, если это нужно
$identity = User::findOne(['username' => $username]);
// логиним пользователя
Yii::$app->user->login($identity);
Метод [[yii\web\User::login()]] устанавливает identity текущего пользователя в [[yii\web\User]]. Если сессии [[yii\web\User::enableSession|включены]], то identity будет сохраняться в сессии, так что состояние статуса аутентификации будет поддерживаться на всём протяжении сессии. Если [[yii\web\User::enableAutoLogin|включен]] вход, основанный на cookie (так называемый "запомни меня" вход), то identity также будет сохранена в cookie так, чтобы статус аутентификации пользователя мог быть восстановлен на протяжении всего времени жизни cookie.
Для включения входа, основанного на cookie, вам нужно установить [[yii\web\User::enableAutoLogin]] в true в конфигурации приложения. Вы также можете настроить время жизни, передав его при вызове метода [[yii\web\User::login()]].
Для выхода пользователя, просто вызовите
Yii::$app->user->logout();
Обратите внимание: выход пользователя имеет смысл только если сессии включены. Метод сбрасывает статус аутентификации сразу и из памяти и из сессии. И по умолчанию, будут также уничтожены все сессионные данные пользователя. Если вы хотите сохранить сессионные данные, вы должны вместо этого вызвать Yii::$app->user->logout(false).
События аутентификации
Класс [[yii\web\User]] вызывает несколько событий во время процессов входа и выхода.
- [[yii\web\User::EVENT_BEFORE_LOGIN|EVENT_BEFORE_LOGIN]]: вызывается перед вызовом [[yii\web\User::login()]]. Если обработчик устанавливает свойство [[yii\web\UserEvent::isValid|isValid]] объекта в
false, процесс входа будет прерван. - [[yii\web\User::EVENT_AFTER_LOGIN|EVENT_AFTER_LOGIN]]: вызывается после успешного входа.
- [[yii\web\User::EVENT_BEFORE_LOGOUT|EVENT_BEFORE_LOGOUT]]: вызывается перед вызовом [[yii\web\User::logout()]]. Если обработчик устанавливает свойство [[yii\web\UserEvent::isValid|isValid]] объекта в
false, процесс выхода будет прерван. - [[yii\web\User::EVENT_AFTER_LOGOUT|EVENT_AFTER_LOGOUT]]: вызывается после успешного выхода.
Вы можете использовать эти события для реализации функции аудита входа, сбора статистики онлайн пользователей. Например, в обработчике для [[yii\web\User::EVENT_AFTER_LOGIN|EVENT_AFTER_LOGIN]] вы можете сделать запись о времени и IP адресе входа в таблицу user.
Html-помощник
- Информация о материале
- Родительская категория: Полное руководство по Yii 2.0
- Категория: Хелперы
Html-помощник
Каждое веб-приложение формирует большое количество HTML-разметки. Если разметка статическая, её можно эффективно сформировать смешиванием PHP и HTML в одном файле, но когда разметка динамическая, становится сложно формировать её без дополнительной помощи. Yii предоставляет такую помощь в виде Html-помощника, который обеспечивает набор статических методов для обработки часто-используемых HTML тэгов, их атрибутов и содержимого.
Note: Если ваша разметка близка к статической, лучше использовать непосредственно HTML. Нет никакой необходимости в том, чтобы всё подряд оборачивать вызовами Html-помощника.
Основы
Так как формирование динамической HTML-разметки при помощи конкатенации строк очень быстро вносит хаос в проект, Yii предоставляет набор методов для управления атрибутами тэгов и формирования тэгов на основе этих атрибутов.
Формирование тэгов
Код формирования тэга выглядит следующим образом:
<?= Html::tag('p', Html::encode($user->name), ['class' => 'username']) ?>
Здесь первый аргумент - это название тэга. Второй - содержимое, которое будет заключено между открывающим и закрывающим тэгами. Заметьте, что мы используем Html::encode. Это связано с тем, что содержимое не экранируется автоматически, чтобы можно было по-необходимости использовать чистый HTML. Третий аргумент - это массив настроек для HTML-кода, а другими словами - массив атрибутов для тэга. В этом массиве ключи являются названиями атрибутов, например class, href или target, а значения в массиве являются значениями этих атрибутов.
Вышеприведённый код сформирует следующую HTML-разметку:
<p class="username">samdark</p>
В тех случаях, когда вам необходимо только закрыть или открыть тэг, можно использовать методы Html::beginTag() и Html::endTag().
Дополнительные атрибуты используются во многих методах Html-помощника и в различных виджетах. Во всех этих случаях в дело вступают механизмы дополнительной обработки данных, о которых следует знать:
-
Если значение равно
null, соответствующий атрибут не будет выведен. -
Атрибуты, значения которых имеют тип boolean, будут интерпретированы как логические атрибуты.
-
Значения атрибутов будут экранированы с использованием метода [[yii\helpers\Html::encode()|Html::encode()]].
-
Если в качестве значения атрибута передан массив, он будет обработан следующим образом:
-
Если атрибут является одним из атрибутов данных, указанных в [[yii\helpers\Html::$dataAttributes]], например
dataилиng, то будет сформирован список атрибутов по одному для каждого элемента массива. Например, код'data' => ['id' => 1, 'name' => 'yii']сформируетdata-id="1" data-name="yii"; а код'data' => ['params' => ['id' => 1, 'name' => 'yii'], 'status' => 'ok']сформируетdata-params='{"id":1,"name":"yii"}' data-status="ok". Заметьте, что в последнем примере используется формат JSON для формирования вывода вложенного массива. -
Если атрибут НЕ является атрибутом данных, значение будет сконвертировано в формат JSON. Например, код
['params' => ['id' => 1, 'name' => 'yii']сформируетparams='{"id":1,"name":"yii"}'.
-
Формирование CSS классов и стилей
При формировании атрибутов для HTML-тэгов часто приходится начинать с некоторых атрибутов по умолчанию, которые затем необходимо изменять. Для того, чтобы добавить или удалить CSS-класс, можно использовать следующий подход:
$options = ['class' => 'btn btn-default'];
if ($type === 'success') {
Html::removeCssClass($options, 'btn-default');
Html::addCssClass($options, 'btn-success');
}
echo Html::tag('div', 'Всё получилось!', $options);
// в случае, если $type содержит строку 'success', будет сформирован вывод
// <div class="btn btn-success">Всё получилось!</div>
Можно указать несколько CSS-классов, используя синтаксис массива:
$options = ['class' => ['btn', 'btn-default']];
echo Html::tag('div', 'Сохранить', $options);
// выведет '<div class="btn btn-default">Сохранить</div>'
При добавлении или удалении классов тоже можно использовать массивы:
$options = ['class' => 'btn'];
if ($type === 'success') {
Html::addCssClass($options, ['btn-success', 'btn-lg']);
}
echo Html::tag('div', 'Сохранить', $options);
// выведет '<div class="btn btn-success btn-lg">Сохранить</div>'
Html::addCssClass() предотвращает дублирование классов, поэтому можно не беспокоиться о том, что какой-либо класс будет добавлен дважды:
$options = ['class' => 'btn btn-default'];
Html::addCssClass($options, 'btn-default'); // класс 'btn-default' уже добавлен
echo Html::tag('div', 'Сохранить', $options);
// выведет '<div class="btn btn-default">Сохранить</div>'
Если CSS-класс задаётся с помощью массива, можно использовать именованные ключи массива для обозначения логического предназначения класса. В этом случае класс с таким же ключом будет проигнорирован во время использования Html::addCssClass():
$options = [
'class' => [
'btn',
'theme' => 'btn-default',
]
];
Html::addCssClass($options, ['theme' => 'btn-success']); // ключ 'theme' уже использован
echo Html::tag('div', 'Сохранить', $options);
// отобразит '<div class="btn btn-default">Сохранить</div>'
CSS-стили могут быть установлены схожим образом с помощью атрибута style:
$options = ['style' => ['width' => '100px', 'height' => '100px']];
// в результате будет style="width: 100px; height: 200px; position: absolute;"
Html::addCssStyle($options, 'height: 200px; position: absolute;');
// в результате будет style="position: absolute;"
Html::removeCssStyle($options, ['width', 'height']);
При использовании метода [[yii\helpers\Html::addCssStyle()|addCssStyle()]] можно указать массив, пары ключ-значение которого соответствуют названиям и значениям CSS-свойств, или строку, например width: 100px; height: 200px;. Эти два формата могут быть преобразованы друг в друга с помощью методов [[yii\helpers\Html::cssStyleFromArray()|cssStyleFromArray()]] и [[yii\helpers\Html::cssStyleToArray()|cssStyleToArray()]]. Метод [[yii\helpers\Html::removeCssStyle()|removeCssStyle()]] принимает на вход массив атрибутов, которые следует удалить. Если удаляется всего один атрибут, его можно передать строкой.
Экранирование контента
Для корректного и безопасного отображения контента специальные символы в HTML-коде должны быть экранированы. В чистом PHP это осуществляется с помощью функций htmlspecialchars и htmlspecialchars_decode. Проблема использования этих функций заключается в том, что приходится указывать кодировку и дополнительные флаги во время каждого вызова. Поскольку флаги всё время одинаковы, а кодировка остаётся одной и той же в пределах приложения, Yii в целях безопасности предоставляет два компактных и простых в использовании метода:
$userName = Html::encode($user->name);
echo $userName;
$decodedUserName = Html::decode($userName);
Формы
Разметка форм состоит из повторяющихся действий и часто приводит к ошибкам, поэтому есть целый набор методов, которые помогают справиться с этой задачей.
Note: Рассмотрите возможность использования [[yii\widgets\ActiveForm|ActiveForm]], если работаете с моделями и нуждаетесь в валидации данных.
Создание форм
Открывающий тэг формы может быть выведен с помощью метода [[yii\helpers\Html::beginForm()|beginForm()]] как показано ниже:
<?= Html::beginForm(['order/update', 'id' => $id], 'post', ['enctype' => 'multipart/form-data']) ?>
Первый аргумент - это URL-адрес, на который будет отправлена форма. Он может быть задан в виде Yii-маршрута и параметров, подходящих для передачи в метод [[yii\helpers\Url::to()|Url::to()]]. Второй аргумент - способ отправки данных: по умолчанию это post. Третий аргумент - массив атрибутов формы. В данном примере мы изменяем способ кодирования данных в POST-запросе на multipart/form-data. Это необходимо для загрузки файлов.
Закрыть тэг формы можно простым кодом:
<?= Html::endForm() ?>
Кнопки
Для формирования кнопок можно использовать следующий код:
<?= Html::button('Нажми меня!', ['class' => 'teaser']) ?>
<?= Html::submitButton('Отправить', ['class' => 'submit']) ?>
<?= Html::resetButton('Сбросить', ['class' => 'reset']) ?>
Первый аргумент во всех трёх методах - это название кнопки, а второй - её атрибуты. Название кнопки не экранируется, поэтому при получении данных от конечных пользователей экранируйте их с помощью метода [[yii\helpers\Html::encode()|Html::encode()]].
Поля ввода
Методы формирования полей ввода делятся на две группы. Первые начинаются со слова active и называются "active inputs", а вторые не содержат в своём названии слова active. "Active inputs" формируют поля ввода, которые получают данные из указанного атрибута модели, в то время как обычные методы формирования полей ввода непосредственно принимают данные.
Наиболее общие методы для формирования полей ввода:
// тип, название поля ввода, установленное в поле значение, атрибуты поля ввода
<?= Html::input('text', 'username', $user->name, ['class' => $username]) ?>
// тип, модель, атрибут модели, атрибуты поля ввода
<?= Html::activeInput('text', $user, 'name', ['class' => $username]) ?>
Если вам заранее известен тип поля ввода, удобнее будет пользоваться этими вспомогательными методами:
- [[yii\helpers\Html::buttonInput()]]
- [[yii\helpers\Html::submitInput()]]
- [[yii\helpers\Html::resetInput()]]
- [[yii\helpers\Html::textInput()]], [[yii\helpers\Html::activeTextInput()]]
- [[yii\helpers\Html::hiddenInput()]], [[yii\helpers\Html::activeHiddenInput()]]
- [[yii\helpers\Html::passwordInput()]] / [[yii\helpers\Html::activePasswordInput()]]
- [[yii\helpers\Html::fileInput()]], [[yii\helpers\Html::activeFileInput()]]
- [[yii\helpers\Html::textarea()]], [[yii\helpers\Html::activeTextarea()]]
Сигнатура методов для формирования радио-переключателей и чекбоксов немного отличается:
<?= Html::radio('agree', true, ['label' => 'Я согласен']) ?>
<?= Html::activeRadio($model, 'agree', ['class' => 'agreement']) ?>
<?= Html::checkbox('agree', true, ['label' => 'Я согласен']) ?>
<?= Html::activeCheckbox($model, 'agree', ['class' => 'agreement']) ?>
Выпадающие и обычные списки могут быть сформированы следующим образом:
<?= Html::dropDownList('list', $currentUserId, ArrayHelper::map($userModels, 'id', 'name')) ?>
<?= Html::activeDropDownList($users, 'id', ArrayHelper::map($userModels, 'id', 'name')) ?>
<?= Html::listBox('list', $currentUserId, ArrayHelper::map($userModels, 'id', 'name')) ?>
<?= Html::activeListBox($users, 'id', ArrayHelper::map($userModels, 'id', 'name')) ?>
Первый аргумент - это значение атрибута name для поля ввода, второй - выбранное в нём значение и, наконец, третий аргумент - это массив, ключами которого является список значений для формирования списка, а значениями массива являются названия пунктов в нём.
Если вы хотите сделать в списке доступными для выбора несколько вариантов, хорошим выбором будет список чекбоксов:
<?= Html::checkboxList('roles', [16, 42], ArrayHelper::map($roleModels, 'id', 'name')) ?>
<?= Html::activeCheckboxList($user, 'role', ArrayHelper::map($roleModels, 'id', 'name')) ?>
Если же нет, используйте радио-переключатель:
<?= Html::radioList('roles', [16, 42], ArrayHelper::map($roleModels, 'id', 'name')) ?>
<?= Html::activeRadioList($user, 'role', ArrayHelper::map($roleModels, 'id', 'name')) ?>
Тэги label и отображение ошибок
Также как и для полей ввода, есть два метода формирования тэгов label для форм. Есть "active label", считывающий данные из модели и обычный тэг "label", принимающий на вход непосредственно сами данные:
<?= Html::label('Имя пользователя', 'username', ['class' => 'label username']) ?>
<?= Html::activeLabel($user, 'username', ['class' => 'label username'])
Для отображения общего списка ошибок формы на основе модели или моделей можно использовать следующий подход:
<?= Html::errorSummary($posts, ['class' => 'errors']) ?>
Для отображения одной отдельной ошибки:
<?= Html::error($post, 'title', ['class' => 'error']) ?>
Атрибуты name и value для полей ввода
Также имеются методы для получения значений атрибутов id, name и value для полей ввода, сформированных на основе моделей. Эти методы используются в основном внутренними механизмами, но иногда могут оказаться подходящими и для прямого использования:
// Post[title]
echo Html::getInputName($post, 'title');
// post-title
echo Html::getInputId($post, 'title');
// моё первое сообщение
echo Html::getAttributeValue($post, 'title');
// $post->authors[0]
echo Html::getAttributeValue($post, '[0]authors[0]');
В вышеприведённом коде первый аргумент - это модель, а второй аргумент - выражение для поиска атрибута модели. В самом простом случае оно представляет собой название атрибута модели, а вообще это может быть название, которому предшествует (и/или после которого следует) индекс массива. Такой формат используется в основном для табличного ввода данных:
[0]contentиспользуется для табличного ввода данных, чтобы указать на атрибут "content" первой модели табличного ввода;dates[0]указывает на первый элемент массива, с помощью которого задан атрибут модели "dates";[0]dates[0]указывает на первый элемент массива, с помощью которого задан атрибут "dates" первой модели табличного ввода.
Для того, чтобы получить название атрибута модели в чистом виде (без суффиксов и префиксов), можно использовать следующий подход:
// dates
echo Html::getAttributeName('dates[0]');
Подключение встроенных стилей и скриптов
Для формирования встроенных скриптов и стилей есть два метода:
<?= Html::style('.danger { color: #f00; }') ?>
Результатом будет:
<style>.danger { color: #f00; }</style>
<?= Html::script('alert("Привет!");', ['defer' => true]) ?>
Результатом будет:
<script defer>alert("Привет!");</script>
Если вы хотите подключить внешний CSS-файл:
<?= Html::cssFile('@web/css/ie5.css', ['condition' => 'IE 5']) ?>
В результате получится:
<!--[if IE 5]>
<link href="http://example.com/css/ie5.css" />
<![endif]-->
Первый аргумент - URL-адрес. Второй - массив настроек. Помимо обычных настроек можно указать следующие:
conditionдля оборачивания тэга<linkс помощью условных комментариев с определённым условием. Надеемся, что вам никогда не понадобятся условные комментарии ;)noscriptможет быть установлен в значениеtrue, чтобы обернуть тэг<linkс помощью тэга<noscript>, таким образом скрипт будет подключён только в том случае, если у пользователя в браузере нет поддержки JavaScript или же пользователь сам отключил его.
Для подключения JavaScript-файла используйте код:
<?= Html::jsFile('@web/js/main.js') ?>
Как и в случае с CSS, первый аргумент указывает ссылку на файл, который должен быть подключен. Настройки задаются во втором аргументе. Можно указать настройку condition таким же образом, каким она указывается для метода cssFile.
Ссылки
Существует удобный метод формирования ссылок:
<?= Html::a('Профиль', ['user/view', 'id' => $id], ['class' => 'profile-link']) ?>
Первый аргумент - это текст ссылки. Он не экранируется, поэтому при использовании данных, полученных от конечных пользователей, необходимо экранировать его с помощью Html::encode(). Второй аргумент - это содержимое атрибута href тэга <a. Смотрите Url::to() для получения подробностей относительно значений, которые могут быть переданы в качестве второго аргумента. Третий аргумент - массив атрибутов для тэга.
Если нужно сформировать ссылку mailto, можно использовать следующий подход:
<?= Html::mailto('Обратная связь', 'admin@example.com') ?>
Изображения
Для формирования тэга изображения используйте следующий код:
<?= Html::img('@web/images/logo.png', ['alt' => 'Наш логотип']) ?>
в результате получится:
<img src="http://example.com/images/logo.png" alt="Наш логотип" />
Помимо псевдонимов первый аргумент может принимать маршруты, параметры и URL-адреса таким же образом как и метод Url::to().
Списки
Неупорядоченные списки могут быть сформированы следующим образом:
<?= Html::ul($posts, ['item' => function($item, $index) {
return Html::tag(
'li',
$this->render('post', ['item' => $item]),
['class' => 'post']
);
}]) ?>
Для формирования упорядоченных списков используйте Html::ol().
Helix Ultimate v2.0.14 с поддержкой последней версии SP Page Builder 5 Lite и многое другое
- Информация о материале
- Родительская категория: JoomShaper
- Категория: Helix Ultimate
- Время очередного обновления Helix Ultimate
- Список изменений Helix Ultimate v2.0.14
- Пакет Quickstart Pack поставляется вместе с SP Page Builder 5.x Lite
- Основные исправления в новом Helix Ultimate v2.0.14
- Обновляйте Helix Ultimate до последней версии прямо сейчас.
Время очередного обновления Helix Ultimate
Пришло время очередного обновления Helix Ultimate, которое, несомненно, внесет оживление в вашу жизнь и создание сайтов на Joomla. В этом выпуске исправлены некоторые нежелательные ошибки, а также добавлено важное обновление, обеспечивающее совместимость Helix Ultimate с последней версией SP Page Builder 5.x Lite.
Так давайте же окунемся в эту тему, чтобы узнать больше!
Список изменений Helix Ultimate v2.0.14.
- Обновление:
- Пакет QuickStart Pack был обновлен до последней версии SP Page Builder 5.0 (Lite).
- Исправления:
- Исправлена проблема дублирования
<li>, вызванная переопределением списка пагинации. - Проблема с загрузкой изображений из Blog Media, когда расширение имени изображения написано с заглавной буквы.
- Исправлена проблема с работой JavaScript при загрузке изображений в медиагалерее.
- Исправлена проблема с веб-аутентификацией во фронтенде.
- Исправлена проблема дублирования
Пакет Quickstart Pack поставляется вместе с SP Page Builder 5.x Lite
После данного обновления Helix Ultimate будет продолжать использовать последние версии SP Page Builder 5.x (Lite-версия) вместе с пакетом Quickstart. Теперь можно воспользоваться преимуществами мощного SP Page Builder 5 и его мощными функциями и улучшить качество работы с Helix Ultimate.
Основные исправления в новом Helix Ultimate v2.0.14.
Самое время обратить внимание на некоторые важные исправления, которые входят в состав этого обновления!
Если в админке была включена веб-аутентификация, то кнопка "Веб-аутентификация" не отображалась в области входа во фронтенд Helix Ultimate. Теперь эта проблема решена, и после обновления пользователь сможет беспрепятственно входить в систему.

Ранее, если расширения имен файлов изображений, таких как .PNG, .JPG, .GIF и т.д., были в верхнем регистре, возникала проблема с загрузкой изображения в раздел "Медиафайлы блога" статьи Joomla. Эта проблема затрагивала как варианты "Галерея", так и "Стандарт". В настоящее время эта проблема успешно решена.
Обновляйте Helix Ultimate до последней версии прямо сейчас
Пожалуйста, просмотрите еще раз журнал изменений, чтобы ознакомиться с полным списком исправлений и улучшений, внесенных в это обновление.
Обновите свой Helix Ultimate до этой последней версии прямо сейчас, чтобы иметь возможность пользоваться новыми возможностями! Также не забудьте сообщить всем о своих впечатлениях в социальных сетях и мессенджерах, поделившись ссылкой на эту потрясающую новость. Счастливого всем самосовершенствования!
Перевод с английского официальных новостей Helix Ultimate от JoomShaper:
https://www.joomshaper.com/blog/helix-ultimate-v2-0-14
Установка Livewire 3
- Информация о материале
- Родительская категория: Документация Livewire 3
- Категория: Начало работы
- Livewire - это пакет расширения Laravel
- Размещение конфигурационного файла Livewire
- Ручное включение ресурсов фронтенда Livewire
- Настройка endpoint обновления Livewire
- Настройка URL-адреса ресурсов Livewire
- Ручная привязка Livewire и Alpine
Livewire - это пакет расширения Laravel
Livewire - это пакет Laravel, поэтому перед установкой и использованием Livewire необходимо иметь запущенное приложение Laravel. Если требуется помощь в настройке нового приложения Laravel, смотрите документацию по установке Laravel.
Чтобы установить Livewire, откройте терминал и перейдите в каталог приложения Laravel, затем выполните следующую команду:
composer require livewire/livewire
Вот, собственно, и все. Если требуется больше возможностей для настройки, продолжайте читать. В противном случае можно сразу приступать к использованию Livewire.
Размещение конфигурационного файла Livewire
Livewire имеет " zero-config", то есть его можно использовать, следуя соглашениям, без какой-либо дополнительной настройки. Однако при необходимости можно опубликовать и настроить конфигурационный файл Livewire, выполнив следующую команду Artisan:
php artisan livewire:publish --config
Это создаст новый файл livewire.php в каталоге config вашего приложения Laravel.
Ручное включение ресурсов фронтенда Livewire
По умолчанию Livewire внедряет необходимые ему JavaScript- и CSS-активы в каждую созданную страницу, включающую компонент Livewire.
Если требуется больший контроль над этим поведением, можно вручную включить активы на страницу с помощью следующих директив Blade:
<html>
<head>
...
@livewireStyles
</head>
<body>
...
@livewireScripts
</body>
</html>
Включая эти активы на страницу вручную, Livewire тем самым определяет, что не нужно внедрять их автоматически.
AlpineJS поставляется в комплекте с Livewire
Поскольку Alpine поставляется в комплекте с JavaScript-активами Livewire, необходимо включать
@livewireScriptsна каждой странице, где будет использоваться Alpine. Даже если вы не будете использовать Livewire на этой странице.
Хотя это требуется редко, можно отключить автоматическую вставку активов в Livewire, изменив параметр inject_assets в файле конфигурации config/livewire.php вашего приложения:
'inject_assets' => false,
Если требуется принудительно внедрить активы Livewire на одну или несколько страниц, можно вызвать следующий глобальный метод из текущего маршрута или из провайдера услуг.
\Livewire\Livewire::forceAssetInjection();
Настройка endpoint обновления Livewire
Каждое обновление компонента Livewire отправляет сетевой запрос на сервер по следующей конечной точке: https://example.com/livewire/update.
Это может быть проблемой для некоторых приложений, использующих локализацию или многопользовательский режим.
В таких случаях можно зарегистрировать собственную конечную точку по своему усмотрению, и если это сделать внутри Livewire::setUpdateRoute(), то Livewire будет знать, что для всех обновлений компонента нужно использовать именно эту конечную точку:
Livewire::setUpdateRoute(function ($handle) {
return Route::post('/custom/livewire/update', $handle);
});
Теперь вместо /livewire/update Livewire будет отправлять обновления компонентов по адресу /custom/livewire/update.
Поскольку Livewire позволяет зарегистрировать собственный маршрут обновления, то можно объявить любой дополнительный middleware, который будет использоваться Livewire, непосредственно в setUpdateRoute():
Livewire::setUpdateRoute(function ($handle) {
return Route::post('/custom/livewire/update', $handle)
->middleware([...]);
});
Настройка URL-адреса ресурсов Livewire
По умолчанию Livewire предоставляет свои JavaScript-активы по следующему URL: https://example.com/livewire/livewire.js. Кроме того, Livewire будет ссылаться на этот актив в теге script следующим образом:
<script src="/livewire/livewire.js" ...
Если ваше приложение имеет глобальные префиксы маршрутов в связи с локализацией или многопользовательским доступом, то можно зарегистрировать собственную конечную точку, которую Livewire должен использовать внутри приложения при получении JavaScript.
Чтобы использовать пользовательскую конечную точку JavaScript-актива, можно зарегистрировать собственный маршрут внутри Livewire::setScriptRoute():
Livewire::setScriptRoute(function ($handle) {
return Route::get('/custom/livewire/livewire.js', $handle);
});
И теперь Livewire загрузит свой JavaScript следующим образом:
<script src="/custom/livewire/livewire.js" ...
Ручная привязка Livewire и Alpine
По умолчанию Alpine и Livewire загружаются с помощью тега <script src="/livewire.js">, то есть нельзя контролировать порядок загрузки этих библиотек. Следовательно, импорт и регистрация плагинов Alpine, как показано в примере ниже, больше не будут работать:
// Внимание: Этот фрагмент демонстрирует, что НЕ нужно делать...
import Alpine from 'alpinejs'
import Clipboard from '@ryangjchandler/alpine-clipboard'
Alpine.plugin(Clipboard)
Alpine.start()
Для решения этой проблемы необходимо сообщить Livewire, что в дальнейшем будет использоваться версия модуля ESM (ECMAScript), и предотвратить внедрение тега <script src="/livewire.js">. Для этого необходимо добавить директиву @livewireScriptConfig в файл макета (resources/views/components/layouts/app.blade.php):
<html>
<head>
<!-- ... -->
@livewireStyles
@vite(['resources/js/app.js'])
</head>
<body>
{{ $slot }}
@livewireScriptConfig
</body>
</html>
Когда Livewire обнаружит директиву @livewireScriptConfig, то воздержится от внедрения скриптов Livewire и Alpine. Если вы используете директиву @livewireScripts для ручной загрузки Livewire, обязательно удалите ее. Обязательно добавьте директиву @livewireStyles, если она еще не присутствует.
Последний шаг - импорт Alpine и Livewire в наш файл app.js, позволяющий зарегистрировать любые пользовательские ресурсы, и, наконец, запуск Livewire и Alpine:
import { Livewire, Alpine } from '../../vendor/livewire/livewire/dist/livewire.esm';
import Clipboard from '@ryangjchandler/alpine-clipboard'
Alpine.plugin(Clipboard)
Livewire.start()
Перевод официальной документации Livewire 3:
https://livewire.laravel.com/docs/installation
Хелперы
- Информация о материале
- Родительская категория: Полное руководство по Yii 2.0
- Категория: Хелперы
Хелперы
Внимание: Этот раздел находиться в стадии разработки.
Yii предоставляет много классов, которые помогают упростить общие задачи программирования, такие как манипуляция со строками или массивами, генерация HTML-кода, и так далее. Все helper-классы организованы в рамках пространства имен yii\helpers и являются статическими методами (это означает, что они содержат в себе только статические свойства и методы и объекты статического класса создать нельзя).
Вы можете использовать helper-класс с помощью вызова одного из статических методов, как показано ниже:
use yii\helpers\Html;
echo Html::encode('Test > test');
Note: Помощь в настройке helper-классов, в Yii каждый основной helper состоит из двух классов: базовый класс (например,
BaseArrayHelper) и конкретный класс (например,ArrayHelper). Когда вы используете helper, вы должны использовать только конкретные версии классов и никогда не использовать базовые классы.
Встроенные хелперы
В этой версии Yii предоставляются следующие основные helper-классы:
- ArrayHelper
- Console
- FileHelper
- FormatConverter
- Html
- HtmlPurifier
- Imagine (provided by yii2-imagine extension)
- Inflector
- Json
- Markdown
- StringHelper
- Url
- VarDumper
Настройка хелперов
Для настройки основных helper-классов (например, [[yii\helpers\ArrayHelper]]), вы должны создать расширяющийся класс из помощников соответствующих базовых классов (например, [[yii\helpers\BaseArrayHelper]]) и дать похожее название вашему классу с соответствующим конкретному классу (например, [[yii\helpers\ArrayHelper]]), в том числе его пространство имен. Тогда созданный класс заменит оригинальную реализацию в фреймворке.
В следующих примерах показывается как настроить метод [[yii\helpers\ArrayHelper::merge()|merge()]] [[yii\helpers\ArrayHelper]] класса:
<?php
namespace yii\helpers;
class ArrayHelper extends BaseArrayHelper
{
public static function merge($a, $b)
{
// ваша собственная реализация
}
}
Сохраните ваш класс в файле с именем ArrayHelper.php. Файл должен находиться в другой директории, например @app/components.
Далее, в приложении входной скрипт, добавьте следующую строчку кода после подключения yii.php файла, которая сообщит автозагрузка классов Yii загрузить ваш класс вместо оригинального helper-класса фреимворка:
Yii::$classMap['yii\helpers\ArrayHelper'] = '@app/components/ArrayHelper.php';
Обратите внимание что пользовательская настройка helper-классов полезна только, если вы хотите изменить поведение существующей функции helper-классов. Если вы хотите добавить дополнительные функции, для использования в вашем приложении, будет лучше создать отдельный helper.
Быстрый старт
- Информация о материале
- Родительская категория: Документация Livewire 3
- Категория: Начало работы
- Давайте знакомиться с Livewire!
- Необходимые условия для запуска Livewire
- Установка Livewire
- Создание компонента в Livewire
- Написание класса Livewire
- Написание представления Livewire.
- Регистрация маршрута Laravel для компонента Livewire
- Создание макета шаблона Livewire
- Тестируем приложение Livewire
Давайте знакомиться с Livewire!
Чтобы начать знакомство с Livewire, рассмотрим простой компонент "счетчик" и отобразим его в браузере. Этот пример — отличный способ для первого знакомства с Livewire, так как он демонстрирует его "живость" в самой простой форме.
Необходимые условия для запуска Livewire
Перед началом работы убедитесь, что у вас установлено следующее:
Установка Livewire
Из корневого каталога приложения Laravel выполните следующую команду Composer:
composer require livewire/livewire
Создание компонента в Livewire
Для быстрого создания новых компонентов в Livewire предусмотрена удобная команда Artisan. Выполните следующую команду, чтобы создать новый компонент Counter:
php artisan make:livewire counter
Эта команда создаст два новых файла в этом проекте:
app/Livewire/Counter.phpresources/views/livewire/counter.blade.php
Написание класса Livewire
Откройте файл app/Livewire/Counter.php и замените его содержимое на следующее:
<?php
namespace App\Livewire;
use Livewire\Component;
class Counter extends Component
{
public $count = 1;
public function increment()
{
$this->count++;
}
public function decrement()
{
$this->count--;
}
public function render()
{
return view('livewire.counter');
}
}
Краткое пояснение к приведенному выше коду:
public $count = 1;- Объявляет публичное свойство
$countс начальным значением1.
- Объявляет публичное свойство
public function increment()- Объявляет публичный метод с именем
increment(), который при каждом вызове увеличивает значение свойства$count. - Подобные публичные методы могут вызываться из браузера различными способами, в том числе и при нажатии пользователем кнопки.
- Объявляет публичный метод с именем
public function render()- Объявляет метод
render(), который возвращает представление Blade. - Это представление Blade будет содержать HTML-шаблон нашего компонента.
- Объявляет метод
Написание представления Livewire
Откройте файл resources/views/livewire/counter.blade.php и замените его содержимое на следующее:
<div>
<h1>{{ $count }}</h1>
<button wire:click="increment">+</button>
<button wire:click="decrement">-</button>
</div>
Этот код будет отображать значение свойства $count и две кнопки, увеличивающие и уменьшающие свойство $count соответственно.
Регистрация маршрута Laravel для компонента Livewire
Откройте файл routes/web.php в вашем приложении Laravel и добавьте следующий код:
use App\Livewire\Counter;
Route::get('/counter', Counter::class);
Теперь наш компонент счетчика назначен маршруту /counter, так что при переходе пользователя по адресу /counter в вашем приложении этот компонент будет отображаться в браузере.
Создание макета шаблона Livewire
Прежде чем перейти к странице /counter в браузере, необходимо создать HTML-макет, в котором будет отображаться наш компонент. По умолчанию Livewire автоматически ищет файл макета с именем: resources/views/components/layouts/app.blade.php
Этот файл можно создать, если он еще не существует, выполнив следующую команду:
php artisan livewire:layout
Эта команда создаст файл с именем resources/views/components/layouts/app.blade.php со следующим содержимым:
<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{{ $title ?? 'Page Title' }}</title>
</head>
<body>
{{ $slot }}
</body>
</html>
Компонент counter будет выведен на место переменной $slot в приведенном выше шаблоне.
Возможно, вы уже заметили, что Livewire не предоставляет никаких JavaScript или CSS ресурсов. Это связано с тем, что Livewire 3 и выше автоматически подставляет все необходимые ему ресурсы для фронтенда.
Тестируем приложение Livewire
После установки класса и шаблонов наш компонент готов к тестированию!
Перейдите в браузере по ссылке /counter, и на экране должно появиться число с двумя кнопками для его увеличения и уменьшения.
Нажав на одну из кнопок, вы заметите, что счетчик обновляется в режиме реального времени, без перезагрузки страницы. В этом и заключается магия Livewire: динамические фронтенд-приложения, написанные полностью на PHP.
Это только начало того, на что способен Livewire. Продолжайте читать документацию, чтобы увидеть все, что может предложить Livewire.
Перевод с английского официальной документации Livewire 3:
https://livewire.laravel.com/docs/quickstart
Порядок разрешения зависимости между репозиториями в Composer
- Информация о материале
- Родительская категория: Программы для автоматизации работы
- Категория: Composer
- Канонические репозитории Composer
- Поведение Composer по умолчанию
- Создание неканонических репозиториев Composer
- Фильтрация пакетов в Composer
Канонические репозитории Composer.
При разрешении зависимостей Composer ищет заданный пакет в самом верхнем хранилище. Если в этом хранилище пакета нет, он переходит к следующему, пока в одном из хранилищ этот пакет не будет найден и процесс не завершится.
Канонические репозитории лучше по нескольким причинам:
- С точки зрения производительности, прекращение поиска пакета после того, как он был найден, более эффективно. Это также позволяет избежать загрузки дублирующихся пакетов, если один и тот же пакет присутствует в нескольких репозиториях.
- С точки зрения безопасности, безопаснее обращаться с ними канонически, поскольку это означает, что пакеты, которые, как вы ожидаете, будут получены из наиболее важных для вас репозиториев, никогда не будут загружены из другого репозитория.
- Допустим, у вас есть частный репозиторий, который не является каноническим, и вам требуется, например, приватный пакет
foo/bar ^2.0. Если кто-то опубликуетfoo/bar 2.999на packagist.org, то Composer немедленно выберет этот пакет, поскольку он имеет более высокую версию, чем ваш последний релиз (скажем,2.4.3), и в итоге вы установите то, что, возможно, не хотели устанавливать. Однако если приватный репозиторий является каноническим, то версия2.999с packagist.org вообще не будет рассматриваться.
- Допустим, у вас есть частный репозиторий, который не является каноническим, и вам требуется, например, приватный пакет
Однако есть несколько случаев, когда требуется загрузить из данного репозитория не все, а некоторые пакеты. Или вы можете захотеть, чтобы данный репозиторий не был каноническим и предпочитался только в том случае, если он имеет более высокие версии пакетов, чем репозитории, определенные в списке ниже.
Поведение Composer по умолчанию.
По умолчанию в Composer 2.x все репозитории являются каноническими. В Composer 1.x все репозитории считались неканоническими.
По умолчанию репозиторий packagist.org всегда неявно добавляется последним, если это условие не отключено.
Создание неканонических репозиториев Composer.
Чтобы отключить это поведение по умолчанию и сделать так, чтобы Composer продолжал искать в других репозиториях, даже если они содержат данный пакет, можно добавить опцию canonical к любому репозиторию.
{
"repositories": [
{
"type": "composer",
"url": "https://example.org",
"canonical": false
}
]
}
Фильтрация пакетов в Composer.
Можно также отфильтровать пакеты, которые будут загружены в репозиторий, выбрав нужные или исключив ненужные.
Например, здесь мы хотим выбрать из данного хранилища Composer только пакет foo/bar и все пакеты от some-vendor/.
{
"repositories": [
{
"type": "composer",
"url": "https://example.org",
"only": ["foo/bar", "some-vendor/*"]
}
]
}
А в другом примере мы исключаем из репозитория пакет toy/package, который мы, возможно, не хотим загружать в этот проект.
{
"repositories": [
{
"type": "composer",
"url": "https://example.org",
"exclude": ["toy/package"]
}
]
}
И only, и exclude должны быть массивами имен пакетов, которые также могут содержать подстановочные знаки (*), которые будут соответствовать любому символу.
Перевод с английского официальной документации Composer:
https://getcomposer.org/doc/articles/repository-priorities.md
Страница 17 из 217