文件历史

20 次代码提交

作者 SHA1 备注 提交日期
Asim Aslam 6733d0c7c4 a2a: verify inbound AP2 mandates into the paid path (opt-in) (#4851)
The AP2 primitives (checkout/payment mandates, Ed25519 sign/verify, the
x402 rail reference, attach-to-message) already existed, but the gateway
only *carried* mandates on the resulting task — it never verified them, so
ap2Verifications was never populated and a downstream paid path had no
trust signal.

Wire opt-in verification: set Options.AP2PublicKey (gateway) or
a2a.WithAP2PublicKey (embedded handler) and each mandate carried on a task
is verified (signature + task/context binding) with the result recorded in
task.AP2Verifications; the x402 settlement rail rides along for the paid
path. Off by default — mandates stay carried-but-unverified — so no payment
trust decision enters the default flow.

Adds a gateway integration test driving a real message/send that carries a
signed x402 payment mandate (verified, rail carried; tampered → surfaced as
unverified) plus a default-path test proving carry-only is unchanged.


Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

Co-authored-by: Claude <noreply@anthropic.com>
2026-07-15 13:10:00 +01:00
Asim Aslam bbeb3ac920 a2a: guard push-notification callbacks against SSRF (#4849)
The A2A gateway's push-notification flow (tasks/pushNotificationConfig/set
→ deliverPush) POSTed task state to a caller-supplied URL via the default
HTTP client, so an untrusted A2A caller could aim the gateway at internal
addresses (loopback, link-local cloud metadata, RFC1918) it would
otherwise never reach — a server-side request forgery vector (#4129).

Add a default SSRF-safe policy: only http/https callbacks whose host does
not resolve to a loopback, private, link-local, multicast, or unspecified
address. It's enforced when the config is set (caller gets a clear
rejection, nothing stored) and again at delivery, and the delivery client
re-checks the resolved IP at dial time so a name that passes validation
can't be rebound to an internal address before connect.

Operators that need a trusted in-cluster receiver set Options.AllowPushURL
(gateway) or a2a.WithPushURLPolicy (embedded handlers) to own the policy;
that path skips the built-in private-IP dial guard by design.

Tests cover blocked/allowed URLs, the dial-time guard, set-time rejection,
default-deny delivery, and the operator override.


Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

Co-authored-by: Claude <noreply@anthropic.com>
2026-07-15 12:20:36 +01:00
Asim Aslam 6950870dd9 a2a: conform to external A2A clients — well-known path + spec SSE events (#4832)
* a2a: conform to external A2A clients — well-known path + spec SSE events

The A2A gateway interoperated go-micro-to-go-micro but a real external
client (ADK, LangGraph, a2a-SDK) would not:

- Discovery: served the Agent Card at /.well-known/agent.json, but A2A
  0.3.0 discovers it at /.well-known/agent-card.json. Serve both, with
  agent-card.json canonical and agent.json a legacy alias — per-agent,
  per-skill, and at the single-agent top level.

- message/stream emitted repeated full Task snapshots. External SSE
  clients parse by `kind` and stop on `final:true`; a Task snapshot has
  neither, so they never terminate. Emit spec-shaped TaskArtifactUpdate
  (append) chunks and close with a TaskStatusUpdate final:true. The
  non-streaming and resubscribe paths also close with a terminal marker.

- A streaming error set both `result` and `error` in one JSON-RPC
  response (strict clients reject it). Emit a failed status-update
  instead — never result and error together.

Tests assert the canonical card path, the status-update/artifact-update
event shapes ending in final:true, and that no response carries both
result and error.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

* harness: update a2a-streaming to the spec-shaped stream events

The A2A gateway now emits artifact-update deltas and a terminal
status-update (final:true) instead of repeated full Task snapshots, so
the conformance harness must reassemble the answer from the append
artifact-update chunks and assert the final:true marker. This makes the
harness a stronger spec check rather than a snapshot-shape check.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

* agent: update a2a stream test to spec-shaped events

TestA2AStreamUsesAgentChatPathWithTools decoded the last SSE event as a
completed Task snapshot with artifacts. The gateway now closes the stream
with a status-update (final:true) and carries the answer as append
artifact-update deltas, so reassemble the answer from those deltas and
assert the terminal completed status-update instead.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

---------

Co-authored-by: Claude <noreply@anthropic.com>
2026-07-12 13:27:27 +01:00
Asim Aslam 96fc06b9e4 Fix A2A fallback empty artifact text (#4548)
Co-authored-by: Codex <codex@openai.com>
2026-07-10 08:56:51 +01:00
Asim Aslam 47ff1bc6f5 Add AP2 mandate foundation for A2A (#3899)
Co-authored-by: Codex <codex@openai.com>
2026-07-04 09:35:01 +01:00
Asim Aslam 064a112c6b a2a: expose resubscribe and input-required support (#3484)
Co-authored-by: Codex <codex@openai.com>
2026-06-30 21:23:43 +01:00
Asim Aslam 09bf82d4f6 fix a2a stream fallback (#3410)
Co-authored-by: Codex <codex@openai.com>
2026-06-30 03:26:42 +01:00
Asim Aslam d831ba2c45 Add typed A2A skill endpoints (#3375)
Co-authored-by: Codex <codex@openai.com>
2026-06-29 20:21:41 +01:00
Asim Aslam 44c08a6bd2 Add A2A resubscribe and input-required handoffs (#3271)
Co-authored-by: Codex <codex@openai.com>
2026-06-28 17:59:49 +01:00
Asim Aslam 5813f53117 test ai streaming conformance (#3263)
Co-authored-by: Codex <codex@openai.com>
2026-06-28 16:17:23 +01:00
Asim Aslam 929cd1ab1d Add A2A task continuation and push callbacks (#3226)
Co-authored-by: Codex <codex@openai.com>
2026-06-28 07:09:03 +01:00
Asim Aslam a576f65b08 Improve A2A streaming task lifecycle (#3203)
Co-authored-by: Codex <codex@openai.com>
2026-06-27 23:57:24 +01:00
Asim Aslam 27f5e2be52 Add OpenAI streaming path (#3185)
Co-authored-by: Codex <codex@openai.com>
2026-06-27 20:01:45 +01:00
Asim Aslam 2af5e6ae8f Record A2A agent replies in task history (#3170)
Co-authored-by: Codex <codex@openai.com>
2026-06-27 16:09:30 +01:00
Asim Aslam bcf2c92931 Add A2A completed-task streaming (#3156)
Co-authored-by: Codex <codex@openai.com>
2026-06-27 10:29:01 +01:00
Asim Aslam 19ad28e04b Propagate A2A request cancellation (#3074)
Co-authored-by: Codex <codex@openai.com>
2026-06-25 14:32:06 +01:00
Asim Aslam 4311b73361 Enhance ADK vs Go Micro comparison and apply lint fixes (#2994)
* docs: compare Go Micro with Google ADK in the comparison guide

Adds a 'vs Agent Frameworks (Google ADK)' section: ADK builds an agent,
Go Micro builds the distributed system the agent lives in (agents are
services in the mesh). Covers the category difference, a feature table,
when to choose each, and MCP/A2A interoperability.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

* docs: replace ADK comparison slogan with concrete explanation

State plainly what each tool provides (ADK builds an agent process; Go Micro
builds the surrounding service mesh) instead of marketing phrasing.

* lint: apply golangci-lint autofixes; exclude ST1003 and demo errcheck

Mechanical, behaviour-preserving fixes applied by 'golangci-lint run --fix':
gofmt, misspell (US spelling), usestdlibvars (http.Method*/Status*), unconvert,
and the auto-fixable staticcheck simplifications (QF*, S1017/S1019/S1023/S1039).

Config: exclude ST1003 (remaining offenders are exported API renames, e.g.
web.Id, which would break compatibility) and skip errcheck for examples/ and
internal/harness/ (demo code where fire-and-forget is intentional).

Build and test compilation verified.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

* lint: WIP cleanup checkpoint (errcheck config + partial fixes)

Checkpoint of an in-progress golangci-lint cleanup (background pass). Builds
cleanly; lint is not yet zero. Follow-up commit will complete the cleanup and
switch CI to a blocking full-tree lint.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CmdEY7pYmV5zzwCjNJ4ykL

---------

Co-authored-by: Claude <noreply@anthropic.com>
2026-06-22 17:21:47 +01:00
Asim Aslam c7657f73f4 Refactor agent plan storage, update docs, and release v6 (#2977)
goreleaser / goreleaser (push) Has been cancelled
* test(harness): read agent plan from the scoped store

The store-scoping change moved an agent's plan from the default table
key agent/{name}/plan to its own table (database "agent", table {name},
key "plan"). The plan-delegate harness tests still read the old key and
failed with 'not found'; read through store.Scope(mem, "agent", name)
like the agent does.

* docs: orient agents-first across README, landing, and docs overview

Lead with agents (then services and flows), surface MCP + A2A as the
interop story, and frame agents as services. Landing hero and feature
grid reordered agents-first with an A2A gateway card.

* v6: module path go-micro.dev/v6, TLS secure by default, NewService

Cut v6. Three breaking changes, bundled so the major bump is paid once:

- Module path go-micro.dev/v5 -> go-micro.dev/v6 across all imports + go.mod.
- TLS verification on by default (was off). MICRO_TLS_SECURE removed;
  MICRO_TLS_INSECURE=true opts out for self-signed/dev.
- micro.NewService(name, opts...) is the canonical service constructor,
  symmetric with NewAgent/NewFlow; micro.New kept as a deprecated alias;
  the old name-less NewService(opts...) removed. Generators emit NewService.

Also ports the JWT auth token provider in-module (go-micro.dev/v6/auth/jwt/token
on golang-jwt/jwt/v5), dropping the v5-pinned github.com/micro/plugins/v5/auth/jwt
and the deprecated dgrijalva/jwt-go.

Docs/README/landing updated to v6 and @latest; v5->v6 migration guide added;
CHANGELOG cut as [6.0.0]. Blog posts left at their historical versions.

---------

Co-authored-by: Claude <noreply@anthropic.com>
2026-06-18 11:55:35 +01:00
Asim Aslam f42c9d1d69 feat(a2a): agents can serve A2A directly, no gateway required (#2975)
Refactor the A2A handler into a reusable dispatcher + Invoke seam and
expose NewAgentHandler(card, invoke) + Card(). An agent now serves its
own A2A endpoint with AgentA2A(addr) / WithA2A — handling tasks
in-process (no RPC hop, no separate gateway). The gateway and embedded
agent share the same handler; the only difference is RPC vs in-process
invocation. Docs, README, and changelog cover both deployment modes.

Co-authored-by: Claude <noreply@anthropic.com>
2026-06-18 10:57:38 +01:00
Asim Aslam 307b94aab7 Implement A2A protocol gateway and update documentation (#2974)
goreleaser / goreleaser (push) Has been cancelled
* feat(a2a): Agent2Agent protocol gateway

Add gateway/a2a — exposes registered agents over the open A2A protocol so
agents on other frameworks can discover and call them. Agent Cards are
generated from registry metadata (the same way the MCP gateway derives
tools from service endpoints); incoming A2A tasks translate to the
agent's existing Agent.Chat RPC, so there's no per-agent code.

v1 is the synchronous JSON-RPC binding: message/send returns a completed
Task, tasks/get retrieves it, and Agent Cards are served for discovery;
streaming and push notifications are advertised as unsupported. Run with
'micro a2a serve' (cmd/micro/a2a). Tests cover card generation,
message/send, tasks/get, listing, and unknown-method errors.

* docs: A2A guide, README contents + A2A section, universe A2A check

- Add a Contents table of contents at the top of the README and an A2A
  subsection under Building Agents.
- Add the Agent2Agent (A2A) guide and register it in the docs nav.
- Exercise the A2A gateway in the universe harness: the concierge agent
  is reached over A2A (message/send -> Agent.Chat -> completed task).

* feat(a2a): outbound client — call external A2A agents

Add a2a.Client (Send/Card) so a Go Micro agent or flow can call an agent
on any framework by URL — the outbound counterpart to the gateway. Wired
in two places: flow.A2A(url) as a workflow step (the cross-framework
Dispatch), and agent delegate to an http(s) URL routes over A2A. The
universe harness now drives the gateway through the client, exercising
both directions. Tests cover client send/card and the round trip.

* docs: A2A both-directions — guide, README, changelog, blog #26

---------

Co-authored-by: Claude <noreply@anthropic.com>
2026-06-17 20:33:20 +01:00