Integrate the Go SDK
Use the Go SDK in services and agents that need Caracal context propagation, agent sessions, delegation, and Gateway-aware HTTP clients.
Install
Section titled “Install”go get github.com/garudex-labs/caracal/packages/sdk/goConnect
Section titled “Connect”package main
import ( "context" "log"
caracal "github.com/garudex-labs/caracal/packages/sdk/go")
func main() { client, err := caracal.New() if err != nil { log.Fatal(err) }
if err := client.Spawn(context.Background(), func(ctx context.Context) error { headers, err := client.Headers(ctx) if err != nil { return err } _ = headers return nil }); err != nil { log.Fatal(err) }}New() loads CARACAL_CONFIG, a caracal.toml in the default config path, or environment variables.
Use an HTTP client
Section titled “Use an HTTP client”httpClient := client.Transport(nil)
err := client.Spawn(context.Background(), func(ctx context.Context) error { req, err := http.NewRequestWithContext(ctx, http.MethodGet, "https://api.example.com/tickets", nil) if err != nil { return err } _, err = httpClient.Do(req) return err})The transport injects Caracal envelope headers from context.Context. For explicit Gateway routing, use GatewayRequest().
Long-lived service agents
Section titled “Long-lived service agents”Daemons and workers that outlive a single request use Service instead of Spawn. It returns a handle you own: keep the session alive by calling Heartbeat on a timer and retire it with Close. A service session is reaped by the coordinator if it stops heartbeating before its lease expires.
svc, err := client.SpawnService(context.Background(), caracal.ServiceOptions{ Labels: []string{"billing-worker"},})if err != nil { return err}defer svc.Close(context.Background())
for running { if err := svc.Heartbeat(context.Background()); err != nil { return err } doWork(svc.Context) time.Sleep(30 * time.Second)}Spawn a narrowed child
Section titled “Spawn a narrowed child”err := client.Spawn(context.Background(), func(ctx context.Context) error { return client.Spawn(ctx, func(child context.Context) error { _, _ = client.Current(child) return nil }, caracal.SpawnOptions{ Grant: caracal.Grant{ Mode: caracal.GrantModeNarrow, Scopes: []string{"tickets:read"}, Constraints: &caracal.DelegationConstraints{MaxHops: 1, Budget: 5}, TTLSeconds: 600, }, })})A plain client.Spawn runs the child under the application’s authority. Set SpawnOptions.Grant to caracal.GrantNarrow(...) only when the child should hold a least-privilege subset, or caracal.GrantNone() for a child with no inherited authority. Use Current(ctx) to inspect the bound Caracal context and Headers(ctx) to project it to outbound HTTP headers.
Troubleshooting
Section titled “Troubleshooting”| Symptom | Check |
|---|---|
| Missing config error | Confirm the runtime profile or required environment variables. |
Headers without context fails | Call inside Spawn, Delegate, or pass RootOptions{AllowRoot: true} intentionally. |
| Delegation fails | Ensure delegation runs from a context with an active agent session. |
| Gateway URL error | Confirm the runtime profile includes gateway_url. |
Related pages: Protect a Go net/http Service and Agent Delegation.

