Laravel 11 Ajax CRUD Operation Tutorial Example
In this tutorial, I will show you step-by-step how to create a Laravel 11 Ajax CRUD Application with a popup modal and datatable.
In this example, we will create a "products" table with "name" and "details" columns. We will use Yajra datatable to list records with pagination, sorting, and filtering (search). We will use Bootstrap 5 modal for creating and updating new records. We will use resource routes to create a CRUD (Create, Read, Update, Delete) application in Laravel.
Let's follow the steps below to create an insert-update-delete functionality using Ajax in a Laravel app.
You can see a preview of the Ajax CRUD app below.
Preview:
List Page
Create Page
Edit Page
Step for Laravel 11 Ajax CRUD with Popup Modal and Datatable Example
- Step 1: Install Laravel 11
- Step 2: Install Yajra Datatable
- Step 3: MySQL Database Configuration
- Step 4: Create Migration Table
- Step 5: Create Route
- Step 6: Add Controller and Model
- Step 7: Add Blade Files
- Run Laravel App
Let's follow the following steps:
Install Laravel 11
This step is not required; however, if you have not created the Laravel app, then you may go ahead and execute the below command:
composer create-project laravel/laravel example-app
Step 2: Install Yajra Datatable
We need to install the Yajra Datatable composer package for datatable, so you can install using the following command:
composer require yajra/laravel-datatables
Step 3: MySQL Database Configuration
In Laravel 11, there is a default database connection using SQLite, but if we want to use MySQL instead, we need to add a MySQL connection with the database name, username, and password to the `.env` file.
.env
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=here your database name(blog)
DB_USERNAME=here database username(root)
DB_PASSWORD=here database password(root)
Step 4: Create Migration Table
We are going to create an AJAX CRUD application for products. So we have to create a migration for the "products" table using Laravel's PHP artisan command. First, fire the command below:
php artisan make:migration create_products_table --create=products
After this command, you will find one file in the following path "database/migrations", and you have to put below code in your migration file to create the products table.
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up(): void
{
Schema::create('products', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->text('detail');
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down(): void
{
Schema::dropIfExists('products');
}
};
Now you have to run this migration by following command:
php artisan migrate
Step 5: Create Route
Here, we need to add a resource route for the product Ajax CRUD application. So open your "routes/web.php" file and add the following route.
routes/web.php
<?php
use Illuminate\Support\Facades\Route;
use App\Http\Controllers\ProductController;
Route::resource('products', ProductController::class);
Step 6: Add Controller and Model
In this step, now we should create a new controller as ProductController. So run the below command and create a new controller.
So, let's copy the below code and put it in ProductController.php file.
app/Http/Controllers/ProductController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\Product;
use DataTables;
use Illuminate\Http\JsonResponse;
class ProductController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index(Request $request)
{
if ($request->ajax()) {
$data = Product::query();
return Datatables::of($data)
->addIndexColumn()
->addColumn('action', function($row){
$btn = '<a href="javascript:void(0)" data-toggle="tooltip" data-id="'.$row->id.'" data-original-title="View" class="me-1 btn btn-info btn-sm showProduct"><i class="fa-regular fa-eye"></i> View</a>';
$btn = $btn. '<a href="javascript:void(0)" data-toggle="tooltip" data-id="'.$row->id.'" data-original-title="Edit" class="edit btn btn-primary btn-sm editProduct"><i class="fa-regular fa-pen-to-square"></i> Edit</a>';
$btn = $btn.' <a href="javascript:void(0)" data-toggle="tooltip" data-id="'.$row->id.'" data-original-title="Delete" class="btn btn-danger btn-sm deleteProduct"><i class="fa-solid fa-trash"></i> Delete</a>';
return $btn;
})
->rawColumns(['action'])
->make(true);
}
return view('products');
}
/**
* Store a newly created resource in storage.
*
* @param \Illuminate\Http\Request $request
* @return \Illuminate\Http\Response
*/
public function store(Request $request): JsonResponse
{
$request->validate([
'name' => 'required',
'detail' => 'required',
]);
Product::updateOrCreate([
'id' => $request->product_id
],
[
'name' => $request->name,
'detail' => $request->detail
]);
return response()->json(['success'=>'Product saved successfully.']);
}
/**
* Show the form for editing the specified resource.
*
* @param \App\Product $product
* @return \Illuminate\Http\Response
*/
public function show($id): JsonResponse
{
$product = Product::find($id);
return response()->json($product);
}
/**
* Show the form for editing the specified resource.
*
* @param \App\Product $product
* @return \Illuminate\Http\Response
*/
public function edit($id): JsonResponse
{
$product = Product::find($id);
return response()->json($product);
}
/**
* Remove the specified resource from storage.
*
* @param \App\Product $product
* @return \Illuminate\Http\Response
*/
public function destroy($id): JsonResponse
{
Product::find($id)->delete();
return response()->json(['success'=>'Product deleted successfully.']);
}
}
Ok, so after running the command below, you will find "app/Models/Product.php" and put the content below in the Product.php file:
app/Models/Product.php
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class Product extends Model
{
use HasFactory;
/**
* Write code on Method
*
* @return response()
*/
protected $fillable = [
'name', 'detail'
];
}
Step 7: Add Blade Files
In the last step, we have to create just a blade file. So, we need to create only one blade file as products.blade.php file.
So let's just create the following file and put the below code.
resources/views/products.blade.php
<!DOCTYPE html>
<html>
<head>
<title>Laravel 11 Ajax CRUD Tutorial Example - ItSolutionStuff.com</title>
<meta name="csrf-token" content="{{ csrf_token() }}">
<link href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/5.0.1/css/bootstrap.min.css" rel="stylesheet">
<link href="https://cdn.datatables.net/1.11.4/css/dataTables.bootstrap5.min.css" rel="stylesheet">
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
<script src="https://cdn.datatables.net/1.11.4/js/jquery.dataTables.min.js"></script>
<script src="https://cdn.datatables.net/1.11.4/js/dataTables.bootstrap5.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/js/bootstrap.bundle.min.js" ></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.5.1/css/all.min.css" />
</head>
<body>
<div class="container">
<div class="card mt-5">
<h2 class="card-header"><i class="fa-regular fa-credit-card"></i> Laravel 11 Ajax CRUD Example - ItSolutionStuff.com</h2>
<div class="card-body">
<div class="d-grid gap-2 d-md-flex justify-content-md-end mb-3">
<a class="btn btn-success btn-sm" href="javascript:void(0)" id="createNewProduct"> <i class="fa fa-plus"></i> Create New Product</a>
</div>
<table class="table table-bordered data-table">
<thead>
<tr>
<th width="60px">No</th>
<th>Name</th>
<th>Details</th>
<th width="280px">Action</th>
</tr>
</thead>
<tbody>
</tbody>
</table>
</div>
</div>
</div>
<div class="modal fade" id="ajaxModel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title" id="modelHeading"></h4>
</div>
<div class="modal-body">
<form id="productForm" name="productForm" class="form-horizontal">
<input type="hidden" name="product_id" id="product_id">
@csrf
<div class="alert alert-danger print-error-msg" style="display:none">
<ul></ul>
</div>
<div class="form-group">
<label for="name" class="col-sm-2 control-label">Name:</label>
<div class="col-sm-12">
<input type="text" class="form-control" id="name" name="name" placeholder="Enter Name" value="" maxlength="50">
</div>
</div>
<div class="form-group">
<label class="col-sm-2 control-label">Details:</label>
<div class="col-sm-12">
<textarea id="detail" name="detail" placeholder="Enter Details" class="form-control"></textarea>
</div>
</div>
<div class="col-sm-offset-2 col-sm-10">
<button type="submit" class="btn btn-success mt-2" id="saveBtn" value="create"><i class="fa fa-save"></i> Submit
</button>
</div>
</form>
</div>
</div>
</div>
</div>
<div class="modal fade" id="showModel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title" id="modelHeading"><i class="fa-regular fa-eye"></i> Show Product</h4>
</div>
<div class="modal-body">
<p><strong>Name:</strong> <span class="show-name"></span></p>
<p><strong>Detail:</strong> <span class="show-detail"></span></p>
</div>
</div>
</div>
</div>
</body>
<script type="text/javascript">
$(function () {
/*------------------------------------------
--------------------------------------------
Pass Header Token
--------------------------------------------
--------------------------------------------*/
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
/*------------------------------------------
--------------------------------------------
Render DataTable
--------------------------------------------
--------------------------------------------*/
var table = $('.data-table').DataTable({
processing: true,
serverSide: true,
ajax: "{{ route('products.index') }}",
columns: [
{data: 'DT_RowIndex', name: 'DT_RowIndex'},
{data: 'name', name: 'name'},
{data: 'detail', name: 'detail'},
{data: 'action', name: 'action', orderable: false, searchable: false},
]
});
/*------------------------------------------
--------------------------------------------
Click to Button
--------------------------------------------
--------------------------------------------*/
$('#createNewProduct').click(function () {
$('#saveBtn').val("create-product");
$('#product_id').val('');
$('#productForm').trigger("reset");
$('#modelHeading').html("<i class='fa fa-plus'></i> Create New Product");
$('#ajaxModel').modal('show');
});
/*------------------------------------------
--------------------------------------------
Click to Edit Button
--------------------------------------------
--------------------------------------------*/
$('body').on('click', '.showProduct', function () {
var product_id = $(this).data('id');
$.get("{{ route('products.index') }}" +'/' + product_id, function (data) {
$('#showModel').modal('show');
$('.show-name').text(data.name);
$('.show-detail').text(data.detail);
})
});
/*------------------------------------------
--------------------------------------------
Click to Edit Button
--------------------------------------------
--------------------------------------------*/
$('body').on('click', '.editProduct', function () {
var product_id = $(this).data('id');
$.get("{{ route('products.index') }}" +'/' + product_id +'/edit', function (data) {
$('#modelHeading').html("<i class='fa-regular fa-pen-to-square'></i> Edit Product");
$('#saveBtn').val("edit-user");
$('#ajaxModel').modal('show');
$('#product_id').val(data.id);
$('#name').val(data.name);
$('#detail').val(data.detail);
})
});
/*------------------------------------------
--------------------------------------------
Create Product Code
--------------------------------------------
--------------------------------------------*/
$('#productForm').submit(function(e) {
e.preventDefault();
let formData = new FormData(this);
$('#saveBtn').html('Sending...');
$.ajax({
type:'POST',
url: "{{ route('products.store') }}",
data: formData,
contentType: false,
processData: false,
success: (response) => {
$('#saveBtn').html('Submit');
$('#productForm').trigger("reset");
$('#ajaxModel').modal('hide');
table.draw();
},
error: function(response){
$('#saveBtn').html('Submit');
$('#productForm').find(".print-error-msg").find("ul").html('');
$('#productForm').find(".print-error-msg").css('display','block');
$.each( response.responseJSON.errors, function( key, value ) {
$('#productForm').find(".print-error-msg").find("ul").append('<li>'+value+'</li>');
});
}
});
});
/*------------------------------------------
--------------------------------------------
Delete Product Code
--------------------------------------------
--------------------------------------------*/
$('body').on('click', '.deleteProduct', function () {
var product_id = $(this).data("id");
confirm("Are You sure want to delete?");
$.ajax({
type: "DELETE",
url: "{{ route('products.store') }}"+'/'+product_id,
success: function (data) {
table.draw();
},
error: function (data) {
console.log('Error:', data);
}
});
});
});
</script>
</html>
Run Laravel App:
All the required steps have been done, now you have to type the given below command and hit enter to run the Laravel app:
php artisan serve
Now, Go to your web browser, type the given URL and view the app output:
http://localhost:8000/products
You can download code from git:
Download Code from Github for Laravel 11 AJAX CRUD App
I hope it can help you....
Hardik Savani
I'm a full-stack developer, entrepreneur and owner of ItSolutionstuff.com. I live in India and I love to write tutorials and tips that can help to other artisan. I am a big fan of PHP, Laravel, Angular, Vue, Node, Javascript, JQuery, Codeigniter and Bootstrap from the early stage. I believe in Hardworking and Consistency.
We are Recommending you
- Laravel 11 Clear Cache of Route, View, Config, Event Commands
- Laravel 11 Send Email using Queue Example
- Laravel 11 Guzzle HTTP Request Example
- Laravel 11 Change Date Format Examples
- Laravel 11 Yajra Datatables Example Tutorial
- Laravel 11 REST API Authentication using Sanctum Tutorial
- Laravel 11 Ajax Request Example Tutorial
- Laravel 11 Markdown | Laravel 11 Send Email using Markdown Mailables
- Laravel 11 Import Export Excel and CSV File Tutorial
- Laravel 11 Generate PDF File using DomPDF Example
- Laravel 11 File Upload Example Tutorial
- Laravel 11 Image Upload Example Tutorial
- Laravel 11 CRUD Application Example Tutorial