1. Autosaves
2. PDF Generation
That can be referenced now until further updates
This is developed to recreate and help navigate between multiple tabs on a single interface, each representing a unique webpage with fields and query boxes for user input. This repository presents code structure, personalised set-up instructions on local machines for deployment, and is even customizable to varied needs.
In this project, I've tried to present and develop the following:
- A sidebar with six clickable tabs (Namely represented as Tab 1, Tab 2, etc.).
- Six webpages that display different fields and query boxes for each tab, with proper redirection.
Each tab in the sidebar corresponds to a webpage where users can input information, which is them aimed to be saved in a database for information storage and retreival - Users can also retrieve this information later. I've build this using React on the frontend, Java Spring Boot on the backend, and MongoDB for data storage for now (subject to change(s)).
- Frontend: React, HTML5, CSS3
- Backend: Java Spring Boot (Given our Java 8 codebase)
- Database: MongoDB
To get started, you would need to have Node.js, Java (JDK 11 or higher), and MongoDB installed on your local machine. I've provided the download links below for reference if needed.
- Download Node.js (at least version 14 or higher).
- Download JDK and then set up Java environment.
- Download MongoDB and then start a local MongoDB server or use MongoDB Atlas for a cloud database.
This repository can be cloned to your local machine by using the commands below:
git clone https://github.com/anaybaid-uwaterloo/nas-forms
cd formsI've divided this project is divided into two main parts: the backend and frontend, each with its own dependencies. They are as follows:
We first navigate to the backend directory (for Java Spring Boot) and create a new Spring Boot project if it hasn't been done already.
cd backendThen you would have to install Spring Boot dependencies (if using Maven or Gradle) in your pom.xml or build.gradle:
- Use Spring Web for creating RESTful APIs.
- Use Spring Data MongoDB for MongoDB interactions.
Here's an example pom.xml file which is as follows:
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-mongodb</artifactId>
</dependency>
</dependencies>We would then move to the frontend directory to install the frontend dependencies as follows:
cd ../frontend
npm installThis should help install all packages needed for the React app.
To connect to MongoDB, we would need to set up environment variables in Java Spring Boot.
To do so, in the backend/src/main/resources directory, we would create an application.properties file (or use the existing one):
spring.data.mongodb.uri=<Your MongoDB Connection String>
server.port=8080Over here, you would have to replace <Your MongoDB Connection String> with your personalised MongoDB URI. If you're using MongoDB locally, then it might look something like this:
spring.data.mongodb.uri=mongodb://localhost:27017/your_personalised_database_name (such as nas-forms)
nas_forms> db.forms.insertOne({ name: "Sample Form", description: "This is a sample form." })
{
acknowledged: true,
insertedId: ObjectId('6724ba8af9513273de24b5b1')
}If MongoDB Atlas is being used, then we you would have to get the connection string from your Atlas dashboard.
Now that (hopefully) everything is set up in terms of repository planning, we can then start on both the backend and frontend servers for this project.
From the backend directory, we would first start the Java Spring Boot server by following the command below:
./mvnw spring-boot:runThe backend server should start on the port specified in the application.properties file (the default is normally 8080). Then there should be a message showing confirming the server is running.
We can now open a new terminal window, then navigate to the frontend directory, and start the frontend server from the command(s) below:
cd ../frontend
npm startThis command should then start the React app, which should normally be available in your local browser at http://localhost:3000.
This is a tentative breakdown that I've thought of the project structure, more so to help me figure out and try to understand where each component fits.
forms/
│
├── backend/
│ ├── src/
│ │ ├── main/
│ │ │ ├── java/com/example/app/
│ │ │ │ ├── controller/
│ │ │ │ │ └── TabController.java # This would have the REST API logic for saving and retrieving data
│ │ │ │ ├── model/
│ │ │ │ │ └── TabData.java # This would define the schema for form data
│ │ │ │ └── repository/
│ │ │ │ └── TabRepository.java # This is for setting up the MongoDB data access interface
│ │ │ └── resources/
│ │ │ └── application.properties # This would have the Spring Boot config file
│ ├── pom.xml # Maven configuration file
│
├── frontend/
│ ├── public/
│ │ └── index.html # This is our main HTML file for the React app
│ ├── src/
│ │ ├── components/
│ │ │ ├── Sidebar.js # Current Sidebar with six tabs for now, can increase / decrease depending on requirements
│ │ │ ├── Webpage.js # This is the Webpage component displaying form for each tab
│ │ │ └── Form.js # Actual Form component with fields and query boxes
│ │ ├── App.js # This is to organise the main React component organizing layout
│ │ ├── api.js # Some helper functions for making API calls
│ │ └── index.js # This is the entry point for the React app
│ └── styles/
│ └── styles.css # Our main CSS file for styling the app, for colour and interactive features based on it
│
└── README.md # This documentation file that is being worked on
TabData.java: This file would define the MongoDB schema for form data (fields likefield1,field2, etc.).TabRepository.java: This creates a Spring Data repository like interface for the purpose of interacting with MongoDB.TabController.java: This was done to define API endpoints (e.g.,/api/tab1, `/api/tab[name]) for saving and retrieving data for each tab, as necessary.
App.js: This is the main component that organizes the layout. It includes the sidebar and displays the appropriate webpage based on the active tab, and other features as necessary for addition.Sidebar.js: This would be for the displays for our six tabs as of now. When we click on a tab, it sets the active tab in theAppcomponent, to be set for viewing.Webpage.js: This would help with displaying the form for the active tab. It should be able to retrieve data from the backend and passes it to theFormcomponent.Form.js: This contains the fields and query boxes for each tab, allowing users to submit or retrieve data.api.js: This contains helper functions for now, likefetchTabDataandsaveTabDatafor the purpose of making API calls to the backend.
I've mentioned a list of API endpoints provided by the Spring Boot backend. We have that each endpoint corresponds to one of the tabs:
- GET /api/tab/{tabId}: This retrieves saved data for a specific tab.
- POST /api/tab/{tabId}: This would help save data entered in a specific tab.
Example usage:
- Retrieve Tab 1 data:
GET /api/tab/1 - Save Tab 1 data:
POST /api/tab/1with JSON payload.
- Sidebar and Tab Navigation: When we click on a tab in the sidebar, the
App.jscomponent updates the active tab, andWebpage.jsrenders the corresponding form. - Form Data Handling: Each form allows users to submit data to the backend via an API call. When data is submitted, it`s saved to MongoDB.
- Data Retrieval: When one navigates back to a tab, the form then retrieves the saved data for that tab from MongoDB, so that we have the data persists across sessions.
- Deploying Backend (Spring Boot): The Spring Boot backend can be deployed on multiple platforms like Heroku, AWS, or DigitalOcean. We have to ensure though that MongoDB is accessible by using a global service like MongoDB Atlas.
- Deploying Frontend: If necessary, we can use deployment tools like Netlify, Vercel, or GitHub Pages - just keeping in mind to update any API URLs to the deployed backend URL.
-
A sample
framework.htmlfile has also been added to this repository while work is in progress, to demonstrate a certain workable framework -
Regarding form autosaves, every time the user types or leaves a field, JavaScript captures the input and temporarily stores it. When switching tabs, instead of the page resetting, the data is retrieved and loaded back into the form, giving the appearance of “auto-saving.” For a temporary save (data stored only for the session), we can use the sessionStorage object, which retains information as long as the browser tab is open. This provides a way to store key-value pairs within a user's session (while keeping the data isolated from other tabs or windows). If we would like the data to persist across browser sessions (even after the user closes and reopens the browser), we’d use localStorage instead, which retains data even after the browser is closed.
-
To implement auto-saving of form data when switching tabs, we have to start by adding JavaScript event listeners to detect changes or when the user leaves an input field. These listeners will trigger every time a field is updated, saving the input’s current value. Then, as data is entered, store each form field’s value in
sessionStorageorlocalStorageusing unique keys, liketab1-namefor the “Name” field in Tab 1, to keep track of data across different tabs. When switching tabs, we have to use JavaScript to checksessionStoragefor any saved values. If saved data is found, load it back into the relevant fields, restoring the user’s progress without the need to re-enter data.
This project is licensed under the MIT License and for NAS Appraisal Services. This free to use, modify, and distribute among NAS members involved in this project, now or in the future.