如何在Laravel 5.1中生成自引用表的种子数据?

4
如何在一个表中使用两个来自同一张表的外键,例如像 messages 表:
迁移:
    public function up()
    {
        Schema::create('messages', function (Blueprint $table) {
            $table->increments('id');
            $table->integer('to')->unsigned();
            $table->integer('from')->unsigned();
            $table->integer('parent_id')->unsigned()->nullable();
            $table->text('body');
            $table->boolean('status')->default(false);
            $table->timestamps();
        });

        Schema::table('messages', function (Blueprint $table) {
            $table->foreign('to')
                    ->references('id')->on('users')
                    ->onDelete('cascade');

            $table->foreign('from')
                    ->references('id')->on('users')
                    ->onDelete('cascade');

            $table->foreign('parent_id')
                    ->references('id')->on('messages');

        });
    }

ModelFactory:
$factory->define(App\Message::class, function($faker) {

    return [
        'body' => $faker->text
        'from' => //user id,
        'to' => //user id,
        'parent_id' => //message id
    ];

});
  1. 我怎么在这里获取用户ID?
  2. 我如何获取特定ID的现有消息行?
2个回答

2
$messages = factory(App\Message::class, 20)->create();
$messageIds = DB::table('messages')->lists('id'); // returns array of userids
DB::table('categories')->where('id', $rowid); // where $rowid is the id which you want

完整的解决方案应该是这样的

class MessagesTableSeeder extends Seeder
{
    public function run()
    {
        // start with some cleanup    
        DB::table('messages')->truncate();
        // Create some App\Message instances...
        $messageCount = 30;
        $messages = factory(App\Message::class, $messageCount)->create();
        $messageIds = DB::table('messages')->lists('id');
        for($i=0; $i<$messageCount - 1; $i++) {
            $randomizedMessageIds = $messageIds;
            shuffle($randomizedMessageIds);
            DB::table('messages')->where('id', $i)->update(['parent_id'=>$randomizedMessageIds[$i]]);
        }
    }
}

快速提醒,列表已在5.3中被弃用,取而代之的是pluck,因此变成了:$messageIds = DB :: table('messages')-> pluck('id');它返回一个集合。为了将数组放入$randomizedMessageIds以进行洗牌,我们需要:$randomizedMessageIds = $messageIds-> all(); - theotherdy

0
有一个解决方案,虽然来晚了:
当为任何模型创建工厂时,前几次让parent_id为0。在数据库中创建指定的条目后,您可以传递已经创建的真实获取数据。
我正在使用此方法自引用类别和子类别。
 $factory->define(CMS\Models\Category::class, function (Faker\Generator $faker) {
    $users = \CMS\Models\User::all()->pluck('user_id')->toArray();

    /* Get all categories, if there are less then 4, the reference 
    is an array with a 0, meaning no parent. After 4 are created, we 
    start picking random categories s a parent ID, the list will grow 
    so does the variation. Of course you can set the minimum amount 
    of created categories as you wish.*/

    $categories = \CMS\Models\Category::all()->pluck('category_id');
    if (count($categories) <= 4) {
        $categories = [0];
    } else {
        $categories = $categories->toArray();
    }
    return [
        'category_id' => $faker->unique()->numberBetween(1,1000),
        'title' => $faker->sentence(1,40),
        'description' => $faker->text(50),
        'content' => $faker->paragraph(rand(3,5)),
        'approved' => $faker->boolean(),
        'trashed' => $faker->boolean(),
        'type' => $faker->randomElement('post','product'),
        'user_id' => $faker->randomElement($users),
        'parent_id' => $faker->randomElement($categories),
        'created_at' => $faker->dateTimeThisYear,
        'updated_at' => $faker->dateTimeThisYear,
    ];
});

使用这种方法,如果您设置count($categories) <= 1,则至少会有一个条目没有父级,这是将parent_id添加到您的数据库所需的。如果绝对需要所有条目都有parent_id,则只需要手动更改数据库中的1列即可。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接