LockOnMount
<LockOnMount> acquires a record lock when it mounts and releases it on unmount. It renders its children when the lock is held, a loading indicator while locking, and a "locked by" message when the record is already locked by someone else.
Installation
pnpm dlx shadcn@latest add @shadmin/lock-on-mountUsage
Wrap the form content inside an edit page to prevent concurrent editing:
import { EditLive } from "@/components/realtime";
import { LockOnMount } from "@/components/realtime";
import { SimpleForm, TextInput } from "@/components/admin";
export const PostEdit = () => (
<EditLive>
<LockOnMount>
<SimpleForm>
<TextInput source="title" />
</SimpleForm>
</LockOnMount>
</EditLive>
);Custom locked state
<LockOnMount
lockedBy={(lock) => (
<div className="p-4 text-destructive">
This record is being edited by {String(lock.identity)}.
</div>
)}
>
<SimpleForm>...</SimpleForm>
</LockOnMount>Props
| Prop | Required | Type | Default | Description |
|---|---|---|---|---|
children | Required | ReactNode | — | Rendered when the lock is successfully acquired |
resource | Optional | string | ResourceContext | Resource name. Falls back to context. |
id | Optional | Identifier | RecordContext.id | Record ID. Falls back to context. |
identity | Optional | Identifier | useGetIdentity() | User identity. Falls back to auth provider. |
meta | Optional | Record<string, unknown> | — | Forwarded to lock() |
loading | Optional | ReactNode | <Skeleton /> | Shown while the lock request is in flight |
lockedBy | Optional | (lock: Lock) => ReactNode | <Alert>Locked by …</Alert> | Shown when a LockConflictError is thrown |
onLockError | Optional | (error: Error) => void | — | Called for any lock error (including conflicts) |
Notes
- Uses
useLockOnMountinternally — see that hook's page for behaviour details. - When
resourceoridare not in context (e.g. outside a<Edit>or<Show>), pass them explicitly. - The lock is released on unmount even if the form was not saved.
LockConflictErroris detected by instance check; other errors are propagated toonLockErrorbut not rendered bylockedBy.