@jeffreycao/copilot-api 2.0.2 → 2.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -401,6 +401,11 @@ request_max_retries = 3
401
401
  stream_max_retries = 1
402
402
  stream_idle_timeout_ms = 300000
403
403
 
404
+ [features.code_mode]
405
+ excluded_tool_namespaces = [
406
+ "mcp__codex_apps__sites"
407
+ ]
408
+
404
409
  [features]
405
410
  remote_compaction_v2 = true
406
411
 
@@ -410,6 +415,8 @@ enabled = false
410
415
 
411
416
  > [!NOTE]
412
417
  > `name` must be set to `"OpenAI"`.
418
+ >
419
+ > For models that do not support `tool_search`, we recommend disabling `mcp__codex_apps__sites` by adding it to `features.code_mode.excluded_tool_namespaces` as shown above. Otherwise, each prompt may consume more than 10,000 additional tokens.
413
420
 
414
421
  When a Codex client (`User-Agent` starts with `codex`) requests the top-level `GET /v1/models`, the gateway merges native Codex models with models available through the Messages adapter. The latter advertise `use_responses_lite: true`: `/v1/responses` uses **Responses → Messages** for Anthropic providers, while OpenAI-compatible providers and Chat-only Copilot models reuse the existing Messages route for **Responses → Messages → Chat Completions**, then translate streaming or JSON results back to Responses.
415
422
 
package/README.zh-CN.md CHANGED
@@ -429,6 +429,11 @@ request_max_retries = 3
429
429
  stream_max_retries = 1
430
430
  stream_idle_timeout_ms = 300000
431
431
 
432
+ [features.code_mode]
433
+ excluded_tool_namespaces = [
434
+ "mcp__codex_apps__sites"
435
+ ]
436
+
432
437
  [features]
433
438
  remote_compaction_v2 = true
434
439
 
@@ -438,6 +443,8 @@ enabled = false
438
443
 
439
444
  > [!NOTE]
440
445
  > `name` 一定要配置为 `"OpenAI"`。
446
+ >
447
+ > 对于不支持 `tool_search` 的模型,建议按上面的配置将 `mcp__codex_apps__sites` 添加到 `features.code_mode.excluded_tool_namespaces` 中。否则每次提问可能会额外消耗 1 万多个 tokens。
441
448
 
442
449
  Codex 客户端(`User-Agent` 以 `codex` 开头)请求顶层 `GET /v1/models` 时,网关会把原生 Codex 模型与可通过 Messages 适配的模型合并返回。后者会声明 `use_responses_lite: true`:调用 `/v1/responses` 后,Anthropic provider 走 **Responses → Messages**,OpenAI 兼容 provider 以及只支持 Chat 的 Copilot 模型则复用现有 Messages 路由继续走 **Responses → Messages → Chat Completions**,最终统一翻译回 Responses(包括流式事件)。
443
450
 
package/dist/main.js CHANGED
@@ -25,7 +25,7 @@ bindElectronFetch();
25
25
  const { auth } = await import("./auth-DH-ThnhJ.js");
26
26
  const { debug } = await import("./debug-D2giR-Kj.js");
27
27
  const { mcp } = await import("./mcp-BG6fpi6q.js");
28
- const { start } = await import("./start-CtwcJQT5.js");
28
+ const { start } = await import("./start-D3oRc7UM.js");
29
29
  await runMain(defineCommand({
30
30
  meta: {
31
31
  name: "copilot-api",
@@ -8139,6 +8139,7 @@ function translateResponsesToMessages(payload, options) {
8139
8139
  content: MESSAGES_COMPACTION_PROMPT
8140
8140
  });
8141
8141
  if (messages.length === 0) throw new ResponsesMessagesTranslationError("Responses input must contain at least one translatable message");
8142
+ applyEphemeralCacheControl(messages, system);
8142
8143
  const reasoningEffort = translateReasoningEffort(payload.reasoning?.effort);
8143
8144
  const messagesPayload = {
8144
8145
  model: options.model,
@@ -8665,6 +8666,24 @@ function resolveMetadataUserId(payload) {
8665
8666
  if (payload.safety_identifier?.trim()) return payload.safety_identifier;
8666
8667
  if (payload.prompt_cache_key?.trim()) return payload.prompt_cache_key;
8667
8668
  }
8669
+ const EPHEMERAL_CACHE_CONTROL = { type: "ephemeral" };
8670
+ function applyEphemeralCacheControl(messages, system) {
8671
+ const lastSystemBlock = system.at(-1);
8672
+ if (lastSystemBlock) lastSystemBlock.cache_control = { ...EPHEMERAL_CACHE_CONTROL };
8673
+ const lastMessage = messages.at(-1);
8674
+ if (!lastMessage) return;
8675
+ if (typeof lastMessage.content === "string") {
8676
+ lastMessage.content = [{
8677
+ type: "text",
8678
+ text: lastMessage.content,
8679
+ cache_control: { ...EPHEMERAL_CACHE_CONTROL }
8680
+ }];
8681
+ return;
8682
+ }
8683
+ const lastBlock = lastMessage.content.at(-1);
8684
+ if (!lastBlock || lastBlock.type === "thinking") return;
8685
+ lastBlock.cache_control = { ...EPHEMERAL_CACHE_CONTROL };
8686
+ }
8668
8687
  function appendAssistantBlock(messages, block) {
8669
8688
  const last = messages.at(-1);
8670
8689
  if (last?.role === "assistant" && Array.isArray(last.content)) {
@@ -8911,7 +8930,7 @@ function isJsonWhitespace(char) {
8911
8930
  }
8912
8931
  //#endregion
8913
8932
  //#region src/routes/responses/messages-stream-translation.ts
8914
- const EMPTY_SIGNATURE_ENCRYPTED_CONTENT = "Y29waWxvdC1hcGk6bWVzc2FnZXMtZW1wdHktc2lnbmF0dXJlOnYx";
8933
+ const EMPTY_SIGNATURE_ENCRYPTED_CONTENT = "";
8915
8934
  async function* translateMessagesStream(chunks, context) {
8916
8935
  const state = createTranslationState(context);
8917
8936
  try {
@@ -10104,4 +10123,4 @@ server.route("/:provider/images", providerImageRoutes);
10104
10123
  //#endregion
10105
10124
  export { server };
10106
10125
 
10107
- //# sourceMappingURL=server-0udg5DWI.js.map
10126
+ //# sourceMappingURL=server-DcL9pgmS.js.map