Skip to content

Commit

Permalink
Merge pull request #8719 from marmelab/Fix-useGetManyAggregate-onSuccess
Browse files Browse the repository at this point in the history
Fix `ReferenceInput` throws an error when referencing the same resource as `Edit` and the reference is undefined
  • Loading branch information
djhi authored Mar 9, 2023
2 parents 743362a + 6d2c96a commit 6cf793f
Show file tree
Hide file tree
Showing 3 changed files with 62 additions and 3 deletions.
2 changes: 1 addition & 1 deletion packages/ra-core/src/dataProvider/useGetManyAggregate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,7 @@ export const useGetManyAggregate = <RecordType extends RaRecord = any>(
placeholderData,
onSuccess: data => {
// optimistically populate the getOne cache
data.forEach(record => {
(data ?? []).forEach(record => {
queryClient.setQueryData(
[resource, 'getOne', { id: String(record.id), meta }],
oldRecord => oldRecord ?? record
Expand Down
15 changes: 15 additions & 0 deletions packages/ra-ui-materialui/src/input/ReferenceInput.spec.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import {
Basic,
WithSelectInput,
dataProviderWithAuthors,
SelfReference,
} from './ReferenceInput.stories';

describe('<ReferenceInput />', () => {
Expand Down Expand Up @@ -217,4 +218,18 @@ describe('<ReferenceInput />', () => {
})
);
});

it('should not throw an error on save when it is a self reference and the reference is undefined', async () => {
jest.spyOn(console, 'log').mockImplementationOnce(() => {});
jest.spyOn(console, 'error').mockImplementationOnce(() => {});
render(<SelfReference />);
fireEvent.click(await screen.findByLabelText('Self reference'));
expect(await screen.findAllByRole('option')).toHaveLength(5);
const titleInput = await screen.findByDisplayValue('War and Peace');
fireEvent.change(titleInput, {
target: { value: 'War and Peace 2' },
});
screen.getByLabelText('Save').click();
await screen.findByText('Proust', undefined, { timeout: 5000 });
});
});
48 changes: 46 additions & 2 deletions packages/ra-ui-materialui/src/input/ReferenceInput.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import * as React from 'react';
import { createMemoryHistory } from 'history';
import { Admin, AdminContext } from 'react-admin';
import { Admin, AdminContext, Datagrid, List, TextField } from 'react-admin';
import { QueryClient } from 'react-query';
import { Resource, Form, testDataProvider } from 'ra-core';
import { Resource, Form, testDataProvider, useRedirect } from 'ra-core';
import polyglotI18nProvider from 'ra-i18n-polyglot';
import englishMessages from 'ra-language-english';
import { Stack, Divider, Typography } from '@mui/material';
Expand Down Expand Up @@ -463,3 +463,47 @@ export const ErrorRadioButtonGroupInput = () => (
/>
</Admin>
);

const AuthorList = () => (
<List>
<Datagrid>
<TextField source="first_name" />
<TextField source="last_name" />
</Datagrid>
</List>
);

const BookEditWithSelfReference = () => {
const redirect = useRedirect();
return (
<Edit
mutationMode="pessimistic"
mutationOptions={{
onSuccess: data => {
// Redirecting to another page is an indirect way to make sure that
// no errors happened during the update nor its side effects
// (used by the jest tests)
redirect('/authors');
},
}}
>
<SimpleForm>
<TextInput source="title" />
<ReferenceInput reference="books" source="self_reference" />
</SimpleForm>
</Edit>
);
};

export const SelfReference = ({ dataProvider = dataProviderWithAuthors }) => (
<Admin dataProvider={dataProvider} history={history}>
<Resource
name="authors"
recordRepresentation={record =>
`${record.first_name} ${record.last_name}`
}
list={AuthorList}
/>
<Resource name="books" edit={BookEditWithSelfReference} />
</Admin>
);

0 comments on commit 6cf793f

Please sign in to comment.