Skip to content

Commit 27b6fb3

Browse files
committed
Add setting up page
1 parent efca339 commit 27b6fb3

File tree

2 files changed

+218
-2
lines changed

2 files changed

+218
-2
lines changed

docs_headless/astro.config.mjs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -240,6 +240,7 @@ export default defineConfig({
240240
{
241241
label: 'Soft Delete',
242242
items: [
243+
enterpriseEntry('SoftDeleteDataProvider', 'Setting up'),
243244
enterpriseEntry('<DeletedRecordsListBase>'),
244245
enterpriseEntry('<ShowDeletedBase>'),
245246
enterpriseEntry('<DeletedRecordRepresentation>'),
@@ -298,10 +299,10 @@ export default defineConfig({
298299
* @param {string} name
299300
* @returns {any}
300301
*/
301-
function enterpriseEntry(name) {
302+
function enterpriseEntry(name, label = name) {
302303
return {
303304
link: `${name.toLowerCase().replace(/</g, '').replace(/>/g, '')}/`,
304-
label: name,
305+
label,
305306
attrs: { class: 'enterprise' },
306307
badge: {
307308
text: 'React Admin Enterprise',
Lines changed: 215 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,215 @@
1+
---
2+
layout: default
3+
title: "Soft Delete Setup"
4+
---
5+
6+
The soft delete feature is an [Enterprise Edition add-on](https://react-admin-ee.marmelab.com/documentation/ra-soft-delete) that allows you to "delete" records without actually removing them from your database.
7+
8+
Use it to:
9+
10+
- Archive records safely instead of permanent deletion
11+
- Browse and filter all deleted records in a dedicated interface
12+
- Restore archived items individually or in bulk
13+
- Track who deleted what and when
14+
15+
It provides drop-in replacements for DeleteButton and BulkDeleteButton.
16+
17+
## Installation
18+
19+
```bash
20+
npm install --save @react-admin/ra-soft-delete
21+
# or
22+
yarn add @react-admin/ra-soft-delete
23+
```
24+
25+
You will need an active Enterprise Edition license to use this package. Please refer to the [Enterprise Edition documentation](https://react-admin-ee.marmelab.com) for more details.
26+
27+
## Data Provider
28+
29+
### Methods
30+
31+
`ra-soft-delete` relies on the `dataProvider` to soft-delete, restore or view deleted records.
32+
In order to use the `ra-soft-delete`, you must add a few new methods to your data provider:
33+
34+
- `softDelete` performs the soft deletion of the provided record.
35+
- `softDeleteMany` performs the soft deletion of the provided records.
36+
- `getOneDeleted` gets one deleted record by its ID.
37+
- `getListDeleted` gets a list of deleted records with filters and sort.
38+
- `restoreOne` restores a deleted record.
39+
- `restoreMany` restores deleted records.
40+
- `hardDelete` permanently deletes a record.
41+
- `hardDeleteMany` permanently deletes many records.
42+
- (OPTIONAL) [`createMany`](#createmany) creates multiple records at once. This method is used internally by some data provider implementations to delete or restore multiple records at once. As it is optional, a default implementation is provided that simply calls `create` multiple times.
43+
44+
### Signature
45+
46+
Here is the full `SoftDeleteDataProvider` interface:
47+
48+
```tsx
49+
const dataProviderWithSoftDelete: SoftDeleteDataProvider = {
50+
...dataProvider,
51+
52+
softDelete: (resource, params: SoftDeleteParams): SoftDeleteResult => {
53+
const { id, authorId } = params;
54+
// ...
55+
return { data: deletedRecord };
56+
},
57+
softDeleteMany: (resource, params: SoftDeleteManyParams): SoftDeleteManyResult => {
58+
const { ids, authorId } = params;
59+
// ...
60+
return { data: deletedRecords };
61+
},
62+
63+
getOneDeleted: (params: GetOneDeletedParams): GetOneDeletedResult => {
64+
const { id } = params;
65+
// ...
66+
return { data: deletedRecord };
67+
},
68+
getListDeleted: (params: GetListDeletedParams): GetListDeletedResult => {
69+
const { filter, sort, pagination } = params;
70+
// ...
71+
return { data: deletedRecords, total: deletedRecords.length };
72+
},
73+
74+
restoreOne: (params: RestoreOneParams): RestoreOneResult => {
75+
const { id } = params;
76+
// ...
77+
return { data: deletedRecord };
78+
},
79+
restoreMany: (params: RestoreManyParams): RestoreManyResult => {
80+
const { ids } = params;
81+
// ...
82+
return { data: deletedRecords };
83+
},
84+
85+
hardDelete: (params: HardDeleteParams): HardDeleteResult => {
86+
const { id } = params;
87+
// ...
88+
return { data: deletedRecordId };
89+
},
90+
hardDeleteMany: (params: HardDeleteManyParams): HardDeleteManyResult => {
91+
const { ids } = params;
92+
// ...
93+
return { data: deletedRecordsIds };
94+
},
95+
};
96+
```
97+
98+
**Tip**: `ra-soft-delete` automatically populates the `authorId` parameter using `authProvider.getIdentity()` if it is implemented. It will use the `id` field of the returned identity object. Otherwise this field will be left blank.
99+
100+
**Tip**: Deleted records are immutable, so you don't need to implement an `updateDeleted` method.
101+
102+
Once your provider has all soft-delete methods, pass it to the `<Admin>` component and you're ready to start using `ra-soft-delete`.
103+
104+
```tsx
105+
// in src/App.tsx
106+
import { Admin } from 'react-admin';
107+
import { dataProvider } from './dataProvider';
108+
109+
const App = () => <Admin dataProvider={dataProvider}>{/* ... */}</Admin>;
110+
```
111+
112+
### Deleted Record Structure
113+
114+
A _deleted record_ is an object with the following properties:
115+
116+
- `id`: The identifier of the deleted record.
117+
- `resource`: The resource name of the deleted record.
118+
- `deleted_at`: The date and time when the record was deleted, in ISO 8601 format.
119+
- `deleted_by`: (optional) The identifier of the user who deleted the record.
120+
- `data`: The original record data before deletion.
121+
122+
Here is an example of a deleted record:
123+
124+
```js
125+
{
126+
id: 123,
127+
resource: "products",
128+
deleted_at: "2025-06-06T15:32:22Z",
129+
deleted_by: "johndoe",
130+
data: {
131+
id: 456,
132+
title: "Lorem ipsum",
133+
teaser: "Lorem ipsum dolor sit amet",
134+
body: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit',
135+
},
136+
}
137+
```
138+
139+
### Builders
140+
141+
`ra-soft-delete` comes with two built-in implementations that will add soft delete capabilities to your data provider without any specific backend requirements. You can choose the one that best fits your needs:
142+
143+
- [`addSoftDeleteBasedOnResource`](./addSoftDeleteBasedOnResource.md) stores the deleted records for all resources in a single resource. This resource is named `deleted_records` by default.
144+
145+
With this builder, all deleted records disappear from their original resource when soft-deleted, and are recreated in the `deleted_records` resource.
146+
147+
```tsx
148+
// in src/dataProvider.ts
149+
import { addSoftDeleteBasedOnResource } from '@react-admin/ra-soft-delete';
150+
import baseDataProvider from './baseDataProvider';
151+
152+
export const dataProvider = addSoftDeleteBasedOnResource(
153+
baseDataProvider,
154+
{ deletedRecordsResourceName: 'deleted_records' }
155+
);
156+
```
157+
158+
- [`addSoftDeleteInPlace`](./addSoftDeleteInPlace.md) keeps the deleted records in the same resource, but marks them as deleted.
159+
160+
With this builder, all deleted records remain in their original resource when soft-deleted, but are marked with the `deleted_at` and `deleted_by` fields. The query methods (`getList`, `getOne`, etc.) automatically filter out deleted records.
161+
162+
You'll need to pass a configuration object with all soft deletable resources as key so that `getListDeleted` knows where to look for deleted records.
163+
164+
```tsx
165+
// in src/dataProvider.ts
166+
import { addSoftDeleteInPlace } from '@react-admin/ra-soft-delete';
167+
import baseDataProvider from './baseDataProvider';
168+
169+
export const dataProvider = addSoftDeleteInPlace(
170+
baseDataProvider,
171+
{
172+
posts: {},
173+
comments: {
174+
deletedAtFieldName: 'deletion_date',
175+
},
176+
accounts: {
177+
deletedAtFieldName: 'disabled_at',
178+
deletedByFieldName: 'disabled_by',
179+
}
180+
}
181+
);
182+
```
183+
184+
**Note:** When using `addSoftDeleteInPlace`, avoid calling `getListDeleted` without a `resource` filter, as it uses a naive implementation combining multiple `getList` calls, which can lead to bad performance. It is recommended to use one list per resource in this case (see [`<DeletedRecordsListBase resource>` property](./DeletedRecordsListBase.md#resource)).
185+
186+
You can also write your own implementation. Feel free to look at these builders source code for inspiration. You can find it under your `node_modules` folder, e.g. at `node_modules/@react-admin/ra-core-ee/src/soft-delete/dataProvider/addSoftDeleteBasedOnResource.ts`.
187+
188+
### Query and Mutation Hooks
189+
190+
Each data provider verb has its own hook so you can use them in custom components:
191+
192+
- `softDelete`: [`useSoftDelete`](./useSoftDelete.md)
193+
- `softDeleteMany`: [`useSoftDeleteMany`](./useSoftDeleteMany.md)
194+
- `getListDeleted`: [`useGetListDeleted`](./useGetListDeleted.md)
195+
- `getOneDeleted`: [`useGetOneDeleted`](./useGetOneDeleted.md)
196+
- `restoreOne`: [`useRestoreOne`](./useRestoreOne.md)
197+
- `restoreMany`: [`useRestoreMany`](./useRestoreMany.md)
198+
- `hardDelete`: [`useHardDelete`](./useHardDelete.md)
199+
- `hardDeleteMany`: [`useHardDeleteMany`](./useHardDeleteMany.md)
200+
201+
202+
## `createMany`
203+
204+
`ra-soft-delete` provides a default implementation of the `createMany` method that simply calls `create` multiple times. However, some data providers may be able to create multiple records at once, which can greatly improve performances.
205+
206+
```tsx
207+
const dataProviderWithCreateMany = {
208+
...dataProvider,
209+
createMany: (resource, params: CreateManyParams): CreateManyResult => {
210+
const {data} = params; // data is an array of records.
211+
// ...
212+
return {data: createdRecords};
213+
},
214+
};
215+
```

0 commit comments

Comments
 (0)