I'm getting the error:
BadMethodCallException in Macroable.php line 74: Method delete does
not exist.
route:
Route::resource('posts', 'PostController');
my controller:
public function destroy($id)
{
$user_id = Auth::user();
$post= Post::where('id', $id)->where('user_id',$user_id)->get();
$post->delete();
return view('/home', [
'posts' => $post
]);
}
view:
<form action="{{ route('posts.destroy', '$post->id') }}" method="post">
<input type="hidden" name="_method" value="DELETE" />
{{ csrf_field() }}
{{ method_field('DELETE') }}
<input type="submit" class="btn btn-danger" value="delete" />
</form>
I tried changing method="post" to delete: error is gone but nothing gets deleted..
This is your code.
$user_id = Auth::user();
$post= Post::where('id', $id)->where('user_id',$user_id)->get();
$post->delete();
just add ->each() before delete like this,
$post->each->delete();
It work's for me.
Remove get() and it will work
$post= Post::where('id', $id)->where('user_id',$user_id);
$post->delete();
If you want to delete first document you can use :
$post= Post::where('id', $id)->where('user_id',$user_id)->first();
$post->delete();
However, you always need to check if $post is found as a query document or its null so addd :
if($post){
$post->delete();
}
use ->first() instead of ->get()
you can't delete an entire collection with delete()
Change get for first, and check if the post belongs to the user afterwards.
public function destroy($id)
{
$post = Post::where('id', $id)->first();
if($post && $post->user_id == \Auth::user()->id){
$post->delete();
return view('/home');
}else{
abort(404);
}
}
controller:
public function destroy($id)
{
$post = Post::find($id);
$post->delete();
//redirect to
return redirect()->back();
}
view:
{!! Form::open(['method' => 'DELETE','route' => ['posts.destroy', $post->id],'style'=>'display:inline']) !!}
{!! Form::submit('Delete', ['class' => 'btn btn-danger']) !!}
{!! Form::close() !!}
Try this.
hope you created the controller with
--resource
flag.
As post id is primary key of posts table you can directly remove from table,
No need of user_id
To fetch user_id from Auth facade you should use,
$user_id = Auth::id();
Only by passing id should work,
Post::find($id)->delete()
However, if you know the primary key of the model, you may delete the model without retrieving it by calling the destroy method. In addition to a single primary key as its argument, the destroy method will accept multiple primary keys, an array of primary keys, or a collection of primary keys:
Post::destroy($id)
Please Try This:
public function destroy($id)
{
$userId = Auth::user()->id;
$post = Post::where([
'id' => $id,
'user_id' => $userId
])->delete();
Session::flash('success', 'Post was successfully deleted!');
return redirect()->route('posts.index');
}
This is how I am able to delete one (or multiple) associated record(s) in a table:
RFIResponseFile::where('rfi_response_id',$response_id)->delete();
Post::where('id', $id)->where('user_id',$user_id)->delete();
Or
$post= Post::where('id', $id)->where('user_id',$user_id);
if($post->get()->count()){
$post->delete();
}
In your controller
Before change code
public function destroy($id)
{
$user_id = Auth::user();
$post= Post::where('id', $id)->where('user_id',$user_id)->get();
$post->delete();
return view('/home', [
'posts' => $post
]);
}
After change code
public function destroy($id)
{
$user_id = Auth::user();
$post= Post::where(['id'=>$id,'user_id'=>$user_id])->get();
Post::where(['id'=>$id,'user_id'=>$user_id])->delete();
return view('/home', [
'posts' => $post
]);
}
Just add this on top of view, i 've error like you and now solved, sorry for bad english.
{!! Form::model($post, ['route' => ['posts.destroy', $post->id], 'method' => 'DELETE']) !!}
and
{!! Form::close() !!}
on bottom
for controller
$post = Post::find($id);
$post->delete();
Session::flash('success', 'Menu was successfully deleted!');
return redirect()->route('posts.index');
Related
I'm trying to have a button pass a query to the database when it's clicked. I'd like to have this set within a Controller that also stores requests and deletes requests. I was able to write to the database using store() and destroy(), but my edit() function gives me routing trouble. What is the best method to edit records using a controller? How would you build the edit() function? Or...should I be using the Update() function? I'm a Laravel/PHP beginner, please explain your answers if you can. Thank you!!
Overview: The project is an employee records table. I want to click a button that changes the employment status of an employee. I already have buttons to add new employee and delete and employee using this same Controller.
This is the route I set for the page:
Route::resource('employees', 'EmployeeController');
This is the front end form code for the button:
$workers = DB::table('employees')->get();
#foreach($workers as $employee)
{!! Form::open(array(
'method' => 'edit',
'route' => [ 'employees.edit', $employee->id]
)
)
!!}
<button type="submit">Release </button>
{!! Form::close() !!}
#endforeach
This is my store function and destroy function:
public function store(Request $request)
{
// Confirm Both Fields Are Not Empty
$this->validate($request, [
'first_name' => 'required',
'last_name' => 'required',
]);
//Add a new employee using the request data
$employee = new Employee;
$employee->first_name = request('first_name');
$employee->last_name = request('last_name');
$employee->position = request('position');
$employee->salary = request('salary');
$employee->hire_date = request('hire_date');
//$employee->attach = request('attach');
//Save it to the database
$employee->save();
//And then redirect back to the Employees page
return redirect('/employees');
}
public function destroy($id)
{
$employee = Employee::find($id);
$destroysignal = $employee->delete();
if($destroysignal) {
return redirect('employees');
}
}
You don't edit records, you update them. In your case you need an update() function in your controller
public function update(Request $request, $id)
{
$employee = Employee::findOrFail($id);
$employee->employment_status = true; //or false or whatever your statuses are
$employee->update();
return redirect()->back()->with('message', 'Employee updated!');
}
In your form, use the update route instead
{!! Form::model($employee, [
'method' => 'PATCH',
'route' => ['employees.update', $employee->id]])
!!}
<button type="submit">Release </button>
{!! Form::close() !!}
When using resource routes, 'route' => [ 'employees.edit', $employee->id] will most like to open a page where you want to edit the object. And the route will be bound to the edit($id) function of your controller.
With that said, the edit route doesn't need a form. A simple anchor would do
Edit Employee
I have table dosen and I want to update data to "statusdosen" column.
I have url : ...admin/dosen/status
When I click save, the page redirect to ..admin/dosen and all data in that row has been reset (empty).
This is my view
{!! Form::model($value, ['route' => ['admin.dosen.update', $value->user_id], 'method' => 'PUT']) !!}
<br>
{!! Form::select('statusdosen', array('1' => 'Dikampus', '0' => 'Tidak Dikampus'), null, ['placeholder' => 'Pilih Status'], ['class' => 'form-control']) !!}
<br><br>
!! Form::button('<i class="fa fa-check-square-o"></i> Simpan', ['type' => 'submit', 'class' => 'btn btn-primary btn-sm'] ) !!}
{!! Form::close() !!}
Method :
public function status()
{
$dosen = Dosen::paginate(10);
return view('admin/dosen.status', compact('dosen'));
}
public function update($id)
{
$dosenUpdate = Request::only(['nipy', 'namadosen', 'alamatdosen', 'notelpdosen', 'tempatlahirdosen', 'tanggallahirdosen']);
$user = User::find($id);
$user->dosen()->update($dosenUpdate);
return redirect('admin/dosen')->with('message', 'Data berhasil diubah!');
}
what i want is after i click save it not redirect to other page. do i must create new update method data for 'statusdosen'?
I think you are looking for something along the line of this
public function update(Request $request, $id) {
// Make sure the value is true/1 or false/0
$this->validate($request, ['statusDosen' => 'boolean']);
// Retrieve only the status
$statusDosen = $request->get('statusDosen');
// Update user->dosen()
$user = User::find($id);
$user->dosen()->update($statusDosen);
// Redirect back to the page you came from with your message
return redirect()->back()->with('message', 'Data berhasil diubah!');
}
Ok that explains evreything
$user = User::find($id);
Actually this is same as
Update
dosen
Set
Columnname1=$data, Columnnam2=data2
Where
user_id = $id
This means all rows with this user_id will be updated.
You should be doing like below
public function update($id) {
$dosenUpdate = Request::only(['nipy', 'namadosen', 'alamatdosen', 'notelpdosen', 'tempatlahirdosen', 'tanggallahirdosen']);
//$user= User::find($id); $user->dosen()->update($dosenUpdate);
$dosen = dosen::find($id); // parameter $id must be id of the dosen you want to update
$dosen->update(dosenUpdate);
return back()->with('message', 'Data berhasil diubah!');
}
The return back() will take you back to the previous page but all input value will not be there as the page is being reloaded.
If you do want to keep the data you've two ways
Use return back()->withInput() and store the data to the corresponding input using old.
Use AJAX, and return a response as json.
Eg:
return response()->json(['message'=>'Data berhasil diubah!');
I am having an issue with my resource route when calling the update method.
I get this error:
Creating default object from empty value
The controller:
public function update($id)
{
$input = Input::all();
$validation = Validator::make($input, Vehicle::$rules, Vehicle::$messages);
if ($validation->passes())
{
$this->vehicle->update($id, $input);
return Redirect::route('admin.vehicles.index')->with('success', 'Car Updated');
}
return Redirect::back()
->withInput()
->withErrors($validation);
}
repository:
public function update($id, $input)
{
$vehicle = Vehicle::find($id);
$vehicle->VRM = $input['VRM'];
$vehicle->make = $input['make'];
$vehicle->model = $input['model'];
$vehicle->description = $input['description'];
$vehicle->save();
}
Route:
Route::resource('/admin/vehicles', 'VehiclesController');
If I print the ID then it shows {vehicle}.
My form is this:
{{ Form::open(['route' => 'admin.vehicles.update', 'class' => 'form-horizontal edit-vehicle-form', 'method' => 'PATCH']) }}
// input fields etc
{{ Form::close() }}
I think there is something wrong with the form possibly? Since when the error is thrown the URL is:
http://localhost/admin/vehicles/%7Bvehicles%7D
Never had any issues before with using resource routes with CRUD applications and cant see where this is going wrong?
You need the id in update route...
{{ Form::open(['route' => array('admin.vehicles.update', $vehicle->id), 'class' => 'form-horizontal edit-vehicle-form', 'method' => 'PATCH']) }}
I am working on CRUD for my first Laravel project. Displaying and showing items is working fine.
I tried to update the entry with Query to confirm that I can change values in the table and it worked:
DB::update("UPDATE seasons SET title = 'foo' WHERE ID = 1");
My Problem is that neither updating nor deleting entries will work.
<?php
class SeasonAdminController extends \BaseController
{
// WORKS
public function store()
{
$season = new Season;
$season->title = Input::get('title');
$season->save();
Session::flash('message', 'success!');
return Redirect::to('backend/season');
}
// NOT WORKING
public function update($id)
{
$season = Season::find($id);
$season->title = Input::get('title');
$season->save();
Session::flash('message', 'success!');
return Redirect::to('backend/season');
}
// NOT WORKING
public function destroy($id)
{
Season::destroy($id);
Session::flash('message', 'success!');
return Redirect::to('backend/season/');
}
}
My Route is the following:
Route::resource('backend/season', 'SeasonAdminController');
The form-tag from the edit page:
{{ Form::model($season, array('route' => array('backend.season.update', $season->ID), 'method' => 'PUT')) }}
The form for deleting an entry:
{{ Form::open(array('url' => 'backend/season/' . $value->ID, 'class' => 'pull-right')) }}
{{ Form::hidden('_method', 'DELETE') }}
{{ Form::submit('Löschen', array('class' => 'btn btn-danger')) }}
{{ Form::close() }}
What am I missing here. I appreciate you help, thank you!
The error was that I had "ID" instead of "id" as a primary key in the database table. I am not quite sure why this should not work, but I guess it has to do with the default primary key from the Eloquent Model.
public function update($id){
$inputs = Input::only(array('title'));
if (!$id->update($inputs)) {
Session::flash('message', 'Error!');
}else{
Session::flash('message', 'success!');
}
return Redirect::to('backend/season');
}
public function destroy($id){
if($id){
if($id->delete()){
Session::flash('message', 'Success: Deleted!');
}else{
Session::flash('message', 'Error: Not Deleted!');
}
}
return Redirect::to('backend/season');
}
Try it out.
By the way, the $id is not the season id, can't use find($id) on it because it's an object.
Edit:
You should follow this tutorial
https://www.packtpub.com/books/content/laravel-4-creating-simple-crud-application-hours
Because you do not yet understand how to use models in routes.
Take special attention on how forms are built.
Check your model
class Session extends Model{
protected $table = 'session '; //DB table name
protected $primaryKey = 'Id'; //Primary key Name... some time ORM cant identify the primary key
}
I am trying to create a functionality for a user to be able to bookmark and article and remove the article from his bookmarks as well. The functionality to bookmark an article works just fine, but when I try to remove the article from the bookmarks then it does not work and instead it inserts the same record but with the article_id being NULL.
Here is my controller:
public function postBookmark() {
$user_id = Auth::user()->id;
$article_id = Input::get('id');
$bookmark = Bookmark::where('user_id', '=', $user_id)->where('article_id', '=', $article_id);
$article = Article::where('id', '=', $article_id);
$article = $article->first();
// I want to check if the article has been already bookmarked by the same user
// but this if statement always returns true
if(!empty($bookmark)) {
$bookmark = Bookmark::create(array(
'user_id' => $user_id,
'article_id' => $article_id,
));
if($bookmark) {
return View::make('article.view')
->with('article', $article)
->with('bookmarked', true);
}
} else {
// Does not work
$bookmark->delete();
return View::make('article.view')
->with('article', $article)
->with('bookmarked', false);
}
return Redirect::route('article-all')
->with('global', 'We were unable to bookmark the article. Please, try again later.');
}
And here is part of my view:
{{ Form::open(array('action' => 'BookmarkController#postBookmark')) }}
<input
type="checkbox"
name="id"
onClick="this.form.submit()"
value="{{ $article->id }}"
id="bookmark"
{{ $bookmarked ? 'checked' : '' }}
/>
<label for="bookmark">Bookmark</label>
{{ Form::close() }}
I do also have a route with a post method for this functionality. I would highly appreciate if anyone could give any idea of why it does not work.
You are not executing your bookmark query.
The $boomark variable in your code example is a Illuminate\Database\Eloquent\Builder object and empty($boomark) will return always false because there is a object stored.
To execute a query you can use get() for example. In your case you want only one result, then you use first() to retrieve the first found bookmark object.
Change:
$bookmark = Bookmark::where('user_id', '=', $user_id)->where('article_id', '=', $article_id);
To this:
$bookmark = Bookmark::where('user_id', '=', $user_id)->where('article_id', '=', $article_id)->first();
Then it should work fine.
If you really want, changing the condition if(!empty($bookmark)) to if ($bookmark->count()) { might do the trick, but it will do another query with COUNT() to the DB and it is not really a good way of doing it.
The problem is with if(!empty($bookmark)), because $bookmark has a QueryBuilder instance, it will never be empty.
The preferred way would be using Eloquent model relations. With relationships you could check by Article::has('bookmark') for instance.
Thanks for the help. I ended up using both of your solutions.
public function postBookmark() {
$user_id = Auth::id();
$article_id = Input::get('id');
$bookmark = User::find($user_id)->bookmarks()->where('article_id', '=', $article_id)->first();
if(empty($bookmark)) {
$bookmark = Bookmark::create(array(
'user_id' => $user_id,
'article_id' => $article_id,
));
if($bookmark) {
return Redirect::route('article-get', array('article_id' => $article_id));
}
} else {
$bookmark->delete();
return Redirect::route('article-get', array('article_id' => $article_id));
}
return Redirect::route('article-all')
->with('global', 'We were unable to bookmark the article. Please, try again later.');
}
Nonetheless, what I really needed to fix was my view. For some reason the id of my input was not being submitted properly, so I ended up creating a hidden field for it as well.
{{ Form::open(array('action' => 'BookmarkController#postBookmark')) }}
<input
type="checkbox"
name="id"
onClick="this.form.submit()"
value="{{ $article->id }}"
id="bookmark"
{{ $bookmarked ? 'checked' : '' }}
/>
<input
type="hidden"
name="id"
value="{{ $article->id }}"
/>
<label for="bookmark">Bookmark</label>
{{ Form::close() }}