> ## Documentation Index
> Fetch the complete documentation index at: https://docs.usehone.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# TypeScript SDK

> Complete reference for the Hone TypeScript SDK: init, begin, end, track, identify, setProperty, and conversation grouping, with runnable examples.

The TypeScript SDK instruments your agent from application code. Install it with `npm install @hone/sdk` and configure it once at startup.

## init

Configure the SDK with your API key. Call it once, early, before any other Hone call.

```typescript theme={null}
import { init } from "@hone/sdk";

init("sk_your_key_here");
```

Pass an `endpoint` to target a non-default base URL, such as a local stack:

```typescript theme={null}
init("sk_your_key_here", { endpoint: "http://localhost:8080" });
```

<Note>
  Load the key from the environment rather than hard-coding it: `init(process.env.HONE_API_KEY!)`. See [Authentication](/authentication).
</Note>

## begin and end

`begin()` opens an interaction for a single agent turn and returns an object you close with `end()`. Latency is captured automatically from the time between the two calls.

```typescript theme={null}
import { begin } from "@hone/sdk";

const interaction = begin({
  userId: "user_8f21",
  agentName: "support-bot",
  input: "How do I reset my password?",
});

const reply = await runAgent("How do I reset my password?");

interaction.end(reply, { success: true });
```

**`begin` options**

| Option      | Type   | Required | Description                               |
| ----------- | ------ | -------- | ----------------------------------------- |
| `userId`    | string | Yes      | Pseudonymous identifier for the end user. |
| `agentName` | string | Yes      | Name of the agent handling this turn.     |
| `input`     | string | Yes      | The user's message for this turn.         |

**`end` arguments**

| Argument  | Type    | Required | Description                                     |
| --------- | ------- | -------- | ----------------------------------------------- |
| `output`  | string  | Yes      | The agent's reply.                              |
| `success` | boolean | No       | Whether the turn succeeded. Defaults to `true`. |

Mark a failed turn so it surfaces in error analytics:

```typescript theme={null}
try {
  const reply = await runAgent(userInput);
  interaction.end(reply, { success: true });
} catch (err) {
  interaction.end(String(err), { success: false });
}
```

## track

`track()` records a completed turn in a single call. Reach for it when you already have both the input and the output and do not need to hold an interaction open.

```typescript theme={null}
import { track } from "@hone/sdk";

track({
  userId: "user_8f21",
  input: "How do I reset my password?",
  output: "Head to Settings, then Security, and choose Reset password.",
  agentName: "support-bot",
  conversationId: "conv_5c19",
});
```

**Options**

| Option           | Type   | Required | Description                                 |
| ---------------- | ------ | -------- | ------------------------------------------- |
| `userId`         | string | Yes      | Pseudonymous end-user identifier.           |
| `input`          | string | Yes      | The user's message.                         |
| `output`         | string | Yes      | The agent's reply.                          |
| `agentName`      | string | No       | Name of the agent.                          |
| `conversationId` | string | No       | Groups related turns into one conversation. |

## Conversation grouping

A conversation is a series of turns between one user and your agent. Pass the same `conversationId` across `track()` calls to thread them together, so the dashboard shows them as one exchange under **User Stories**.

```typescript theme={null}
const conversationId = "conv_5c19";

track({
  userId: "user_8f21",
  input: "How do I reset my password?",
  output: "Head to Settings, then Security, and choose Reset password.",
  conversationId,
});

track({
  userId: "user_8f21",
  input: "I don't see a Security tab.",
  output: "It's under your profile menu on the top right.",
  conversationId,
});
```

Generate a fresh id when a new conversation starts, and reuse it for every follow-up turn in that exchange.

## identify

`identify()` attaches traits to a user id. Traits enrich the user profile in the dashboard and become dimensions you can filter and segment on. Keep the id pseudonymous.

```typescript theme={null}
import { identify } from "@hone/sdk";

identify("user_8f21", {
  plan: "enterprise",
  signupCohort: "2026-Q2",
  region: "eu-west",
});
```

## setProperty and setProperties

Within an open interaction, attach custom properties such as the model used, token counts, or cost. These ride along on the event and power metadata-driven charts and filters.

```typescript theme={null}
const interaction = begin({
  userId: "user_8f21",
  agentName: "support-bot",
  input: "Summarize this thread.",
});

interaction.setProperty("model", "claude-sonnet-4");

interaction.setProperties({
  inputTokens: 1840,
  outputTokens: 220,
  costUsd: 0.0142,
});

interaction.end(reply, { success: true });
```

Use `setProperty` for a single key and `setProperties` to attach several at once. Define the corresponding keys under **Settings → Metadata Keys** so they become selectable dimensions in the dashboard.

## Full example

```typescript theme={null}
import { init, begin, identify } from "@hone/sdk";

init(process.env.HONE_API_KEY!);

identify("user_8f21", { plan: "enterprise", region: "eu-west" });

const interaction = begin({
  userId: "user_8f21",
  agentName: "support-bot",
  input: "How do I export my data?",
});

interaction.setProperty("model", "claude-sonnet-4");

const reply = "Open Settings, choose Export, and pick a format. We'll email a link.";
interaction.setProperties({ outputTokens: 96, costUsd: 0.0031 });

interaction.end(reply, { success: true });
```

<Note>
  To capture MCP tool, resource, and prompt calls automatically, see [MCP](/mcp).
</Note>
