返回技能列表

test-a2a-interop

pjt222
更新于 2 days ago
4 次查看
17
2
17
在 GitHub 上查看
测试aitestingautomationdesign

关于

This skill tests A2A interoperability by validating Agent Card conformance, exercising all task lifecycle states, and verifying streaming and error handling. Use it for verifying new A2A server implementations, validating interoperability between agents, or running conformance tests in CI/CD pipelines. It's essential for debugging multi-agent workflows and certifying agents against A2A protocol requirements.

快速安装

Claude Code

推荐
主要方式
npx skills add pjt222/agent-almanac -a claude-code
插件命令备选方式
/plugin add https://github.com/pjt222/agent-almanac
Git 克隆备选方式
git clone https://github.com/pjt222/agent-almanac.git ~/.claude/skills/test-a2a-interop

在 Claude Code 中复制并粘贴此命令以安装该技能

技能文档

試 A2A 之互操

驗 A2A 代理之實合協規——試 Agent Card 之發現、任務生命週期之治、SSE 流、誤治、多代理之通模。

用時

  • 驗新 A2A 服之實於部前乃用
  • 驗二或多 A2A 代理之互操乃用
  • 行合規之試於 A2A 之 CI/CD 乃用
  • 調多代理 A2A 流之敗乃用
  • 證代理合 A2A 協為註冊乃用

  • 必要:所試 A2A 代理之基 URL
  • 必要:驗身憑(若代理須之)
  • 可選:第二代理之 URL 為雙向互操試
  • 可選:所試之具技(默:Agent Card 中諸技)
  • 可選:每任務試之超時(默:60 秒)
  • 可選:合規報之出格(jsonmarkdownjunit

第一步:取而驗 Agent Card

1.1. 自 well-known 端取 Agent Card:

curl -s https://agent.example.com/.well-known/agent.json -o agent-card.json

1.2. 驗頂層必之域:

const requiredFields = ["name", "description", "url", "skills"];
for (const field of requiredFields) {
  assert(agentCard[field] !== undefined, `Missing required field: ${field}`);
}

1.3. 驗各技條:

for (const skill of agentCard.skills) {
  assert(skill.id, "Skill missing id");
  assert(skill.name, "Skill missing name");
  assert(skill.description, "Skill missing description");
  assert(
    Array.isArray(skill.inputModes) && skill.inputModes.length > 0,
    `Skill ${skill.id} missing inputModes`
  );
  assert(
    Array.isArray(skill.outputModes) && skill.outputModes.length > 0,
    `Skill ${skill.id} missing outputModes`
  );
}

1.4. 驗驗身之設:

  • authentication.schemesoauth2,驗 credentials.oauth2tokenUrl
  • authentication.schemesapiKey,驗 credentials.apiKeyheaderName

1.5. 驗能旗為布爾值。

1.6. 記驗果於合規報:

interface ConformanceResult {
  test: string;
  category: "agent-card" | "lifecycle" | "streaming" | "error-handling" | "interop";
  status: "pass" | "fail" | "skip";
  message?: string;
  duration_ms?: number;
}

得:Agent Card 過諸構驗察。

敗則:記各驗敗附其域與因。勿止;續他試。無效之 Agent Card 自為一試果。

第二步:發試任務以覆諸生命態

2.1. 試:任務之投(submitted -> working -> completed)

依代理所宣之技發其能治之任務:

const submitResult = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 1,
  method: "tasks/send",
  params: {
    id: `test-${uuid()}`,
    sessionId: `session-${uuid()}`,
    message: {
      role: "user",
      parts: [{ type: "text", text: skillExamples[0] }],
    },
  },
});

assert(submitResult.result, "tasks/send should return a result");
assert(submitResult.result.id, "Result should include task ID");
assert(
  ["submitted", "working", "completed"].includes(submitResult.result.status.state),
  `Unexpected initial state: ${submitResult.result.status.state}`
);

2.2. 試:任務之輪詢(tasks/get)

輪詢至任務達終態:

let task = submitResult.result;
const startTime = Date.now();
while (!["completed", "failed", "canceled"].includes(task.status.state)) {
  if (Date.now() - startTime > TEST_TIMEOUT_MS) {
    fail(`Task ${task.id} did not complete within ${TEST_TIMEOUT_MS}ms`);
    break;
  }
  await sleep(1000);
  const getResult = await sendJsonRpc(agentUrl, {
    jsonrpc: "2.0",
    id: 2,
    method: "tasks/get",
    params: { id: task.id },
  });
  task = getResult.result;
}

assert(task.status.state === "completed", `Task should complete, got: ${task.status.state}`);

2.3. 試:任務之取消

投任務而即取消:

const cancelTask = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 3,
  method: "tasks/send",
  params: { id: `test-cancel-${uuid()}`, sessionId: `session-${uuid()}`, message: { ... } },
});

const cancelResult = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 4,
  method: "tasks/cancel",
  params: { id: cancelTask.result.id },
});

assert(
  cancelResult.result.status.state === "canceled",
  "Canceled task should be in canceled state"
);

2.4. 試:須輸入態(多輪)

若某技支多輪交互,發歧之請以致 input-required,而獻續:

// Send ambiguous request
const multiTurnTask = await sendJsonRpc(agentUrl, { ... });

// Poll until input-required or completed
// If input-required, send follow-up
if (task.status.state === "input-required") {
  const followUp = await sendJsonRpc(agentUrl, {
    jsonrpc: "2.0",
    id: 6,
    method: "tasks/send",
    params: {
      id: task.id,
      sessionId: task.sessionId,
      message: { role: "user", parts: [{ type: "text", text: "Column A and Column B" }] },
    },
  });
  assert(
    ["working", "completed"].includes(followUp.result.status.state),
    "Follow-up should resume task"
  );
}

2.5. 試:態轉之史

若 Agent Card 宣 stateTransitionHistory: true

const getWithHistory = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 7,
  method: "tasks/get",
  params: { id: completedTaskId, historyLength: 100 },
});

assert(
  Array.isArray(getWithHistory.result.history),
  "Task should include history array"
);
assert(
  getWithHistory.result.history.length >= 2,
  "History should have at least 2 entries (submitted and completed)"
);

得:諸生命態之轉皆正。任務成完、淨取消、多輪交互於支時行。

敗則:記敗之具態轉,期態,實態。報含全 JSON-RPC 應為調。

第三步:驗 SSE 流之應

3.1. 若 Agent Card 宣 streaming: false,略此步。

3.2. 發 tasks/sendSubscribe 請而驗 SSE 流:

const response = await fetch(`${agentUrl}/subscribe`, {
  method: "POST",
  headers: { "Content-Type": "application/json" },
  body: JSON.stringify({
    jsonrpc: "2.0",
    id: 10,
    method: "tasks/sendSubscribe",
    params: {
      id: `test-stream-${uuid()}`,
      sessionId: `session-${uuid()}`,
      message: { role: "user", parts: [{ type: "text", text: "Stream test task" }] },
    },
  }),
});

assert(
  response.headers.get("content-type")?.includes("text/event-stream"),
  "Response must be text/event-stream"
);

3.3. 析 SSE 事件而驗其構:

const events: SSEEvent[] = [];
const reader = response.body.getReader();
const decoder = new TextDecoder();
let buffer = "";

while (true) {
  const { done, value } = await reader.read();
  if (done) break;
  buffer += decoder.decode(value, { stream: true });

  // Parse SSE events from buffer
  const lines = buffer.split("\n");
  for (const line of lines) {
    if (line.startsWith("event: ")) {
      currentEvent.type = line.slice(7);
    } else if (line.startsWith("data: ")) {
      currentEvent.data = JSON.parse(line.slice(6));
      events.push(currentEvent);
    }
  }
}

3.4. 驗事序:

  • 首事當為 status 事,態為 submittedworking
  • 中事可含 status 之新與 artifact 之獻
  • 末事當有 final: true 與終態
  • 末事後無事至

3.5. 驗 SSE 連之清:

  • 流中關連
  • 驗仍可由 tasks/get 取任務
  • 驗無服誤自此早斷

得:SSE 流獻正格之事於正序,終於末終事。

敗則:若宣 SSE 而端返非 SSE,記為合規敗。若事至序亂,記其序。若流不終,記超時。

第四步:試誤治與邊例

4.1. 試:未知之法

const unknownMethod = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 20,
  method: "tasks/nonexistent",
  params: {},
});
assert(unknownMethod.error?.code === -32601, "Should return method not found");

4.2. 試:壞 JSON-RPC 之請

const malformed = await fetch(agentUrl, {
  method: "POST",
  headers: { "Content-Type": "application/json" },
  body: '{"not": "valid jsonrpc"}',
});
const response = await malformed.json();
assert(response.error?.code === -32600, "Should return invalid request");

4.3. 試:取不存之任務

const notFound = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 22,
  method: "tasks/get",
  params: { id: "nonexistent-task-id" },
});
assert(notFound.error, "Should return error for nonexistent task");

4.4. 試:取消已完之任務

const cancelCompleted = await sendJsonRpc(agentUrl, {
  jsonrpc: "2.0",
  id: 23,
  method: "tasks/cancel",
  params: { id: completedTaskId },
});
assert(cancelCompleted.error, "Should error when canceling completed task");

4.5. 試:驗身之施

若驗身已設,發無憑之請:

const unauthResponse = await fetch(agentUrl, {
  method: "POST",
  headers: { "Content-Type": "application/json" },
  body: JSON.stringify({ jsonrpc: "2.0", id: 24, method: "tasks/get", params: { id: "x" } }),
});
assert(unauthResponse.status === 401, "Should reject unauthenticated requests");

4.6. 試:Agent Card 公可取,無須驗

const publicCard = await fetch(`${agentUrl}/.well-known/agent.json`);
assert(publicCard.status === 200, "Agent Card should be publicly accessible");

得:諸誤之境返宜 JSON-RPC 誤碼,不潰服。

敗則:記每敗之誤治試。誤試中之服潰為要敗,部前必修。

第五步:生互操合規報

5.1. 合諸試果為構之報:

interface ConformanceReport {
  agentUrl: string;
  agentName: string;
  agentVersion: string;
  testDate: string;
  summary: {
    total: number;
    passed: number;
    failed: number;
    skipped: number;
  };
  categories: {
    agentCard: ConformanceResult[];
    lifecycle: ConformanceResult[];
    streaming: ConformanceResult[];
    errorHandling: ConformanceResult[];
    interop: ConformanceResult[];
  };
  conformanceLevel: "full" | "partial" | "minimal" | "non-conformant";
}

5.2. 算合規之階:

  • full:諸試皆過,含流與推通
  • partial:核生命試過,某可選敗
  • minimal:Agent Card 有效,基任務 send/get 行
  • non-conformant:Agent Card 無效或基生命斷

5.3. 生報於所請之格:

  • json:機讀為 CI/CD 合
  • markdown:人讀,過敗之表
  • junit:XML 格為試框合

5.4. 含修敗之薦:

## Failed Tests

| Test | Category | Message | Recommendation |
|------|----------|---------|----------------|
| cancel-completed-task | error-handling | Server returned 500 | Add guard for terminal state transitions |
| sse-final-event | streaming | No final event received | Ensure SSE sends event with final:true |

5.5. 若請雙向試(二代理),驗:

  • 代理甲可發現代理乙之 Agent Card
  • 代理甲可發任務於乙
  • 代理乙可發任務於甲
  • 二代理治並發任務無互擾

得:完之合規報,含過敗果、合規階、可行薦。

敗則:若報生本身敗,出生試果於 stdout 為退。試資不當因報誤而失。

  • Agent Card 已取而構驗
  • 至少一任務完全生命循(submitted -> working -> completed)
  • 任務之取消正行
  • 誤之應用正 JSON-RPC 誤碼
  • 若能宣 SSE,已試流
  • 任務端施驗身而 Agent Card 不施
  • 合規報於所請之格已生
  • 敗試含可行修導
  • 試套可於 CI/CD 行而不須手介

  • 試於冷服:某代理須時始。試前加健察或暖請。
  • 硬編試資:用動之任務與會 ID(UUIDs)以避反復行試之撞。勿假特任務 ID 可得。
  • 忽時序:任務之轉異步。常以退而輪詢,勿假即態變。
  • SSE 析之繁:SSE 事或跨多塊。緩入資而析全事,非生塊。
  • 唯試樂路:誤治試與成試同要。壞請、無效轉、驗身敗皆當覆。
  • 網依:試當可於本機行為開發,於遠 URL 行為產。參數化代理 URL。
  • 假技行:試套驗協合規,非技正。用 Agent Card 之例語觸技,勿斷具出容。

  • design-a2a-agent-card — 設所試之 Agent Card
  • implement-a2a-server — 實所試之服
  • build-ci-cd-pipeline — 合合規試於 CI/CD
  • troubleshoot-mcp-connection — 適 A2A 連之調模
  • review-software-architecture — 多代理系之構審

GitHub 仓库

pjt222/agent-almanac
路径: i18n/wenyan/skills/test-a2a-interop
0
agentsagentskillsai-assisted-developmentclaude-codeskillsteams

相关推荐技能

evaluating-llms-harness

测试

该Skill通过60+个学术基准测试(如MMLU、GSM8K等)评估大语言模型质量,适用于模型对比、学术研究及训练进度追踪。它支持HuggingFace、vLLM和API接口,被EleutherAI等行业领先机构广泛采用。开发者可通过简单命令行快速对模型进行多任务批量评估。

查看技能

cloudflare-cron-triggers

测试

这个Claude Skill提供了关于Cloudflare Cron Triggers的完整知识库,用于通过cron表达式定时执行Workers。它支持配置周期性任务、维护作业和自动化工作流,并能处理常见的cron触发错误。开发者可以用它来设置定时任务、测试cron处理器,并集成Workflows和Green Compute功能。

查看技能

webapp-testing

测试

该Skill为开发者提供了基于Playwright的本地Web应用测试工具集,支持自动化测试前端功能、调试UI行为、捕获屏幕截图和查看浏览器日志。它包含管理服务器生命周期的辅助脚本,可直接作为黑盒工具运行而无需阅读源码。适用于需要快速验证本地Web应用界面和交互功能的开发场景。

查看技能

finishing-a-development-branch

测试

这个Skill用于开发分支完成后的集成决策,当代码实现完成且测试通过时,它会引导开发者选择合适的工作流。它首先验证测试状态,然后提供合并、创建PR或清理等结构化选项。核心价值在于确保代码质量的同时,标准化分支收尾流程。

查看技能