Session.
Stateful multi-turn conversations with a session object.
A Session wraps an Agent with auto-managed conversationId and accumulates turn results. The server maintains conversation history server-side using the conversationId, so each turn has full context.
createSession(agent, options?)
import { createSession } from '@maincode-ai/matilda-agent-sdk';
const session = createSession({
name: 'tutor',
instructions: 'You are a patient programming tutor. Explain concepts simply.',
});
console.log('Conversation ID:', session.conversationId);
// Turn 1
const r1 = await session.run('What is a closure in JavaScript?');
console.log('Turn 1:', r1.finalOutput.slice(0, 100), '...');
// Turn 2 — the server remembers the previous exchange via conversationId
const r2 = await session.run('Can you show me a simple example?');
console.log('Turn 2:', r2.finalOutput.slice(0, 100), '...');
// The session accumulates all turn results
console.log('Total turns:', session.turns.length);
console.log('Last turn stream ID:', session.lastTurn?.streamId);Session class
session.run(input, options?)
Runs a turn and accumulates the result in session.turns.
| Field | type | description |
|---|---|---|
| input | string | The user's message. |
| options | Omit<AgentRunOptions, 'conversationId'> | Per-turn options. Merged with session defaults. |
Returns Promise<AgentRunResult>.
session.stream(input, options?)
Streams a turn, yielding AgentRunEvent as they arrive. The result is accumulated in session.turns when the stream completes.
for await (const event of session.stream('Explain async/await in one paragraph.')) {
if (event.type === 'message.delta') {
process.stdout.write(event.delta);
}
}
console.log('\n[Turns accumulated]:', session.turns.length);
console.log('[Final output cached]:', session.lastTurn?.finalOutput.slice(0, 60), '...');session.conversationId
The auto-generated (or provided) conversation ID. Reused across all turns.
session.turns
A readonly array of AgentRunResult — one per completed turn.
session.lastTurn
Getter for the most recent AgentRunResult, or undefined if no turns have run.
SessionOptions
Extends Omit<AgentRunOptions, 'conversationId'>.
| Field | type | description |
|---|---|---|
| runner | Runner | Custom runner instance. Defaults to defaultRunner. |
| conversationId | string | Explicit conversation ID. Auto-generated when omitted. |
| (all AgentRunOptions fields) | — | Session-level defaults applied to every turn. |
Metadata passthrough
Metadata can be set at multiple levels: Agent construction, Session construction, or per-call. Per-call metadata merges with (and overrides) session defaults.
const session = createSession(
{
name: 'helper',
instructions: ({ metadata }) =>
`Environment: ${metadata.env ?? 'unknown'}. User: ${metadata.user ?? 'anonymous'}.`,
},
{ metadata: { env: 'staging', user: 'demo-user' } },
);
// Session-level metadata is used by default
await session.run('Who am I?');
// Per-call metadata overrides session defaults
await session.run('Who am I now?', { metadata: { user: 'admin' } });
// → env=staging (from session), user=admin (overridden per-call)Custom runner
A Session can use a custom Runner for dependency injection in tests or isolated configuration:
import { Runner, Session } from '@maincode-ai/matilda-agent-sdk';
const myRunner = new Runner();
const session = new Session(
{ name: 'custom-runner-agent', instructions: 'Be brief.' },
{ runner: myRunner },
);
const result = await session.run('What is 2 + 2?');