Skip to content

Experimentation Steps - Add group.experiment() documentation#1444

Open
AndyInternet wants to merge 1 commit intomainfrom
andy/e13n-initial-docs
Open

Experimentation Steps - Add group.experiment() documentation#1444
AndyInternet wants to merge 1 commit intomainfrom
andy/e13n-initial-docs

Conversation

@AndyInternet
Copy link
Copy Markdown
Contributor

This pull request adds comprehensive documentation for the new group.experiment() API, which enables running A/B and feature experiments within durable functions. It also updates the navigation structure to surface this documentation in the TypeScript reference. The documentation covers usage, configuration options, selection strategies, advanced examples, and observability features.

Key changes:

Documentation for Experiments API:

  • Adds a new reference page group-experiment.mdx describing the group.experiment() API, including detailed usage examples, configuration options, built-in selection strategies (fixed, weighted, bucket, custom), advanced patterns (multi-step variants, multiple experiments per function), and observability details.

Navigation Update:

  • Updates the TypeScript v4 reference navigation to include a new "Experiments" section, with a link to the group.experiment() documentation, marked as "new".

@AndyInternet AndyInternet self-assigned this Mar 2, 2026
@vercel
Copy link
Copy Markdown

vercel bot commented Mar 2, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
website Building Building Preview, Comment Mar 2, 2026 7:10pm

Request Review

AndyInternet added a commit to inngest/inngest-js that referenced this pull request Mar 9, 2026
## Summary
This PR introduces a native experimentation framework to the Inngest
TypeScript SDK, allowing developers to run A/B tests and feature
experiments directly within durable functions with guaranteed
consistency and observability.

## 1. Core Tool: `group.experiment()`

The `group.experiment()` tool is the primary entry point for running
experiments. It coordinates variant selection and execution while
ensuring durability.

- **Durable Selection**: The selection process is wrapped in a memoized
step. This ensures that once a variant is chosen for a specific run, the
same variant is used across all replays, even if the selection logic
involves randomness.
- **Flexible Execution**: Each variant is defined as a callback. The
selected variant's callback is executed at the top level, allowing its
internal `step.*` calls to participate in normal step discovery.
- **Result Handling**: By default, it returns the result of the selected
variant's callback. Using `withVariant: true` allows the caller to
receive both the result and the name of the selected variant.

### Example Usage:
```ts
const result = await group.experiment("checkout-flow", {
  variants: {
    control: () => step.run("old-flow", () => oldLogic()),
    treatment: () => step.run("new-flow", () => newLogic()),
  },
  select: experiment.weighted({ control: 50, treatment: 50 }),
});
```

## 2. Selection Strategies (`experiment.*`)

The PR provides a set of pre-built strategies for variant selection:

- **`experiment.fixed(variantName)`**: Always selects the specified
variant. Useful for manual overrides or testing.
- **`experiment.weighted(weights)`**: Performs weighted random
selection. It is deterministic per run because it is seeded with the
Inngest `runId`.
- **`experiment.bucket(value, options?)`**: Uses consistent hashing
(SHA-256) to map a value (like a `userId`) to a variant. The same input
value will always result in the same variant for a given set of weights.
- **`experiment.custom(fn)`**: Allows developers to provide their own
selection logic (e.g., fetching a flag from an external provider). The
result is still memoized durably by Inngest.

## 3. Observability and Metadata

The framework is deeply integrated with the Inngest platform for better
visibility:

- **Automatic Metadata**: The selection step automatically carries
`inngest.experiment` metadata, including:
  - Experiment name
  - Selected variant
  - Selection strategy used
  - Available variants and their weights
- **Context Propagation**: Using `AsyncLocalStorage`, the experiment
context (experiment ID and variant name) is propagated to all steps
executed within the selected variant's callback. This allows the Inngest
UI to group and attribute these steps to the experiment.
- **Dashboard Warnings**: Includes built-in warnings, such as when
`experiment.bucket()` receives a null/undefined value.

## 4. Reliability and Safety

- **Zero-Step Guard**: To ensure durability, the SDK detects if a
variant callback completes without invoking any Inngest step tools.
Since non-step logic re-runs on every replay, the SDK throws a
`NonRetriableError` to force developers to wrap their variant logic in
`step.run()`.
- **Validation**:
  - Ensures at least one variant is defined.
  - Validates that weights are non-negative and have a positive total.
- Verifies that `custom` or `bucket` strategies return a valid variant
name defined in the experiment.
- **Runtime Support**: Requires `AsyncLocalStorage` for context
propagation and zero-step detection, falling back gracefully where
possible in restricted environments.


## Checklist
<!-- Tick these items off as you progress. -->
<!-- If an item isn't applicable, ideally please strikeout the item by
wrapping it in "~~"" and suffix it with "N/A My reason for skipping
this." -->
<!-- e.g. "- [ ] ~~Added tests~~ N/A Only touches docs" -->

- [x] Added a [docs PR](https://github.com/inngest/website) that
references this PR - [docs
here](inngest/website#1444)
- [x] Added unit/integration tests
- [x] Added changesets if applicable

## Related
<!-- A space for any related links, issues, or PRs. -->
<!-- Linear issues are autolinked. -->
<!-- e.g. - INN-123 -->
<!-- GitHub issues/PRs can be linked using shorthand. -->
<!-- e.g. "- inngest/inngest#123" -->
<!-- Feel free to remove this section if there are no applicable related
links.-->
- INN-

---------

Co-authored-by: jakobevangelista <jakobevangelista@gmail.com>
@AndyInternet AndyInternet marked this pull request as ready for review March 16, 2026 13:36
@AndyInternet AndyInternet changed the title Add group.experiment() documentation Experimentation Steps - Add group.experiment() documentation Mar 31, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant