0
votes

Within my model I wanting to add a role attribute that is a value based on what relationships the return user model has, so my user model has various relationships on it like below,

   /*
    * User - Supers
    * 1:1
    */
    public function super() {
        return $this->hasOne('App\Super');
    }

   /*
   * User - Teachers
   * 1:1
    */
   public function staff() {
        return $this->hasOne('App\Teacher');
   }

    /**
     * User - Students
     * 1:1
     */
    public function student() {
        return $this->hasOne('App\Student');
    }

What I am wanting to do is check if the user has a student or super relationship and set a role attribute based on that.

I thought I would be able to something like this,

public function getRoleAttribute() {
    if($this->student()->user_id) {
        return "Student";
    }
    //if($this->super)
}

but sadly not, the exception that gets return is this,

Undefined property: Illuminate\Database\Eloquent\Relations\HasOne::$user_id

does anyone have any idea how I can achieve this?

1
What was the issue doing that? What it returned?Avik Aghajanyan
added further information.Udders
does your 'students' table have that column?Avik Aghajanyan
It certainly does.Udders
Try accessing relationship without braces: $this->student. This should return the student model, whereas $this->student() returns the method.isa424

1 Answers

0
votes

Ok, I misunderstood the question at first.

A better way is to create a relation detection function and call it inside the model's constructor, then assign it to a new attribute.

<?php namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class User extends Model {

    protected $table = 'Users'; 
    private $role;

    public __construct() {
        $this->setRole();
    }

    private function setRole() {
        if (count($this->super)){
            $this->role = 'super';
        }elseif (count($this->staff)) {
            $this->role = 'staff';
        } elseif (count($this->student)) {
            $this->role = 'student';
        } else {
            $this->role = 'none';
            throw new \exception('no relation');
        }
    }

    public function super() {
        return $this->hasOne('App\Super');
    }

    /*
    * User - Teachers
    * 1:1
    */
    public function staff() {
        return $this->hasOne('App\Teacher');
    }

    /**
    * User - Students
    * 1:1
    */
    public function student() {
        return $this->hasOne('App\Student');
    }  
}

I based part of my answer on Laravel check if related model exists

edit: Laravel has a built-in-way to set attributes https://github.com/illuminate/database/blob/v4.2.17/Eloquent/Model.php#L2551