CookieMonster's avatar

How do I send put method on an anchor tag?

I want to use destroy method on laravel to delete an existing item for the user. Normally, one would use a route::put or patch along with the form to mask the submit button to send the delete request.

I was wondering if I have a delete icon and I can use anchor tag with route to perform the request like below:

Blade view:

 <div class="row">
                               <div class="offset-2 col-5">         
                                    <a href="{{route('shop.perfect-list.destroy',[$item->product->global_product_id])}}"> <i class="fa fa-trash-o fa-2x text-muted mt-4 padding-left-icon"></i></a>
                               </div>
                           </div>

Route:

Route::put('/remove/{product_id}','Shop\WishListController@destroy')->name('shop.perfect-list.destroy');

Controller:

 //Remove the specified item from storage.
    public function destroy($product_id){
        $userID = Auth::user()->id;
        $perfectList = new Favorite;
        $perfectList = $perfectList->where('user_id',$userID)->where('product_id',$product_id)->first();
        dd($perfectList);
    }

Of course running this gives me the error:

The GET method is not supported for this route. Supported methods: PUT.

Since I am not masking a @csrf into my blade.

Any alternatives or suggestion I could use?

0 likes
26 replies
MichalOravec's avatar

@nickywan123 You can add hidden form, and with js submit form when you click on the link.

<a href="{{ route('shop.perfect-list.destroy',[$item->product->global_product_id]) }}" onclick="event.preventDefault(); document.getElementById('submit-form').submit();">
    <i class="fa fa-trash-o fa-2x text-muted mt-4 padding-left-icon"></i>
</a>

<form id="submit-form" action="{{ route('shop.perfect-list.destroy',[$item->product->global_product_id]) }}" method="POST" class="hidden">
    @csrf

    @method('PUT')
</form>
CookieMonster's avatar

So I just add a hidden form and that's it?

Tried your method and still throws same error.

CookieMonster's avatar

I use dd to display and every different item I click still shows the same product id =16, why is that?

Is it because I use first()?

piljac1's avatar

Alternatively, you can also wrap your content in the form itself :

<form id="perfect-list-destroy" action="{{ route('shop.perfect-list.destroy', [$item->product->global_product_id]) }}" method="POST">
    @method('PUT')
    @csrf
    <a href="javascript:void(0);" onclick="document.getElementById('perfect-list-destroy').submit();"> <i class="fa fa-trash-o fa-2x text-muted mt-4 padding-left-icon"></i></a>
</form>

Also, you should consider using the "DELETE" method since you're destroying something.

MichalOravec's avatar
Level 75

@nickywan123 Change it to this

Route::delete('/remove/{product_id}', 'Shop\WishListController@destroy')->name('shop.perfect-list.destroy');
public function destroy($product_id){
    Favorite::where('user_id', Auth::id())->where('product_id', $product_id)->firstOrFail()->delete();
}
<a href="{{ route('shop.perfect-list.destroy',[$item->product->global_product_id]) }}" onclick="event.preventDefault(); document.getElementById('submit-form').submit();">
    <i class="fa fa-trash-o fa-2x text-muted mt-4 padding-left-icon"></i>
</a>

<form id="submit-form" action="{{ route('shop.perfect-list.destroy',[$item->product->global_product_id]) }}" method="POST" class="hidden">
    @csrf

    @method('DELETE')
</form>
2 likes
piljac1's avatar

Your request might be redirected, hence why you would it will be calling your route using GET. That is the case if you're using Laravel Localization. You need to ignore this URL in your configs if it is the case.

CookieMonster's avatar

I tried to dd to get my product id but all the items I click delete returns 16 so obviously, I didn't pass the correct product id.

piljac1's avatar

That of course is a problem, but it isn't the source of your original problem though.

CookieMonster's avatar

I don't know if the javascript introduced in the blade cause my product id not to be detected?

MichalOravec's avatar

@nickywan123 Of course not, you send there $item->product->global_product_id so search here for your problem. What is it global_product_id?

CookieMonster's avatar

It is a product id uniquely for each item. By right, my logic is correct and should return the product id for the item I click delete for. It's inside the foreach loop so it should be able to identify the product id of each item. What else should I be looking for?

MichalOravec's avatar

@nickywan123 Check your source code if you have everytime different generated url withroute('shop.perfect-list.destroy',[$item->product->global_product_id])

CookieMonster's avatar

Your solution gives me this error:

The PUT method is not supported for this route. Supported methods: DELETE."

MichalOravec's avatar

@nickywan123 You need to use

@method('DELETE')

instead of

@method('PUT')

If your route is

Route::delete('/remove/{product_id}', 'Shop\WishListController@destroy')->name('shop.perfect-list.destroy');
CookieMonster's avatar

I did that, I believe I need to use:

@method('delete')

instead of

@method('DELETE')

Somehow it works if I use lowercase. Why is that?

CookieMonster's avatar

Also, why do you use delete() instead of destroy()?

When do I use each?

Please or to participate in this conversation.