Let’s create Dynamic, Reusable DataTable Component with Laravel 8, Bootstrap 5, ReactJS : With Pagination, Sort, Search Functionality
--
In this article we will learn to create dynamic reusable data table component using Laravel 8 and ReactJS from scratch.
Preparing the backend:
Scaffold new Laravel app: laravel new reactable
Create new database reactable
and update .env
file accordingly
Update default users
migration file:
Schema::create('users', function (Blueprint $table) { $table->id(); $table->string('name'); $table->string('email')->unique(); $table->timestamp('email_verified_at')->nullable(); $table->string('password'); $table->string('address'); $table->rememberToken(); $table->timestamps();});
Update UserFactory.php file:
return [ 'name' => $this->faker->name,'email' => $this->faker->unique()->safeEmail,'address' => $this->faker->address,'email_verified_at' => now(),'password' => '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi', // password'remember_token' => Str::random(10),];
So your DatabaseSeeder.php file should have following method:
\App\Models\User::factory(500)->create();
Run the migration: php artisan migrate
Run the seeder: php artisan db:seed
Make the following changes on the app/Http/Controllers/Controller.php
<?phpnamespace App\Http\Controllers;use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
use Illuminate\Foundation\Bus\DispatchesJobs;
use Illuminate\Foundation\Validation\ValidatesRequests;
use Illuminate\Routing\Controller as BaseController;class Controller extends BaseController
{
public const PER_PAGE = 10;
public const DEFAULT_SORT_FIELD = 'created_at';
public const DEFAULT_SORT_ORDER = 'asc'; use AuthorizesRequests, DispatchesJobs, ValidatesRequests;
}
Create new controller: php artisan make:controller UsersController
Inside: app/Http/Controllers/UserController.php
<?phpnamespace App\Http\Controllers;use App\Http\Resources\UserResource;
use App\Models\User;
use Illuminate\Http\Request;
use Illuminate\Http\Resources\Json\AnonymousResourceCollection;class UsersController extends Controller
{
/**
* @var string[]
*/
protected array $sortFields = ['name', 'address', 'email'];/**
* UsersController constructor.
*
* @param User $user
*/
public function __construct(public User $user)
{
}/**
* Display a listing of the resource.
*
* @param Request $request
*
* @return AnonymousResourceCollection
*/
public function index(Request $request): AnonymousResourceCollection
{
$sortFieldInput = $request->input('sort_field', self::DEFAULT_SORT_FIELD);
$sortField = in_array($sortFieldInput, $this->sortFields) ? $sortFieldInput : self::DEFAULT_SORT_FIELD;
$sortOrder = $request->input('sort_order', self::DEFAULT_SORT_ORDER);
$searchInput = $request->input('search');
$query = $this->user->orderBy($sortField, $sortOrder);
$perPage = $request->input('per_page') ?? self::PER_PAGE;
if (!is_null($searchInput)) {
$searchQuery = "%$searchInput%";
$query = $query->where('name', 'like', $searchQuery)->orWhere('email', 'like', $searchQuery)->orWhere(
'address',
'like',
$searchQuery
);
}
$users = $query->paginate((int)$perPage);return UserResource::collection($users);
}
}
Create UserResouce file: php artisan make:resource UserResource
which will create a file called UserResource.php
inside app/Http/Resources
and update the content of the to following:
<?phpnamespace App\Http\Resources;use App\Models\User;
use Carbon\Carbon;
use Illuminate\Http\Request;
use Illuminate\Http\Resources\Json\JsonResource;class UserResource extends JsonResource
{
/**
* Transform the resource into an array.
*
* @param $request
*
* @return array
*/
public function toArray($request): array
{
/** @var User $this */
return [
'name' => $this->name,
'email' => $this->email,
'address' => $this->address,
'created_at' => Carbon::parse($this->created_at)->toDayDateTimeString(),
];
}
}
Update routes/api.php
file to include:
Route::get('/users', [UsersController::class, 'index']);
With this, we are ready with our backend api.
Frontend part:
- Install required dependencies for bootstrap:
yarn add bootstrap@next react react-dom @babel/preset-react — dev
- Update
webpack.mix.js
file:
mix.js("resources/js/app.js", "public/js").react().sass("resources/sass/app.scss", "public/css");
- Let’s create two new components inside
resources/js/components:
### DataTable.js
### Paginator.js
### App.js
Now let’s create another root App component on the same directory: