Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/iii-hq/sdk/llms.txt

Use this file to discover all available pages before exploring further.

Overview

The III SDK automatically reconnects when the WebSocket connection drops, using exponential backoff with jitter to prevent thundering herd problems. All functions, triggers, and services are automatically re-registered after reconnection.

Default Behavior

By default, the SDK reconnects indefinitely with these settings:
import { DEFAULT_BRIDGE_RECONNECTION_CONFIG } from 'iii-sdk'

const defaults = {
  initialDelayMs: 1000,      // Start with 1 second delay
  maxDelayMs: 30000,         // Cap at 30 seconds
  backoffMultiplier: 2,      // Double delay each attempt
  jitterFactor: 0.3,         // ±30% randomization
  maxRetries: -1             // Retry forever
}

Reconnection Algorithm

The SDK calculates retry delays using exponential backoff with jitter:
const exponentialDelay = initialDelayMs * (backoffMultiplier ** attemptNumber)
const cappedDelay = Math.min(exponentialDelay, maxDelayMs)
const jitter = cappedDelay * jitterFactor * (2 * Math.random() - 1)
const finalDelay = cappedDelay + jitter
Example retry sequence (with defaults):
  • Attempt 1: ~1s (1000ms ± 300ms)
  • Attempt 2: ~2s (2000ms ± 600ms)
  • Attempt 3: ~4s (4000ms ± 1200ms)
  • Attempt 4: ~8s (8000ms ± 2400ms)
  • Attempt 5: ~16s (16000ms ± 4800ms)
  • Attempt 6+: ~30s (30000ms ± 9000ms) - capped

Custom Configuration

Basic Configuration

import { init } from 'iii-sdk'

const iii = init('ws://localhost:49134', {
  reconnectionConfig: {
    initialDelayMs: 500,       // Faster initial retry
    maxDelayMs: 10000,         // Lower cap (10s max)
    backoffMultiplier: 1.5,    // Gentler backoff
    jitterFactor: 0.2,         // Less jitter
    maxRetries: 10             // Give up after 10 attempts
  }
})

OpenTelemetry Connection Reconnection

The OpenTelemetry telemetry system uses a separate WebSocket connection for traces, metrics, and logs. You can configure its reconnection independently:
import { init } from 'iii-sdk'

const iii = init('ws://localhost:49134', {
  // Main connection (functions, triggers)
  reconnectionConfig: {
    maxRetries: -1  // Never give up
  },
  
  // Telemetry connection (traces, metrics, logs)
  otel: {
    enabled: true,
    reconnectionConfig: {
      maxRetries: 5,           // Give up after 5 attempts
      initialDelayMs: 2000,    // Slower retries (less critical)
      maxDelayMs: 60000        // Higher cap (1 minute)
    }
  }
})

Connection State Monitoring

1

Track connection state

Monitor the connection lifecycle to implement custom logic:
import type { IIIConnectionState } from 'iii-sdk'

const unsubscribe = iii.onConnectionStateChange((state: IIIConnectionState) => {
  console.log(`Connection state: ${state}`)
  
  switch (state) {
    case 'disconnected':
      // Initial state or after close
      break
    case 'connecting':
      // First connection attempt
      break
    case 'connected':
      // Successfully connected
      console.log('✓ All functions re-registered')
      break
    case 'reconnecting':
      // Attempting to reconnect after disconnect
      console.warn('Connection lost, reconnecting...')
      break
    case 'failed':
      // Max retries exceeded
      console.error('Connection failed permanently')
      // Trigger alert, switch to backup, etc.
      break
  }
})

// Later: stop monitoring
unsubscribe()
2

Query current state

Check the current connection state synchronously:
const state = iii.getConnectionState()

if (state === 'connected') {
  await iii.call('my-function', data)
} else {
  console.log('Not connected, queueing for later')
}

Automatic Re-registration

When the connection is re-established, the SDK automatically re-registers:
  • All registered functions (local and HTTP)
  • All registered trigger types
  • All registered triggers
  • All registered services
  • Pending invocation messages (queued while disconnected)
// No action needed - happens automatically on reconnect
iii.registerFunction({ id: 'users::get' }, getUserHandler)
iii.registerTrigger({ type: 'http', function_id: 'users::get', config: {} })

// Connection drops and reconnects
// → Both function and trigger are re-registered automatically

Invocation Behavior During Reconnection

Queuing Messages

Messages sent while disconnected are queued (up to 1000 messages) and sent when the connection is restored:
// Connection is down
iii.callVoid('log::info', { message: 'Hello' })  // Queued
iii.callVoid('log::info', { message: 'World' })  // Queued

// Connection restored → both messages sent immediately

Timeout Behavior

Invocations with await that were sent before disconnect will timeout normally:
try {
  // Connection drops after this is sent
  const result = await iii.call('my-function', data, 5000)
} catch (error) {
  // Error: Invocation timeout after 5000ms: my-function
  console.error('Timed out waiting for response')
}

Configuration Examples

Development (Fast Retries)

const iii = init('ws://localhost:49134', {
  reconnectionConfig: {
    initialDelayMs: 100,   // Very fast initial retry
    maxDelayMs: 2000,      // Low cap for quick feedback
    maxRetries: 3          // Give up quickly
  }
})

Production (Resilient)

const iii = init('ws://production-engine:49134', {
  reconnectionConfig: {
    initialDelayMs: 1000,
    maxDelayMs: 60000,     // 1 minute max
    backoffMultiplier: 2,
    jitterFactor: 0.3,
    maxRetries: -1         // Never give up
  }
})

Ephemeral Workers (No Retries)

// For short-lived processes (CI, cron jobs)
const iii = init('ws://localhost:49134', {
  reconnectionConfig: {
    maxRetries: 0  // Don't retry, fail immediately
  }
})

Debugging Reconnection

// Enable debug logging (Node.js)
process.env.DEBUG = 'iii:*'

// Logs:
// [iii] Reconnecting in 1234ms (attempt 1)...
// [iii] Reconnecting in 2456ms (attempt 2)...

Best Practices

Reconnection Strategy Checklist:
  • ✅ Use infinite retries (maxRetries: -1) in production
  • ✅ Monitor connection state for critical paths
  • ✅ Use jitter (jitterFactor > 0) to prevent thundering herd
  • ✅ Set reasonable maxDelayMs (30-60s) to balance responsiveness and load
  • ✅ Configure telemetry reconnection separately (less critical than functions)
  • ✅ Test failure scenarios (network partitions, engine restarts)
  • ✅ Implement alerting when state reaches 'failed'

Build docs developers (and LLMs) love