Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can I use php artisan db:seed to seed related tables?

Is it possible to seed related tables using the following in Laravel 5?

php artisan db:seed

I have two tables

users 
    id
    first name

projects
    id
    name

and a pivot table

project_user
    project_id
    user_id

I would like to create a number of users, a number of projects and then relate the users and their respective projects.

Seeding the users and projects isn't a problem but I am not sure how to handle the pivot table.

Is it possible?

like image 840
Mhluzi Bhaka Avatar asked Nov 10 '22 08:11

Mhluzi Bhaka


1 Answers

Of course you can. If you are using Eloquent, you can simply work with normal relations (maybe the easiest way). Or if you use the SQL builder directly, you can feed the table just as normal, but you need to stick to your foreign key rules.

Just give in a try and you'll see. But make sure you import classes you use.


Adding a relation between two models is easy, but there are some differences between the common relation types (and he perspective): one-to-many, many-to-one and many-to-many.


One-to-Many and Many-to-One

Assumed that each of your project has a creator, an owner so-to-say, you could have a 1:n relation between User and Project.

public class User {
    public function ownedProjects() {
        return $this->hasMany('App\Project');
    }
}

public class Project {
    public function owner() {
        return $this->belongsTo('App\User');
    }
}

In this relation, you can either attach a Project to a User or tell the Project who his owner is.

// Attach a project to an user
$project = Project::create([]);
User::find($id)->ownedProjects()->save($project);
// There is also a function saveMany() for an array of projects

// Tell the project who his owner is
$project = Project::create([]);
$project->owner()->associate(User::find($id));


Many-to-Many

In your case, we need a Many-to-Many relation between Users and Projects. The syntax is a bit different, but the outcome quite straight forward. First we need a relation between the both models:

public class User {
    public function projects() {
        return $this->belongsToMany('App\Project');
    }
}

public class Project {
    public function users() {
        return $this->belongsToMany('App\User');
    }
}

Then we can query the relation just like that:

$project = Project::create([]);
User::find($id)->projects()->attach($project->id);

You can also attach a whole bunch of projects, do the same things from the other side, detach models or synchronize them, if you want to make sure that an exact amount (and only this amount) is in relation:

// Adds a relation for the user to projects with ids 1, 2, 4 and 6
User::find($id)->projects()->attach([1, 2, 4, 6]);

// Adds the users with ids 19 and 173 to this project
Project::find($id)->users()->attach([19, 173]);

// Removes the user 19 from the projects relations
Project::find($id)->users()->detach(19);

// Removes all relations between this user and projects that are 
// not listed in the synchronization array and adds a relation 
// to all projects where none exists yet
User::find($id)->projects()->sync([4, 7, 19, 6, 38]);

This is the normal syntax for Many-to-Many relations, but you can also attach models just like in a One-to-Many relation:

// Creation of project could also be done before and saved to a variable
User::find($id)->projects()->save(Project::create([]));
like image 152
Namoshek Avatar answered Nov 14 '22 22:11

Namoshek