Building a Basic CRUD Application: Walking through the process of creating a simple CRUD (Create, Read, Update, Delete) application using Laravel
Introduction
In this tutorial, we will walk you through the process of building a basic CRUD application using Laravel, a popular PHP framework. We will be creating a simple Task Manager application where users can create, read, update, and delete tasks. To make our application visually appealing, we will utilize the Bootstrap framework for the frontend.
Prerequisites
PHP installed on your local machine
Composer installed on your local machine
Laravel installed on your local machine
Basic understanding of PHP and Laravel
Laravel CRUD Steps
Step 1:
Create a new Laravel project First, let's create a new Laravel project using the Laravel installer. Open your terminal and run the following command:
composer create-project --prefer-dist laravel/laravel task-manager
This will create a new Laravel project named "task-manager".
Step 2:
Set up the database Next, let's configure the database for our application. Open the .env
file in the root directory of your project and update the following lines with your database credentials:
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=your_database_name
DB_USERNAME=your_username
DB_PASSWORD=your_password
Save the changes and create a new database in your MySQL server with the name specified in the .env
file.
Note: In case you don't have the .env
file simply copy the ..env.example
and rename it to .env
Step 3:
Create the Task model and migration Now, let's create a model and migration for our Task. In your terminal, navigate to the root directory of your project and run the following command:
php artisan make:model Task -m
This will generate a new model file Task.php
and a migration file. Open the migration file located in the database/migrations
directory and update it with the following code:
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateTasksTable extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('tasks', function (Blueprint $table) {
$table->id();
$table->string('title');
$table->text('description')->nullable();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('tasks');
}
}
Save the changes and run the migration command in your terminal:
php artisan migrate
This will create the tasks
table in your database.
Step 4:
We need to specify the fillable attributes in the Task
model to allow mass assignment. Open Task
model in app/Models/Task.php
and update it with:
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class Task extends Model
{
use HasFactory;
protected $fillable = ['title', 'description'];
}
Make sure to add the $fillable
array with the desired attributes that can be mass assigned. In this case, we have title
and description
attributes.
Save the changes to the Task.php
file.
Step 5:
Create a seeder To populate our tasks
table with some sample data, let's create a seeder. Run the following command in your terminal:
php artisan make:seeder TaskSeeder
This will generate a new seeder file TaskSeeder.php
in the database/seeders
directory. Open the TaskSeeder.php
file and update it with the following code:
<?php
namespace Database\Seeders;
use App\Models\Task;
use Carbon\Carbon;
use Illuminate\Database\Seeder;
use Illuminate\Support\Facades\DB;
class TaskSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
DB::table('tasks')->insert([
'title' => 'Blog Post',
'description' => 'Write blog post on laravel crud',
'created_at' => Carbon::now(),
]);
}
}
Save the changes.
Let's register our TaskSeeder, open the Database\Seeder and modify with the code below.
<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
class DatabaseSeeder extends Seeder
{
/**
* Seed the application's database.
*
* @return void
*/
public function run()
{
$this->call(TaskSeeder::class);
}
}
Step 6:
Run the seeder Now, let's run the seeder to populate our tasks
table with sample data. In your terminal,
run the following command:
php artisan db:seed --class=TaskSeeder
This will execute the run()
method within the TaskSeeder
class and create 10 sample tasks in the tasks
table.
Step 7:
Set up routes and controller Let's define the routes and controller methods for our CRUD operations. Open the routes/web.php
file and update it with the following code:
<?php
use App\Http\Controllers\TaskController;
use Illuminate\Support\Facades\Route;
Route::get('/', [TaskController::class, 'index'])->name('tasks.index');
Route::get('/tasks/create', [TaskController::class, 'create'])->name('tasks.create');
Route::post('/tasks', [TaskController::class, 'store'])->name('tasks.store');
Route::get('/tasks/{task}', [TaskController::class, 'show'])->name('tasks.show');
Route::get('/tasks/{task}/edit', [TaskController::class, 'edit'])->name('tasks.edit');
Route::put('/tasks/{task}', [TaskController::class, 'update'])->name('tasks.update');
Route::delete('/tasks/{task}', [TaskController::class, 'destroy'])->name('tasks.destroy');
Save the changes.
We can also use resource routing instead of defining each route ourselves. To do that we replace the above code with this:
use App\Http\Controllers\TaskController;
Route::resource('tasks', TaskController::class);
Next, we create a new controller file by running the following command in your terminal:
php artisan make:controller TaskController --resource
This will generate a new controller file TaskController.php
with resourceful methods for CRUD operations.
Note: We can use the below command to create the model, migration and controller with resources at once using this command:
php artisan make:mode -mcr
Now that we have created our controller let open the TaskController.php
file located in the app/Http/Controllers
directory and update it with the following code:
<?php
namespace App\Http\Controllers;
use App\Models\Task;
use Illuminate\Http\Request;
class TaskController extends Controller
{
// This display all task
public function index()
{
$tasks = Task::latest()->get();
return view('pages.tasks.index', compact('tasks'));
}
// Return the form for creating task
public function create()
{
return view('pages.tasks.create');
}
// Store request from task form
public function store(Request $request)
{
$request->validate([
'title' => 'required',
'description' => 'nullable',
]);
Task::create($request->all());
return redirect('/')
->with('success', 'Task created successfully!');
}
// Show single task
public function show(Task $task)
{
return view('pages.tasks.show', compact('task'));
}
// Display edit task form
public function edit(Task $task)
{
return view('pages.tasks.edit', compact('task'));
}
// Store request from task update form
public function update(Request $request, Task $task)
{
$request->validate([
'title' => 'required',
'description' => 'nullable',
]);
$task->update($request->all());
return redirect('/')
->with('success', 'Task updated successfully!');
}
// Delete a single task
public function destroy(Task $task)
{
$task->delete();
return redirect('/')
->with('success', 'Task deleted successfully!.');;
}
}
Save the changes.
Step 8:
Create the views Next, let's create the views for our Task Manager application. Create a new directory named pages
inside the resources/views
and another directory called tasks
inside the resources/views
directory. Inside the tasks
directory, create the following blade templates:
index.blade.php
(listing all tasks)create.blade.php
(form for creating a new task)show.blade.php
(displaying a single task)edit.blade.php
(form for editing a task)
How, let's modify each of the blade templates. Open each blade template and update accordingly:
index.blade.php
@extends('layouts.app') @section('content') <h1>Task Manager</h1> <a href="{{ route('tasks.create') }}" class="btn btn-primary mb-3">Create Task</a> <table class="table table-responsive table-bordered"> <thead> <tr> <th class="col-md-8">Title</th> <th class="col-md-4">Actions</th> </tr> </thead> <tbody> @forelse ($tasks as $task) <tr> <td class="col-md-8">{{ $task->title }}</td> <td class="col-md-4"> <a href="{{ route('tasks.show', $task->id) }}" class="btn btn-info btn-sm">View</a> <a href="{{ route('tasks.edit', $task->id) }}" class="btn btn-primary btn-sm">Edit</a> <form action="{{ route('tasks.destroy', $task->id) }}" method="POST" class="d-inline"> @csrf @method('DELETE') <button type="submit" class="btn btn-danger btn-sm" onclick="return confirm('Are you sure you want to delete this task?')">Delete</button> </form> </td> </tr> @empty <tr> <td colspan="3">No tasks found.</td> </tr> @endforelse </tbody> </table> @endsection
create.blade.php
@extends('layouts.app') @section('content') <h1>Create Task</h1> <form action="{{ route('tasks.store') }}" method="POST"> @csrf <div class="form-group"> <label for="title">Title</label> <input type="text" name="title" id="title" class="form-control" required> </div> <div class="form-group"> <label for="description">Description</label> <textarea name="description" id="description" class="form-control"></textarea> </div> <button type="submit" class="btn btn-primary">Create</button> </form> @endsection
show.blade.php
@extends('layouts.app') @section('content') <h1>{{ $task->title }}</h1> <p>{{ $task->description }}</p> <a href="{{ route('tasks.index') }}" class="btn btn-secondary">Back</a> @endsection
edit.blade.php
@extends('layouts.app') @section('content') <h1>Edit Task</h1> <form action="{{ route('tasks.update', $task->id) }}" method="POST"> @csrf @method('PUT') <div class="form-group"> <label for="title">Title</label> <input type="text" name="title" id="title" class="form-control" value="{{ $task->title }}" required> </div> <div class="form-group"> <label for="description">Description</label> <textarea name="description" id="description" class="form-control">{{ $task->description }}</textarea> </div> <button type="submit" class="btn btn-primary">Update</button> </form> @endsection
Save the changes.
Step 9:
Include Bootstrap Styles To make our application visually appealing, let's include the Bootstrap styles. Open
the app.blade.php
file located in the resources/views/layouts
directory and update it with the following code:
<!DOCTYPE html>
<html>
<head>
<title>Task Manager</title>
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css" rel="stylesheet"
integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC" crossorigin="anonymous">
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/js/bootstrap.bundle.min.js"
integrity="sha384-MrcW6ZMFYlzcLA8Nl+NtUVF0sA7MsXsP1UyJoMp4YLEuNSfAP+JcXn/tWtIaxVXM" crossorigin="anonymous">
</script>
<meta name="csrf-token" content="{{ csrf_token() }}">
</head>
<body>
<nav class="navbar navbar-expand-lg navbar-light bg-light">
<a class="navbar-brand" href="{{ route('tasks.index') }}">Task Manager</a>
</nav>
<div class="container mt-4">
<div class="notifications">
{{-- Notification Alert --}}
@if (session('success'))
<div class="alert alert-success alert-dismissible fade show" role="alert" id="success-alert">
{{ session('success') }}
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
</div>
@elseif (session('error'))
<div class="alert alert-danger alert-dismissible fade show" role="alert" id="success-alert">
{{ session('error') }}
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
</div>
@endif
</div>
@yield('content')
</div>
</body>
</html>
Save the changes.
Step 10:
Test the application That's it! You've successfully built a basic CRUD application using Laravel and Bootstrap. To test the application, run the following command in your terminal:
php artisan serve
Open your browser and navigate to http://localhost:8000
. You should see the Task Manager application, where you can create, read, update, and delete tasks.
You can get the full source code for this project on my GitHub
Conclusion
In this episode, we walked through the process of building a basic CRUD application using Laravel and Bootstrap. We created a Task Manager application where users can perform CRUD operations on tasks. Laravel's routing, controllers, models, and views made it easy to implement the desired functionality. Bootstrap's styles helped us create a visually appealing interface. Feel free to explore further and enhance the application with additional features based on your requirements.
That's it for this episode! In our next installment, we'll be discussing "Working with Eloquent ORM: Understanding Laravel's powerful Object-Relational Mapping (ORM) tool, Eloquent, and using it for database querying and relationships."
Remember, Laravel's documentation and vibrant community are valuable resources for further exploration.
Note: This blog post provides an overview of the core concepts of Laravel. Each concept deserves more in-depth exploration, and it's recommended to refer to the official Laravel documentation for comprehensive understanding.
If you found this series helpful and want to support our series, there are a few things you can do:
Share the knowledge: Spread the word about this tutorial series to your friends, colleagues, or anyone who might be interested in learning Laravel. The more people we can reach, the more we can help aspiring developers.
Engage with us: Leave comments on our blog posts or YouTube videos, asking questions or providing feedback. Your engagement helps us understand your needs better and deliver content that addresses your concerns.
Donate: If you find value in our tutorials and would like to contribute financially, you can consider making a donation. Your support allows me to continue producing quality content and improving the learning experience for our audience.
Subscribe and follow: Subscribe to our blog or YouTube channel I plan on also doing video content soon. Also follow me on social media to stay updated with the latest episodes, tutorials, and announcements. By staying connected, you'll never miss an opportunity to enhance your Laravel skills.
Thank you for being a part of my Laravel series. Your support and engagement mean the world to me. Together, let's make the journey of learning Laravel an exciting and fulfilling experience. See you in our next episode.
Happy coding!