Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
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
77 changes: 77 additions & 0 deletions .changeset/action-callback-retired-7068.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
---
'@object-ui/types': minor
---

**Breaking for authored metadata:** the legacy `ActionSchema`'s Phase-2 callback
pair — `onSuccess` / `onFailure`, each carrying an `ActionCallback` object — is
RETIRED, and the `ActionCallback` type and its Zod mirror `ActionCallbackSchema`
(with the inferred `ActionCallbackSchemaType`) are DELETED from `@object-ui/types`
and `@object-ui/types/zod` (objectui#7068; maintainer ruling option 1 of
2026-09-05, immediate, no deprecation window; ADR-0049 enforce-or-remove).

**What an author who wrote the shape sees now.** A `{ type: 'action', … }`
document authoring `onSuccess: { type: 'toast', message: '…' }` (or any
`onFailure` callback) no longer validates: the parse fails loudly on the
`onSuccess` / `onFailure` path (`invalid_type`, expected `never`) with the
explanation and the migration in the message, and the TypeScript members are
`?: never` tombstones so the same document is a `tsc` error at the authoring
site. `import type { ActionCallback } from '@object-ui/types'` and
`import { ActionCallbackSchema } from '@object-ui/types/zod'` fail to resolve.

**What was measured, on this branch's base (`900f8d99`).** `ActionCallback`
(`{ type: 'toast' | 'message' | 'redirect' | 'reload' | 'custom' | 'ajax' |
'dialog', message?, url?, api?, method?, dialog?, handler? }`) was declared in
`crud.ts`, mirrored in `zod/crud.zod.ts`, re-exported by both barrels, and
carried on the legacy `ActionSchema` as `onSuccess?` / `onFailure?`. Producers:
the package's own `phase2-schemas.test.ts` fixture and three `ts` fences in
`content/docs/core/enhanced-actions.mdx` — nothing else (`git grep -l
ActionCallback` over `packages content skills` hit the five `packages/types`
files; positive control `SchemaNodeSchema` hit 22). Runtime readers: none —
`ActionRunner` imports `UIActionSchema`, never this interface, and its own
`ActionDef.onFailure` is a different (runner-native) meaning. It was the THIRD
meaning of one key: objectui#5934 had already retired the runner's callback
meaning of `onSuccess` and converged it on the spec's block.

**Why authored JSON that passed publish is unaffected.** `@objectstack/spec`'s
`ActionSchema` (installed pin 17.2.0) already refused the callback shape at
publish — `invalid_type` at `onSuccess.navigate` plus `unrecognized_keys` on the
`onSuccess` block, and `onFailure` refused as an unrecognized key on the action —
so no published or saved metadata could carry it. Only TypeScript code that
typed a callback against the legacy interface, or JSON validated solely through
`@object-ui/types/zod`, meets the new refusal.

**Where the live meaning lives.** Post-success navigation is the spec's
`onSuccess` block, `{ navigate, openIn }`, declared on `UIActionSchema`
(`ui-action.ts`) and forwarded to the runner (objectui#5934). A success or
failure notice is `successMessage` / `errorMessage` — adjacent keys on the same
legacy `ActionSchema`, NOT retired, and still accepted on both faces.

**Two published faces, one retirement — tombstone on the keys, deletion of the
type.** `BaseSchema` is `.passthrough()` on the mirror and carries an index
signature on the interface, so DELETING the two keys would have ADMITTED an
authored callback unchecked on both faces; they stay declared as `?: never` /
`retirementTombstone()` (the PR #7761 / #7769 shape) and the base-vs-extended
contrast is pinned. The standalone `ActionCallback` / `ActionCallbackSchema` have
no such escape hatch and are deleted outright, the route objectui#7664 / PR #7743
took for the `DeclarativeKanban*` trio; the parity ledger drops the pair
(`EXPECTED_MIRROR_PAIRS` 159 → 158) and the absence is pinned in
`action-callback-retired-7068.test.ts`.

**Docs, same change.** `content/docs/core/enhanced-actions.mdx` — the three
`onSuccess` / `onFailure` fences author `successMessage` / `errorMessage`
instead, and the "Callbacks" section is a "Post-success behaviour" note pointing
at the spec block (no fence: the legacy type carries no spec-derived block).
`content/docs/guide/schema-overview.md` — the fragment line, the feature bullet
and the checklist row are rewritten to the truth (the ✅ claim is now a
retirement note).

**Migration:** delete `onSuccess` / `onFailure` from any legacy `ActionSchema`
document or fixture; write `successMessage` / `errorMessage` for notices, put
follow-up work in `chain`, and author post-success navigation as the spec's
`onSuccess: { navigate, openIn }` block on `UIActionSchema`.

Graded `minor`, not `patch`: this narrows the accepted input set on both faces
and removes two exports, which is breaking for any consumer who wrote the shape.
It is not `major` per this repo's fixed-group convention (objectui's own breaking
changes ship as `minor`; the group's major tracks `@objectstack` — AGENTS.md
版本号策略, mechanically enforced by `scripts/check-changeset-no-major.mjs`).
91 changes: 25 additions & 66 deletions content/docs/core/enhanced-actions.mdx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
---
title: "Enhanced Actions"
description: "Advanced action system with AJAX calls, chaining, conditions, and callbacks"
description: "Advanced action system with AJAX calls, chaining, conditions, and tracking"
---

import { SchemaExample } from '@/app/components/ComponentDemo';
Expand All @@ -15,7 +15,7 @@ The enhanced `ActionSchema` provides:
- **New action types**: `ajax`, `confirm`, `dialog`
- **Action chaining**: Execute multiple actions sequentially or in parallel
- **Conditional execution**: a `condition` predicate gates whether an action runs
- **Callbacks**: Success and failure handlers
- **Notices**: `successMessage` / `errorMessage` strings
- **Tracking**: Event logging and analytics
- **Retry logic**: Automatic retry with configurable backoff

Expand Down Expand Up @@ -54,14 +54,8 @@ const ajaxAction: ActionSchema = {
data: {
filter: 'active'
},
onSuccess: {
type: 'toast',
message: 'Data loaded successfully'
},
onFailure: {
type: 'message',
message: 'Failed to load data'
}
successMessage: 'Data loaded successfully',
errorMessage: 'Failed to load data'
};
```

Expand Down Expand Up @@ -302,47 +296,25 @@ for an either/or.
> diagnostic at runtime. The shape is now refused by `ActionSchema`'s zod schema
> instead of being accepted and ignored.

## Callbacks

Handle success and failure scenarios:
## Post-success behaviour

```ts
import type { ActionSchema } from '@object-ui/types';
This legacy `ActionSchema` has no callback slot. The Phase-2 pair it used to
declare — `onSuccess` / `onFailure` carrying an `ActionCallback` object
(`{ type: 'toast' | 'message' | 'redirect' | 'reload' | 'custom' | 'ajax' | 'dialog', message, url, api, … }`)
— was RETIRED (objectui#7068): nothing ever read it (the runner never consumed
the shape), and `@objectstack/spec`'s `ActionSchema` refuses it at publish. Both
keys are `never` on the TypeScript face and named refusals on the Zod mirror, so an
authored callback fails at the authoring site with the migration in the message.

const actionWithCallbacks: ActionSchema = {
type: 'action',
label: 'Submit',
actionType: 'ajax',
api: '/api/submit',
method: 'POST',

onSuccess: {
type: 'toast',
message: 'Submitted successfully!'
},

onFailure: {
type: 'dialog',
dialog: {
type: 'dialog',
title: 'Submission Failed',
content: {
type: 'text',
content: 'Please try again or contact support.'
}
}
}
};
```
What to write instead:

**Callback Types:**
- `toast` - Show toast notification
- `message` - Show message dialog
- `redirect` - Navigate to URL
- `reload` - Reload data
- `ajax` - Execute another API call
- `dialog` - Open dialog
- `custom` - Custom handler
- **A notice** — `successMessage` / `errorMessage`, plain strings (the runner
surfaces `successMessage` as a toast after a successful action).
- **Post-success navigation** — the spec's `onSuccess` block, `{ navigate, openIn }`,
declared on `UIActionSchema` and forwarded to the runner (objectui#5934). It is
a spec key, not a member of this legacy type, so it is not shown in a fence here.
- **Follow-up work** — `chain` (see [Action Chaining](#action-chaining)): declared
actions, not callbacks.

## Action Tracking

Expand Down Expand Up @@ -446,22 +418,9 @@ const complexAction: ActionSchema = {
],
chainMode: 'sequential',

// Callbacks
onSuccess: {
type: 'toast',
message: 'Order processed successfully!'
},
onFailure: {
type: 'dialog',
dialog: {
type: 'dialog',
title: 'Order Processing Failed',
content: {
type: 'text',
content: 'Unable to process order. Please try again.'
}
}
},
// Notices
successMessage: 'Order processed successfully!',
errorMessage: 'Unable to process order. Please try again.',

// Tracking
tracking: {
Expand Down Expand Up @@ -514,15 +473,15 @@ Enhanced Actions are ideal for:

- **API integration** - Connect to backend services and external APIs
- **Multi-step processes** - Execute complex workflows with multiple stages
- **Form submissions** - Handle form data with validation and callbacks
- **Form submissions** - Handle form data with validation and chained follow-up actions
- **Confirmation dialogs** - Add safety checks for critical operations
- **Event tracking** - Monitor user interactions for analytics
- **Batch operations** - Process multiple items in sequence or parallel

## Best Practices

1. **Use confirm for destructive actions** - Always confirm delete, archive, etc.
2. **Provide clear feedback** - Use callbacks to inform users of success/failure
2. **Provide clear feedback** - Set `successMessage` / `errorMessage` so users learn what happened
3. **Chain related operations** - Group logically related API calls
4. **Track important events** - Enable tracking for business-critical actions
5. **Set appropriate timeouts** - Don't let users wait indefinitely
Expand Down
11 changes: 5 additions & 6 deletions content/docs/guide/schema-overview.md
Original file line number Diff line number Diff line change
Expand Up @@ -70,9 +70,9 @@ turns it into the CSS variables your components already read.
### Advanced Actions

#### [Enhanced Actions](/docs/core/enhanced-actions)
Powerful action system with AJAX calls, chaining, conditions, and callbacks.
Powerful action system with AJAX calls, chaining, conditions, and tracking.

<!-- doc-snippet: fragment — a shape excerpt: `chain`, `onSuccess` and `tracking` are written as literal `[...]` / `{...}` ellipses so the section can list the action keys without a worked example of each -->
<!-- doc-snippet: fragment — a shape excerpt: `chain` and `tracking` are written as literal `[...]` / `{...}` ellipses so the section can list the action keys without a worked example of each -->

```typescript
const action: ActionSchema = {
Expand All @@ -81,7 +81,6 @@ const action: ActionSchema = {
api: '/api/submit',
chain: [...],
condition: '${...}',
onSuccess: {...},
tracking: {...}
};
```
Expand All @@ -94,7 +93,7 @@ const action: ActionSchema = {
**Key Features:**
- Action chaining (sequential/parallel)
- Conditional execution (a `condition` predicate gates whether an action runs)
- Success/failure callbacks
- Success / failure notices (`successMessage` / `errorMessage`)
- Event tracking
- Retry logic

Expand Down Expand Up @@ -274,7 +273,7 @@ The `ActionSchema` provides comprehensive action handling:
- ✅ Action types: `ajax`, `confirm`, `dialog`
- ✅ Action chaining via the `chain` array (sequential or parallel)
- ✅ Conditional execution with the `condition` property
- Success/failure callbacks: `onSuccess` and `onFailure`
- Success/failure callbacks: `onSuccess` / `onFailure` were RETIRED (objectui#7068) — both faces refuse them; write `successMessage` / `errorMessage` for notices, and the spec's `onSuccess` block `{ navigate, openIn }` on `UIActionSchema` for post-success navigation (objectui#5934)
- ✅ Event tracking with the `tracking` configuration
- ✅ Automatic retry logic

Expand All @@ -300,7 +299,7 @@ ObjectUI includes enhanced view components:

3. **Set up theming** - Hand a `Theme` document to `ThemeProvider` for consistent styling (optional)

4. **Implement actions** - Use advanced action features like `confirm` and callbacks
4. **Implement actions** - Use advanced action features like `confirm` and chaining

5. **Test your application** - Verify all functionality works as expected

Expand Down
Loading
Loading