当我在执行axios.put
后尝试从对象的状态数组更新和属性时,会出现我的问题。
这是我的代码:
状态 - 使用效果
//...
const [volunteers, setVolunteers] = useState([]);
//...
useEffect(() => {
async function loadVolunteers() {
api
.get('volunteers')
.then(response => {
const data = response.data.map(volunteer => ({
...volunteer,
notChecked: volunteer.confirmed === null,
confirmedText: volunteer.confirmed ? 'Deferido' : 'Indeferido',
createdDateFormatted: format(
parseISO(volunteer.createdAt),
"d 'de' MMMM'/'yyyy",
{
locale: pt,
}
),
}));
setVolunteers(data);
})
.then(() => {
api
.get('departments')
.then(response => {
setDepartments(response.data);
setLoading(false);
})
.catch(() => {
toast.error(
'Ops! Aconteceu algum problema ao buscar as Inscrições. Tente novamente mais tarde e/ou contate o Programador'
);
});
})
.catch(() => {
toast.error(
'Ops! Aconteceu algum problema ao buscar as Inscrições. Tente novamente mais tarde e/ou contate o Programador'
);
});
}
if (!isAdmin) {
history.push('/dashboard');
}
loadVolunteers();
dispatch(changePage('inscricoes'));
}, []); // eslint-disable-line
//...
const updateDepartment = async (id, department_id) => {
try {
await api.put(`volunteers/${id}/department`, {
department_id,
});
setVolunteers(
volunteers.map(volunteer => {
if (volunteer.id === id) {
volunteer.department_id = department_id;
return volunteer;
}
return volunteer;
})
);
toast.success('Departamento atualizado');
} catch (err) {
toast.error('Erro ao atualizar departamento');
}
};
如果我删除setVolunteers
指令,此方法将立即运行。
但是当我尝试在志愿者数组/状态中执行该映射时,应用程序会冻结 1~2 秒。
为什么?
在反应代码的其余部分下方迭代志愿者数组。
{volunteers.map((volunteer, index) => (
<Card
key={volunteer.id}
className={classes.card}
variant="outlined"
>
<CardContent>
<TextField
variant="outlined"
margin="none"
required
select
fullWidth
id="gender"
value={volunteer.department_id}
placeholder="Selecione"
onChange={e =>
updateDepartment(volunteer.id, e.target.value)
}
label="Selecione seu sexo"
name="gender"
>
{departments.map(option => (
<MenuItem key={option.id} value={option.id}>
{option.name}
</MenuItem>
))}
</TextField>
<Typography variant="h5" component="h2">
{volunteer.user.name}
</Typography>
<Typography className={classes.pos} color="textSecondary">
{volunteer.user.phone}
</Typography>
<Typography variant="body2" component="p">
<strong>Líder: </strong>
{volunteer.user.leader_name}
</Typography>
</CardContent>
<CardActions className={classes.subActions}>
{volunteer.notChecked ? (
<>
<Button
size="small"
fullWidth
variant="contained"
color="primary"
disabled={loadConfirm}
onClick={() =>
handleConfirmation(index, volunteer.id, true)
}
>
Deferido
</Button>
<Button
size="small"
fullWidth
variant="contained"
disabled={loadConfirm}
onClick={() =>
handleConfirmation(index, volunteer.id, false)
}
>
Indeferido
</Button>
</>
) : (
<Button
size="small"
fullWidth
variant="contained"
color="primary"
disabled
>
{volunteer.confirmed ? 'Deferido' : 'Indeferido'}
</Button>
)}
<Button
size="small"
fullWidth
variant="contained"
className={classes.deny}
disabled={loadConfirm}
onClick={() => handleDelete(index, volunteer.id, true)}
>
Excluir
</Button>
</CardActions>
</Card>
))}
可以使用回调函数来更新状态。
试试这个。
const updateDepartment = async (id, department_id) => {
try {
await api.put(`volunteers/${id}/department`, {
department_id
});
setVolunteers(prevState => {
let Volunteers = prevState.map(volunteer => {
if (volunteer.id === id) {
volunteer.department_id = department_id;
return volunteer;
}
return volunteer;
});
return Volunteers;
});
toast.success("Departamento atualizado");
} catch (err) {
toast.error("Erro ao atualizar departamento");
}
};