How to pass id from ajax to controller - Laravel & Ajax - ajax

Currently, i am on the show page that is i am running the function show as in my controller so my url is showing like dashboard/1/people in the url address bar. Now, when i click on a person, it routes to a different page and that is where getPeople is called.
How can i get the id of the person i clicked which is 1 from the ajax request in the scripts and pass to my controller?
PS: At the moment, i have hardcoded 1 in the ajax request but i want it to be dynamic please
How do i get this done?
Script
datatable = $('#table').DataTable({
"ajax": "{{ route('dashboard/1/people') }}",
"columns": [
{data: 'check', name: 'check'},
],
Controller
public function show($id)
{
$class = Class::whereId($id)->first();
return view('show');
}
public function getPeople($id)
{
$get_id = $id;
$class = Class::whereId($get_id)->first();
$people = $class->peoples()->get();
return Datatables::of($people)->addColumn('action', function ($ppl) {
//return
})->make(true);
}

This should work:
In your getPeople method store the id in a session variable:
public function getPeople($id)
{
$get_id = $id;
//using session helper method
session(['show_id' => $id]);
$class = Class::whereId($get_id)->first();
$people = $class->peoples()->get();
return Datatables::of($people)->addColumn('action', function ($ppl) {
//return
})->make(true);
}
and then access it in you ajax code:
datatable = $('#table').DataTable({
"ajax": "{{ route('dashboard/'.session('show_id').'/people') }}",
"columns": [
{data: 'check', name: 'check'},
],

DataTable ajax allows yo to pass extra parameters in object format just like this:
datatable = $('#table').DataTable({
"ajax": {
"type": "GET",
data:{id: my_id_var},
"url": "my_route"
}
}
And in your function just get the Request var
public function getPeople(Request $request){
$get_id = $request->id;
$class = Class::whereId($get_id)->first();
$people = $class->peoples()->get();
return Datatables::of($people)->addColumn('action', function ($ppl) {
//return
})->make(true);
}
More Information in Sorce Page

Related

laravel using jQuery Ajax | Ajax Cart

I'm Trying to Save The Product into The Database By Clicking On Add To Cart
But It's Not Adding I Also Use Ajax `
I Want To Add The Cart To DataBase And It's Not Adding.
This is The Error That I cant Add Any Product To The Cart Because Of It
message: "Call to undefined method App\User\Cart::where()", exception: "Error",…
enter image description here
Model Page.
class Cart extends Model
{
use HasFactory; I
protected $table = 'carts';
protected $fillable = [
'user_id',
'prod_id',
'prod_qty',
];
}
Controller page.
public function addToCart(Request $request)
{
$product_qty = $request->input('product_qty');
$product_id = $request->input ('product_id');
if(Auth::check())
{
$prod_check = Product::where('id',$product_id)->first();
if($prod_check)
{
if(Cart::where('prod_id',$product_id)->where('user_id',Auth::id())->exists())
{
return response()->json(['status' => $prod_check->pname." Already Added to cart"]);
}
else
{
$cartItem - new Cart();
$cartItem->user_id = Auth::id();
$cartItem->prod_qty = $product_qty;
$cartItem->save();
return response()->json(['status' => $prod_check->pname." Added to cart"]);
}
}
}
else{
return response()->json(['status' => "Login to Continue"]);
}
}
javascript page.
This Is MY First Time To Use Ajax And Sure That Every Thing Is Correct I Want Know Why Its Not Add
$('.addToCartBtn').click(function (e) {
e.preventDefault();
var product_id = $(this).closest('.product_data').find('.prod_id').val();
var product_qty = $(this).closest('.product_data').find('.qty-input').val();
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
$.ajax({
method: "POST",
url: "/add-to-cart",
data: {
'product_id': product_id,
'product_qty': product_qty,
},
success: function (response) {
alert(response.status);
}
});
// alert(product_id);
// alert(product_qty);
// // alert ("test ") ;
});
Route:
Route::middleware(['auth'])->group(function () {
Route::post('/add-to-cart', [App\Http\Controllers\User\indexController::class, 'addToCart' ]);});
So why this error occurs, how can I fix it?`
This look like an error in importation like App\Models\Cart not like this?
verify if you had added use App\Models\Cart;

how to get id for use in another function in controller laravel

I'm trying to use the id from my show function in my controller,
My controller works correctly with this $id
public function show($id)
{
$DigestReport = Meo::find($id);
return view('digest-report.show', ['DigestReport' => $DigestReport]);
}
I'm trying to use the same $id for another function
public function getMailRecipients($id){
$meoId = Meo::find(id);
$mailRecipients = $this->meoRepository->getMailRecipients($meoId);
return DataTables::of($mailRecipients)->make();
}
but I get the following error
Too few arguments to function
DigestReportController::getMailRecipients(), 0 passed on line 54 and
exactly 1 expected
How can I fix it?
added: if necessary, this is my repository
public function getMailRecipients($meoId){
return DB::table('mail_recipients')->where('meo_id', '=', $meoId)->select('id', 'name', 'email')->get();
My api.php where are my stored routes
Route::get('/digest-report/mail-recipients', 'DigestReportController#getMailRecipients')->name('digest-report.mail-recipients');
My view where I'm using this controller, is for make a datatable
$(document).ready(function () {
$('#mail-recipient-table').DataTable({
"processing": true,
"serverSide": true,
"ajax": '{{route('digest-report.mail-recipients')}}',
"columns": [{data:'id'},{data: 'name'},{data: 'email'}]
});
})
Thanks
Ok you have two ways to do this
in your web.php you will update your route to be
Route::get('/digest-report/mail-recipients/{id}', 'DigestReportController#getMailRecipients')->name('digest-report.mail-recipients');
then you javascript code will be
$(document).ready(function () {
$('#mail-recipient-table').DataTable({
"processing": true,
"serverSide": true,
"ajax": '{{route('digest-report.mail-recipients', $DigestReport->id)}}',
"columns": [{data:'id'},{data: 'name'},{data: 'email'}]
});
})
in you controller you will update getMailRecipients
public function getMailRecipients(Request $request){
$meoId = Meo::find($request->id); // or using helper request('id') function
$mailRecipients = $this->meoRepository->getMailRecipients($meoId);
return DataTables::of($mailRecipients)->make();
}
and your javascript code will be the same

How to return back to a paginated page?

Using Laraver Inertia Vue
I use a vue with a paginated list of posts. For each post I only load a few column from the database such as title and author. Then I visit url to load the details of a chosen post in the list. I do so using visit url with the lazy loading functionality. After that I am ready to edit the post without reloading the full page. Once the post is updated I submit it and correctly save it into the database. After that I can return back to the page. Everything happens without any reloading on the list.
In order to be able to load the details on a specific post lazily, my on controller is like this.
class PostController extends Controller
{
public function Index($id = null)
{
$this->id = $id;
return Inertia::render('Posts/Index', [
'posts' => Post::select('id', 'title', 'created_at')
->addSelect([
'userfirstname' => User::select('firstname')->whereColumn('id', 'posts.user_id'),
'userlastname' => User::select('familyname')->whereColumn('id', 'posts.user_id')
])
->orderBy('created_at', 'DESC')
->paginate(10),
//lazily evaluated
'details' => function () {
if ($this->id) {
$post = Post::find($this->id);
} else {
$post = null;
}
return $post;
},
]);
}
public function Update(Request $request)
{
$request->validate([
'id'=>'required',
'abstract'=>'required',
//TODO :to be completed
]);
$post=Post::find($request->input('id'));
$post->abstract=$request->input('abstract');
$post->title=$request->input('title');
//TODO to be completed
$post->save();
return Redirect::back();
}
}
and the method I use to load page and details are these:
//visit this url to get the lazzy evaluation of post details
if (to_visit) {
this.$inertia
.visit(`/posts/${to_visit}`, {
method: "get",
data: {},
replace: false,
preserveState: true,
preserveScroll: true,
only: ["details"],
headers: {}
})
.then(to_visit => {
console.log("fetched " + this.details.title);
});
}
},
updatePost(form) {
console.log("form submitted");
this.$inertia.visit(`/post`, {
method: "put",
data: form,
replace: false,
preserveState: true,
preserveScroll: true,
only: [],
headers: {}
});
},
This works fine as long as the particular post I update is on the first page, but when it is on the any other paginated page on the list, post saving is ok but I don't return on the paginated page but always on the first one.
Would be happy to ear about a solution!

yajra/laravel-datatables, Reply Slow

Summary of problem or feature request
The reply o load datatable is very slow, betwen 3-5seg
How can I optimize the data load?
when I did not use server inside it was much faster..
first of all, Thanks
Code snippet of problem
Controller
public function list_user(){
$users = User::all();
$users->each(function ($users)
{
$users->role;
});
return datatables()->collection($users)->toJson();
}
Js
function activar_tabla_users() {
$('#DataTableUser').DataTable({
"processing" : true,
"serverSide" : true,
"searchDelay" : 500,
"responsive": {
orthogonal: 'responsive'
},
"language": {
"url": '{!! asset('/plugins/datatables.net/latino.json') !!}'
} ,
"lengthMenu": [5,10, 25, 50, 75 ],
"ajax":'{!! url('admin/list_user') !!}',
columns: [
{data: 'id' },
{data: 'username'},
{data: 'name',
render: function (data, type, row, meta) {
return row.name + ' ' + row.lastname;
}
},
{data: 'email'},
{data: 'role.name',
render: function(data, type, row, meta) {
var html = ''
if ( row.role.name == 'Administrador' )
{
html = '<span class="label label-danger" > <label style="width:80px;"> '+row.role.name+' </label></span>';
}else {
html = '<span class="label label-primary" > <label style="width:80px;"> '+row.role.name+' </label></span>';
}
return html;
}
}
}],
});
}
activar_tabla_users();
You are using server side to get table data. Don't call all() as it will get all.
Replace:
$users = User::all();
With:
$users = User::query();
This only renders the required data in data-table page.
And, don't use loop to get role. Use eager loading using with();
$users = User::query()->with('role');
$users = User::all();
$users->each(function ($users)
{
$users->role;
});
with this the following?
$users = User::with('role');
Datatable adds pagination options automatically. if you use all() it calls all the data from the table.
Another thing is did you checked that it takes 2/3sec to get data from the server or does it takes this time to format the data in the view?
replace
$users = User::all();
$users->each(function ($users)
{
$users->role;
});
with this:
$users = User::with('role')->get();
This will use one db request instead of over 1k requests (you were making a call for each user to get their role). If you display all 1300 users at once, only request the "page" you need with laravels built in pagination, https://laravel.com/docs/5.6/pagination#paginating-eloquent-results

nested set save to database

I'm trying to implement jqTree with Laravel app.
Controller gets data and return view:
public function index()
{
$categories = Category::get(['id', 'name', '_lft', '_rgt', 'parent_id'])->toTree();
return view('category.index', [
'categories' => $categories
]);
}
Here is a view (javascript part):
var data = {!! $categories !!};
$('#tree').tree({
data: data,
dragAndDrop: true,
onDragStop: handleMove,
});
function handleMove() {
var treeData = $('#tree').tree('toJson');
$.ajax({
url: 'category',
type: 'POST',
headers: { 'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content') },
data: { data: treeData },
});
}
This builds tree properly and I can drag & drop items. However, I want to save reordered tree back to database. Here is a post method in a controller:
public function store(Request $request)
{
$data = $request->data;
$result = Category::rebuildTree($data);
...
}
After calling rebuildTree method, I'm getting this error:
Type error: Argument 1 passed to Kalnoy\\Nestedset\\QueryBuilder::rebuildTree() must be of the type array, string given
I have tried with this:
public function store(Request $request)
{
$data = $request->data;
$data = json_decode($request->data);
$array_data = (array) $data;
$result = Category::rebuildTree($data);
...
}
This however returns:
Cannot use object of type stdClass as array
How can I get array of data passed so I can use rebuildTree() method and update database?
Here is a result of dd($request->data):
[{"name":"Storage","id":3,"_lft":17,"_rgt":18,"parent_id":null,"is_open":true,
"children":[{"name":"Laptops","id":1,"_lft":1,"_rgt":10,"parent_id":null,"is_open":true,
"children":[{"name":"Monitors","id":2,"_lft":11,"_rgt":16,"parent_id":null,
"children":[{"name":"IPS","id":5,"_lft":14,"_rgt":15,"parent_id":2}]},
{"name":"Macbook","id":6,"_lft":2,"_rgt":3,"parent_id":1},
{"name":"Acer","id":7,"_lft":4,"_rgt":5,"parent_id":1},
{"name":"New Subcategory Name","id":8,"_lft":6,"_rgt":7,"parent_id":1},
{"name":"New Subcategory ame","id":9,"_lft":8,"_rgt":9,"parent_id":1}]}]},
{"name":"Memory","id":4,"_lft":19,"_rgt":20,"parent_id":null}]
Also, just to be clear: I'm using jqTree
Nested set is lazychaser/laravel-nestedset
You are getting json in $request->data; you need to decode it in array using json_decode() along with second parameter as true for assoc
see the manual
assoc
When TRUE, returned objects will be converted into associative
arrays.
public function store(Request $request)
{
$result = Category::rebuildTree(json_decode($request->data,True));
...
}
and if you need to pass it in $data then pass it like this.
$data = json_decode($request->data,True);
Alternatively
foreach ($request->data as $value)
$array[] = $value->name;
then pass this $array into your query like this
$result = Category::rebuildTree($array);

Resources