<? phpukraine ДОКУМЕНТАЦІЯ
Пошук по платформі
Документація українською

Переклад офіційної документації українською. Кожен розділ показує стан готовності: недоперекладене позначене відкрито, а не приховане.

ВЕРСІЯ
АКТУАЛЬНА Актуальний реліз. Переклад наздоганяє оригінал, розділи з низьким відсотком позначені у змісті.
ELOQUENT · ПЕРЕКЛАДЕНО оновлено 15 вересня 2026

Мутатори і касти · Laravel

Аксесори (accessors), мутатори (mutators) і касти атрибутів дозволяють перетворювати значення атрибутів Eloquent при читанні або записі їх на екземплярах моделі. Наприклад, ви можете шифрувати значення за допомогою шифрувальника Laravel, поки воно зберігається в базі даних, а потім автоматично розшифровувати атрибут при зверненні до нього на моделі Eloquent. Або ж вам може знадобитися перетворювати JSON-рядок, збережений у базі даних, на масив при доступі через модель Eloquent.

Аксесори і мутатори

Оголошення аксесора

Аксесор перетворює значення атрибута Eloquent під час звернення до нього. Щоб оголосити аксесор, створіть на моделі protected-метод, який представляє доступний атрибут. Імʼя цього методу має відповідати запису «camel case» справжнього атрибута моделі чи стовпця бази даних, якщо таке зіставлення можливе.

У цьому прикладі ми оголосимо аксесор для атрибута first_name. Eloquent викликатиме його автоматично при спробі отримати значення атрибута first_name. Усі методи аксесорів і мутаторів атрибутів мають оголошувати тип повернення Illuminate\Database\Eloquent\Casts\Attribute:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Casts\Attribute;
use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * Отримати імʼя користувача.
     */
    protected function firstName(): Attribute
    {
        return Attribute::make(
            get: fn (string $value) => ucfirst($value),
        );
    }
}

Усі методи аксесорів повертають екземпляр Attribute, який визначає, як атрибут буде прочитано і, за потреби, змінено. У цьому прикладі ми визначаємо лише читання: для цього передаємо аргумент get у конструктор класу Attribute.

Як бачите, в аксесор передається початкове значення стовпця, тож ви можете обробити його і повернути результат. Щоб дістати значення аксесора, просто зверніться до атрибута first_name на екземплярі моделі:

use App\Models\User;

$user = User::find(1);

$firstName = $user->first_name;

[!NOTE] Якщо ви хочете, щоб ці обчислені значення потрапляли в представлення моделі у вигляді масиву чи JSON, їх треба додати через append.

Побудова обʼєктів-значень із кількох атрибутів

Іноді аксесору потрібно перетворити кілька атрибутів моделі на єдиний «обʼєкт-значення» (value object). Для цього ваше замикання get може приймати другий аргумент $attributes, який буде автоматично переданий у замикання і міститиме масив усіх поточних атрибутів моделі:

use App\Support\Address;
use Illuminate\Database\Eloquent\Casts\Attribute;

/**
 * Взаємодія з адресою користувача.
 */
protected function address(): Attribute
{
    return Attribute::make(
        get: fn (mixed $value, array $attributes) => new Address(
            $attributes['address_line_one'],
            $attributes['address_line_two'],
        ),
    );
}

Кешування аксесорів

Коли аксесор повертає обʼєкт-значення, будь-які зміни цього обʼєкта автоматично синхронізуються назад у модель перед її збереженням. Це можливо тому, що Eloquent утримує повернуті аксесором екземпляри і повертає той самий екземпляр при кожному наступному виклику аксесора:

use App\Models\User;

$user = User::find(1);

$user->address->lineOne = 'Updated Address Line 1 Value';
$user->address->lineTwo = 'Updated Address Line 2 Value';

$user->save();

Іноді ви захочете ввімкнути кешування і для примітивних значень на кшталт рядків та булевих, особливо якщо їх обчислення затратне. Для цього викличте метод shouldCache при оголошенні аксесора:

protected function hash(): Attribute
{
    return Attribute::make(
        get: fn (string $value) => bcrypt(gzuncompress($value)),
    )->shouldCache();
}

Якщо ви хочете вимкнути кешування обʼєктів для атрибута, викличте метод withoutObjectCaching при його оголошенні:

/**
 * Взаємодія з адресою користувача.
 */
protected function address(): Attribute
{
    return Attribute::make(
        get: fn (mixed $value, array $attributes) => new Address(
            $attributes['address_line_one'],
            $attributes['address_line_two'],
        ),
    )->withoutObjectCaching();
}

Оголошення мутатора

Мутатор перетворює значення атрибута Eloquent під час його встановлення. Щоб оголосити мутатор, передайте аргумент set при оголошенні атрибута. Оголосимо мутатор для атрибута first_name. Він викликатиметься автоматично щоразу, коли ми намагаємося встановити значення атрибута first_name на моделі:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Casts\Attribute;
use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * Взаємодія з імʼям користувача.
     */
    protected function firstName(): Attribute
    {
        return Attribute::make(
            get: fn (string $value) => ucfirst($value),
            set: fn (string $value) => strtolower($value),
        );
    }
}

Замикання мутатора отримає значення, яке встановлюється в атрибут, тож ви можете обробити його і повернути змінене значення. Щоб скористатися нашим мутатором, достатньо встановити атрибут first_name на моделі Eloquent:

use App\Models\User;

$user = User::find(1);

$user->first_name = 'Sally';

У цьому прикладі колбек set буде викликано зі значенням Sally. Мутатор застосує до імені функцію strtolower і запише результат у внутрішній масив $attributes моделі.

Зміна кількох атрибутів

Іноді мутатору потрібно встановити кілька атрибутів моделі. Для цього поверніть масив із замикання set. Кожен ключ масиву має відповідати атрибуту чи стовпцю бази даних, повʼязаному з моделлю:

use App\Support\Address;
use Illuminate\Database\Eloquent\Casts\Attribute;

/**
 * Взаємодія з адресою користувача.
 */
protected function address(): Attribute
{
    return Attribute::make(
        get: fn (mixed $value, array $attributes) => new Address(
            $attributes['address_line_one'],
            $attributes['address_line_two'],
        ),
        set: fn (Address $value) => [
            'address_line_one' => $value->lineOne,
            'address_line_two' => $value->lineTwo,
        ],
    );
}

Касти атрибутів

Касти атрибутів дають функціональність, схожу на аксесори й мутатори, але не вимагають оголошувати додаткові методи на моделі. Натомість метод casts моделі надає зручний спосіб перетворювати атрибути на поширені типи даних.

Метод casts має повертати масив, де ключ - це імʼя атрибута, який приводиться, а значення - тип, до якого ви хочете привести стовпець. Підтримувані типи кастів:

  • array
  • AsFluent::class
  • AsStringable::class
  • AsUri::class
  • AsVector::class
  • boolean
  • collection
  • date
  • datetime
  • immutable_date
  • immutable_datetime
  • decimal:<precision>
  • double
  • encrypted
  • encrypted:array
  • encrypted:collection
  • encrypted:object
  • float
  • hashed
  • integer
  • object
  • real
  • string
  • timestamp

Щоб продемонструвати касти атрибутів, приведімо атрибут is_admin, який зберігається в базі даних як ціле число (0 або 1), до булевого значення:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * Отримати атрибути, які треба привести до типу.
     *
     * @return array<string, string>
     */
    protected function casts(): array
    {
        return [
            'is_admin' => 'boolean',
        ];
    }
}

Після оголошення касту атрибут is_admin завжди приводитиметься до булевого значення при зверненні до нього, навіть якщо в базі даних воно збережене як ціле число:

$user = App\Models\User::find(1);

if ($user->is_admin) {
    // ...
}

Якщо вам потрібно додати новий тимчасовий каст під час виконання, скористайтеся методом mergeCasts. Ці визначення кастів буде додано до тих, які вже оголошені на моделі:

$user->mergeCasts([
    'is_admin' => 'integer',
    'options' => 'object',
]);

[!WARNING] Атрибути зі значенням null не приводяться. Крім того, ніколи не оголошуйте каст (чи атрибут) з таким самим імʼям, як у звʼязку, і не призначайте каст первинному ключу моделі.

Каст Stringable

Ви можете скористатися класом касту Illuminate\Database\Eloquent\Casts\AsStringable, щоб привести атрибут моделі до обʼєкта Illuminate\Support\Stringable:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Casts\AsStringable;
use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * Отримати атрибути, які треба привести до типу.
     *
     * @return array<string, string>
     */
    protected function casts(): array
    {
        return [
            'directory' => AsStringable::class,
        ];
    }
}

Касти масивів і JSON

Каст array особливо корисний для стовпців, у яких зберігається серіалізований JSON. Наприклад, якщо у вашій базі даних є поле типу JSON чи TEXT із серіалізованим JSON, каст array на цьому атрибуті автоматично десеріалізує його в PHP-масив при зверненні через модель Eloquent:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * Отримати атрибути, які треба привести до типу.
     *
     * @return array<string, string>
     */
    protected function casts(): array
    {
        return [
            'options' => 'array',
        ];
    }
}

Після оголошення касту ви можете звертатися до атрибута options, і він автоматично десеріалізуватиметься з JSON у PHP-масив. Коли ви встановлюєте значення атрибута options, переданий масив автоматично серіалізується назад у JSON для зберігання:

use App\Models\User;

$user = User::find(1);

$options = $user->options;

$options['key'] = 'value';

$user->options = $options;

$user->save();

Щоб оновити одне поле JSON-атрибута коротшим синтаксисом, ви можете зробити атрибут масово призначуваним і використати оператор -> при виклику методу update:

$user = User::find(1);

$user->update(['options->key' => 'value']);

JSON і Unicode

Якщо ви хочете зберігати атрибут-масив як JSON без екранування Unicode-символів, скористайтеся кастом json:unicode:

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'options' => 'json:unicode',
    ];
}

Касти Array Object і Collection

Стандартного касту array вистачає для багатьох застосунків, але він має недоліки. Оскільки каст array повертає примітивний тип, змінити окремий елемент масиву напряму неможливо. Наприклад, такий код спричинить помилку PHP:

$user = User::find(1);

$user->options['key'] = $value;

Щоб вирішити це, Laravel пропонує каст AsArrayObject, який приводить ваш JSON-атрибут до класу ArrayObject. Цю можливість реалізовано через механізм власних кастів Laravel, що дозволяє фреймворку розумно кешувати і перетворювати змінений обʼєкт, тож окремі елементи можна модифікувати без помилки PHP. Щоб скористатися кастом AsArrayObject, просто призначте його атрибуту:

use Illuminate\Database\Eloquent\Casts\AsArrayObject;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'options' => AsArrayObject::class,
    ];
}

Так само Laravel пропонує каст AsCollection, який приводить ваш JSON-атрибут до екземпляра Collection:

use Illuminate\Database\Eloquent\Casts\AsCollection;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'options' => AsCollection::class,
    ];
}

Якщо ви хочете, щоб каст AsCollection створював екземпляр власного класу колекції замість базового класу Laravel, передайте імʼя класу колекції як аргумент касту:

use App\Collections\OptionCollection;
use Illuminate\Database\Eloquent\Casts\AsCollection;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'options' => AsCollection::using(OptionCollection::class),
    ];
}

Метод of вказує, що елементи колекції треба відобразити в заданий клас через метод колекції mapInto:

use App\ValueObjects\Option;
use Illuminate\Database\Eloquent\Casts\AsCollection;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'options' => AsCollection::of(Option::class)
    ];
}

При відображенні колекцій в обʼєкти клас обʼєкта має реалізовувати інтерфейси Illuminate\Contracts\Support\Arrayable і JsonSerializable, щоб визначити, як його екземпляри серіалізуються в базу даних у вигляді JSON:

<?php

namespace App\ValueObjects;

use Illuminate\Contracts\Support\Arrayable;
use JsonSerializable;

class Option implements Arrayable, JsonSerializable
{
    public string $name;
    public mixed $value;
    public bool $isLocked;

    /**
     * Створити новий екземпляр Option.
     */
    public function __construct(array $data)
    {
        $this->name = $data['name'];
        $this->value = $data['value'];
        $this->isLocked = $data['is_locked'];
    }

    /**
     * Отримати екземпляр у вигляді масиву.
     *
     * @return array{name: string, data: string, is_locked: bool}
     */
    public function toArray(): array
    {
        return [
            'name' => $this->name,
            'value' => $this->value,
            'is_locked' => $this->isLocked,
        ];
    }

    /**
     * Вказати дані, які треба серіалізувати в JSON.
     *
     * @return array{name: string, data: string, is_locked: bool}
     */
    public function jsonSerialize(): array
    {
        return $this->toArray();
    }
}

Каст векторів

Ви можете використати клас касту Illuminate\Database\Eloquent\Casts\AsVector, щоб приводити стовпець-вектор бази даних до PHP-масиву і навпаки:

use Illuminate\Database\Eloquent\Casts\AsVector;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'embedding' => AsVector::class,
    ];
}

При встановленні атрибута каст приймає PHP-масив або екземпляр Arrayable, наприклад колекцію Laravel. При читанні атрибута каст повертає масив чисел із плаваючою комою.

Бінарний каст

Якщо ваша модель Eloquent, окрім стовпця з автоінкрементним ID, має стовпець uuid або ulid бінарного типу, ви можете скористатися кастом AsBinary, щоб автоматично перетворювати значення в його бінарне представлення і назад:

use Illuminate\Database\Eloquent\Casts\AsBinary;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'uuid' => AsBinary::uuid(),
        'ulid' => AsBinary::ulid(),
    ];
}

Після оголошення касту на моделі ви можете присвоювати атрибуту UUID / ULID екземпляр обʼєкта або рядок. Eloquent автоматично перетворить значення на бінарне представлення. При читанні значення атрибута ви завжди отримаєте звичайний текстовий рядок:

use Illuminate\Support\Str;

$user->uuid = Str::uuid();

return $user->uuid;

// "6e8cdeed-2f32-40bd-b109-1e4405be2140"

Касти дат

За замовчуванням Eloquent приводить стовпці created_at і updated_at до екземплярів Carbon, який розширює PHP-клас DateTime і додає набір корисних методів. Ви можете приводити й інші атрибути-дати, оголосивши додаткові касти дат у методі casts моделі. Зазвичай для дат використовують типи кастів datetime або immutable_datetime.

Оголошуючи каст date чи datetime, ви можете також вказати формат дати. Цей формат використовуватиметься, коли модель серіалізується в масив або JSON:

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'created_at' => 'datetime:Y-m-d',
    ];
}

Коли стовпець приводиться як дата, ви можете встановити відповідному атрибуту моделі UNIX-мітку часу, рядок дати (Y-m-d), рядок дати й часу або екземпляр DateTime / Carbon. Значення дати буде коректно перетворене і збережене у вашій базі даних.

Формат серіалізації за замовчуванням для всіх дат моделі можна змінити, оголосивши на моделі метод serializeDate. Цей метод не впливає на те, як дати форматуються для зберігання в базі даних:

/**
 * Підготувати дату для серіалізації в масив / JSON.
 */
protected function serializeDate(DateTimeInterface $date): string
{
    return $date->format('Y-m-d');
}

Щоб задати формат, який використовується при фактичному зберіганні дат моделі в базі даних, скористайтеся аргументом dateFormat атрибута Table вашої моделі:

use Illuminate\Database\Eloquent\Attributes\Table;

#[Table(dateFormat: 'U')]
class Flight extends Model
{
    // ...
}

Касти дат, серіалізація і часові пояси

За замовчуванням касти date і datetime серіалізують дати в рядок дати UTC ISO-8601 (YYYY-MM-DDTHH:MM:SS.uuuuuuZ) незалежно від часового поясу, вказаного в конфігураційній опції timezone вашого застосунку. Наполегливо рекомендуємо завжди використовувати цей формат серіалізації, а також зберігати дати застосунку в часовому поясі UTC, не змінюючи опцію timezone зі стандартного значення UTC. Послідовне використання UTC у всьому застосунку дасть максимальний рівень сумісності з іншими бібліотеками роботи з датами на PHP і JavaScript.

Якщо до касту date чи datetime застосовано власний формат, наприклад datetime:Y-m-d H:i:s, під час серіалізації дати використовуватиметься внутрішній часовий пояс екземпляра Carbon. Зазвичай це пояс, вказаний у конфігураційній опції timezone застосунку. Проте зверніть увагу, що стовпці timestamp на кшталт created_at і updated_at є винятком із цієї поведінки і завжди форматуються в UTC, незалежно від налаштування часового поясу застосунку.

Каст переліків

Eloquent також дозволяє приводити значення атрибутів до PHP-переліків (enum). Для цього вкажіть атрибут і перелік, до якого треба приводити, у методі casts моделі:

use App\Enums\ServerStatus;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'status' => ServerStatus::class,
    ];
}

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

if ($server->status == ServerStatus::Provisioned) {
    $server->status = ServerStatus::Ready;

    $server->save();
}

Каст масивів переліків

Іноді моделі потрібно зберігати масив значень переліку в одному стовпці. Для цього скористайтеся кастами AsEnumArrayObject або AsEnumCollection, які надає Laravel:

use App\Enums\ServerStatus;
use Illuminate\Database\Eloquent\Casts\AsEnumCollection;

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'statuses' => AsEnumCollection::of(ServerStatus::class),
    ];
}

Каст із шифруванням

Каст encrypted шифрує значення атрибута моделі вбудованими засобами шифрування Laravel. Касти encrypted:array, encrypted:collection, encrypted:object, AsEncryptedArrayObject і AsEncryptedCollection працюють так само, як їхні незашифровані відповідники, але, як і можна очікувати, значення шифрується при зберіганні в базі даних.

Оскільки кінцева довжина зашифрованого тексту непередбачувана і більша за довжину відкритого тексту, переконайтеся, що відповідний стовпець бази даних має тип TEXT або більший. Крім того, оскільки значення в базі даних зашифровані, ви не зможете виконувати запити чи пошук за зашифрованими значеннями атрибутів.

Ротація ключа

Як ви, можливо, знаєте, Laravel шифрує рядки за допомогою значення конфігурації key, вказаного у файлі конфігурації app вашого застосунку. Зазвичай це значення відповідає змінній середовища APP_KEY. Якщо вам потрібно змінити ключ шифрування застосунку, ви можете зробити це плавно.

Касти під час запиту

Іноді касти потрібно застосувати під час виконання запиту, наприклад коли ви вибираєте сире значення з таблиці. Розгляньмо такий запит:

use App\Models\Post;
use App\Models\User;

$users = User::select([
    'users.*',
    'last_posted_at' => Post::selectRaw('MAX(created_at)')
        ->whereColumn('user_id', 'users.id')
])->get();

Атрибут last_posted_at у результатах цього запиту буде звичайним рядком. Було б чудово застосувати до нього каст datetime під час виконання запиту. На щастя, це можна зробити методом withCasts:

$users = User::select([
    'users.*',
    'last_posted_at' => Post::selectRaw('MAX(created_at)')
        ->whereColumn('user_id', 'users.id')
])->withCasts([
    'last_posted_at' => 'datetime'
])->get();

Власні касти

Laravel має різноманітні вбудовані корисні типи кастів, але іноді вам знадобиться оголосити власні. Щоб створити каст, виконайте Artisan-команду make:cast. Новий клас касту буде розміщено в теці app/Casts:

php artisan make:cast AsJson

Усі класи власних кастів реалізують інтерфейс CastsAttributes. Класи, що реалізують цей інтерфейс, мають оголосити методи get і set. Метод get відповідає за перетворення сирого значення з бази даних на приведене значення, а метод set має перетворити приведене значення на сире, придатне для зберігання в базі даних. Для прикладу ми перереалізуємо вбудований тип касту json як власний:

<?php

namespace App\Casts;

use Illuminate\Contracts\Database\Eloquent\CastsAttributes;
use Illuminate\Database\Eloquent\Model;

class AsJson implements CastsAttributes
{
    /**
     * Привести задане значення.
     *
     * @param  array<string, mixed>  $attributes
     * @return array<string, mixed>
     */
    public function get(
        Model $model,
        string $key,
        mixed $value,
        array $attributes,
    ): array {
        return json_decode($value, true);
    }

    /**
     * Підготувати задане значення до зберігання.
     *
     * @param  array<string, mixed>  $attributes
     */
    public function set(
        Model $model,
        string $key,
        mixed $value,
        array $attributes,
    ): string {
        return json_encode($value);
    }
}

Оголосивши власний тип касту, ви можете прикріпити його до атрибута моделі за імʼям класу:

<?php

namespace App\Models;

use App\Casts\AsJson;
use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * Отримати атрибути, які треба привести до типу.
     *
     * @return array<string, string>
     */
    protected function casts(): array
    {
        return [
            'options' => AsJson::class,
        ];
    }
}

Каст до обʼєктів-значень

Ви не обмежені приведенням значень до примітивних типів. Значення можна приводити й до обʼєктів. Оголошення власних кастів, що приводять значення до обʼєктів, дуже схоже на приведення до примітивів, але якщо ваш обʼєкт-значення охоплює більш ніж один стовпець бази даних, метод set має повернути масив пар ключ / значення, які будуть використані для запису сирих значень у модель. Якщо обʼєкт-значення стосується лише одного стовпця, просто поверніть значення для зберігання.

Для прикладу оголосимо клас власного касту, який приводить кілька значень моделі до єдиного обʼєкта-значення Address. Припустимо, що обʼєкт-значення Address має дві публічні властивості: lineOne і lineTwo:

<?php

namespace App\Casts;

use App\ValueObjects\Address;
use Illuminate\Contracts\Database\Eloquent\CastsAttributes;
use Illuminate\Database\Eloquent\Model;
use InvalidArgumentException;

class AsAddress implements CastsAttributes
{
    /**
     * Привести задане значення.
     *
     * @param  array<string, mixed>  $attributes
     */
    public function get(
        Model $model,
        string $key,
        mixed $value,
        array $attributes,
    ): Address {
        return new Address(
            $attributes['address_line_one'],
            $attributes['address_line_two']
        );
    }

    /**
     * Підготувати задане значення до зберігання.
     *
     * @param  array<string, mixed>  $attributes
     * @return array<string, string>
     */
    public function set(
        Model $model,
        string $key,
        mixed $value,
        array $attributes,
    ): array {
        if (! $value instanceof Address) {
            throw new InvalidArgumentException('The given value is not an Address instance.');
        }

        return [
            'address_line_one' => $value->lineOne,
            'address_line_two' => $value->lineTwo,
        ];
    }
}

При приведенні до обʼєктів-значень будь-які зміни обʼєкта автоматично синхронізуються назад у модель перед її збереженням:

use App\Models\User;

$user = User::find(1);

$user->address->lineOne = 'Updated Address Value';

$user->save();

[!NOTE] Якщо ви плануєте серіалізувати моделі Eloquent з обʼєктами-значеннями в JSON чи масиви, реалізуйте на обʼєкті-значенні інтерфейси Illuminate\Contracts\Support\Arrayable і JsonSerializable.

Кешування обʼєктів-значень

Коли атрибути, приведені до обʼєктів-значень, розвʼязуються, Eloquent кешує їх. Тому при повторному зверненні до атрибута буде повернено той самий екземпляр обʼєкта.

Якщо ви хочете вимкнути кешування обʼєктів для класів власних кастів, оголосіть на класі касту публічну властивість withoutObjectCaching:

class AsAddress implements CastsAttributes
{
    public bool $withoutObjectCaching = true;

    // ...
}

Серіалізація в масив / JSON

Коли модель Eloquent перетворюється на масив чи JSON методами toArray і toJson, обʼєкти-значення ваших власних кастів зазвичай теж серіалізуються, якщо вони реалізують інтерфейси Illuminate\Contracts\Support\Arrayable і JsonSerializable. Проте при використанні обʼєктів-значень зі сторонніх бібліотек ви можете не мати змоги додати ці інтерфейси до обʼєкта.

Тому ви можете вказати, що за серіалізацію обʼєкта-значення відповідатиме клас вашого власного касту. Для цього клас касту має реалізувати інтерфейс Illuminate\Contracts\Database\Eloquent\SerializesCastableAttributes. Цей інтерфейс вимагає, щоб ваш клас містив метод serialize, який повертає серіалізовану форму обʼєкта-значення:

/**
 * Отримати серіалізоване представлення значення.
 *
 * @param  array<string, mixed>  $attributes
 */
public function serialize(
    Model $model,
    string $key,
    mixed $value,
    array $attributes,
): string {
    return (string) $value;
}

Вхідні касти

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

Власні касти лише для вхідних значень мають реалізовувати інтерфейс CastsInboundAttributes, який вимагає оголосити тільки метод set. Artisan-команду make:cast можна викликати з опцією --inbound, щоб згенерувати клас касту лише для вхідних значень:

php artisan make:cast AsHash --inbound

Класичний приклад такого касту - «хешування». Наприклад, ми можемо оголосити каст, який хешує вхідні значення заданим алгоритмом:

<?php

namespace App\Casts;

use Illuminate\Contracts\Database\Eloquent\CastsInboundAttributes;
use Illuminate\Database\Eloquent\Model;

class AsHash implements CastsInboundAttributes
{
    /**
     * Створити новий екземпляр класу касту.
     */
    public function __construct(
        protected string|null $algorithm = null,
    ) {}

    /**
     * Підготувати задане значення до зберігання.
     *
     * @param  array<string, mixed>  $attributes
     */
    public function set(
        Model $model,
        string $key,
        mixed $value,
        array $attributes,
    ): string {
        return is_null($this->algorithm)
            ? bcrypt($value)
            : hash($this->algorithm, $value);
    }
}

Параметри касту

Прикріплюючи власний каст до моделі, ви можете вказати параметри касту, відділивши їх від імені класу символом :, а кілька параметрів - комами. Параметри буде передано в конструктор класу касту:

/**
 * Отримати атрибути, які треба привести до типу.
 *
 * @return array<string, string>
 */
protected function casts(): array
{
    return [
        'secret' => AsHash::class.':sha256',
    ];
}

Порівняння приведених значень

Якщо ви хочете визначити, як порівнювати два приведені значення, щоб зрозуміти, чи вони змінилися, ваш клас власного касту може реалізувати інтерфейс Illuminate\Contracts\Database\Eloquent\ComparesCastableAttributes. Це дає точний контроль над тим, які значення Eloquent вважає зміненими і, відповідно, зберігає в базу даних при оновленні моделі.

Цей інтерфейс вимагає, щоб ваш клас містив метод compare, який повертає true, якщо задані значення вважаються рівними:

/**
 * Визначити, чи задані значення рівні.
 *
 * @param  \Illuminate\Database\Eloquent\Model  $model
 * @param  string  $key
 * @param  mixed  $firstValue
 * @param  mixed  $secondValue
 * @return bool
 */
public function compare(
    Model $model,
    string $key,
    mixed $firstValue,
    mixed $secondValue
): bool {
    return $firstValue === $secondValue;
}

Castables

Можливо, ви захочете, щоб обʼєкти-значення вашого застосунку самі визначали свої класи власних кастів. Замість того щоб прикріплювати до моделі клас касту, ви можете прикріпити клас обʼєкта-значення, який реалізує інтерфейс Illuminate\Contracts\Database\Eloquent\Castable:

use App\ValueObjects\Address;

protected function casts(): array
{
    return [
        'address' => Address::class,
    ];
}

Обʼєкти, що реалізують інтерфейс Castable, мають оголосити метод castUsing, який повертає імʼя класу власного касту, відповідального за приведення до класу Castable і назад:

<?php

namespace App\ValueObjects;

use Illuminate\Contracts\Database\Eloquent\Castable;
use App\Casts\AsAddress;

class Address implements Castable
{
    /**
     * Отримати імʼя класу касту, який використовується при приведенні до цієї цілі касту і назад.
     *
     * @param  array<string, mixed>  $arguments
     */
    public static function castUsing(array $arguments): string
    {
        return AsAddress::class;
    }
}

Використовуючи класи Castable, ви все одно можете передавати аргументи у визначенні методу casts. Ці аргументи буде передано в метод castUsing:

use App\ValueObjects\Address;

protected function casts(): array
{
    return [
        'address' => Address::class.':argument',
    ];
}

Castables і анонімні класи кастів

Поєднавши «castables» з анонімними класами PHP, ви можете описати обʼєкт-значення і логіку його приведення як один castable-обʼєкт. Для цього поверніть анонімний клас із методу castUsing вашого обʼєкта-значення. Анонімний клас має реалізовувати інтерфейс CastsAttributes:

<?php

namespace App\ValueObjects;

use Illuminate\Contracts\Database\Eloquent\Castable;
use Illuminate\Contracts\Database\Eloquent\CastsAttributes;

class Address implements Castable
{
    // ...

    /**
     * Отримати клас касту, який використовується при приведенні до цієї цілі касту і назад.
     *
     * @param  array<string, mixed>  $arguments
     */
    public static function castUsing(array $arguments): CastsAttributes
    {
        return new class implements CastsAttributes
        {
            public function get(
                Model $model,
                string $key,
                mixed $value,
                array $attributes,
            ): Address {
                return new Address(
                    $attributes['address_line_one'],
                    $attributes['address_line_two']
                );
            }

            public function set(
                Model $model,
                string $key,
                mixed $value,
                array $attributes,
            ): array {
                return [
                    'address_line_one' => $value->lineOne,
                    'address_line_two' => $value->lineTwo,
                ];
            }
        };
    }
}
ЯК ЦЯ СТОРІНКА ВИГЛЯДАЄ В ПОШУКУ
phpukraine.com/docs/laravel/mutators
Мутатори і касти | Документація Laravel українською
Мутатори і касти у Laravel 13.x: переклад офіційної документації українською. Оновлено 15 вересня 2026. Приклади коду, пояснення та посилання на питання зі співбесід.
Стан перекладу

Перекладаємо з офіційної документації, розділ за розділом, і не ховаємо недоперекладене. Помітили неточність у терміні чи реченні: напишіть, виправимо.

90%
Готовності
10
У роботі
0
Ще не перекладено
Глосарій термінів