Reputation:
I'm developing an admin panel for the library. I need insert book with more authors. I bild book insert in my controller/ But i don`t understand how i can insert authors i to table "authors" from BooksController, with the condition that I need to check, there is my such author in the table and if there is not to add. Thath code of BooksController:
public function insert(Request $request)
{
$BookName = $request->input('bookname');
if(!empty($BookName)){
$NewBook = new Books;
$NewBook->name = $BookName;
$BookFile = $request->file('books_file');
if(!empty($BookFile)){
$NewBook->img = $BookFile->getClientOriginalName();
$BookFile->move( storage_path('images/books/'), $BookFile->getClientOriginalName());
}
$NewBook->save();
$AuthorsNames = $request->input('authors');
if(!empty($AuthorsNames)){
$AuthorsFiles = $request->file('authfiles');
}
return "Scs";
}else{
return 'Enter book title';
}
}
I read the documentation about the necessary functions, but I did not understand how to use them. In my code, I accept an array of authors, since one book can have many authors. I will be very grateful not for the code, but for the necessary functions and an explanation of how to use them.
Upvotes: 1
Views: 69
Reputation: 35337
The Laravel docs cover this in detail.
https://laravel.com/docs/5.5/eloquent-relationships#updating-many-to-many-relationships
Attaching / Detaching
Eloquent also provides a few additional helper methods to make working with related models more convenient. For example, let's imagine a user can have many roles and a role can have many users. To attach a role to a user by inserting a record in the intermediate table that joins the models, use the attach method:
$user = App\User::find(1);
$user->roles()->attach($roleId);
When attaching a relationship to a model, you may also pass an array of additional data to be inserted into the intermediate table:
In your example, an author should already exist because a many to many relationship means you have a book in the books table, an author in the authors table, and both primary keys (id) linked in an intermediate table.
If the author does not yet exist, save the author and get the id and use attach to add their id to the book. A Book model should not care about the author name, only the ID.
Authors and Books should be thought of as completely separate until you link them. So a Book should be created separately and an Author should be created separately then you link them. In other words, you really shouldn't be creating authors from the BookController, but if you want to, create an Author model like you would with any other, something like $author = Author::create($data)
, then attach it using $book->authors()->attach($author->id)
The major problem I see with your structure is how do you know if an author already exists? Two different authors could share the same name. Ideally, I'd recommended passing ids to the BookController, not names.
Upvotes: 1
Reputation: 197
Basically you need two other table beside your book table, one is author table which for that you need to create a model class for your Author and with that you can add Author. And a pivot table authors_books, since it is a many to many relation.
Author::create(['name' => $name,....]);
and
Schema::create('authors_books', function (Blueprint $table) {
$table->increments('id');
$table->integer('author_id')->unsigned();
$table->integer('book_id')->unsigned();
$table->foreign('author_id')->references('id')->on('authors')->onDelete('cascade');
$table->foreign('book_id')->references('id')->on('books')->onDelete('cascade');
$table->timestamps();
});
And you can add to the pivot table:
DB::table('authors_books')->insert(
['author_id' => $author, 'book_id' => $book_id]
);
Upvotes: 1