Home > Net >  Laravel attach data to pivot table
Laravel attach data to pivot table

Time:10-22

So i am working on a laravel project with multiple table's and pivot table's but i cant attach data to a specific pivot table because it wont accept the name. as a user i want to be able to download files from the 'file' crud. That works. but after i downloaded i want to be able to see who downloaded what file as an admin, this does not work

the query i get is:INSERT INTO file_user (file_id, user_id) VALUES (7, 2)

i basically want to change the: file_user to download. but i have no idea how to do that without making a full query

table 'file'

  • id -name -file (document)

table 'user' -id -name -username -role

pivot table 'download' -id -file_id -user_id

user model:

 public function role(){
        return $this->belongsTo(Role::class,'role_id');
    }
    public function file(){
        return $this->belongsToMany(File::class);
    }
    

file model:

   public function user(){
        return $this->belongsToMany(User::class);
    }
    

    protected $table = 'file';

download model (pivot)

  protected $table = 'download';
    protected $fillable = [
        'file_id',
        'user_id',
    ];

    public function file() {
        return $this->belongsTo('file');
    }

    public function user() {
        return $this->belongsTo('users');
    }

controller:

 public function download(Request $request, int $fileId)
    {
        $id = Auth::user();
        $fullfile = File::find($fileId);
       
        $downloadfile = File::find($fullfile, ['file'])->pluck('file')->last();

       // return response()->download($downloadfile);
       dd($fullfile->user()->attach($id));
        return back();
    }

CodePudding user response:

In this case you have to pass the table name too.

public function file(){
    return $this->belongsToMany(File::class, 'download');
}
   public function user(){
    return $this->belongsToMany(User::class, 'download');
}

CodePudding user response:

I use a pivtot table for my application to simply be able to link multiple users to a task. However I do not use a model for my pivot table.. I don't think it is needed, you just need to migration table,

    {
        Schema::create('task_user', function (Blueprint $table) {
            $table->foreignId('task_id')->constrained()->onDelete('cascade');
            $table->foreignId('user_id')->constrained()->onDelete('cascade');
        });
    }
    

This is what I have.. If you did this it will simply save a user and your file when you attach a user.. if this function has the download too you could just check for the users on that file(they will have downloaded it)

you could go

$file->users()

And this would get your downloads (or make a scope for this since it will be easier to read)

I hope this helps!

CodePudding user response:

to work with pivot table in laravel, you most likely choose between 2 things: the pivot method and making a Pivot Model:

files[ id, name]
users[ id, name]
downloads[ id, file_id, user_id, download_at]

First solution: pivot method:

File Model (i will only put the relationship method here):

public function users()
{
   return $this->belongsToMany(User::class, 'downloads') //'downloads' is the table name, default is 'user_file'
            ->as('download');  //optional, this is how to access the table in code, default is 'pivot' $user->files->pivot, now $user->files->download
}

User Model:

public function files()
{
   return $this->belongsToMany(File::class, 'downloads')->as('download');
}

How to use:

//get user with id '1' and all of the files that he downloaded:
    $user = User::with('files')->find(1);

    $all_of_the_files_he_downloaded = $user->files;


//get file with id '2' and all the users that downloaded this file
    $file = File::with('users')->find(2);

    $all_users_that_downloaded_the_file = $file->users


//get the download time of every file that John Doe downloaded
    $user = User::with('files')->where('name', 'John Doe')->get();

    foreach($user->files as $file)
    {
        echo $file->download->downloadAt; //if you didn't use the ->as('download'): $file->pivot->downloadAt
    }

//get the download time of every user that downloaded the file with name 'Rick Roll'
    $file = File::with('users')->where('name', 'Rick Roll')->get();

    foreach($file->users as $user)
    {
        echo $user->download->downloadAt;
    }

Second solution: pivot Model

Download Model

<?php

    namespace App\Models;

    use Illuminate\Database\Eloquent\Relations\Pivot;

    class Progress extends Pivot
    {
        protected $table = 'downloads'; //here we need to specify a table because we didnt follow convention, aka. Download instead of UserFile

        public $incrementing = true; //specify auto-increment id
    }

User Model:

public function files()
{
   return $this->belongsToMany(File::class)->using(Download::class);
}

File Model:

public function users()
{
   return $this->belongsToMany(User::class)->using(Download::class);
}
  • Related