Контроль розширення взаємозв'язків у патерні Factory в Laravel

0
Перекладено ШІ
Оригінал: Laravel News
Оновлено: 02 жовтня, 2025
Laravel пропонує зручні фабрики для автоматичного створення зв'язків між моделями, але іноді це призводить до зайвих записів у базі даних під час тестування. Чи знаєте ви, як уникнути цього та оптимізувати свій тестовий процес? Дізнайтеся більше про метод `dontExpandRelationshipsByDefault()` і про те, як він може спростити ваші тести!

Фабрики Laravel автоматично створюють пов’язані моделі, коли визначені відносини, але це може призвести до створення зайвих записів у базі даних під час тестування. Метод dontExpandRelationshipsByDefault() контролює, чи фабрики автоматично ініціюють батьківські зв’язки.

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

use App\Models\OrderItem;
use Database\Factories\OrderItemFactory;

public function test_price_calculation(): void
{
    OrderItemFactory::dontExpandRelationshipsByDefault();

    $item = OrderItem::factory()->make([
        'quantity' => 2,
        'unit_price' => 15.50,
        'order_id' => 999,
    ]);

    $this->assertEquals(31.00, $item->calculateTotal());
}

Цей тест перевіряє логіку розрахунку ціни без створення записів Order, Product або Customer. Фабрика генерує лише необхідний екземпляр OrderItem для перевірки.

Тестування колекцій з вимкненим розширенням зв’язків дозволяє зосередитися на перевірюваній логіці:

use App\Models\Subscription;
use Database\Factories\SubscriptionFactory;

public function test_active_subscriptions_filter(): void
{
    SubscriptionFactory::dontExpandRelationshipsByDefault();

    $subscriptions = collect([
        Subscription::factory()->make(['status' => 'active', 'plan_id' => 1]),
        Subscription::factory()->make(['status' => 'cancelled', 'plan_id' => 2]),
        Subscription::factory()->make(['status' => 'active', 'plan_id' => 1]),
    ]);

    $active = $subscriptions->filter(fn($sub) => $sub->isActive());

    $this->assertCount(2, $active);
}

Допоміжний метод відновлює поведінку за замовчуванням:

SubscriptionFactory::expandRelationshipsByDefault();

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

Для тестування прав, де потрібні певні комбінації атрибутів без накладних витрат на записи користувача і компанії:

use App\Models\Permission;
use Database\Factories\PermissionFactory;

public function test_permission_scope(): void
{
    PermissionFactory::dontExpandRelationshipsByDefault();

    $permissions = collect([
        Permission::factory()->make([
            'type' => 'read',
            'resource_id' => 100,
            'user_id' => 5,
        ]),
        Permission::factory()->make([
            'type' => 'write',
            'resource_id' => 100,
            'user_id' => 5,
        ]),
        Permission::factory()->make([
            'type' => 'read',
            'resource_id' => 200,
            'user_id' => 5,
        ]),
    ]);

    $writePermissions = $permissions->where('type', 'write');

    $this->assertCount(1, $writePermissions);
}

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

Популярні

Logomark Logotype

Простий пакет RabbitMQ для Laravel

Вам цікаво дізнатися, як спростити інтеграцію RabbitMQ у вашому Laravel-додатку? У нашій статті ми розглянемо пакет Simple RabbitMQ, який дозволяє легко налаштувати багатозʼєднання, публікувати повідомлення та обробляти черги за допомогою простого синтаксису. Читайте далі, щоб дізнатися більше!

Logomark Logotype

Як задокументувати кілька API в Laravel за допомогою Scramble

Ви знали, що в одному додатку Laravel можна реалізувати кілька API? У нашій статті ви дізнаєтеся, як за допомогою Scramble легко документувати різні версії API та налаштувати доступ до документації, щоб зробити її публічною або приватною. Читайте далі, щоб дізнатися більше

Logomark Logotype

Laravel Boost — ваш стартовий набір для програмування з використанням штучного інтелекту

Вперше у світі Laravel з'являється можливість, яка значно спростить ваше повсякденне програмування завдяки новому пакету Laravel Boost. Читайте статтю, щоб дізнатися, як посилена інтеграція штучного інтелекту може підвищити ефективність вашої роботи та оптимізувати створення проектів у Laravel