yiddishe-kop
yiddishe-kop

Reputation: 508

Laravel generate multiple models using factory HasMany relationship

In Laravel 8 we can create a user with multiple posts (hasMany relation) like so:

User::factory()
      ->has(Post::factory()->count(3))
      ->create();

But I want to create 3 users, each with 3 posts. I tried the following [added times(3)]:

User::factory()
      ->has(Post::factory()->count(3))
      ->times(3)
      ->create();

But this doesn't work. It creates the users, but not the posts.

I tried this in a seeder, and in tinker, with the same result.

I know I can do it in a loop, but isn't there a fluent way to do it? 💡

Upvotes: 3

Views: 4681

Answers (1)

Evangelos Bitsilis
Evangelos Bitsilis

Reputation: 885

For this example i assume you have a posts migration like the following

class CreatePostsTable extends Migration {

  public function up() {
    Schema::create('posts', function (Blueprint $table) {
        $table->id();
        $table->foreignId("user_id")->references("id")->on("users")->onDelete("cascade");
        $table->string("name");
        $table->timestamps();
    });
  }

  public function down() {
    Schema::dropIfExists('posts');
  }
}

PostsFactory.php like this one

class PostFactory extends Factory {

  protected $model = Post::class;

  public function definition() {

    return [
        "name" => $this->faker->words($nb = 3, $asText = true)
    ];
  }
}

and finally User.php model like this

  class User extends Authenticatable {
    use HasFactory, Notifiable;

    public function posts() {

      return $this->hasMany('App\Models\Post');

    }

  }

with that said you may do something like this in your DatabaseSeeder.php

User::factory()->times(3)->hasPosts(3)->create();

Then you can simply use: "php artisan migrate --seed" if your database is empty or "php artisan migrate:refresh --seed" in case it is not

Keep in mind that any records will be permanently lost after this action and the seeder will create new records

Upvotes: 3

Related Questions