@arizeai/phoenix-client
Version:
A client for the Phoenix API
157 lines • 7.24 kB
TypeScript
import { type RunnerHooks } from "./runner";
import { type KVMap, type SuiteConfig, type TestEachRow, type TestFn, type TestParams } from "./types";
/**
* Declare Phoenix eval test suites.
*
* Drop-in replacement for the test runner's own `describe`. The suite name
* doubles as the dataset and experiment name on the Phoenix server, and the
* optional {@link SuiteConfig} controls dataset naming, repetitions, dry-run
* mode, and CI acceptance criteria.
*
* @example
* ```ts
* import * as px from "@arizeai/phoenix-client/vitest";
*
* px.describe("generate sql demo", () => {
* px.test("offtopic input", { input: { question: "hi" } }, async ({ input }) => {
* // ...
* });
* }, { metadata: { model: "gpt-4o-mini" } });
* ```
*/
export interface PhoenixDescribe {
/**
* Declare a Phoenix eval test suite.
*
* @param name - Suite name; doubles as the dataset / experiment name on Phoenix.
* @param fn - Suite body that declares its `test` / `it` cases.
* @param config - Optional suite-level config (dataset name, repetitions, dry-run, acceptance criteria).
*/
(name: string, fn: () => void, config?: SuiteConfig): void;
/**
* Run only this suite, skipping all sibling suites
* (matches the runner's `describe.only`).
*
* @param name - Suite name; doubles as the dataset / experiment name on Phoenix.
* @param fn - Suite body that declares its `test` / `it` cases.
* @param config - Optional suite-level config.
*/
only(name: string, fn: () => void, config?: SuiteConfig): void;
/**
* Skip this suite entirely (matches the runner's `describe.skip`). No dataset
* or experiment is created on Phoenix.
*
* @param name - Suite name; doubles as the dataset / experiment name on Phoenix.
* @param fn - Suite body (not executed).
* @param config - Optional suite-level config.
*/
skip(name: string, fn: () => void, config?: SuiteConfig): void;
}
/**
* The test body returned by {@link PhoenixTest.each} after a table is bound.
*
* @param name - Test name, or a template (`%i` / `%s` / `%j`), or a function
* that derives the name from the row and its index.
* @param fn - The test handler, run once per row in the bound table.
* @param timeout - Optional per-test timeout in milliseconds.
*/
export type PhoenixTestEach<Input extends KVMap = KVMap, Expected extends KVMap = KVMap> = (name: string | ((row: TestEachRow<Input, Expected>, index: number) => string), fn: TestFn<Input, Expected>, timeout?: number) => void;
/**
* Declare a single Phoenix eval test case.
*
* Drop-in replacement for the test runner's own `test` / `it`. The `params`
* argument carries the `input` and the reference output (`expected` /
* `reference` / `output`) that become the dataset example; whatever the handler
* returns (or passes to `logOutput()`) is recorded as the experiment run's
* output and made available to evaluators.
*
* `it` is the canonical alias for `test`; the two are identical.
*
* @example
* ```ts
* px.test(
* "summarizes the article",
* { input: { article }, expected: { summary } },
* async ({ input, expected }) => {
* const output = await summarize(input.article);
* px.logOutput(output);
* await px.evaluate({ name: "matches", evaluate: () => output === expected.summary });
* }
* );
* ```
*/
export interface PhoenixTest {
/**
* Declare a single Phoenix eval test case.
*
* @param name - Test case name; doubles as the dataset example label.
* @param params - Inline `input` and reference output that become the dataset example.
* @param fn - Test handler; receives `{ input, expected, metadata }`.
* @param timeout - Optional per-test timeout in milliseconds.
*/
<Input extends KVMap = KVMap, Expected extends KVMap = KVMap>(name: string, params: TestParams<Input, Expected>, fn: TestFn<Input, Expected>, timeout?: number): void;
/**
* Run only this test case, skipping its siblings
* (matches the runner's `test.only`).
*
* @param name - Test case name; doubles as the dataset example label.
* @param params - Inline `input` and reference output that become the dataset example.
* @param fn - Test handler; receives `{ input, expected, metadata }`.
* @param timeout - Optional per-test timeout in milliseconds.
*/
only<Input extends KVMap = KVMap, Expected extends KVMap = KVMap>(name: string, params: TestParams<Input, Expected>, fn: TestFn<Input, Expected>, timeout?: number): void;
/**
* Skip this test case (matches the runner's `test.skip`). No dataset example
* or experiment run is created on Phoenix.
*
* @param name - Test case name; doubles as the dataset example label.
* @param params - Inline `input` and reference output (not used while skipped).
* @param fn - Test handler (not executed).
* @param timeout - Optional per-test timeout in milliseconds.
*/
skip<Input extends KVMap = KVMap, Expected extends KVMap = KVMap>(name: string, params: TestParams<Input, Expected>, fn: TestFn<Input, Expected>, timeout?: number): void;
/**
* Run the same test handler across many examples. Returns a function that
* takes a name (or template / name-builder) and the shared test body; each
* row in `table` becomes its own dataset example and experiment run.
*
* @param table - Rows of `{ input, expected?, metadata?, ... }` to fan out over.
* @returns A {@link PhoenixTestEach} that binds the name and shared handler.
*
* @example
* ```ts
* px.test.each([
* { input: { a: 1, b: 2 }, expected: { sum: 3 } },
* { input: { a: 2, b: 2 }, expected: { sum: 4 } },
* ])("adds %j", async ({ input, expected }) => {
* // ...
* });
* ```
*/
each<Input extends KVMap, Expected extends KVMap>(table: TestEachRow<Input, Expected>[]): PhoenixTestEach<Input, Expected>;
}
/** The public testing surface returned by {@link createTestApi}. */
export interface PhoenixTestApi {
/** Declare a Phoenix eval test suite. See {@link PhoenixDescribe}. */
describe: PhoenixDescribe;
/** Declare a Phoenix eval test case. See {@link PhoenixTest}. */
test: PhoenixTest;
/** Canonical alias for {@link PhoenixTestApi.test}. */
it: PhoenixTest;
}
/**
* Build the public `describe`/`test`/`it` API for a runner adapter.
*
* Both the jest and vitest entrypoints expose the identical surface; the only
* thing that differs between them is how the {@link RunnerHooks} are obtained
* (vitest imports them statically, jest resolves them lazily from globals).
* That difference is captured by `getHooks`, which is invoked once per
* declaration so adapters are free to resolve hooks lazily.
*
* The JSDoc that surfaces in editors lives on the {@link PhoenixDescribe} and
* {@link PhoenixTest} interfaces rather than the implementations below, so the
* docs survive the `export const { describe, test, it } = createTestApi(...)`
* destructuring in each adapter.
*/
export declare function createTestApi(getHooks: () => RunnerHooks): PhoenixTestApi;
//# sourceMappingURL=define-api.d.ts.map