I am working on a simple react app that takes a todo title via a form, and submits to my own API created with json-server package. My code is working so far but, after submitting the data I have to reload the app to show the changes. Now my question is, how to show changes in the UI not by reloading the page ?
I am giving my code references
Simple db.json file in root directory
{
"todos": [
{
"id": 1,
"title": "first todo"
},
{
"id": 2,
"title": "second todo"
},
{
"id": 3,
"title": "third todo"
}
]
}
To run the json-server run this script "json-server": "json-server --watch db.json --port 3001"
In App.js
import { useState, useEffect } from "react";
import axios from "axios";
import TodoForm from "./components/TodoForm";
import TodoList from "./components/TodoList";
const App = () => {
const [todos, setTodos] = useState();
useEffect(() => {
async function fetchData() {
const { data } = await axios.get("http://localhost:3001/todos");
setTodos(data);
}
fetchData();
}, []);
return (
<>
<TodoForm />
<TodoList todos={todos} />
</>
);
};
export default App;
In components/TodoForm/index.js
import { Formik, Form, Field, ErrorMessage } from "formik";
import * as Yup from "yup";
import axios from "axios";
const initialValues = {
title: "",
};
const validationSchema = Yup.object({
title: Yup.string().required("Required!"),
});
const onSubmit = async (values) => {
console.log("Form data", values);
await axios.post("http://localhost:3001/todos", values);
};
const TodoForm = () => {
return (
<Formik
initialValues={initialValues}
validationSchema={validationSchema}
onSubmit={onSubmit}
>
<Form className="bg-slate-100 p-4 max-w-sm flex flex-col gap-4">
<div className="flex gap-2 flex-col">
<label
htmlFor="title"
className="font-poppins font-bold text-lg"
>
Title
</label>
<Field name="title" className="rounded-md">
{({ field, form, meta }) => {
return (
<div>
<input
type="text"
id="title"
className="rounded-md"
{...field}
/>
{meta.touched && meta.error && (
<p className="text-sm text-red-500">
{meta.error}
</p>
)}
</div>
);
}}
</Field>
</div>
<button
type="submit"
className="px-4 py-1 bg-green-500 rounded-md"
>
Submit
</button>
</Form>
</Formik>
);
};
export default TodoForm;
In components/TodoList/index.js
const TodoList = ({ todos }) => {
return (
<>
{todos && todos.length > 0 ? (
<>
<p className="text-5xl font-poppins font-bold">
Todos length: {todos.length}
</p>
<ul>
{todos.map((todo) => (
<li key={todo.id}>{todo.title}</li>
))}
</ul>
</>
) : (
<p>Yay! everything is done.