CRUD App in ReactJS Hooks with Axios and Web API Laravel 8 RESTful API

By Super Admin | Jul 17, 2021 | React JS
Share : Whatsapp

https://www.fundaofwebit.com/post/crud-app-in-react-js-with-hooks-using-laravel-8-restful-api

Create a CRUD App in React JS with Hooks Using Laravel 8 RESTful API

In this post, we are going to create a React JS CRUD application with Hooks. For managing the data and database operations, we will be using the RESTful APIs. You are already familiar with the term RESTful APIs. For the back-end, we will be using the Laravel 8 with MySQL Database. 


Lets get started:

Step 1: Create React App

You’ll need to have Node >= 10.16 and npm >= 5.6 on your machine. To create a project, run: Open your terminal:

$ npx create-react-app studentcrud

cd studentcrud

$ npm start

Step 2: Install Bootstrap in React JS . (https://getbootstrap.com/)

$ npm install bootstrap

after successful installation of Bootstrap. Now, import Bootstrap in React JS in src/index.js file.

import 'bootstrap/dist/css/bootstrap.min.css';
import 'bootstrap/dist/js/bootstrap.bundle.js';

Install React Router Dom for routing from one page to another:

$ npm install react-router-dom@5.0.0

Step 3: Lets create the User Interface and Routes for Student CRUD. Lets move to App.js file to create routes.

import React from 'react';
import {BrowserRouter as RouterSwitch, Routefrom 'react-router-dom';

import Navbar from './pages/Navbar';

import ViewStudent from './pages/ViewStudent';
import AddStudent from './pages/AddStudent';
import EditStudent from './pages/EditStudent';

import axios from 'axios';
axios.defaults.baseURL = "http://localhost:8000/";

function App() {
  return (
    <div className="App">
        <Router>

       <Navbar />

          <Switch>

            <Route path="/students" component={ViewStudent} />
            <Route path="/add-students" component={AddStudent} />
            <Route path="/edit-student/:id" component={EditStudent} />

          </Switch>
        </Router>
    </div>
  );
}

export default App;

Now, lets setup the Navbar guys as follows:

import React from 'react';
import { Link } from 'react-router-dom';

function Navbar ()
{
  return(
    <div className="pb-5">
        <nav className="navbar navbar-expand-lg navbar-dark bg-dark">
        <div className="container">
          <Link className="navbar-brand" to="/">Navbar</Link>

          <button className="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
            <span className="navbar-toggler-icon"></span>
          </button>
          <div className="collapse navbar-collapse" id="navbarSupportedContent">
            <ul className="navbar-nav ms-auto mb-2 mb-lg-0">
              <li className="nav-item">
                <Link className="nav-link" to="/">Home</Link>
              </li>
              <li className="nav-item">
                <Link className="nav-link" to="/students">Student</Link>
              </li>
              <li className="nav-item">
                <Link className="nav-link" to="/add-student">Add Student</Link>
              </li>
            </ul>
          </div>
        </div>
      </nav>
    </div>
  );
}

export default Navbar;

Step 4: Let's Add/Insert data into database in react js using hooks with api laravel:

create a file as follows: src/pages/AddStudent.js in and paste the below code to create FORM and send data with axios using api in react js hooks.

import React, {useStatefrom 'react';
import {LinkuseHistoryfrom 'react-router-dom';
import axios from 'axios';
import swal from 'sweetalert';

function AddStudent() {

    const history = useHistory();
    const [studentInputsetStudent] = useState({
        name: '',
        course: '',
        email: '',
        phone: '',
        error_list: [],
    });

    const handleInput = (e=> {
        e.persist();
        setStudent({...studentInput[e.target.name]: e.target.value })
    }

    const saveStudent = (e=> {
        e.preventDefault();
        
        const data = {
            name:studentInput.name,
            course:studentInput.course,
            email:studentInput.email,
            phone:studentInput.phone,
        }

        axios.post(`/api/add-student`data).then(res => {

            if(res.data.status === 200)
            {
                swal("Success!",res.data.message,"success");
                setStudent({
                    name: '',
                    course: '',
                    email: '',
                    phone: '',
                    error_list: [],
                });
                history.push('/students');
            }
            else if(res.data.status === 422)
            {
                setStudent({...studentInputerror_list: res.data.validate_err });
            }
        });
    }

    return (
        <div>
            <div className="container">
                <div className="row justify-content-center">
                    <div className="col-md-6">
                        <div className="card">
                            <div className="card-header">
                                <h4>Add Students 
                                    <Link to={'/'} className="btn btn-danger btn-sm float-end"> BACK</Link>
                                </h4>
                            </div>
                            <div className="card-body">
                                
                                <form onSubmit={saveStudent} >
                                    <div className="form-group mb-3">
                                        <label>Student Name</label>
                                        <input type="text" name="name" onChange={handleInput} value={studentInput.name} className="form-control" />
                                        <span className="text-danger">{studentInput.error_list.name}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <label>Student Course</label>
                                        <input type="text" name="course" onChange={handleInput} value={studentInput.course}  className="form-control" />
                                        <span className="text-danger">{studentInput.error_list.course}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <label>Student Email</label>
                                        <input type="text" name="email" onChange={handleInput} value={studentInput.email}  className="form-control" />
                                        <span className="text-danger">{studentInput.error_list.email}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <label>Student Phone</label>
                                        <input type="text" name="phone" onChange={handleInput} value={studentInput.phone}  className="form-control" />
                                        <span className="text-danger">{studentInput.error_list.phone}</span>
                                    </div>

                                    <div className="form-group mb-3">
                                        <button type="submit" className="btn btn-primary">Save Student</button>
                                    </div>
                                </form>

                            </div>
                        </div>
                    </div>
                </div>
            </div>
        </div>
    );

}

export default AddStudent;

Step 5: Let's Fetch/Retrieve data from database in React JS using hooks with api laravel and also with delete data from database in reac js hooks with laravel API.

create a file as follows: src/pages/ViewStudent.js in and paste the below code:

import React, {useStateuseEffectfrom 'react';
import {LinkuseHistoryfrom 'react-router-dom';
import axios from 'axios';
import swal from 'sweetalert';

function ViewStudent() {

    const [loadingsetLoading] = useState(true);
    const [studentssetStudents] = useState([]);

    useEffect(() => {

        axios.get(`/api/students`).then(res=>{
            if(res.status === 200)
            {
                setStudents(res.data.students)
                setLoading(false);
            }
        });

    }, []);

    const deleteStudent = (eid=> {
        e.preventDefault();
        
        const thisClicked = e.currentTarget;
        thisClicked.innerText = "Deleting";

        axios.delete(`/api/delete-student/${id}`).then(res=>{
            if(res.data.status === 200)
            {
                swal("Deleted!",res.data.message,"success");
                thisClicked.closest("tr").remove();
            }
            else if(res.data.status === 404)
            {
                swal("Error",res.data.message,"error");
                thisClicked.innerText = "Delete";
            }
        });
    }

    if(loading)
    {
        return <h4>Loading Student Data...</h4>
    }
    else
    {
        var student_HTMLTABLE = "";
       
        student_HTMLTABLE = students.map( (itemindex=> {
            return (
                <tr key={index}>
                    <td>{item.id}</td>
                    <td>{item.name}</td>
                    <td>{item.course}</td>
                    <td>{item.email}</td>
                    <td>{item.phone}</td>
                    <td>
                        <Link to={`edit-student/${item.id}`} className="btn btn-success btn-sm">Edit</Link>
                    </td>
                    <td>
                        <button type="button" onClick={(e=> deleteStudent(eitem.id)} className="btn btn-danger btn-sm">Delete</button>
                    </td>
                </tr>
            );
        });
    }

    return (
        <div>
            <div className="container">
                <div className="row">
                    <div className="col-md-12">
                        <div className="card">
                            <div className="card-header">
                                <h4>Students Data
                                    <Link to={'add-student'} className="btn btn-primary btn-sm float-end"> Add Student</Link>
                                </h4>
                            </div>
                            <div className="card-body">
                                
                                <table className="table table-bordered table-striped">
                                    <thead>
                                        <tr>
                                            <th>ID</th>
                                            <th>Name</th>
                                            <th>Course</th>
                                            <th>Email Id</th>
                                            <th>Phone</th>
                                            <th>Edit</th>
                                            <th>Delete</th>
                                        </tr>
                                    </thead>
                                    <tbody>
                                        {student_HTMLTABLE}
                                    </tbody>
                                </table>

                            </div>
                        </div>
                    </div>
                </div>
            </div>
        </div>
    );

}

export default ViewStudent;

Step 6: Edit and Update data into database in React JS using hooks with api laravel:

create a file as follows: src/pages/EditStudent.js in and paste the below code:

import React, {useStateuseEffectfrom 'react';
import {LinkuseHistoryfrom 'react-router-dom';
import axios from 'axios';
import swal from 'sweetalert';

function EditStudent(props) {

    const history = useHistory();
    const [loadingsetLoading] = useState(true);
    const [studentInputsetStudent] = useState([]);
    const [errorInputsetError] = useState([]);

    useEffect(() => {
        
        const student_id = props.match.params.id;
        axios.get(`/api/edit-student/${student_id}`).thenres => {

            if(res.data.status === 200)
            {
                setStudent(res.data.student);
                setLoading(false);
            }
            else if(res.data.status === 404)
            {
                swal("Error",res.data.message,"error");
                history.push('/students');
            }
        });

    }, [history]);

    const handleInput = (e=> {
        e.persist();
        setStudent({...studentInput[e.target.name]: e.target.value });
    }

    const updateStudent = (e=> {
        e.preventDefault();
        
        const student_id = props.match.params.id;
        // const data = studentInput;
        const data = {
            name: studentInput.name,
            course: studentInput.course,
            email: studentInput.email,
            phone: studentInput.phone,
        }

        axios.put(`/api/update-student/${student_id}`data).then(res=>{
            if(res.data.status === 200)
            {
                swal("Success",res.data.message,"success");
                setError([]);
                history.push('/students');
            }
            else if(res.data.status === 422)
            {
                swal("All fields are mandetory","","error");
                setError(res.data.validationErrors);
            }
            else if(res.data.status === 404)
            {
                swal("Error",res.data.message,"error");
                history.push('/students');
            }
        });
    }

    if(loading)
    {
        return <h4>Loading Edit Student Data...</h4>
    }
    
    return (
        <div>
            <div className="container">
                <div className="row justify-content-center">
                    <div className="col-md-6">
                        <div className="card">
                            <div className="card-header">
                                <h4>Edit Students 
                                    <Link to={'/students'} className="btn btn-danger btn-sm float-end"> BACK</Link>
                                </h4>
                            </div>
                            <div className="card-body">
                                
                                <form onSubmit={updateStudent} >
                                    <div className="form-group mb-3">
                                        <label>Student Name</label>
                                        <input type="text" name="name" onChange={handleInput} value={studentInput.name} className="form-control" />
                                        <span className="text-danger">{errorInput.name}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <label>Student Course</label>
                                        <input type="text" name="course" onChange={handleInput} value={studentInput.course}  className="form-control" />
                                        <span className="text-danger">{errorInput.course}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <label>Student Email</label>
                                        <input type="text" name="email" onChange={handleInput} value={studentInput.email}  className="form-control" />
                                        <span className="text-danger">{errorInput.email}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <label>Student Phone</label>
                                        <input type="text" name="phone" onChange={handleInput} value={studentInput.phone}  className="form-control" />
                                        <span className="text-danger">{errorInput.phone}</span>
                                    </div>
                                    <div className="form-group mb-3">
                                        <button type="submit" id="updatebtn" className="btn btn-primary">Update Student</button>
                                    </div>
                                </form>

                            </div>
                        </div>
                    </div>
                </div>
            </div>
        </div>
    );

}

export default EditStudent;


Lets begin with the BACKEND using Laravel Application as follows:


Step 1: Create a migration named students as follows:

$ php artisan make:migration create_students_table

Step 2: Create a Model named Student as follows:

$ php artisan make:model Student

Step 3: Create a Controller named StudentController in API folder as follows and paste the below code:

$ php artisan make:controller API/StudentController
<?php

namespace App\Http\Controllers\API;

use App\Models\Student;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use Illuminate\Support\Facades\Validator;

class StudentController extends Controller
{
    public function index()
    {
        $students = Student::all();
        return response()->json([
            'status'=> 200,
            'students'=>$students,
        ]);
    }

    public function store(Request $request)
    {
        $validator = Validator::make($request->all(),[
            'name'=>'required|max:191',
            'course'=>'required|max:191',
            'email'=>'required|email|max:191',
            'phone'=>'required|max:10|min:10',
        ]);

        if($validator->fails())
        {
            return response()->json([
                'status'=> 422,
                'validate_err'=> $validator->messages(),
            ]);
        }
        else
        {
            $student = new Student;
            $student->name = $request->input('name');
            $student->course = $request->input('course');
            $student->email = $request->input('email');
            $student->phone = $request->input('phone');
            $student->save();

            return response()->json([
                'status'=> 200,
                'message'=>'Student Added Successfully',
            ]);
        }

    }

    public function edit($id)
    {
        $student = Student::find($id);
        if($student)
        {
            return response()->json([
                'status'=> 200,
                'student' => $student,
            ]);
        }
        else
        {
            return response()->json([
                'status'=> 404,
                'message' => 'No Student ID Found',
            ]);
        }

    }

    public function update(Request $request$id)
    {
        $validator = Validator::make($request->all(),[
            'name'=>'required|max:191',
            'course'=>'required|max:191',
            'email'=>'required|email|max:191',
            'phone'=>'required|max:10|min:10',
        ]);

        if($validator->fails())
        {
            return response()->json([
                'status'=> 422,
                'validationErrors'=> $validator->messages(),
            ]);
        }
        else
        {
            $student = Student::find($id);
            if($student)
            {

                $student->name = $request->input('name');
                $student->course = $request->input('course');
                $student->email = $request->input('email');
                $student->phone = $request->input('phone');
                $student->update();

                return response()->json([
                    'status'=> 200,
                    'message'=>'Student Updated Successfully',
                ]);
            }
            else
            {
                return response()->json([
                    'status'=> 404,
                    'message' => 'No Student ID Found',
                ]);
            }
        }
    }

    public function destroy($id)
    {
        $student = Student::find($id);
        if($student)
        {
            $student->delete();
            return response()->json([
                'status'=> 200,
                'message'=>'Student Deleted Successfully',
            ]);
        }
        else
        {
            return response()->json([
                'status'=> 404,
                'message' => 'No Student ID Found',
            ]);
        }
    }
}

Step 4: Create an API as follows in the following path: routes/api.php and paste the below api code:

<?php

use App\Http\Controllers\API\StudentController;

Route::get('students', [StudentController::class'index']);
Route::post('/add-student', [StudentController::class'store']);
Route::get('/edit-student/{id}', [StudentController::class'edit']);
Route::put('update-student/{id}', [StudentController::class'update']);
Route::delete('delete-student/{id}', [StudentController::class'destroy']);

Step 5: thats it guys, we done. Run the project and get started


for React JS:
in Terminal: npm start
path: http://localhost:3000/students

for Laravel: 
in Terminal: php artisan serve
path: http://localhost:8000/ 


Thanks for reading...