Can anyone advise on how to approach this problem?
i have a form with various state. When the user changes any of the forms inputs and clicks save, a function sends the data to the backend. The problem is that I send the whole object to the backend when I only want to send the changed value / the state that has changed. How would I do that?
Here is an example:
const [streetName, setStreetName] = useState<string>('');
const [zipCode, setZipCode] = useState<string>('');
const [city, setCity] = useState<string>('');
const [email, setEmail] = useState<string>('');
const [phone, setPhone] = useState<string>('');
const userData = {
streetName,
zipCode,
city,
email,
phone
};
const saveDataOnClickHandler = (userData) => {
updateUserMutation(userData);
};
CodePudding user response:
Assuming that you start with empty string and this initial state (useState<string>('');
), you can simply filter fields with empty string before sending e.g.
const userData = {
streetName !== '' ? streetName : undefined,
zipCode !== '' ? zipCode : undefined,
city !== '' ? city : undefined,
email !== '' ? email : undefined,
phone !== '' ? phone : undefined
};
If you want to send fields that changed from last send, then you need to save these values and compare it with actual input
streetName !== previouslySentStreetName ...
CodePudding user response:
It depends, as you are not showing the form i would assume that the actual value of the inputs its linked to the state. In this case i would add a hasChanged property to each state and onSubmit i would send a fresh new userData object:
const initValue = {
value: '',
hasChanged: false,
};
const [streetName, setStreetName] = useState(initValue);
const [zipCode, setZipCode] = useState(initValue);
const [city, setCity] = useState(initValue);
const [email, setEmail] = useState(initValue);
const [phone, setPhone] = useState(initValue);
const userData = {
streetName,
zipCode,
city,
email,
phone,
};
const handleOnStreetChange = (event)=>{
setStreetName({
value: event.target.value,
hasChanged: true,
});
}
const handleOnZipCodeChange = (event)=>{
setZipCode({
value: event.target.value,
hasChanged: true,
});
}
const saveDataOnClickHandler = (userData) => {
let freshUserData = {};
Object.entries(userData).forEach((data) => {
[key, value] = data;
freshUserData = value.hasChanged
? { ...freshUserData, [key]: value }
: freshUserData;
});
sendDataToBackend(freshUserData)
};
const submitForm = (e) => {
e.preventDefault();
saveDataOnClickHandler(userData)
};
return (
<>
<form aria-label='form'>
<input
type='text'
placeholder='Street Name'
name='streetName'
value={streetName}
onChange={handleOnStreetChange}
/>
<input
type='text'
placeholder='Zip Code'
name='zipCode'
value={zipCode}
onChange={handleOnZipCodeChange}
/>
<button type="submit" onClick={submitForm}>
Send
</button>
</form>
</>
);