Customer Management

project / March 12th, 2024

Customer Management - Customers

GitHub

Background

A full-stack application that enables users to register, log in, and create, delete, and edit stored customers in a database and display them in a dashboard.

This is a project that was completed as a result of following the Full Stack Professional course from Amigoscode, and is intended to guide students through the entire process of building, testing, and deploying full-stack web applications fro start to finish.

Purpose

Upon finishing the industry-sponsored capstone team project (Historical Giving PDF Generator Application for Benevity) during my Software Engineering Masters program, I developed a better understanding of the areas I needed to improve upon in order to become a full-stack developer. Because the majority of my contributions to the capstone project was in front-end development, I wanted to learn more about back-end development, testing, and deployment by enrolling in the Full Stack Professional course. Through building this project, my goal was to gain a clearer idea of the entire full-stack development workflow from start to finish.

Concepts and Tools Used

  • Java Spring Boot

  • Back-end development

  • Layered or N-Tier Architecture for REST APIs

  • PostgreSQL Database

  • Docker

  • Postman

  • Spring Data JPA and Spring JDBC Template

  • Flyway

  • Unit and Integration Testing

  • Mockito

  • Jib

  • Continuous Integration and Continuous Deployment

  • GitHub Actions

  • AWS

  • Elastic Beanstalk

  • Slack

  • Front-end development

  • React

  • Chakra UI

  • Axios

  • Formik

  • Yup

  • Spring Security and JSON Web Tokens

  • AWS Amplify

  • Angular

  • PrimeNG

  • S3 Buckets

Process

The process starts by developing an N-Tier Architecture REST API using Java Spring Boot, with layers for API, Business and Data Access. The API layer contains methods to intercept the HTTP requests and sends them to the business layer. The business layer contains the business logic for the entire application. The Data Access Object (DAO) layer is responsible for interacting with the PostgreSQL database.

Docker was installed to run a PostgreSQL container for use as a database during the development stage. I also explored the use of the JDBC Template for writing SQL commands to a relational database and how it differs from the Spring JPA (which contains the Hibernate Object Relational Mapper) for mapping the Customer model Java class to tables in a relational database and performing CRUD operations from the Data Access Service layer. Postman was used to test CRUD operations in the API without the use of a front-end. Flyway was used in conjunction with JDBC template to migrate between different versions of the database schema and create database tables without JPA/Hibernate.

Automated testing for each layer (starting with the DAO) was performed using Testcontainers to create a throwaway instance of the PostgreSQL database during testing, which enabled queries to be run without affecting the database. Mockito was used to mock the JPARepository class containing the CRUD operations in the DAO layer. Integration testing is done for the API layer by using WebTestClient to simulate HTTP requests and the potential use cases for a user.

The Spring Boot and Maven plugins were used to run the unit and integration tests for the back-end and build an executable JAR file that can be containerized into a Docker Image using Jib (allows you to build Docker images without Docker Daemon). We then create an Elastic Beanstalk environment on AWS for running Dockerized applications. GitHub Actions was used to setup a CI/CD workflow for the Spring Boot app, which also include messages being sent on Slack at different stages of the deployment.

The front-end was built using components from the Chakra UI library in React and Axios was used to fetch data from the back-end. Formik was installed to use pre-built form inputs and Yup was used for form validation. A Dockerfile was created to build a Docker image for the React app before pushing it to DockerHub. Another CI/CD workflow was built in GitHub actions to deploy the front-end app to AWS Elastic Beanstalk.

Customer Management - Create New Customer

JSON Web Tokens and Spring Security was used to secure the API. The customer registration endpoint was modified to issue a signed JWT token upon registration. Spring Security filters in the API were created to intercept requests and validate JWT tokens. The PasswordEncoder class was used for password hashing. We also introduced a DTO pattern with the CustomerDTO class, in order to control which fields can be exposed to clients. The CustomerDTOMapper class was created to map the Customer entity to the CustomerDTO class and the CustomerService and CustomerServiceTests were modified to accommodate DTO-related changes. The API layer (CustomerController class) was modified to return DTOs instead of Customer entities.

Next, registration and login functionalities were created to store the JWT token received from the back-end inside local storage, to enable persistent authentication across sessions. React Router was used for navigation and the Context API used to manage global state for the login, logout, and user authentication statuses. A logout functionality was implemented to remove the token from local storage and reset the user state to null. Protected routes were also implemented to restrict access to authenticated users only. A function was implemented to check token expiration and automatically redirect users to the login page when the token is expired.

Customer Management - Registration PageCustomer Management - Login Page

For a scalable and reliable application, the Elastic Beanstalk environment includes a load balancer to distribute incoming traffic among multiple EC2 instances (virtual servers). The React front-end is now deployed using AWS Amplify with Docker now used to deploy only the API. The load balancer listeners are updated to support HTTPS and to redirect all HTTP requests to HTTPS.

The same front-end application is then re-created in the Angular framework using PrimeNG components. The Angular HttpClientModule is used to make HTTP requests and user authentication is implemented using JWT tokens. Route guards are used to secure routes based on user authentication status. The Angular front-end is also deployed using AWS Amplify.

Finally, functionality to upload profile pictures from the client to an AWS S3 bucket using the react-dropzone library is implemented.

Customer Management - Update CustomerCustomer Management - Customer Updated

Outcome and Takeaways

This was a comprehensive project that helped develop more insight into the entire full-stack development process from start to finish. It touched on various key areas like back-end development, testing, continuous integration and continuous deployment, and front-end deployment. Learning to build the same front-end application in both React and Angular was especially useful. Gaining exposure to using Docker, GitHub Actions, and AWS for the continuous integration and continuous deployment process was really important for my skill development, as I had never used either of these technologies before. Learning to build and test a back-end in Java Spring Boot was also an important knowledge gap I was able to fill, and has provided a solid foundation of steps that I can reference later for future projects.

Possible Improvements Going Forward

Given more time, I would love to customize and personalize this application to suit projects and passions that I am interested it. For learning purposes, it would also help if I learned how to implement pagination, in case the number of customers becomes extremely large.


External Links