Skip to main content

AxonFlow v7.4.2 Release Notes

Platform v7.4.2 is a documentation-grade patch — OpenAPI spec corrections, no platform behavior change. Released alongside it is the v6 SDK alignment cycle: TypeScript and Java cut a major (v6.0.0) for breaking changes; Python (v6.7.0) and Go (v5.7.0) ship as additive minors on the same day. The wire-shape contract gates that landed across all four SDKs over the prior two days drove the audit; the OpenAPI spec corrections in v7.4.2 close two of the remaining drift entries that gate flagged.

SurfaceVersionChange type
Platformv7.4.2PATCH — OpenAPI spec corrections
TypeScript SDKv6.0.0MAJORPolicyInfoMCPPolicyInfo rename + 19 wire-shape additions
Java SDKv6.0.0MAJORWebhookSubscription equality is now identity-based
Python SDKv6.7.0MINOR — additive wire-shape sweep
Go SDKv5.7.0MINOR — additive wire-shape sweep

Platform v7.4.2 — OpenAPI spec corrections

Two OpenAPI schemas were stale relative to what the server has been emitting. AxonFlow's hand-written SDKs (TypeScript, Python, Go, Java) have always read against server reality and gain no functional change from this release — the fix lives entirely in the spec artefacts under docs/api/. Code-generated clients written against the prior spec would have read undefined for the affected fields.

AISystemRegistry.materialitymateriality_classification

Source of truth: platform/orchestrator/masfeat/types.go. The AISystemRegistry struct exposes a 3-dimensional risk rating per the MAS AI Risk Management Guidelines 2025 refactor — risk_rating_impact, risk_rating_complexity, and an aggregate materiality_classification derived from the rating dimensions. The OpenAPI spec at docs/api/masfeat-api.yaml was still declaring the legacy materiality key from before the refactor. If you generate a MAS FEAT client from the spec, regenerate against v7.4.2 — the field name on GET /api/v1/masfeat/registry/{id} and POST /api/v1/masfeat/registry payloads is materiality_classification, not materiality.

DynamicPolicyInfo 8 → 4 fields

Source of truth: platform/shared/policy/types.go. The DynamicPolicyInfo struct on MCP and proxy responses carries the result of orchestrator-evaluated tenant policies. The actual server shape is four fields: policies_evaluated, matched_policies, orchestrator_reachable, processing_time_ms. The prior agent-api.yaml declared eight fields including aspirational ones (policy_version, tenant_namespace, evaluation_chain, cache_status) that the server has never populated. Removed.

The matching documentation page at MCP Policy Enforcement → DynamicPolicyInfo Object already documents the correct 4-field shape — only the OpenAPI artefact was out of sync.


TypeScript SDK v6.0.0 — major

BREAKING — PolicyInfo and MCPPolicyInfo renamed

In v5.x, two different concepts shared overlapping names:

  • PolicyInfo (in src/types/proxy.ts) was the proxy-mode shape returned by /api/request — fields like policiesEvaluated, staticChecks, processingTime, tenantId, codeArtifact.
  • MCPPolicyInfo (in src/types/connector.ts) was the MCP shape returned by /api/v1/mcp/check-input and friends — fields like policies_evaluated, blocked, block_reason, processing_time_ms, matched_policies. This is what the OpenAPI spec calls PolicyInfo.

The names have been swapped to align with the OpenAPI spec:

In v5.xIn v6.0.0
PolicyInfo (proxy shape)ProxyPolicyInfo (renamed)
MCPPolicyInfo (MCP shape)PolicyInfo (renamed; matches OpenAPI spec)

Migration:

  • If you imported PolicyInfo to read proxy-mode responses, change to ProxyPolicyInfo (or use the PolicyInfoLegacyProxyShape type alias as a one-major-version shim).
  • If you imported MCPPolicyInfo for MCP responses, change to PolicyInfo. The MCPPolicyInfo name is kept as a type alias for one major-version migration window and will be removed in v7.0.0.

Code that reads response.policyInfo on ExecuteQueryResponse continues to work — the property type is now ProxyPolicyInfo with the same fields. The break only affects code that imported the type names by hand.

Added — 19+ wire-shape fields

A wire-shape contract gate landed in the SDK over the prior two days; this release closes the audit. Every field added below was already on the wire and silently dropped because the SDK type didn't declare it.

  • WebhookSubscription.secret — HMAC-SHA256 signing key required to verify the X-AxonFlow-Signature header on inbound webhook deliveries. Without it, callers couldn't validate payload authenticity. Also adds org_id and tenant_id.
  • StepGateRequest carries cost_usd, tokens_in, tokens_out for budget-aware policy evaluation at gate time.
  • StepGateResponse.decision_id — audit correlator linking a gate response to its audit row.
  • StepGateResponse.policies_evaluated / policies_matched — wire-canonical snake_case. The previous camelCase forms (policiesEvaluated / policiesMatched) always read undefined because the gate decoder is a JSON.parse passthrough; both forms are kept (camel marked @deprecated) and removed in v7.
  • ListWorkflowsResponse.limit / offset — pagination echo.
  • StaticPolicy.policy_id / priority / has_override — wire-canonical fields surfaced.
  • CreateStaticPolicyRequest.priority / tags and UpdateStaticPolicyRequest.priority / tags — match the spec.
  • UpdatePlanRequest.metadata — opaque plan metadata.
  • UsageBreakdownItem.group_by — dimension name (provider/model/agent/etc.) on each item.
  • BudgetAlert.acknowledged — alert dismissal flag.
  • Budget.org_id / tenant_id — ownership scoping.
  • UsageRecord gains created_at, success, error_message, latency_ms, team_id, tenant_id, user_id, workflow_id. Legacy timestamp is @deprecated.
  • WorkflowStatusResponse.metadata — workflow metadata.
  • CreateWorkflowResponse.started_at — wire-canonical timestamp; legacy created_at and source are @deprecated.
  • ExecutionSnapshot.retryCount — number of retry attempts on a step.
  • Finding.article — regulatory article reference (e.g. MAS FEAT principle number).
  • PolicyOverride.id / enabled_override — wire-canonical fields. active is @deprecated.
  • PolicyVersion.id / policy_id / change_summary / snapshot — match the wire shape (versions are immutable snapshots, not before/after diffs).
  • DynamicPolicyMatch.message — wire-canonical name. reason is @deprecated.
  • ExfiltrationCheckInfo.exceeded / limit_type — match the wire. within_limits is @deprecated.
  • CancelPlanResponse.success — wire-canonical boolean. message is @deprecated.
  • PlanResponse gains the wire top-level fields success, version, result, error, workflow_execution_id, policy_info.
  • EffectivePoliciesResponse gains the tier-stratified wire shape (static, dynamic, tenant_id, organization_id, computed_at).
  • ResumePlanResponse.result — final aggregated result. Five legacy fields are @deprecated — none were ever populated.

Java SDK v6.0.0 — major

BREAKING — WebhookSubscription equality is identity-based on id

WebhookSubscription is an entity, not a value object. Two instances with the same id represent the same logical webhook regardless of whether one view has loaded secret (only returned by createWebhook) and another has not, or whether updatedAt / active have moved between fetches.

Previously equals() / hashCode() compared every field. That meant a webhook constructed locally with the legacy 6-arg constructor compared unequal to the same logical webhook deserialized from a server response that included secret / tenantId / orgId. Set<WebhookSubscription>, Map keying, and identity-tracking caches all broke under those semantics.

Identity-based equality is the canonical entity semantics; the prior value-based equality was a bug. Because equals() / hashCode() are part of the observable Java contract, the fix is a breaking change per strict semver — even though the new behaviour corrects incorrect semantics rather than introducing them. If you need content-equality (e.g. to detect a rotated secret), compare the relevant getters directly. The 6-arg constructor is preserved as a source-compat overload; only equals() / hashCode() semantics changed. toString() is unchanged (still emits full state with secret redacted).

Added

  • Wire-shape contract gate (.github/workflows/wire-shape-contract.yml). CI fails any PR introducing drift between Java @JsonProperty annotations and the OpenAPI specs pinned at tests/fixtures/wire-shape-baseline.json::openapi_specs_sha. Four gates: cross-spec schema divergence, intra-file schema duplicates, per-type SDK-vs-spec drift, registered-type rename-escape. The pinned spec SHA is itself guarded by a spec-pin-bump PR label so a single PR can't both move the SHA and silence drift. Mirrors the Python, Go, and TypeScript gates landed earlier this week.
  • Version alignment check (.github/workflows/validate-version-alignment.yml). CI fails any PR or push to main where pom.xml's <version> drifts from the first released ## [X.Y.Z] section in CHANGELOG.md. Matches the pattern in the platform repo and the Go SDK.
  • WebhookSubscription.secret — HMAC-SHA256 signing key now exposed on the response from createWebhook. Required to verify X-AxonFlow-Signature. Adds tenantId and orgId. The 6-arg constructor is preserved as a source-compat overload that delegates to the 9-arg with nulls for the new fields. toString() redacts secret.
  • BudgetAlert.acknowledged — alert dismissal flag.

Fixed

  • Telemetry pings now deliver reliably from short-lived JVMs (CLI, serverless, cold-starts). AxonFlow construction blocks briefly while the ping is sent synchronously, bounded by the telemetry timeout (3s).
  • Telemetry path is bounded at TIMEOUT_SECONDS (3s) total; the /health probe and POST share a single monotonic deadline instead of stacking independent timeouts.

Python SDK v6.7.0 — minor (additive)

Wire-shape audit sweep against the contract gate. All changes are additive (new fields default to None) or DEPRECATED-marked alias fields kept for compile-time compat. Removal scheduled for v7. Same field set as the TypeScript v6.0.0 additions — WebhookSubscription.secret, StepGateRequest.tokens_in/tokens_out/cost_usd, StepGateResponse.decision_id, pagination echoes, ownership scoping on Budget, UsageRecord wire-canonical fields, MCPCheckInputRequest.client_id/tenant_id/user_id/user_role/user_token, etc. Full list on the Python SDK v6.7.0 release page.


Go SDK v5.7.0 — minor (additive)

Wire-shape audit sweep against the contract gate. All changes are additive — new fields are pointer or ,omitempty-tagged so existing user code keeps compiling; deprecated aliases preserved for source-compat. Same field set as Python: WebhookSubscription.Secret, StepGateRequest.TokensIn/TokensOut/CostUSD, StepGateResponse.DecisionID, pagination echoes, Budget.OrgID/TenantID, UsageRecord wire-canonical fields. Full list on the Go SDK v5.7.0 release page.


SDK and plugin compatibility

SurfaceVersion
Python SDKv6.7.0
Go SDKv5.7.0
TypeScript SDKv6.0.0
Java SDKv6.0.0
OpenClaw pluginv1.3.2
Claude Code / Cursor pluginsv0.5.2
Codex pluginv0.4.2

Who is affected

  • Hand-written TypeScript SDK users: if you imported PolicyInfo or MCPPolicyInfo directly, follow the migration table above. Code that reads response.policyInfo on a typed response continues to work unchanged. Both legacy names are retained as @deprecated aliases for one major; removal in v7.
  • Hand-written Java SDK users: if you keyed WebhookSubscription instances in a Set or Map, the new identity-based equality makes that work correctly across requests where one view has secret populated and another doesn't. Content-equality checks need explicit getter comparisons.
  • Python and Go SDK users: no migration. Bump the pin to pick up the new fields and the DynamicPolicyInfo baseline-drift auto-resolution that came with the platform v7.4.2 spec correction.
  • Code-generated client users: regenerate against docs/api/masfeat-api.yaml and docs/api/agent-api.yaml from v7.4.2 to pick up the spec corrections (materiality_classification field name + the 4-field DynamicPolicyInfo).
  • Operators of the platform: the v7.4.2 platform release is a documentation-grade patch with no behavior change; rolling restart is sufficient.