kumareth
kumareth

Reputation: 317

Model Relationships not working in Laravel 5.5

I am trying to relate my Picture Model to the User Model by belongsTo and hasMany methods.


Heres the code written in Picture.php model file:

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Picture extends Model{

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

}


Here's the code of my User.php model file:

  <?php

  namespace App;

  use Illuminate\Notifications\Notifiable;
  use Illuminate\Foundation\Auth\User as Authenticatable;

  class User extends Authenticatable
  {

  use Notifiable;

  /**
   * The attributes that are mass assignable.
   *
   * @var array
   */
  protected $fillable = [
      'name',
      'email',
      'password',
  ];

  /**
   * The attributes that should be hidden for arrays.
   *
   * @var array
   */
  protected $hidden = [
      'password', 'remember_token',
  ];

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

  }


I want to show the pictures uploaded by the user itself in the manage view which is demonstrated in my RouteController file:

  <?php

  namespace App\Http\Controllers;

  use Illuminate\Http\Request;
  use App\Picture;
  use App\User;
  use DB;

 class RouteController extends Controller
  {
  /**
   * Create a new controller instance.
   *
   * @return void
   */
  public function __construct()
  {
      $this->middleware('auth', ['except' => ['welcome', 'auth.login', 'auth.register']]);
  }

  public function welcome()
  {
      $pictures = Picture::all();
      return view('welcome')->with('pictures', $pictures);
  }

  public function login()
  {
      return view('auth.login');
  }

  public function register()
  {
      return view('auth.register');
  }

  public function manage()
  {
      $user_id = auth()->user('id');
      $user = User::find($user_id);
      $pictures = Picture::all();
      return view('pictures.manage')->with('pictures', $pictures->user);
  }
  }


And in the manage.blade.php I have to output the pictures. For that, I written this code:

@foreach ($pictures as $picture)
   <div class="well">
     <h3>{{ $picture->hash }}</h3>
   </div>
@endforeach


And after all this hustle and bustle, it gives me an error which says: Property [user] does not exist on this collection instance.
I want the pictures owned by the user to output in manage view. If you want to see all the files in the project, visit this GitHub commit.

Thanks for help in advance

Upvotes: 0

Views: 667

Answers (4)

Tpojka
Tpojka

Reputation: 7111

In your pictures migration you need to add user_id foreign key to be able having relation between users and pictures as you have in your models. Something like this:

use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;

class CreatePicturesTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('pictures', function (Blueprint $table) {
            $table->increments('id');
            // $table->string('storage_url');
            // $table->string('preview_url');
            $table->string('hash');
            $table->unsignedInteger('user_id');// or $table->integer('user_id')->unsigned();
            $table->timestamps();
        });

        Schema::table('pictures', function (Blueprint $table) {
            $table->foreign('user_id')->references('id')->on('users');
            // also you can put some triggered actions ->onUpdate('cascade')->onDelete('cascade')
        });
    }
    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::table('pictures', function (Blueprint $table) {
            $table->dropForeign(['user_id']);
        });

        Schema::dropIfExists('pictures');
    }
}

Just be certain that users.id and pictures.user_id have to be same type fields.

Check various options in docs. And then, what other said in answers.

Upvotes: 1

divya_kanak
divya_kanak

Reputation: 142

Please add relationship between user and pictures.

Make new migration for add foreign key in pictures model . Please refer below link. https://laravel.com/docs/5.6/migrations

Also add foreign key column name in pictures model in fillable part.

Then after change your mange method code like...

$user = User::with(['pictures'])->where('id', Auth::id())->first();

return view('pictures.manage')->with(['pictures' => $user['pictures']);

Upvotes: 0

Maru Amallo
Maru Amallo

Reputation: 430

I think tour problem is into manage method.
Try to do that

  public function manage()
  {
      $user = auth()->user();
      $pictures = $user->pictures;
      return view('pictures.manage')->with(['pictures' => $pictures]);
  }

Upvotes: 1

DevK
DevK

Reputation: 9942

This happens because you're calling $pictures->user. $pictures holds a collection (enhanced array) of all pictures from this statement: $pictures = Picture::all();. A collection is not an object and doesn't have properties.

Also, you're not scoping your pictures to user's only anywhere. You're calling Picture::all() which will return all pictures from all users.

Assuming your relationships work as intended you could get currently logged in user's picture with $user->pictures method. This is all you need:

  $pictures = auth()->user()->pictures;
  return view('pictures.manage')->with('pictures', $pictures);

And also remove the ->user part from ->with('pictures', $pictures).

Upvotes: 1

Related Questions