реагировать-администратор: ОШИБКА: dataProvider выдал ошибку. Вместо этого он должен вернуть отклоненное обещание - легко исправить? - PullRequest
2 голосов
/ 25 февраля 2020

В форме редактирования activ-admin 3.2.3 мне нужно показать связанные записи (список записей заданий) из другого ресурса. Отношение немного странное и требует парсинга строк, поэтому я не могу просто использовать встроенный ReferenceField. Вот почему я пытаюсь вызвать функцию dataProvider getList, используя хук useGetList. К сожалению, я получаю ошибку при рендеринге формы:

DataProvider выдал ошибку. Вместо этого он должен вернуть отклоненное обещание

Это функция getList моего пользовательского провайдера данных:

 getList: (resource, params) => {
        console.log('DataProvider.GetList ');
        console.log(resource);
        console.log(params);
        const { page, perPage } = params.pagination;
        const { field, order } = params.sort;
        const query = {
            ...fetchUtils.flattenObject(params.filter),
            _sort: field,
            _order: order,
            _start: (page - 1) * perPage,
            _end: page * perPage,
        };
        const url = `${getUrl(resource)}?${stringify(query)}`;
        const paging = supportsPaging(resource);

        return httpClient(url).then(
            ({ headers, json }) => {
                var result = [];

                // Implementierung von clientseitigem Paging & Filtering
                var filtered = applyFilter(json, params.filter);
                if (!paging) {
                    filtered=applyPagination(filtered, page, perPage);
                }
                else {
                    result = filtered;
                }

                return {
                    data: result,
                    total: json.length 
                };
            }, ({ reason }) => {

                console.log(reason);
            }).catch((e)=>{
                console.log(e);
            });
    }

Я использую этот пользовательский компонент в форме редактирования.

export const CSEJobList = ({ ...props }) => {
    const form = useForm();
    var formdata = form.getState().values;
    console.log("CSEJobList");
    if (formdata && formdata.status && formdata.status.id >= 2) {
        var data = GetJobData({ 'filter': { type: 'abeitsschein_id_' + formdata.id } });
        return data;
    }
    else {
        return <div>Test</div>
    }
};
CSEJobList.defaultProps = { label: 'Arbeitsschein', addLabel: true };

  const GetJobData = (params) => {
        let parms = { "pagination": { "page": 0, "perPage": 25 }, "sort": { "field": "id", "order": "ASC" }, "filter": {} };
        const { data, loading, error } = useGetList('jobs', parms);
        if (loading) { return <LinearProgress />; }
        if (error) { return <p>ERROR</p>; }
        return <p>{data}</p>;
    };

Это просто базовый c тест. Правильное отображение данных результатов пока не реализовано, так как вызов приводит к указанной ошибке.

Я прочитал документацию (https://marmelab.com/react-admin/Actions.html#specialized -hooks ) о запросах API, много возился , но я терплю неудачу из-за моего ограниченного понимания обещаний.

Есть ли простое исправление?

Обновление:

Я изменил dataProvider getList Функция так, вернуть отклоненные обещания как предложено:

getList: (resource, params) => {
    console.log('DataProvider.GetList ');
    console.log(resource);
    console.log(params);
    const { page, perPage } = params.pagination;
    const { field, order } = params.sort;
    const query = {
        ...fetchUtils.flattenObject(params.filter),
        _sort: field,
        _order: order,
        _start: (page - 1) * perPage,
        _end: page * perPage,
    };
    const url = `${getUrl(resource)}?${stringify(query)}`;
    const paging = supportsPaging(resource);

    return httpClient(url).then(
        ({ headers, json }) => {
            var result = [];

            // Implementierung von clientseitigem Paging & Filtering
            var filtered = applyFilter(json, params.filter);
            if (!paging) {
                filtered=applyPagination(filtered, page, perPage);
            }
            else {
                result = filtered;
            }

            return {
                data: result,
                total: json.length,  // Erfordert nun keinen speziellen Header mehr, CSE-Connect kompatibel
            };
        }, ({ reason }) => {
            return Promise.reject(reason);
        }).catch((e)=>{
            console.log(e);
            return Promise.reject(e);
        });
},

Это не имело никакого эффекта. После некоторой отладки я понял, что в функции GetJobData строка

if (loading) { return <LinearProgress />; }

вызывает ошибку. Точно так же работает и в других частях кода, поэтому подозреваемый не LinearProgress. Я на самом деле понятия не имею, что вызывает ошибку. Отладку трудно или невозможно из-за тайм-аутов.

Это полная трассировка стека:

useDataProvider.js:334 Uncaught Error: The dataProvider threw an error. It should return a rejected Promise instead.
    at performQuery (useDataProvider.js:334)
    at Proxy.<anonymous> (useDataProvider.js:163)
    at JSON.stringify.query (useQueryWithStore.js:116)
    at commitHookEffectList (react-dom.development.js:22030)
    at commitPassiveHookEffects (react-dom.development.js:22064)
    at HTMLUnknownElement.callCallback (react-dom.development.js:336)
    at Object.invokeGuardedCallbackDev (react-dom.development.js:385)
    at invokeGuardedCallback (react-dom.development.js:440)
    at flushPassiveEffectsImpl (react-dom.development.js:25392)
    at unstable_runWithPriority (scheduler.development.js:697)
    at runWithPriority$2 (react-dom.development.js:12149)
    at flushPassiveEffects (react-dom.development.js:25361)
    at performSyncWorkOnRoot (react-dom.development.js:24251)
    at react-dom.development.js:12199
    at unstable_runWithPriority (scheduler.development.js:697)
    at runWithPriority$2 (react-dom.development.js:12149)
    at flushSyncCallbackQueueImpl (react-dom.development.js:12194)
    at flushSyncCallbackQueue (react-dom.development.js:12182)
    at batchedUpdates$1 (react-dom.development.js:24392)
    at Object.notify (Subscription.js:19)
    at Subscription.notifyNestedSubs (Subscription.js:92)
    at Subscription.handleChangeWrapper (Subscription.js:97)
    at dispatch (redux.js:222)
    at middleware.js:22
    at redux-saga-core.esm.js:1410
    at useDataProvider.js:300

Ответы [ 2 ]

0 голосов
/ 22 марта 2020

Текущая реализация перехватывает исключение, если оно есть, и говорит нам, что исключение не должно вызываться поставщиком данных, но ошибка должна быть возвращена как отклоненное обещание:

Ошибка: dataProvider скинул ошибку. Вместо этого он должен вернуть отклоненное обещание.

Давайте посмотрим на текущий код , это выглядит так:

} catch (e) {
    if (process.env.NODE_ENV !== 'production') {
        console.error(e);
    }
    throw new Error(
        'The dataProvider threw an error. It should return a rejected Promise instead.'
    );
}

Из этого мы можем видеть эта фактическая ошибка выводится на консоль непосредственно перед тем, как запускается упомянутая ошибка об отклоненном обещании.

Таким образом, чтобы решить проблему, нам нужно прокрутить консоль до ранее отображаемой ошибки и исправить ее вместо ошибка обещания, которая находится ниже в консоли и на самой странице. И, если возможно, также исправьте провайдера, чтобы перейти к отклоненному обещанию. Однако достаточно исправить предыдущую ошибку.

0 голосов
/ 27 февраля 2020

в случае возникновения ошибки ваш dataProvider должен вернуть следующее значение:

import { HttpError } from 'react-admin'
...
return Promise.reject(new HttpError(message, status, body))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...