Allow for passing metadata on action dispatch
Description
Currently, when dispatching an insert action in Puck, there is no standardized way to pass ephemeral metadata associated with that specific action.
For example, when programmatically inserting an item, a developer might want to tag it as "newly added" to trigger a specific UI behavior (like automatically opening the item's settings or highlighting it) only for that specific insertion event.
Currently, developers have to resort to external state tracking (e.g., a global Set of IDs) to track which items were added in the current session versus loaded from the server. This is brittle and disconnected from the Puck state loop.
Considerations
- This change would likely affect the
insertaction definition and the reducer that handles it. - The metadata should ideally be ephemeral and available during the action handling or state update phase to trigger side effects, without necessarily polluting the persistent data structure.
Proposals
Proposal 1
Update the insert action to accept a metadata property (or similar) in its payload.
dispatch({
type: 'insert',
metadata: { newlyAdded: true },
...rest
})
This metadata could then be surfaced in onAction or accessible in the resulting state update context, allowing developers to react to the insertion with context.
For example, to open an item immediately after it is added:
// Hypothetical usage
<Puck
onAction={(action) => {
if (action.type === 'insert' && action.metadata?.newlyAdded) {
// Logic to open the item editor for the new item
setSelectedItem(action.payload.item.props.id);
}
}}
/>
or
const selectedItem = usePuckStable((s) => s.selectedItem);
useEffect(() => {
if (selectedItem selectedItem.metadata.newlyAdded) {
// run something
}
}, [selectedItem]);