3

I have a view that list all objects in a database and for each object creates a form for saving to a different table. My problem is, that the value isn't being passed to my function.

Here is my blade.php file:

@extends('layouts.app')
@section('content')
<div class="container">
 <div class="row justify-content-center">
 <div class="col-md-12">
 <div class="card">
 <div class="card-header">{{ __('Items') }}</div>
 <div class="card-body">
 <div class="row">
 @foreach($items as $item)
 <div class="col-md-3 col-xs-12">
 <div class="card">
 <img src="..." class="card-img-top" alt="...">
 <div class="card-body">
 <h5 class="card-title">{{ $item->name }}</h5>
 <p class="card-text">$ {{ $item->price }}</p>
 @auth
 <form method="post" action="{{ route('carts.store', $item) }}"> 
 @csrf
 @method('post')
 <button type="submit" class="form-control btn">add to cart</button>
 </form>
 @endauth
 <form method="post" action="{{ route('item.destroy', $item) }}"> 
 @csrf
 @method('delete')
 <button type="submit" class="form-control btn btn-danger">delete</button>
 </form>
 </div>
 </div>
 </div>
 @endforeach
 </div>
 </div>
 </div>
 </div>
 </div>
</div>
@endsection

and my function in the CartsController:

public function store(Item $item)
{
 $cart = new Cart();
 $cart->user_id = auth()->id();
 $cart->item_id = $item->id;
 
 $cart->save();
 return redirect('/item');
}

When I click on add to cart I get this error:

SQLSTATE[23000]: Integrity constraint violation: 1048 Column 'item_id' cannot be null (SQL: insert into `carts` (`user_id`, `item_id`, `updated_at`, `created_at`) values (1, ?, 2020年08月24日 07:35:44, 2020年08月24日 07:35:44))

I've tried passing the id to the function directly but that also doesn't seem to work. I'm very confused as to why this is happening since I can use $item two rows earlier without a problem.

asked Aug 24, 2020 at 7:48
3
  • 1
    Are you using implicit or explicit route model binding? Commented Aug 24, 2020 at 8:03
  • implicit I think. I'm still very new to php and laravel Commented Aug 24, 2020 at 8:08
  • You suppose to pass the $item->id as in action="{{ route('carts.store', $item->id ) }}". Commented Aug 24, 2020 at 8:10

1 Answer 1

2

Provided that your route model binding is setup correctly, it won't actually matter whether you pass the id of an object or the object itself to the the route() function.

https://laravel.com/docs/7.x/routing#implicit-binding

When you run php artisan route:list, you should see something similar to this:

POST | cart/store/item/{item} | carts.store | App\Http\Controllers\CartController@store 

Laravel automatically resolves Eloquent models defined in routes or controller actions whose type-hinted variable names match a route segment name.

So any of the following will actually work

{{ route('carts.store', $item) }}

OR

{{ route('carts.store', $item->id) }}

OR

{{ route('carts.store', ['item' => $item->id]) }}

Should all resolve to the same thing.


Addendum

So the route you are using doesn't have a route parameter for your item (i.e {item}), as such it won't know which Item object you are referencing.

You can either:

  1. Amend your route to include this route parameter

OR

  1. use the Request object to resolve the Item instead.

Blade

<form method="post" action="{{ route('carts.store') }}"> 
 @csrf
 @method('post')
 <input type="hidden" name="item_id" value="{{ $item->id }}">
 <button type="submit" class="form-control btn">add to cart</button>
</form>

Controller

public function store(Request $request)
{
 $cart = new Cart();
 $cart->user_id = auth()->id();
 $cart->item_id = $request->item_id;
 
 $cart->save();
 return redirect('/item');
}
answered Aug 24, 2020 at 8:25
Sign up to request clarification or add additional context in comments.

2 Comments

php artisan routes:list returns this POST | carts | carts.store | App\Http\Controllers\CartsController@store | web The $fillable array is also set up correctly. But it's still not working
See the addendum to my answer with an explaination of what's going on

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.