【问题标题】:Nested relationships with Laravel faker - laravel seeder与 Laravel faker 的嵌套关系 - laravel 播种机
【发布时间】:2018-05-26 07:16:49
【问题描述】:

如 laravel 文档 https://laravel.com/docs/5.5/database-testing 中的关系部分所述,我想与用户和 cmets 一起创建一个 post seeder

  $users = factory(App\User::class, 3)
     ->create()
     ->each(function ($u) {
          $u->posts()->save(factory(App\Post::class)
            ->create()
            ->each(function($p){
                $p->comments()->save(factory(App\Comment::class,5)
                  ->create()
                  ->each(function($c){
                      $c->user()->save(factory(App\User::class)
                        ->make()
                      );
                  })
                );
              })
            );
        }
    );

预期的输出是让 3 个用户的帖子每人有 5 个 cmets。

但是发生了错误:

在 Builder.php 第 2459 行:调用未定义的方法 Illuminate\Database\Query\Builder::save()

【问题讨论】:

    标签: php laravel factories eloquent-relationship


    【解决方案1】:

    试试这个:

    $users = factory(App\User::class, 3)
         ->create()
         ->each(function ($u) {
              $u->posts()->save(factory(App\Post::class)->make())
                ->each(function($p){
                    $p->comments()->save(factory(App\Comment::class,5)->make())
                      ->each(function($c){
                          $c->user()->save(factory(App\User::class)
                            ->make()
                          );
                      })
                    );
                  })
                );
            }
        );
    

    使用常规 foreach 的解决方案

    $users = factory(App\User::class, 3)->create();
    
    foreach($users as $user){
        $post = $user->posts()
                              ->create(factory(App\Post::class)->make()->toArray());
        $post->comments()
                         ->createMany(
                                   factory(App\Comment::class, 5)
                          ->make(['user_id' => factory(App\User::class)
                                   ->create()->id])->toArray());
    }
    

    【讨论】:

    • 呃,我刚刚编辑了你的代码,问题是你试图在工厂创建的模型上使用 save() 方法。我认为使用常规 foreach 会不那么复杂
    • 我正在编辑我的解决方案,可能无法正常工作,因为我无法立即对其进行测试,但您可以大致了解 :)
    • 您的解决方案不起作用..但我知道我做错了什么..谢谢..在您的解决方案中,我们必须在创建方法中使用数组..不是吗..
    • 哈哈是的!确实 !它只是缺少 ->toArray() 吗?我编辑了我的答案,但如果你有一个可行的解决方案,你也可以编辑它:)
    • 上面的代码显示完整性约束违规:1062 Duplicate entry '1' for key 'PRIMARY' ..
    【解决方案2】:

    例如,您的解决方案中有几个问题

    $p->comments()->save(factory(App\Comment::class,5)
    

    您正在尝试使用 save() 保存多个 cmets,这将导致错误,您应该使用 saveMany() 代替。 但是,您的问题的解决方案可能是这样的:

    $users = factory(App\User::class, 3)->create()
            ->each(function ($user) {
                $user->posts()->saveMany(factory(App\Post::class, 5)->make());
            });
    foreach ($users as $user){
      foreach ($user->posts as $post){
        $post->comments()->saveMany(factory(App\Comment::class, 5)->make());
      }
    }
    

    这将按预期工作。

    【讨论】:

      【解决方案3】:

      试试这个方法:

              $users = factory(App\User::class, 5)->create();
      
          foreach ($users as $user) {
              $articles = factory(App\Article::class, 5)->create([
                  'user_id' => $user->id
              ]);
      
              foreach ($articles as $article) {
                  factory(App\Comment::class, 5)->create([
                      'article_id' => $article['id']
                  ]);
              }
          }
      

      【讨论】:

        猜你喜欢
        • 2019-05-18
        • 1970-01-01
        • 2018-09-10
        • 2018-09-03
        • 1970-01-01
        • 2016-05-28
        • 2017-10-17
        • 1970-01-01
        • 2014-10-27
        相关资源
        最近更新 更多