Следующий компонент React представляет собой форму, которая позволяет пользователю одновременно обновлять сотни записей. Чтобы сохранить масштабируемость сервера, я решил следовать рекомендациям в этом посте, библиотеке pLimit, чтобы ограничить количество одновременных запросов, попадающих на сервер: Каков наилучший способ ограничить параллелизм при использовании ES6 Promise.all ( )? .
Однако я не смог обойти эти две ошибки:
- Обработано больше хуков, чем во время предыдущего рендеринга
- Хуки могут только быть вызванным внутри тела функционального компонента
Я попытался использовать хуки useMutation для вызова мутации для каждой записи. Проблема в том, что у меня не может быть хука useMutation в функции в оболочке pLimit Promise, если эта функция не является компонентом. Но я не могу сделать эту функцию компонентом, иначе я столкнусь со второй ошибкой выше.
Итак, я пытался найти решение этой проблемы.
- https://www.apollographql.com/docs/react/api/link/apollo-link-batch-http/#options
- Имейте состояние React словаря, которое постепенно обновляется параллельными вызовами updateIndividual, ограниченным pLimit.
import pLimit from 'p-limit'
function updateIndividual(x) {
let [update, {called, loading, error}] = useMutation(UpdateMutation, {
client: client,
variables: {...},
});
update()
let label = x.name + " ";
label += loading ? "updating..." : error ? `error... ${error}` : called ? "updated" : "start";
return label
}
export default function Form(props) {
const [rows, setRows] = useState(props.data.reduce(function(map, val) {
map[val] = undefined; // { 'one': undefined, 'two': undefined...}
return map;
}, {}));
const limit = pLimit(3);
const promises = data?.map(x => {
return limit(() => updateIndividual(x));
});
(async () => {
setRows(await Promise.all(promises));
})();
return <div id='update-rows'>
{rows.map((k, v) => (
<div id={k}>{rows}</div>
))}
</div>
}