I am learning React from few days and I am trying to learn Axios, Everything worked fine until I tried to insert data, which I successfully inserted but My React Page did not updated contact list immediately.
HERE's MY CODE:
App.js
`
import React, { useState, useEffect } from "react";
import Add__Contact from "./api/Add__Contact";
import Axios from "axios";
const App = () => {
const [name, setName] = useState("");
const [phone, setPhone] = useState("");
const [contacts, setContacts] = useState([]);
const url = "http://localhost:3006/contacts";
//get all availbale contacts
useEffect(() => {
// get all contacts async
async function getUsers() {
Axios.get(url).then((response) => {
setContacts(response.data);
});
}
getUsers();
console.log(contacts);
// get all contacts non-async
// Axios.get(url).then((response) => {
// setContacts(response.data);
// });
}, []);
//add new contact to server
const addContact = () => {
const saveRes = Add__Contact({ name, phone });
};
// view
return (
<div>
<h4>Add contact</h4>
<div>
<input type="text" name="name" value={name} onChange={(e) => setName(e.target.value)} placeholder="name here" />
<br />
<br />
<input type="text" name="phone" value={phone} onChange={(e) => setPhone(e.target.value)} placeholder="Phone here" />
<br />
<br />
<button onClick={addContact}>Add to Contact</button>
</div>
<hr />
<h4>List of Contacts</h4>
<div>
{contacts.map((contact) => {
return (
<div key={contact.id}>
<span>{contact.name} : </span>
<span> {contact.phone}</span>
</div>
);
})}
</div>
</div>
);
};
export default App;
`
Add__Contact.js
`
import Axios from "axios";
const Add__Contact = async ({ name, phone }) => {
Axios({
method: "post",
url: "http://localhost:3006/contacts",
headers: {
"Content-Type": "application/json",
},
data: {
name,
phone,
},
}).then(function (res) {
// console.log(res);
});
};
export default Add__Contact;
`
db.json
`
{
"contacts": [
{
"name": "Max",
"phone": "123456",
"id": 1
},
{
"name": "John",
"phone": "13454",
"id": 2
},
{
"name": "Candy",
"phone": "1245781245",
"id": 3
}
]
}
`
I am not sure why it's not updating list automatically, I thought useEffect
will run everytime I click and call Add__Contact()
. Can you please tell me what did i missed or doing wrong?
I am not sure if useEfeect
hook is good for what I want to achieve or not, so please guide me. Thank you in advance.
data insertion is working fine, but after I insert it, it's not updating ui, even if I am fetching data inside useEffect
CodePudding user response:
Your useEffect
hook is only ran once - when the component mounts. This is because you have given it an empty dependency array (the 2nd argument).
The dependency array determines when the effect function will run. If its empty, it will only run when the component is mounted (displayed for the very first time). If you add something in the array, the effect will run on mount, and whenever the provided value changes.
In your case, you have an event (the click event from the Add to Contacts button) after which you want your data to be fetched again. But you also want to fetch data when the page loads.
One way to do it is something like this:
const Add__Contact = async ({ name, phone }) => {
// Return the Promise returned from the Axios call
return Axios({
method: "post",
url: "http://localhost:3006/contacts",
headers: {
"Content-Type": "application/json",
},
data: {
name,
phone,
},
});
};
const App = () => {
const [name, setName] = useState("");
const [phone, setPhone] = useState("");
const [contacts, setContacts] = useState([]);
const url = "http://localhost:3006/contacts";
// Add a function to fetch contacts
const fetchContacts = async () => {
const res = await Axios.get(url);
setContacts(res.data);
};
// Effect that fetches contacts when the component loads
useEffect(() => {
fetchContacts();
}, []);
//add new contact to server
const addContact = async () => {
// await the Promise returned
const saveRes = await Add__Contact({ name, phone });
// Fetch the contacts list again
await fetchContacts();
};
// view
return (
<div>
<h4>Add contact</h4>
<div>
<input type="text" name="name" value={name} onChange={(e) => setName(e.target.value)} placeholder="name here" />
<br />
<br />
<input
type="text"
name="phone"
value={phone}
onChange={(e) => setPhone(e.target.value)}
placeholder="Phone here"
/>
<br />
<br />
<button onClick={addContact}>Add to Contact</button>
</div>
<hr />
<h4>List of Contacts</h4>
<div>
{contacts.map((contact) => {
return (
<div key={contact.id}>
<span>{contact.name} : </span>
<span> {contact.phone}</span>
</div>
);
})}
</div>
</div>
);
};
CodePudding user response:
So you'r Contacts Array is not updated .Even you got a data from axios call .
Like if axios is returning data then i think you'r state in not updating then you have to use
setContacts((prv)=>[...prv,...res.data])
If you'r facing problem on Add time . Then make a separate function then use that in useEffect() && your ADD_Contact() .
const App = () => {
const [name, setName] = useState("");
const [phone, setPhone] = useState("");
const [contacts, setContacts] = useState([]);
const getContacts = async () => {
const res = await Axios.get('http://localhost:3006/contacts');
setContacts(res.data);
};
useEffect(() => {
getContacts();
}, []);
const addContact = async () => {
const saveRes = await Add__Contact({ name, phone });
await getContacts();
};
return (
<div>
<h4>Add contact</h4>
<div>
<input type="text" name="name" value={name} onChange={(e) => setName(e.target.value)} placeholder="name here" />
<br />
<br />
<input
type="text"
name="phone"
value={phone}
onChange={(e) => setPhone(e.target.value)}
placeholder="Phone here"
/>
<br />
<br />
<button onClick={addContact}>Add to Contact</button>
</div>
<hr />
<h4>List of Contacts</h4>
<div>
{contacts.map((contact) => {
return (
<div key={contact.id}>
<span>{contact.name} : </span>
<span> {contact.phone}</span>
</div>
);
})}
</div>
</div>
);
};