简体   繁体   中英

How can I get a pivot on my relationship in Laravel?

I have a relationship in my app. A candidate can have several "candidate_trainings" and each "candidate_training" is associated with a training. I wanted to avoid making "candidate_trainings" the piviot since it's hard to delete the right values when detaching, etc. So, how can I, on my hasMany relationship get the CandidateTraining model with the data from the Training model.

Here are my relationships:

<?php

namespace App;

use App\Traits\SanitizeIds;
use App\Salary;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Facades\Storage;

class Candidate extends Model
{

    public function saveTraining($data) {
        $this->candidateTrainings()->delete();
        foreach(json_decode($data['training']) as $training) {
            if(Training::find($training->training)->first()) {
                $candidateTraining = new CandidateTraining;
                $candidateTraining->description = $training->value;
                $candidateTraining->training_id = $training->training;
                $this->candidateTrainings()->save($candidateTraining);
            }
        }
    }


    public function candidateTrainings() {
        return $this->hasMany('\App\CandidateTraining');
    }

    public function trainings() {
        return $this->belongsToMany('\App\Training');
    }

}

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Training extends Model
{
    protected $fillable = ['name_french', 'name_english'];

    public function candidates() {
        return $this->belongsToMany('\App\Candidate');
    }

    public function candidateTrainings() {
        return $this->hasMany('\App\CandidateTraining');
    }
}

<?php

namespace App;

use Illuminate\Database\Eloquent\Relations\Pivot;

class CandidateTraining extends Pivot
{
    public function candidate() {
        return $this->belongsTo('\App\Candidate');
    }

    public function training() {
        return $this->belongsTo('\App\Training');
    }
}

Thank you!

For you to be able to update the data directly on the CandidateTraining model, you need to add the $fillable fields to it.

protected $fillable = ['training_id', 'description'];

Your code should work! But if you don't mind, I did a little refactoring. You can accomplish this in another way:

<?php

namespace App;

use App\Traits\SanitizeIds;
use App\Salary;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Facades\Storage;

class Candidate extends Model
{
    public function saveTraining($data)
    {
        // remove all relationships
        $this->trainings()->detach();

        // add new ones
        foreach(json_decode($data['training']) as $training)
        {
            if(Training::find($training->training)->first())
            {
                $this->trainings()->attach($training->training, [
                    'description' => $training->value,
                ]);
            }
        }
    }

    public function candidateTrainings()
    {
        return $this->hasMany(App\CandidateTraining::class);
    }

    public function trainings()
    {
        return $this->belongsToMany(App\Training::class)
            ->withTimestamps()
            ->using(App\CandidateTraining::class)
            ->withPivot([
                'id',
                'training_id',
                'description',
            ]);
    }
}

That $training->training stuff is not readable, change it to something like $training->id if you are able to.

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Training extends Model
{
    protected $fillable = ['name_french', 'name_english'];

    public function candidates()
    {
        return $this->belongsToMany(App\Candidate::class)
            ->withTimestamps()
            ->using(App\CandidateTraining::class)
            ->withPivot([
                'id',
                'training_id',
                'description',
            ]);;
    }

    public function candidateTrainings()
    {
        return $this->hasMany(App\CandidateTraining::class);
    }
}

<?php

namespace App;

use Illuminate\Database\Eloquent\Relations\Pivot;

class CandidateTraining extends Pivot
{
    protected $fillable = ['training_id', 'description'];

    public function candidate()
    {
        return $this->belongsTo(App\Candidate::class);
    }

    public function training()
    {
        return $this->belongsTo(App\Training::class);
    }
}

If you want to access the pivot object from a controller:

$candidates = Candidate::with(['trainings'])->get();
foreach ($candidates as $candidate)
{
    dd($candidate->pivot);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM