Skip to content

SDK parity

Three SDKs, deliberately not identical. The gaps are listed so you find them here rather than three files into an integration.

GoPythonTypeScript
Typed verbs
Governance interpretation
Retries + Retry-After
Typed errors
Idempotent writes
Environment facadeFromEnv()from_env()
Auth / credential exchange
Context metercallTool
Testing fakevectadynetestFakeControlPlane
AsyncgoroutinesAsyncVectadynenative
Compile-time request validationpartialpartialbest

Nothing in the ❌ column is a missing capability — everything is reachable through callTool with the same validated shapes. What is missing is convenience.

GoThe most complete. Pick it for production agents, especially unattended ones — it has auth, a meter and a testing fake
PythonComplete, and where most framework integrations live (LangChain, LangGraph). Sync and async facades at parity
TypeScriptBest compile-time safety. Pick it for browser or Node agents, and expect to write the auth and telemetry wiring

This is the one thing that will bite you, so it is not buried in a footnote:

SDKFieldtrue means
GoGuidance.Holdstop
TypeScriptguidance.holdstop
PythonGovernanceDecision.proceedgo

Never port a branch between languages by eye. See Interpret a verdict.

These are contract, not implementation detail — every SDK proves each with a test:

  • A warn proceeds. Never a hold.
  • An unknown decision holds. Fail-closed on a vocabulary the client cannot interpret.
  • A refusal is never retried. A block, a warn and a forbidden fault each produce exactly one request.
  • No synthesized verdict. An unreachable control plane is a typed transport error, never an invented allow.
  • Retry-After is honoured, and surfaces typed when retries are exhausted.
  • A write freezes its payload. Serialized once per logical call and replayed byte-identically, so a retry cannot append a duplicate.
  • Credentials are structurally redacted. Every formatting path yields <redacted>; reading the value is explicit and greppable.
  • Nothing sensitive is logged. Not tokens, secrets, prompt_block, memory content or evidence summaries — enforced by the log hook’s signature, which cannot see a body.

None of them ship framework glue. It would force that framework into the build of every consumer who does not use it, and it rots on the framework’s release schedule rather than ours.

The glue lives in your agent and is short. See LangChain and ADK (Go).

Same reasoning. Propagation is a seam: supply an HTTP client whose transport injects traceparent — exactly what otelhttp.NewTransport does — and the SDK carries whatever headers it sets.

If you emit spans, a governance refusal is a span EVENT, never a span ERROR, and the span status stays OK. Marking warn as an error teaches every dashboard that governance is a failure mode.

Use two levels: an attempt span may be Error on a transport failure; the logical call is OK if any attempt succeeded. One level either paints a recovered call red or an exhausted one green.

Gogo.vectadyne.ai/vectadynepkg.go.dev
Pythonvectadyne-agent (imports as vectadyne) — PyPI
TypeScript@vectadyne/sdknpm