Перейти до основного вмісту

← Початок роботи · Повернутися до README · Попереднє завантаження →

Робота з налаштуваннями

Один сервіс працює і зі значеннями за замовчуванням, і зі значеннями моделей. Точка входу визначає, яка область читається або змінюється:

Точка входуОбласть
(new User)->defaultSettings()Значення за замовчуванням для всіх збережених моделей User
$user->settings()Підсумкові налаштування одного збереженого користувача

Спільні значення за замовчуванням​

Значення за замовчуванням застосовуються до всіх збережених моделей з однаковим morph-класом Eloquent:

$defaults = (new User)->defaultSettings();

$defaults->set('timezone', 'UTC');
$defaults->set('notifications', ['email' => true]);

Читайте або видаляйте значення за замовчуванням через той самий сервіс:

$timezone = $defaults->get('timezone');
$all = $defaults->all();

$defaults->forget('timezone');

Для кожного класу моделі значення за замовчуванням незалежні.

Перевизначення для моделей​

set() створює налаштування або замінює його поточне значення:

$user->settings()->set('timezone', 'Europe/Paris');
$user->settings()->set('timezone', 'America/Toronto');

Змінюється лише налаштування цієї моделі. Інші моделі продовжують використовувати власне перевизначення або спільне значення за замовчуванням.

get(), has() і all() вибирають значення з однаковим пріоритетом:

$timezone = $user->settings()->get('timezone');
$hasTimezone = $user->settings()->has('timezone');
$settings = $user->settings()->all();

all() повертає Illuminate\Support\Collection із ключами за назвами налаштувань.

get() приймає лише ключ. Спочатку він повертає перевизначення моделі, потім збережене значення класу за замовчуванням, а потім null. Метод не приймає резервне значення від викликача. has() відрізняє відсутній ключ від збереженого JSON null:

if ($user->settings()->has('timezone')) {
$timezone = $user->settings()->get('timezone');
}

Наприклад, одне перевизначення замінює лише відповідне значення за замовчуванням:

(new User)->defaultSettings()->set('timezone', 'UTC');
(new User)->defaultSettings()->set('locale', 'en');

$user->settings()->set('timezone', 'Europe/Paris');

assert($user->settings()->all()->sortKeys()->all() === [
'locale' => 'en',
'timezone' => 'Europe/Paris',
]);

Видалення значення​

Після видалення перевизначення моделі знову використовується значення за замовчуванням:

(new User)->defaultSettings()->set('timezone', 'UTC');

$user->settings()->set('timezone', 'Europe/Paris');
$user->settings()->forget('timezone');

assert($user->settings()->get('timezone') === 'UTC');

Щоб видалити саме значення за замовчуванням, викличте forget() через defaultSettings():

(new User)->defaultSettings()->forget('timezone');

Виклик forget() для відсутнього ключа нічого не змінює.

Групові зміни​

Використовуйте setMany() і forgetMany(), коли в одній області потрібно змінити кілька ключів:

$user->settings()->setMany([
'timezone' => 'Europe/Paris',
'locale' => 'fr',
]);

$user->settings()->forgetMany(['timezone', 'locale']);

Обидва методи приймають будь-який iterable. Перед записом setMany() нормалізує кожен ключ. Якщо кілька вхідних ключів перетворюються на один збережений ключ, використовується останнє значення. Усі значення зберігаються; рядки видаляють лише forget() і forgetMany().

Непорожній пакет setMany() виконує один нативний upsert у транзакції. forgetMany() видаляє всі перелічені ключі одним запитом. Кількість запитів обмежена типом операції та не залежить від кількості ключів.

Використовуйте purge(), щоб повністю очистити поточну область:

$user->settings()->purge();

Для settings() метод purge() видаляє лише перевизначення цього власника, після чого знову видно збережені значення за замовчуванням. Для defaultSettings() він видаляє значення за замовчуванням цього класу моделі, не зачіпаючи перевизначення моделей. Усі три групові методи повертають void.

JSON-значення​

set() і setMany() зберігають JSON-значення без змін:

ЗначенняРезультат
nullЗберігається
'' або рядок лише з пробілівЗберігається
[]Зберігається
0Зберігається
falseЗберігається
'0'Зберігається

Збережений null вважається наявним значенням. has($key) повертає true, а get($key) — null. Перевизначення моделі зі значенням null також приховує заповнене значення класу за замовчуванням, доки перевизначення не буде видалене через forget().

Ключі налаштувань​

Ключами можуть бути рядки, цілі числа або PHP-переліки, що реалізують UnitEnum:

enum SettingKey: string
{
case Timezone = 'timezone';
}

$user->settings()->set(SettingKey::Timezone, 'Europe/Paris');

$timezone = $user->settings()->get(SettingKey::Timezone);

Laravel зберігає backed enum як його базове значення, а pure unit enum — як назву варіанта. Під час читання, заміни й видалення використовуйте той самий ключ або варіант переліку.

Порожні ключі та ключі лише з пробілів викидають DragonCode\LaravelModelSettings\Exceptions\InvalidSettingKey. Перевірка виконується після нормалізації цілих чисел і переліків у збережуваний рядок. Виняток не містить відхилений ключ або дані налаштування.

Крапки вважаються звичайними символами. Ключ mail.from.address — це один непрозорий ключ налаштування, а не вкладений шлях:

$user->settings()->set('mail.from.address', '[email protected]');

$address = $user->settings()->get('mail.from.address');

Ідентифікатори моделей​

Підтримуються цілочислові, рядкові, UUID- та ULID-первинні ключі.

Для зміни налаштувань моделі потрібен збережений власник із ключем, що не дорівнює null. Для незбереженої моделі get() повертає null, has() — false, а all() — порожню колекцію без запиту перевизначень. Її set(), setMany(), forget(), forgetMany() і purge() викидають InvalidSettingsOwnerException до виконання запиту до сховища або читання iterable.

Збережені моделі з цілим ідентифікатором 0 або рядковим '0' підтримують ті самі операції читання та зміни, що й будь-який інший збережений власник. Дискримінатор області відокремлює їхні перевизначення від значень класу за замовчуванням, хоча обидва рядки зберігають item_id = '0'. Інші рядкові ключі, включно з '00', залишаються допустимими.

Налаштування зберігаються для поточного morph-класу моделі. Якщо після запису налаштувань додати або змінити псевдонім у morph map, наявні значення item_type доведеться оновити.

Див. також​