Skip to Content
ContributingTypeScript SDK

TypeScript SDK

@protolabsai/sdk provides programmatic access to proto for building integrations, tools, and automation.

Install

npm install @protolabsai/sdk

Requirements: Node.js ≥ 20.0.0 and proto installed and in PATH.

[!note] If you use nvm, the SDK may not auto-detect the proto executable. Set pathToProtoExecutable explicitly.

Quick start

import { query } from '@protolabsai/sdk'; const session = query({ prompt: 'What files are in the current directory?', options: { cwd: '/path/to/project' }, }); for await (const message of session) { if (message.type === 'assistant') { console.log('Assistant:', message.message.content); } else if (message.type === 'result') { console.log('Done:', message.result); break; } }

Multi-turn conversations

async function* conversation() { yield { type: 'human', content: 'Analyse the project structure' }; yield { type: 'human', content: 'Write a summary to README.md' }; } const session = query({ prompt: conversation() }); for await (const msg of session) { ... }

Permission modes

const session = query({ prompt: 'Fix all failing tests', options: { permissionMode: 'auto-edit' }, });

Modes: default, plan, auto-edit, yolo.

Custom per-tool approval:

const session = query({ prompt: '...', options: { canUseTool: async (toolName, toolInput) => { if (toolName === 'run_shell_command') { return { behavior: 'ask' }; // always prompt for shell } return { behavior: 'allow' }; }, }, });

Sub-agents

import { query, type SubagentConfig } from '@protolabsai/sdk'; const reviewer: SubagentConfig = { name: 'code-reviewer', description: 'Reviews code for bugs and security issues', systemPrompt: 'You are a code reviewer...', level: 'session', tools: ['read_file', 'glob', 'grep_search'], modelConfig: { model: 'claude-sonnet-4-6' }, }; const session = query({ prompt: 'Review the changes in the current branch', options: { agents: [reviewer] }, });

Hook callbacks

import { query, type HookCallback } from '@protolabsai/sdk'; const securityGate: HookCallback = async (input) => { const data = input as { tool_name?: string; tool_input?: Record<string, unknown>; }; if (data.tool_name === 'Bash') { const cmd = String(data.tool_input?.command ?? ''); if (cmd.includes('rm -rf')) { return { shouldSkip: true, message: 'Blocked' }; } } return {}; }; const session = query({ prompt: '...', options: { hookCallbacks: { PreToolUse: [securityGate] } }, });

Abort a session

const controller = new AbortController(); const session = query({ prompt: '...', options: { abortController: controller }, }); setTimeout(() => controller.abort(), 30_000); for await (const msg of session) { ... }

LSP integration

const session = query({ prompt: 'Fix all type errors in src/', options: { lsp: true, permissionMode: 'auto-edit' }, });

MCP servers

const session = query({ prompt: 'Query the database for recent errors', options: { mcpServers: { db: { command: 'python', args: ['-m', 'db_mcp_server'], env: { DB_URL: process.env.DB_URL }, }, }, }, });

Key QueryOptions

OptionTypeDefaultDescription
cwdstringprocess.cwd()Working directory
modelstringModel ID
permissionModestringdefaultApproval mode
canUseToolfunctionPer-tool approval callback
allowedToolsstring[]Auto-approved tools
excludeToolsstring[]Blocked tools (highest priority)
coreToolsstring[]If set, only these tools available
agentsSubagentConfig[]Sub-agent configs
mcpServersobjectMCP server configs
hookCallbacksobjectHook event callbacks
lspbooleanfalseEnable LSP
resumestringSession ID to resume
maxSessionTurnsnumber-1Max turns before auto-terminate
includePartialMessagesbooleanfalseStream partial tokens
abortControllerAbortControllerautoCancel signal

See Reference → SDK API for the full reference.

Examples

See Contributing → Examples for complete, runnable patterns:

Last updated on