# Copilot CLI ACP 服务器

了解 GitHub Copilot 命令行界面 (CLI) 的代理客户端协议服务器。

> [!NOTE]
> GitHub Copilot 命令行界面 (CLI) 中的 ACP 支持处于 公共预览版 状态，可能会发生变化。

## 概述

代理客户端协议（ACP）是一种协议，用于标准化客户端（如代码编辑器和 IDE）和代理（如 Copilot 命令行界面（CLI）） 之间的通信。 有关此协议的更多详细信息，请参阅 [官方简介](https://agentclientprotocol.com/get-started/introduction)。

## 用例

*               **IDE 集成：** 将 Copilot 支持构建到任何编辑器或开发环境中。
* **CI/CD 管道：** 在自动化工作流中协调代理编码任务。
* **自定义前端：** 为特定开发人员工作流创建专用接口。
* **多代理系统：** 使用标准协议与其他 AI 代理协调 Copilot 。

## 启动 ACP 服务器

              GitHub Copilot 命令行界面 (CLI) 可以使用 `--acp` 标志作为 ACP 服务器启动。 服务器支持两种模式， `stdio` 以及 `TCP`。

### stdio 模式（建议用于 IDE 集成）

默认情况下，在提供 `--acp` 标志时，`stdio` 模式将被推断出。 
              `--stdio`还可以提供标志来消除歧义。

```bash
copilot --acp --stdio
```

### TCP 模式

              `--port`如果标志与`--acp`标志结合使用，则服务器以 TCP 模式启动。

```bash
copilot --acp --port 3000
```

## 与 ACP 服务器集成

库生态系统不断增加，以编程方式与 ACP 服务器交互。 假设 GitHub Copilot 命令行界面 (CLI) 正确安装和进行身份验证，以下示例演示了如何使用 [typescript](https://agentclientprotocol.com/libraries/typescript) 客户端发送单个提示并打印 AI 响应。

```typescript
import * as acp from "@agentclientprotocol/sdk";
import { spawn } from "node:child_process";
import { Readable, Writable } from "node:stream";

async function main() {
  const executable = process.env.COPILOT_CLI_PATH ?? "copilot";

  // ACP uses standard input/output (stdin/stdout) for transport; we pipe these for the NDJSON stream.
  const copilotProcess = spawn(executable, ["--acp", "--stdio"], {
    stdio: ["pipe", "pipe", "inherit"],
  });

  if (!copilotProcess.stdin || !copilotProcess.stdout) {
    throw new Error("Failed to start Copilot ACP process with piped stdio.");
  }

  // Create ACP streams (NDJSON over stdio)
  const output = Writable.toWeb(copilotProcess.stdin) as WritableStream<Uint8Array>;
  const input = Readable.toWeb(copilotProcess.stdout) as ReadableStream<Uint8Array>;
  const stream = acp.ndJsonStream(output, input);

  const client: acp.Client = {
    async requestPermission(params) {
      // This example should not trigger tool calls; if it does, refuse.
      return { outcome: { outcome: "cancelled" } };
    },

    async sessionUpdate(params) {
      const update = params.update;

      if (update.sessionUpdate === "agent_message_chunk" && update.content.type === "text") {
        process.stdout.write(update.content.text);
      }
    },
  };

  const connection = new acp.ClientSideConnection((_agent) => client, stream);

  await connection.initialize({
    protocolVersion: acp.PROTOCOL_VERSION,
    clientCapabilities: {},
  });

  const sessionResult = await connection.newSession({
    cwd: process.cwd(),
    mcpServers: [],
  });

  process.stdout.write("Session started!\n");
  const promptText = "Hello ACP Server!";
  process.stdout.write(`Sending prompt: '${promptText}'\n`);

  const promptResult = await connection.prompt({
    sessionId: sessionResult.sessionId,
    prompt: [{ type: "text", text: promptText }],
  });

  process.stdout.write("\n");

  if (promptResult.stopReason !== "end_turn") {
    process.stderr.write(`Prompt finished with stopReason=${promptResult.stopReason}\n`);
  }

  // Best-effort cleanup
  copilotProcess.stdin.end();
  copilotProcess.kill("SIGTERM");
  await new Promise<void>((resolve) => {
    copilotProcess.once("exit", () => resolve());
    setTimeout(() => resolve(), 2000);
  });
}

main().catch((error) => {
  console.error(error);
  process.exitCode = 1;
});
```

## 延伸阅读

* [官方 ACP 文档](https://agentclientprotocol.com/protocol/overview)