Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

override useShowController onFailure behavior and return error object #6625

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 12 additions & 6 deletions docs/Show.md
Original file line number Diff line number Diff line change
Expand Up @@ -148,7 +148,7 @@ const PostShow = props => (
```
{% endraw %}

You can use the `useRecordContext` hook to display non-editable details about the current record in the aside component:
You can use the `useRecordContext` hook to display non-editable details about the current record in the aside component:

{% raw %}
```jsx
Expand Down Expand Up @@ -184,7 +184,7 @@ const PostShow = props => (
</Show>
);

// use a custom component as root component
// use a custom component as root component
const PostShow = props => (
<Show component={MyComponent} {...props}>
...
Expand Down Expand Up @@ -224,7 +224,7 @@ React-admin provides guessers for the `List` view (`ListGuesser`), the `Edit` vi
The `<Show>` component takes care of two things:

1. (the "controller") Fetching data based on the URL and transforming it
2. (the "view") Rendering the page title, the actions, the content and aside areas
2. (the "view") Rendering the page title, the actions, the content and aside areas

In some cases, you may want to customize the view entirely (i.e. keep the code for step 1, and provide your own code for step 2). For these cases, react-admin provides a hook called `useShowController()`, which contains just the controller part of the `<Show>` component.

Expand All @@ -242,7 +242,10 @@ const MyShow = props => {
record, // record fetched via dataProvider.getOne() based on the id from the location
resource, // the resource name, deduced from the location. e.g. 'posts'
version, // integer used by the refresh feature
} = useShowController(props);
error, // error returned by dataProvider (not accessible by default )
// This property is not accessible by default:due to redirect to basePath
// In order to access error, override props.onFailure
} = useShowController({ ...props, onFailure: () => {} });
return (
<div>
<h1>{defaultTitle}</h1>
Expand All @@ -251,6 +254,7 @@ const MyShow = props => {
record,
resource,
version,
error,
})}
</div>
);
Expand All @@ -267,7 +271,9 @@ const PostShow = props => (

This custom Show view has no action buttons or aside component - it's up to you to add them in pure React.

**Tip**: You don't have to clone the child element. If you can't reuse an existing form component like `<SimpleShowLayout>`, feel free to write the form code inside your custom `MyShow` component.
**Tip**: You don't have to clone the child element. If you can't reuse an existing form component like `<SimpleShowLayout>`, feel free to write the form code inside your custom `MyShow` component.

**Tip**: When data provider returns an error, users are notified and redirected to component's base URL; to override this behavior, provide `onFailure` property to `useShowController`.

## The `<SimpleShowLayout>` component

Expand Down Expand Up @@ -409,7 +415,7 @@ You can find components for react-admin in third-party repositories.

## Displaying Fields depending on the user permissions

You might want to display some fields only to users with specific permissions.
You might want to display some fields only to users with specific permissions.

Before rendering the `Show` component, react-admin calls the `authProvider.getPermissions()` method, and passes the result to the component as the `permissions` prop. It's up to your `authProvider` to return whatever you need to check roles and permissions inside your component.

Expand Down
21 changes: 12 additions & 9 deletions packages/ra-core/src/controller/details/useShowController.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ export interface ShowProps {
hasList?: boolean;
id?: Identifier;
resource?: string;
onFailure?: (e: any) => void;
[key: string]: any;
}

Expand All @@ -34,6 +35,7 @@ export interface ShowControllerProps<RecordType extends Record = Record> {
record?: RecordType;
refetch: Refetch;
version: number;
error?: any;
}

/**
Expand Down Expand Up @@ -64,18 +66,18 @@ export const useShowController = <RecordType extends Record = Record>(
const redirect = useRedirect();
const refresh = useRefresh();
const version = useVersion();
const { data: record, loading, loaded, refetch } = useGetOne<RecordType>(
resource,
id,
{
action: CRUD_GET_ONE,
onFailure: () => {
const { data: record, loading, loaded, refetch, error } = useGetOne<
RecordType
>(resource, id, {
action: CRUD_GET_ONE,
onFailure:
props.onFailure ??
(() => {
notify('ra.notification.item_doesnt_exist', 'warning');
redirect('list', basePath);
refresh();
},
}
);
}),
});

const getResourceLabel = useGetResourceLabel();
const defaultTitle = translate('ra.page.show', {
Expand All @@ -97,5 +99,6 @@ export const useShowController = <RecordType extends Record = Record>(
hasList,
hasShow,
version,
error,
};
};