diff --git a/docs/content/docs/index.mdx b/docs/content/docs/index.mdx index d0fced9..fd3347e 100644 --- a/docs/content/docs/index.mdx +++ b/docs/content/docs/index.mdx @@ -8,10 +8,19 @@ Use workflows for durable, multi-step execution with replay safety. ## What are workflows? -A workflow is a durable, replayable actor definition. It supports the full actor -configuration, including actions and lifecycle hooks, while its `run` function -uses replay-safe workflow primitives. +A workflow is a durable, replayable actor definition created with `workflow({...})` +from `@rivet-dev/workflows`. It supports the full actor configuration, including +actions and lifecycle hooks, while its `run` function uses replay-safe workflow +primitives. - Survives restarts: workflow progress is saved automatically. - Re-runs safely: replay follows the same recorded steps. - Event-driven: workflows can pause for queue messages, then continue. + +## Migrating from `rivetkit/workflow` + +Workflows previously lived at `rivetkit/workflow` and were wrapped in an actor as +`actor({ run: workflow(...) })`. Now `workflow({...})` from `@rivet-dev/workflows` +is the actor definition itself: move the actor's options into `workflow({...})` and +pass your `run` function directly. The workflow history encoding is unchanged, so +in-flight workflows resume after the upgrade. diff --git a/docs/content/docs/quickstart.mdx b/docs/content/docs/quickstart.mdx index 10bcad1..4ed9e1a 100644 --- a/docs/content/docs/quickstart.mdx +++ b/docs/content/docs/quickstart.mdx @@ -6,6 +6,14 @@ skill: true import { Hosting } from "@/components/docs/Hosting"; +## Install + +```sh +npm install @rivet-dev/workflows +``` + +The package re-exports RivetKit, so `setup`, `actor`, and `queue` come from the same `@rivet-dev/workflows` import. Clients keep using `rivetkit/client`. + ## Simple workflow Use this when you need a short multi-step sequence. diff --git a/docs/content/docs/steps.mdx b/docs/content/docs/steps.mdx index f516045..d400ffa 100644 --- a/docs/content/docs/steps.mdx +++ b/docs/content/docs/steps.mdx @@ -17,27 +17,7 @@ Use `tryStep` when a step failure should produce data instead of failing the who Use `try` when you want to recover from terminal `step`, `join`, or `race` failures inside a named block. -```ts -async function runPaymentFlow(ctx: any) { - return await ctx.try("payment-flow", async (blockCtx: any) => { - const auth = await blockCtx.step("authorize", async (blockCtx) => - authorizeOrder("order-123"), - ); - const capture = await blockCtx.step("capture", async (blockCtx) => - captureOrder("order-123"), - ); - return { auth, capture }; - }); -} - -async function authorizeOrder(orderId: string): Promise { - return `auth-${orderId}`; -} - -async function captureOrder(orderId: string): Promise { - return `capture-${orderId}`; -} -``` + - `tryStep` and `try` only catch terminal failures. Retry backoff, sleeps, queue waits, eviction, and history divergence still rethrow. - Catching a failure does not undo it. `state` and `vars` mutations made before the failure remain visible after `tryStep` or `try` returns, so use explicit compensating steps when a caught failure needs cleanup. diff --git a/examples/docs/actors-workflows/try-block.ts b/examples/docs/actors-workflows/try-block.ts new file mode 100644 index 0000000..04754eb --- /dev/null +++ b/examples/docs/actors-workflows/try-block.ts @@ -0,0 +1,38 @@ +import { setup, workflow } from "@rivet-dev/workflows"; +export const paymentFlowActor = workflow({ + state: { + auth: null as string | null, + capture: null as string | null, + failed: false, + }, + run: async (ctx) => { + const result = await ctx.try("payment-flow", async (blockCtx) => { + const auth = await blockCtx.step("authorize", async (step) => { + const auth = await authorizeOrder("order-123"); + step.state.auth = auth; + return auth; + }); + const capture = await blockCtx.step("capture", async (step) => { + const capture = await captureOrder("order-123"); + step.state.capture = capture; + return capture; + }); + return { auth, capture }; + }); + if (!result.ok) { + await ctx.step("mark-failed", async (step) => { + step.state.failed = true; + }); + } + }, + actions: { + getState: (c) => c.state, + }, +}); +async function authorizeOrder(orderId: string): Promise { + return `auth-${orderId}`; +} +async function captureOrder(orderId: string): Promise { + return `capture-${orderId}`; +} +export const registry = setup({ use: { paymentFlowActor } });