Skip to content

ThirdKeyAI/symbiont-sdk-js

Repository files navigation

Symbiont JavaScript/TypeScript SDK

npm version TypeScript License

A comprehensive, type-safe JavaScript/TypeScript SDK for building and managing AI agents on the Symbiont platform. Get started quickly with full TypeScript support, intelligent caching, and enterprise-grade security.

🚀 Quick Start

Prerequisites

The Symbiont SDK requires a running Symbiont runtime. Choose one of these options:

Option 1: Docker (Recommended)

# Start Symbiont runtime with Docker
docker run --rm -p 8080:8080 ghcr.io/thirdkeyai/symbi:latest mcp

Option 2: Homebrew

brew tap thirdkeyai/tap && brew install symbi
symbi mcp --port 8080

Option 3: Install Script

curl -fsSL https://raw.githubusercontent.com/thirdkeyai/symbiont/main/scripts/install.sh | bash
symbi mcp --port 8080

Option 4: Build from Source

# Clone and build the runtime
git clone https://github.com/thirdkeyai/symbiont
cd symbiont
cargo build --release
cargo run -- mcp --port 8080

Installation

npm install @symbi/core

Hello World

import { SymbiontClient } from '@symbi/core';

const client = new SymbiontClient({
  apiKey: process.env.SYMBIONT_API_KEY,
  environment: 'production'
});

await client.connect();

// Create and execute your first agent
const agent = await client.agents.createAgent({
  name: 'textProcessor',
  description: 'Processes and analyzes text input',
  parameters: [{ name: 'text', type: { name: 'string' }, required: true }],
  returnType: { name: 'string' },
  capabilities: ['text_processing']
});

const result = await client.agents.executeAgent(
  agent.id,
  { text: 'Hello, Symbiont!' }
);

console.log('Result:', result.result);

✨ Core Features

  • 🤖 AI Agent Management - Create, deploy, and execute intelligent agents
  • 🔐 Security-First - Built-in policy management and secrets handling
  • 🔑 AgentPin Integration - Client-side credential verification, discovery, and trust bundles
  • 🛡️ Type Safety - Full TypeScript support with runtime validation
  • ⚡ High Performance - Intelligent caching and optimized networking
  • 🔄 Auto-Authentication - Seamless token management and refresh
  • 📦 Modular Design - Use only what you need
  • 🌍 Cross-Platform - Node.js, browser, and edge runtime support

📚 Documentation

Complete installation guide, configuration options, and your first agent

📖 User Guides

Complete API documentation with examples and type definitions

🏗️ Architecture

📦 SDK Packages

Package Purpose Installation
@symbi/core Main client and authentication npm install @symbi/core
@symbi/agent Agent lifecycle management npm install @symbi/agent
@symbi/policy Policy creation and validation npm install @symbi/policy
@symbi/secrets Secure secrets management npm install @symbi/secrets
@symbi/tool-review Security review workflow npm install @symbi/tool-review
@symbi/mcp MCP protocol integration npm install @symbi/mcp

🔑 AgentPin: Credential Verification

The SDK integrates with AgentPin for domain-anchored cryptographic identity verification of AI agents. AgentPin operations run client-side — no Symbiont Runtime required.

Key Generation & Credential Issuance

const { privateKeyPem, publicKeyPem } = client.agentpin.generateKeyPair();
const kid = client.agentpin.generateKeyId(publicKeyPem);

const jwt = client.agentpin.issueCredential({
  privateKeyPem,
  kid,
  issuer: 'example.com',
  agentId: 'data-analyzer',
  capabilities: ['read:data', 'write:reports'],
  ttlSecs: 3600,
});

Credential Verification

// Online verification (fetches discovery document automatically)
const result = await client.agentpin.verifyCredential(jwt);
console.log(result.valid, result.agent_id, result.capabilities);

// Offline verification with pre-fetched documents
const discovery = await client.agentpin.fetchDiscoveryDocument('example.com');
const offlineResult = client.agentpin.verifyCredentialOffline(jwt, discovery);

// Trust bundle verification (fully offline, no network)
const bundle = client.agentpin.createTrustBundle();
const bundleResult = client.agentpin.verifyCredentialWithBundle(jwt, bundle);

Discovery & Key Pinning

// Fetch and validate discovery documents
const doc = await client.agentpin.fetchDiscoveryDocument('example.com');
client.agentpin.validateDiscoveryDocument(doc, 'example.com');

// TOFU key pinning
const pinStore = client.agentpin.createPinStore();

// JWK utilities
const jwk = client.agentpin.pemToJwk(publicKeyPem, kid);
const pem = client.agentpin.jwkToPem(jwk);

🛠️ Configuration

Environment Variables

# Required
SYMBIONT_API_KEY=your_api_key_here

# Optional
SYMBIONT_API_URL=https://api.symbiont.dev
SYMBIONT_ENVIRONMENT=production

Client Configuration

const client = new SymbiontClient({
  apiKey: process.env.SYMBIONT_API_KEY,
  environment: 'production',
  validationMode: 'strict',
  timeout: 30000,
  debug: false
});

🎯 Common Use Cases

Agent Creation and Execution

// Create a data analysis agent
const agent = await client.agents.createAgent({
  name: 'dataAnalyzer',
  description: 'Analyzes datasets and generates insights',
  parameters: [
    { name: 'dataset', type: { name: 'object' }, required: true },
    { name: 'analysisType', type: { name: 'string' }, required: false }
  ],
  capabilities: ['data_processing', 'visualization'],
  policies: [dataAccessPolicy]
});

const insights = await client.agents.executeAgent(agent.id, {
  dataset: myData,
  analysisType: 'trend_analysis'
});

Policy Management

import { PolicyBuilder } from '@symbi/policy';

// Create access control policy
const policy = new PolicyBuilder('dataAccessPolicy')
  .allow('read', 'analyze')
    .where('user.department', 'equals', 'analytics')
    .where('data.classification', 'not-equals', 'restricted')
  .require('approval')
    .where('action', 'equals', 'export')
  .build();

Secrets Management

import { SecretManager } from '@symbi/secrets';

const secrets = new SecretManager({
  providers: [
    { name: 'environment', priority: 100 },
    { name: 'vault', priority: 200, endpoint: 'https://vault.company.com' }
  ]
});

const apiKey = await secrets.getSecret('EXTERNAL_API_KEY');

Webhook Verification

Verify inbound webhook signatures from GitHub, Stripe, Slack, or custom providers:

import {
    HmacVerifier, JwtVerifier, createProviderVerifier,
} from '@symbi/core';

// Use a provider preset
const verifier = createProviderVerifier('GITHUB', Buffer.from(secret));
verifier.verify(request.headers, Buffer.from(request.body));

// Manual HMAC with prefix stripping
const hmac = new HmacVerifier(
    Buffer.from(secret), 'X-Hub-Signature-256', 'sha256='
);
hmac.verify(headers, body);

// JWT-based verification
const jwtVerifier = new JwtVerifier(
    Buffer.from(secret), 'Authorization', 'expected-issuer'
);
jwtVerifier.verify(headers, body);

Provider presets: GITHUB, STRIPE, SLACK, CUSTOM.

Markdown Memory Persistence

File-based agent context that survives restarts:

import { MarkdownMemoryStore } from '@symbi/core';

const store = new MarkdownMemoryStore('/data/memory', 30);

await store.saveContext('agent-1', {
    agentId: 'agent-1',
    facts: ['User prefers dark mode', 'Timezone is UTC-5'],
    procedures: ['Always greet by name'],
    learnedPatterns: ['Responds better to bullet points'],
    metadata: { lastSession: '2026-02-15' },
});

const context = await store.loadContext('agent-1');
const agents = await store.listAgentContexts();
await store.compact('agent-1');
const stats = await store.getStorageStats();

Agent Skills (ClawHavoc Scanning)

Scan and load agent skill definitions with security scanning:

import { SkillScanner, SkillLoader } from '@symbi/core';

// Scan for security issues (10 built-in ClawHavoc rules)
const scanner = new SkillScanner();
const findings = scanner.scanContent(content, 'SKILL.md');

// Scan an entire skill directory
const result = scanner.scanSkill('/path/to/skill');

// Load skills from paths
const loader = new SkillLoader({
    loadPaths: ['/skills/verified', '/skills/community'],
    requireSigned: false,
    scanEnabled: true,
});

const skills = loader.loadAll();
const skill = loader.loadSkill('/path/to/skill');

Detects: pipe-to-shell, wget-pipe-to-shell, env file references, SOUL.md/memory.md tampering, eval+fetch, base64-decode-exec, rm-rf, chmod-777.

Metrics Collection & Export

Runtime metrics retrieval and local export:

import {
    FileMetricsExporter, CompositeExporter, MetricsCollector,
} from '@symbi/core';

// Fetch from runtime API
const snapshot = await client.metricsClient.getSnapshot();
const scheduler = await client.metricsClient.getSchedulerMetrics();
const system = await client.metricsClient.getSystemMetrics();

// Export to file (atomic JSON write)
const exporter = new FileMetricsExporter({ filePath: '/tmp/metrics.json' });
await exporter.export(snapshot);

// Fan-out to multiple backends
const composite = new CompositeExporter([exporter, otherExporter]);

// Background collection
const collector = new MetricsCollector(composite, 60000);
collector.start(fetchFn);
collector.stop();

Scheduling

const schedule = await client.schedules.create({
    agentId: 'my-agent',
    cron: '0 */6 * * *',
    parameters: { task: 'cleanup' },
});

const schedules = await client.schedules.list();
const health = await client.schedules.getSchedulerHealth();

Reasoning Loop (v1.6.0)

Run autonomous reasoning loops with policy gates, circuit breakers, and knowledge recall:

import { SymbiontClient } from '@symbi/core';

const client = new SymbiontClient({ apiKey: process.env.SYMBIONT_API_KEY });

// Run a reasoning loop
const response = await client.reasoning.runLoop('agent-1', {
  config: { max_iterations: 10, timeout_ms: 60000 },
  initial_message: 'Analyze the latest sales data and create a report.',
});

console.log('Output:', response.result.output);
console.log('Iterations:', response.result.iterations);
console.log('Termination:', response.result.termination_reason.type);

// Check loop status
const status = await client.reasoning.getLoopStatus('agent-1', response.loop_id);

// Read journal entries
const journal = await client.reasoning.getJournalEntries('agent-1', { limit: 50 });

// Cedar policy management
await client.reasoning.addCedarPolicy('agent-1', {
  name: 'deny-file-write',
  source: 'forbid(principal, action == "tool_call", resource) when { resource.name == "write_file" };',
  active: true,
});
const policies = await client.reasoning.listCedarPolicies('agent-1');

// Circuit breaker status
const breakers = await client.reasoning.getCircuitBreakerStatus('agent-1');

// Knowledge bridge
await client.reasoning.storeKnowledge('agent-1', 'sales', 'grew_by', '15%');
const facts = await client.reasoning.recallKnowledge('agent-1', 'sales growth');

What's New in v1.6.0

  • Reasoning Loopclient.reasoning.runLoop(), getLoopStatus(), cancelLoop() for autonomous ORGA cycles
  • Journal SystemgetJournalEntries(), compactJournal() for loop event replay and auditing
  • Cedar PolicieslistCedarPolicies(), addCedarPolicy(), evaluateCedarPolicy() for action-level governance
  • Circuit BreakersgetCircuitBreakerStatus(), resetCircuitBreaker() for tool failure isolation
  • Knowledge BridgerecallKnowledge(), storeKnowledge() for persistent agent memory
  • Type Definitions — Zod schemas for all reasoning types in @symbi/types

Previous Releases

v0.6.0

  • Webhook VerificationHmacVerifier, JwtVerifier, provider presets (GitHub, Stripe, Slack)
  • Markdown MemoryMarkdownMemoryStore for file-based agent context persistence
  • Agent SkillsSkillScanner with 10 ClawHavoc rules, SkillLoader with frontmatter parsing
  • MetricsMetricsApiClient sub-client, FileMetricsExporter, CompositeExporter, MetricsCollector
  • Type Definitions — Zod schemas for webhooks, skills, and metrics in @symbi/types

License

Apache License 2.0