Предотвратить создание модели отношений на заводе, если иностранный идентификатор передан как атрибут

65
7

Предположим, что эта фабрика:

PostFactory.php

$factory->define(Post::class, function (Faker $faker) {
return [
'title'=>$faker->word,
'user_id'=>factory(User::class)->create()->id
];
});

то я использую его следующим образом:

$user = factory(User::class)->create();
factory(Post::class, 5)->create(['user_id'=>$user->id]);

Я ожидаю, что будут созданы 1 пользователь и 5 должностей. Но на самом деле в базе данных 6 пользователей, потому что PostFactory создает пользователя, user_id ли user_id или нет.

Есть ли способ предотвратить создание нового пользователя, если атрибут user_id передан для create метода?

спросил(а) 2021-01-27T21:37:26+03:00 8 месяцев, 3 недели назад
1
Решение
80

Там обходной путь для этого.

$factory->define(Post::class, function (Faker $faker) {
return [
'title'=>$faker->word,
'user_id'=> function () { return factory(User::class)->create()->id; }
];
});

Laravel вызывает помощник value() при объединении атрибутов. Если user_id существует в атрибутах, он не будет выполнять обратный вызов, иначе он будет.

Вы можете увидеть его в документе здесь с точно такими же моделями, как ваши.

ответил(а) 2021-01-27T21:37:26+03:00 8 месяцев, 3 недели назад
46

Для Larave 5.1 вам необходимо передать параметр и вручную проверить, прошел ли идентификатор.

Вот обсуждение вопроса. https://github.com/laravel/framework/issues/9245


$factory->define(App\User::class, function ($faker, $attributes) {

$accountId = isset($attributes['account_id']) ? $attributes['account_id']: factory(App\Account::class)->create()->id;

return [
'account_id' => $accountId,
'email' => $faker->email,
'password' => 'secret',
'name' => $faker->name
];

});

ответил(а) 2021-01-27T21:37:26+03:00 8 месяцев, 3 недели назад
Ваш ответ
Введите минимум 50 символов
Чтобы , пожалуйста,
Выберите тему жалобы:

Другая проблема