Search Tutorials


React + Spring Boot 3 Application Hello World Example | JavaInUse

React + Spring Boot 3 Application Hello World Example

In this tutorial we be creating a full stack application where we expose endpoints using Spring Boot and consume these endpoints using React application and display the data. React is one of the most powerful Javascript libraries using which we can build single page applications. In the next tutorial we will be further enhancing this application and performing CRUD operations.
You can find the demo of the application we will be having at the end of this tutorial series here. For this deployed demo, i have not deployed the mysql db but instead made use of mocked responses.

Video

This tutorial is explained in the below Youtube Video.

We will be making use of the following technology Stack
Backend Frontend
Spring Boot 3 ReactJS 18
Spring Data JPA (Hibernate) Bootstrap
Spring Security 6 Axios
JWT
MySQL Database
What is a full stack application?
In full stack application we expose the back end point to get the data. This data can then be used by any application or device as per the need. In future even if another front end device is to be used, there will not be much change and the new device will need to consume these end points.
Full Stack Application Example
Following will be the spring boot + react application we will be developing -
React and Spring Boot Full Stack Application
For this tutorial we will be implementing the following -
React 18 and Spring Boot 3 Application
  • Spring Boot Application

    We will be making use of Spring Initializr to create a spring boot project as follows -
    Spring Boot 3 Initializr
    Maven Project will be as follows-

    Spring Boot Maven

    The maven will be as follows -
    <?xml version="1.0" encoding="UTF-8"?>
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    	xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    	<modelVersion>4.0.0</modelVersion>
    	<parent>
    		<groupId>org.springframework.boot</groupId>
    		<artifactId>spring-boot-starter-parent</artifactId>
    		<version>3.2.1</version>
    		<relativePath/> <!-- lookup parent from repository -->
    	</parent>
    	<groupId>com.javainuse</groupId>
    	<artifactId>boot-react</artifactId>
    	<version>0.0.1-SNAPSHOT</version>
    	<name>boot-react</name>
    	<description>Demo project for Spring Boot</description>
    	<properties>
    		<java.version>17</java.version>
    	</properties>
    	<dependencies>
    		<dependency>
    			<groupId>org.springframework.boot</groupId>
    			<artifactId>spring-boot-starter-web</artifactId>
    		</dependency>
    
    		<dependency>
    			<groupId>org.springframework.boot</groupId>
    			<artifactId>spring-boot-starter-test</artifactId>
    			<scope>test</scope>
    		</dependency>
    	</dependencies>
    
    	<build>
    		<plugins>
    			<plugin>
    				<groupId>org.springframework.boot</groupId>
    				<artifactId>spring-boot-maven-plugin</artifactId>
    			</plugin>
    		</plugins>
    	</build>
    
    </project>
    
    Create the Employee model class as follows-
    package com.javainuse.bootreact.model;
    
    public class Employee {
    	
    	private long id;
    	private String name;
    	private String department;
    
    	public long getId() {
    		return id;
    	}
    
    	public void setId(long id) {
    		this.id = id;
    	}
    
    	public String getName() {
    		return name;
    	}
    
    	public void setName(String name) {
    		this.name = name;
    	}
    
    	public String getDepartment() {
    		return department;
    	}
    
    	public void setDepartment(String department) {
    		this.department = department;
    	}
    }
    

    Next we define a Spring MVC REST controller class called EmployeeController. The controller has a private List<Employee> employees variable that is initialized with a method called createList(). The controller has one GET mapping for the URL "/employees". When this URL is accessed, it returns the list of employees. The createList() method creates a new ArrayList of Employee objects, initializes two Employee objects with some values, and adds them to the list. The method then returns the list.
    package com.javainuse.bootreact.controller;
    
    import java.util.ArrayList;
    import java.util.List;
    
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    import org.springframework.web.bind.annotation.RestController;
    
    import com.javainuse.bootreact.model.Employee;
    
    @RestController
    public class EmployeeController {
    
    	private List<Employee> employees = createList();
    
    	@RequestMapping(value = "/employees", method = RequestMethod.GET,
    	produces = "application/json")
    	public List<Employee> getEmployees() {
    		return employees;
    	}
    	
    	private static List<Employee> createList() {
    		List<Employee> tempEmployees = new ArrayList<>();
    		
    		Employee emp1 = new Employee();
    		emp1.setName("emp1");
    		emp1.setId(1);
    		emp1.setDepartment("HR");
    
    		Employee emp2 = new Employee();
    		emp2.setName("emp2");
    		emp2.setId(2);		
    		emp2.setDepartment("Finance");
    		
    		tempEmployees.add(emp1);
    		tempEmployees.add(emp2);
    		
    		return tempEmployees;
    	}
    
    }
    
    Compile and the run the SpringBootHelloWorldApplication.java as a Java application.
    Go to localhost:8080/employees
    Spring Boot Application Output




React development

  • Install node js by downloading the installable from Install NodeJS
  • We can now check the nodejs and npm version
    node --version
    npm --version
    

    nodejs and npm version
  • Next we will create a react project using the npx command as follows
    npx create-react-app emp-app
    

    npx create-react-app
  • Next start the react project using the npm start command
    npm start
    

    npm start
Go to localhost:3000
reactjs hello world
I will be using the Miscrosoft Visual Studio Code IDE for angular. So import the project we developed earlier in Miscrosoft Visual Studio Code IDE.

reactjs Miscrosoft Visual Studio
In React the App component is the core component which acts as the parent for all other components that are to be displayed.
React App Component
The App component is defined in the App.js. Modify the App.js as follows-
import logo from './logo.svg';
import './App.css';

function App() {
  return (
    <div className="App">
      App Component
    </div>
  );
}

export default App;

If we now go to localhost:3000 we can see that 'Employee App' gets displayed.
React App Component Display

React Components

A component in ReactJS is an independent and reusable code block that helps divide the user interface (UI) into smaller, manageable pieces. Each component encapsulates its own logic, structure, and functionality, making it easier to build and maintain complex UIs.
By breaking down UI into components, developers can create modular and reusable code. Components can be used multiple times across different parts of an application, reducing code duplication and making it easier to make changes or add new features.
Components can be as small as a button or as large as a complex form. They can have their own properties (props) that are used to pass data and customize their behavior. Components can also have their own state, allowing them to manage and update their data internally.
Components can be implemented in 2 ways -
React Components - Functional Components+Class Components
  • Functional Components: These components are implemented as normal JavaScript functions and return a React element. They are simple, easy to understand, and used mostly for rendering UI elements. Example:
    function MyComponent() {
      return <h1>Hello, World!</h1>;
    }
    
  • Class Components: These are ES6 classes that extend the `React.Component` class. Example:
    class MyComponent extends React.Component {
      render() {
        return <h1>Hello, World!</h1>;
      }
    }
    
In earlier react versions only class components could have state associated with it. Functional components could not associate state. However from 16.8 by making use of hooks even function components can make use of state.
So now react applications mostly make use of functional components.

JSX

JSX stands for JavaScript XML. JSX is a popular JavaScript library for building user interfaces. JSX is a combination of HTML and JavaScript syntax. It is a syntax extension for JavaScript that allows users to write HTML-like code within your JavaScript code.
React JSX

JSX syntax rules dictate how JSX code should be written to ensure it is valid and can be properly interpreted by React.
  • A component should return a single React element, such as a div, section, article, or fragment. This means that the return statement in a component should only contain one top-level element.
    function MyComponent() {
      return (
        <div>
          <h1>Hello World!</h1>
          <p>This is a single React element.</p>
        </div>
      );
    }
    
  • When writing HTML on multiple lines, it is recommended to wrap the HTML code inside parentheses to avoid syntax errors.
    function MyComponent() {
      return (
        <div>
          <h1>Hello World!</h1>
          <p>
            In JSX, HTML code can be written on multiple lines by wrapping it in parentheses.
            This ensures proper syntax and readability.
          </p>
        </div>
      );
    }
    
  • JSX is stricter than HTML and requires all closing tags to be explicitly included. Unlike in HTML, self-closing tags cannot be used for elements that don't have any children.
    function MyComponent() {
      return (
        <div>
          <input type="text" />
        </div>
      );
    }
    
  • CSS classes should be specified using the className attribute instead of the class attribute. This is because the class keyword is reserved in JavaScript.
    function MyComponent() {
      return (
        <div className="my-class">
          <p>This element has the CSS class 'my-class'.</p>
        </div>
      );
    }
    
  • Event handlers in JSX should be specified using camelCase syntax. For example, onClick should be used instead of onclick, and onChange instead of onchange.
    function MyComponent() {
    	  const handleClick = () => {
    	    console.log('Button clicked!');
    	  };
    
    	  return (
    	    <div>
    	      <button onClick={handleClick}>Click me</button>
    	    </div>
    	  );
    	}
    
Next inside the app component we will be creating the employee component. The employee component will consist of other required components.
React App Component Display
For this in the source folder create a folder named components
reactjs component folder
Create a file named EmployeeApp.js with the following code-
export default function EmployeeApp(){
    return(
        <div className="EmployeeApp">
            Employee App
        </div>
    )
}
Next we will be adding the employee component to the app component.
import logo from './logo.svg';
import './App.css';
import EmployeeApp from './components/employee/Employee'

function App() {
  return (
    <div className="App">
      <EmployeeApp/>
    </div>
  );
}

export default App;

If we now go to localhost:3000 we can see that the employee component gets displayed.
reactjs EmployeeApp folder
The employee component that we created above will be the parent component of all other child components like ListEmployees, UpdateEmployee etc that we will be creating. Next we will be creating a component named ListEmployees which will fetch all the employees data from spring boot application and display it. So in the components folder create a file named ListEmployees.js.
reactjs ListEmployees component
export default function ListEmployeesApp(){
    return(
        <div className="ListEmployeesApp">
            List Employees
        </div>
    )
}
Next we add the ListEmployees component to the employee component as follows-
import ListEmployeesApp from "./ListEmployees";

export default function EmployeeApp() {
    return (
        <div className="EmployeeApp">
            <ListEmployeesApp />
        </div>
    )
}
If we now go to localhost:3000 we can see that the list employees component gets displayed as follows-
reactjs ListEmployees component
Now suppose we create another component using which we will be modifying the individual employee details. For this in the component folder create a file named UpdateEmployee.js
export default function UpdateEmployeeApp(){
    return(
        <div className="UpdateEmployeeApp">
            Update Employee
        </div>
    )
}
And now we want to display this component in the parent employee component
import ListEmployeesApp from "./ListEmployees";
import UpdateEmployeeApp from "./UpdateEmployee";

export default function EmployeeApp() {
    return (
        <div className="EmployeeApp">
            <ListEmployeesApp />
            <UpdateEmployeeApp />
        </div>
    )
}
If we now go to localhost:3000 we see that both the list employees and update employee components get displayed together as follows-
reactjs multiple component
But we do not want this. We want the list employees and update employee components to be viewed separately. In future tutorials we will be adding different components like the login component. So all these components should be shown separately.
For this we will be adding routing to the react application. To implement routing we will need to add react-router-dom to our project.
npm install react-router-dom

reactjs npm install react-router-dom
Next we modify the employee component to add the routes. We will be using the React Router library to handle navigation and routing.
The <BrowserRouter> component is used as the top-level component to enable routing functionality. It listens to changes in the URL and updates the application accordingly.
Inside the <BrowserRouter>, there is a `<Routes>` component. This component is responsible for defining the different routes within the application. There are two routes defined in this code snippet:
  • 1. The first route is specified with the path="/employees" attribute. It points to the "/employees" URL path and renders the <ListEmployeesApp> component when the URL matches this path.
  • 2. The second route is specified with the path="/update" attribute. It points to the "/update" URL path and renders the <UpdateEmployeeApp> component when the URL matches this path.
import { BrowserRouter, Route, Routes } from "react-router-dom";
import ListEmployeesApp from "./ListEmployees";
import UpdateEmployeeApp from "./UpdateEmployee";

export default function EmployeeApp() {
    return (
        <div className="EmployeeApp">
            <BrowserRouter>
                <Routes>
                    <Route path="/employees" element={<ListEmployeesApp />}></Route>
                    <Route path="/update" element={<UpdateEmployeeApp />}></Route>
                </Routes>
            </BrowserRouter>
        </div>
    )
}
If we now go to localhost:3000/employees we can see the list employees component.
reactjs BrowserRouter
Similarly if we go to localhost:3000/update we can see the update employee component.
reactjs Routes
Next we will be modifying the list employees component to display hard coded employee data.
Following code creates a list of employees by rendering a table with two columns: "id" and "name". The data for the table is taken from the employees array.
export default function ListEmployeesApp(){
    const employees = [{ id: 1, name: 'employee1' },
    { id: 2, name: 'employee2' }]

    return (
        <div className="EmployeeApp">
            <h1>Employees List</h1>
            <div>
                <table>
                    <thead>
                        <tr>
                            <th>id</th>
                            <th>name</th>
                        </tr>
                    </thead>
                    <tbody>
                        {
                            employees.map(
                                employee => (
                                    <tr>
                                        <td>{employee.id}</td>
                                        <td>{employee.name}</td>
                                    </tr>
                                )

                            )
                        }
                    </tbody>


                </table>
            </div>
        </div>
    )
}
If we now go to localhost:3000/employees we can see the employee list as follows-
reactjs employee list
Next we will be modifying the employee component to fetch the employee list from the REST endpoint exposed using spring boot. We will add a button which will fetch data from the spring boot application. Initially the click of the button will only print in the console.
Another modification we will be making is that for the employees.map we pass the key property. In our case the key property is employee.id.
The key property is important because it helps React identify which elements have changed, been added, or been removed. Without the key property, React may have difficulty efficiently updating the components. It is generally recommended to include a unique key property when mapping over arrays in React to improve performance and avoid potential issues.
export default function ListEmployeesApp() {
    const employees = [{ id: 1, name: 'employee1' },
    { id: 2, name: 'employee2' }]

    function getEmployees() {
        console.log('Fetching Employees')
    }

    return (
        <div className="EmployeeApp">
            <h1>Employee App</h1>
            <div>
                <table>
                    <thead>
                        <tr>
                            <th>id</th>
                            <th>name</th>
                        </tr>
                    </thead>
                    <tbody>
                        {
                            employees.map(
                                employee => (
                                    <tr key={employee.id}>
                                        <td>{employee.id}</td>
                                        <td>{employee.name}</td>
                                    </tr>
                                )

                            )
                        }
                    </tbody>


                </table>
            </div>
            <button className="btn btn-success" onClick={getEmployees}>Get Employees</button>
        </div>


    )
}

reactjs employee list
Next instead of using the hardcoded data we will be making the actual REST call to get the employees list from the backend spring boot application. For this we make use of axios framework.
For this we first install axios as follows-
npm install axios

reactjs npm install axios
In the list employees component using Axios library we make a HTTP GET request to the "http://localhost:8080/employees" endpoint. This fetches employee data from the specified URL, handles the success and error responses accordingly, and prints a message indicating the completion of the request.
import axios from "axios";

export default function ListEmployeesApp() {
    const employees = [{ id: 1, name: 'employee1' },
    { id: 2, name: 'employee2' }]

    function getEmployees() {
        console.log('Fetching Employee')
        axios.get('http://localhost:8080/employees')
            .then((response) => onSuccess(response))
            .catch((response) => onError(response))
            .finally(() => console.log('Finally done'))
    }

    function onSuccess(response) {
        console.log(response);
    }

    function onError(response) {
        console.log(response);
    }

    return (
        <div className="EmployeeApp">
            <h1>Employee App</h1>
            <div>
                <table>
                    <thead>
                        <tr>
                            <th>id</th>
                            <th>name</th>
                        </tr>
                    </thead>
                    <tbody>
                        {
                            employees.map(
                                employee => (
                                    <tr key={employee.id}>
                                        <td>{employee.id}</td>
                                        <td>{employee.name}</td>
                                    </tr>
                                )

                            )
                        }
                    </tbody>


                </table>
            </div>
            <button className="btn btn-success" onClick={getEmployees}>Get Employees</button>
        </div>
    )
}
If we now go to localhost:3000/employees and click on the get employees button we get a CORS exception.
reactjs Spring Boot CORS exception
CORS errors happen when a webpage makes a request to a different domain than the one that served the page, and the server responds with an HTTP error because the "Origin" header in the request is not allowed by the server's CORS configuration.
For us this is happening because our react app is running on port 3000 while the spring boot app is running on port 8080. For this we need to enable cross-origin resource sharing to allow the react frontend get data from spring boot backend.
package com.javainuse.bootreact.controller;

import java.util.ArrayList;
import java.util.List;

import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import com.javainuse.bootreact.model.Employee;

@CrossOrigin(origins = "http://localhost:3000")
@RestController
public class EmployeeController {

	private List<Employee> employees = createList();

	@RequestMapping(value = "/employees", method = RequestMethod.GET,
	produces = "application/json")
	public List<Employee> getEmployees() {
		return employees;
	}
	
	private static List<Employee> createList() {
		List<Employee> tempEmployees = new ArrayList<>();
		
		Employee emp1 = new Employee();
		emp1.setName("emp1");
		emp1.setId(1);
		emp1.setDepartment("HR");

		Employee emp2 = new Employee();
		emp2.setName("emp2");
		emp2.setId(2);		
		emp2.setDepartment("Finance");
		
		tempEmployees.add(emp1);
		tempEmployees.add(emp2);
		
		return tempEmployees;
	}

}
If we now restart the spring boot appication and click on the get employees button we get the employees list as follows-
reactjs Spring Boot axios call
Now that we have the employee list from the spring boot application, we will be displaying it instead of the hardcoded data. This is achieved using react state. A state is an object that holds data related to a React component. It can be used to store, manage, and update data within the application.
We add state to the list employee component using useState which is a react hook. A hook is a special function that lets us "hook into" React features. The useState hook takes an initial value as an argument and returns an updated state value whenever the setter funtion is called.
const [state, setState] = useState(initialValue);
So here-
initialValue - The value to begin with.
state - The current state.
setState - The setter using which we can change the value of the state.
For our example we will be having the hook as follows-
const [employees, setEmployee] = useState([])
The initial value of the state will be an empty array. Next when we fetch the employee list we will update the current state using the setEmployee method.
So let us make these changes.
import axios from "axios";
import { useState } from "react";

export default function ListEmployeesApp() {
    const [employees, setEmployee] = useState([])

    function getEmployees() {
        console.log('Fetching Employee')
        axios.get('http://localhost:8080/employees')
            .then((response) => onSuccess(response))
            .catch((response) => onError(response))
            .finally(() => console.log('Finally done'))
    }

    function onSuccess(response) {
        console.log(response);
       setEmployee(response.data);
    }

    function onError(response) {
        console.log(response);
    }

    return (
        <div className="EmployeeApp">
            <h1>Employee App</h1>
            <div>
                <table>
                    <thead>
                        <tr>
                            <th>id</th>
                            <th>name</th>
                        </tr>
                    </thead>
                    <tbody>
                        {
                            employees.map(
                                employee => (
                                    <tr key={employee.id}>
                                        <td>{employee.id}</td>
                                        <td>{employee.name}</td>
                                    </tr>
                                )

                            )
                        }
                    </tbody>


                </table>
            </div>
            <button className="btn btn-success" onClick={getEmployees}>Get Employees</button>
        </div>


    )
}
If we now go to localhost:8080/employees and click on the get employees button, the list gets displayed.
reactjs Spring Boot useState Hook
Currently we are fetching and displaying the list on click of the button. However we want to do this when the page loads. We implement this using another React Hook named useEffect. This Hook, you tell React that your component needs to do something after render.
import axios from "axios";
import { useEffect, useState } from "react";

export default function ListEmployeesApp() {

    const [employees, setEmployee] = useState([])

    useEffect(
        () => getEmployees(), []
    )

    function getEmployees() {
        console.log('Fetching Employee')
        axios.get('http://localhost:8080/employees')
            .then((response) => onSuccess(response))
            .catch((response) => onError(response))
            .finally(() => console.log('Finally done'))
    }

    function onSuccess(response) {
        console.log(response);
        setEmployee(response.data);
    }

    function onError(response) {
        console.log(response);
    }

    return (
        <div className="EmployeeApp">
            <h1>Employee App</h1>
            <div>
                <table>
                    <thead>
                        <tr>
                            <th>id</th>
                            <th>name</th>
                        </tr>
                    </thead>
                    <tbody>
                        {
                            employees.map(
                                employee => (
                                    <tr key={employee.id}>
                                        <td>{employee.id}</td>
                                        <td>{employee.name}</td>
                                    </tr>
                                )

                            )
                        }
                    </tbody>


                </table>
            </div>
        </div>


    )
}

reactjs Spring Boot useEffecr Hook

Download Source Code

Download it -
React Hello World example code
Spring Boot Hello World example code