copilot-api-node20 0.40.4 → 0.41.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/dist/main.mjs +1 -1
- package/package.json +1 -1
package/dist/main.mjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import{defineCommand as e,runMain as t}from"citty";import o,{LogLevels as n,consola as r}from"consola";import a from"node:fs/promises";import i from"node:os";import s from"node:path";import{SpanKind as l,SpanStatusCode as c,context as u,metrics as p,trace as d}from"@opentelemetry/api";import m from"clipboardy";import{execFile as f,execSync as h}from"node:child_process";import g from"node:process";import{SeverityNumber as _,logs as y}from"@opentelemetry/api-logs";import{OTLPLogExporter as k}from"@opentelemetry/exporter-logs-otlp-http";import{OTLPMetricExporter as w}from"@opentelemetry/exporter-metrics-otlp-http";import{OTLPTraceExporter as b}from"@opentelemetry/exporter-trace-otlp-http";import{resourceFromAttributes as v}from"@opentelemetry/resources";import{BatchLogRecordProcessor as T}from"@opentelemetry/sdk-logs";import{PeriodicExportingMetricReader as $}from"@opentelemetry/sdk-metrics";import{NodeSDK as x}from"@opentelemetry/sdk-node";import{ATTR_SERVICE_INSTANCE_ID as A,ATTR_SERVICE_NAME as S,ATTR_SERVICE_VERSION as E}from"@opentelemetry/semantic-conventions";import{Client as C,request as O}from"undici";import{createHash as I,randomBytes as P,randomUUID as R}from"node:crypto";import{promisify as N}from"node:util";import{Hono as q}from"hono";import{cors as j}from"hono/cors";import{streamSSE as D}from"hono/streaming";import{events as M}from"fetch-event-stream";import{Tokenizer as H,models as B}from"ai-tokenizer";import*as F from"ai-tokenizer/encoding/claude";import{accessSync as U}from"node:fs";import{serve as L}from"srvx";import{isIP as G}from"node:net";import{generate as z}from"selfsigned";const J=s.join(i.homedir(),".local","share","copilot-api"),K={APP_DIR:J,GITHUB_TOKEN_PATH:s.join(J,"github_token"),MACHINE_ID_PATH:s.join(J,"machine_id"),SESSION_ID_PATH:s.join(J,"session_id")};async function W(){await a.mkdir(K.APP_DIR,{recursive:!0}),await V(K.GITHUB_TOKEN_PATH),await V(K.SESSION_ID_PATH)}async function V(e){try{await a.access(e,a.constants.W_OK)}catch{await a.writeFile(e,""),await a.chmod(e,384)}}const Y=6e5,X={accountType:"individual",manualApprove:!1,rateLimitWait:!1,showToken:!1,timeoutMs:Y,webSearchProviders:[],errorReporting:!0,connectivity:{probeEndpoints:["https://api.github.com","https://www.google.com","https://1.1.1.1"],fastProbeInterval:5e3,slowProbeInterval:1e4,timeoutMs:15e3,jitterMaxMs:1e3,connectionPooling:!0,dnsCache:!0,h2:!1,h2Keepalive:!1}},Z=" │ ",Q=e=>{if(e>=1e6){let t=e/1e6;return Number.isInteger(t)?`${t}M`:`${t.toFixed(1)}M`}return e>=1e4?`${Math.round(e/1e3)}K`:e>=1e3?`${(e/1e3).toFixed(1)}K`:e.toString()},ee=(e,t)=>e.padEnd(t),te=e=>`${(e/1e3).toFixed(1)}s`.padStart(6),oe=(e,t,o)=>` --\x3e ${ee(e,4)} ${ee(t,21)} ${ee(o,3)}`,ne=e=>{let t=(e.reasoningEffort??"-")+(e.effortClamped?"*":"");return(e=>ee(e.length>21?`${e.slice(0,20)}…`:e,22))(e.model??"—")+ee(t,8)},re=e=>{let t=e?.inputTokens??0,o=e?.cachedTokens??0,n=e?Q(Math.max(t-o,0)):"—",r=e?Q(e.outputTokens??0):"—",a=o?Q(o):"—";return`↑${n.padStart(5)} ⚡${a.padStart(5)} ↓${r.padStart(5)}`},ae=(e,t)=>{if(!e?.inputTokens||!t)return`ctx ${ee("—",10)}`;let o=Math.round(e.inputTokens/t*100),n=Q(e.inputTokens).padStart(5),r=`${o}%`;return`ctx ${n}${r.padStart(Math.max(10-n.length,r.length+1))}`},ie=e=>{if(void 0===e.ttfbMs)return`e2e ${te(e.e2eMs)}`;let t=`(+${((e.e2eMs-e.ttfbMs)/1e3).toFixed(1)}s)`.padStart(8);return`ttfb ${te(e.ttfbMs)} → e2e ${te(e.e2eMs)} ${t}`},se=e=>e?X.models?.data.find(t=>t.id===e)?.capabilities.limits?.max_context_window_tokens:void 0,le=e=>({...e?.inputTokens&&{"copilot_api.input_tokens":e.inputTokens},...e?.inputTokens&&{"copilot_api.fresh_input_tokens":Math.max(e.inputTokens-(e.cachedTokens??0),0)},...e?.outputTokens&&{"copilot_api.output_tokens":e.outputTokens},...e?.cachedTokens&&{"copilot_api.cached_tokens":e.cachedTokens}}),ce={completionCallbacks:new Map,registerCompletion(e,t,o){this.completionCallbacks.set(e,{context:t,startTime:o,requestId:e})},executeCompletion(e){let t=this.completionCallbacks.get(e);t&&(this.logCompletion(t),this.completionCallbacks.delete(e))},logCompletion(e){let{context:t,startTime:n}=e,r=Math.round(performance.now()-n),a=t.get("requestData"),i=a?.upstreamTotalMs??a?._d1,s=(e=>[oe(e.method,e.path,e.status),ne(e),re(e.tokenUsage),ae(e.tokenUsage,e.maxContextTokens),ie({ttfbMs:e.ttfbMs,e2eMs:e.e2eMs})].join(Z))({method:t.req.method,path:t.req.path,status:t.res.status.toString(),model:a?.model,reasoningEffort:a?.reasoningEffort,effortClamped:a?.effortClamped,tokenUsage:a?.tokenUsage,maxContextTokens:se(a?.model),ttfbMs:a?.upstreamTtfbMs,e2eMs:r});o.info(s),Ke(_.INFO,"INFO","Request completed",(e=>{let{c:t,requestData:o,duration:n,upstreamTotal:r}=e;return{"http.method":t.req.method,"http.path":t.req.path,"http.status_code":t.res.status,"copilot_api.duration_ms":n,...o?.model&&{"copilot_api.model":o.model},...o?.reasoningEffort&&{"copilot_api.reasoning_effort":o.reasoningEffort},...o?.effortClamped&&{"copilot_api.effort_clamped":!0},...void 0!==o?.upstreamTtfbMs&&{"copilot_api.upstream_ttfb_ms":Math.round(o.upstreamTtfbMs)},...void 0!==r&&{"copilot_api.upstream_total_ms":Math.round(r),"copilot_api.copilot_duration_ms":Math.round(r)},...le(o?.tokenUsage)}})({c:t,requestData:a,duration:r,upstreamTotal:i}),t.get("requestTraceContext"))},logRateLimit(e,t){let{context:n,startTime:r}=e,a=Math.round(performance.now()-r),i=(t.headers.get("x-ratelimit-exceeded")||"").split(":")[1]||"unknown",s=t.headers.get("retry-after")||t.headers.get("x-ratelimit-user-retry-after")||"?",l=n.get("requestData");o.warn((e=>[oe(e.method,e.path,"429"),ne(e),`rate-limited retry ${e.retry}s (${e.rateLimitType})`.padEnd(37),`e2e ${te(e.e2eMs)}`].join(Z))({method:n.req.method,path:n.req.path,model:l?.model,reasoningEffort:l?.reasoningEffort,effortClamped:l?.effortClamped,retry:s,rateLimitType:i,e2eMs:a}))},logError(e,t,n){let{context:r,startTime:a}=e,i=Math.round(performance.now()-a),s=r.get("requestData");o.error((e=>{let t=oe(e.method,e.path,e.status.toString()),o=ne(e),n=e.message.replaceAll(/\s+/g," ").trim();return[t,o,(n.length>37?`${n.slice(0,36)}…`:n).padEnd(37),`e2e ${te(e.e2eMs)}`].join(Z)})({method:r.req.method,path:r.req.path,status:t,model:s?.model,reasoningEffort:s?.reasoningEffort,effortClamped:s?.effortClamped,message:n,e2eMs:i}))},cleanup(){let e=performance.now()-12e5;for(let[t,o]of this.completionCallbacks)o.startTime<e&&this.completionCallbacks.delete(t);if(this.completionCallbacks.size>1e3){let e=Array.from(this.completionCallbacks.entries()).sort(([,e],[,t])=>e.startTime-t.startTime),t=e.slice(0,e.length-1e3);for(let[e]of t)this.completionCallbacks.delete(e)}}};setInterval(()=>ce.cleanup(),6e4);let ue,pe,de=Date.now();const me={"x-honeycomb-team":"hcaik_01km2y7yf1rrn70xvxce5kx9dyz936dwm21b9bgvnwf3pxq0cmqkcwha8n"};function fe(){let e=process.env.OTEL_EXPORTER_OTLP_ENDPOINT??"https://api.honeycomb.io",t=process.env.OTEL_EXPORTER_OTLP_HEADERS?function(e){return e?Object.fromEntries(e.split(",").map(e=>e.trim()).filter(Boolean).map(e=>{let t=e.indexOf("=");return-1===t?[e,""]:[decodeURIComponent(e.slice(0,t)),decodeURIComponent(e.slice(t+1))]})):{}}(process.env.OTEL_EXPORTER_OTLP_HEADERS):me;return{endpoint:e.replace(/\/$/,""),headers:t}}const he=d.getTracer("copilot-api"),ge=p.getMeter("copilot-api"),_e=y.getLogger("copilot-api"),ye=ge.createCounter("copilot_api.requests.total",{unit:"{request}",description:"Total requests received"}),ke=ge.createCounter("copilot_api.requests.errors",{unit:"{error}",description:"Total error responses"}),we=ge.createCounter("copilot_api.tokens.input",{unit:"{token}",description:"Total input tokens consumed"}),be=ge.createCounter("copilot_api.tokens.output",{unit:"{token}",description:"Total output tokens generated"}),ve=ge.createCounter("copilot_api.tokens.cached",{unit:"{token}",description:"Total cached prompt tokens"}),Te=ge.createCounter("copilot_api.rate_limit.triggers",{unit:"{trigger}",description:"Rate limit trigger count"}),$e=ge.createCounter("copilot_api.model_validation.errors",{unit:"{error}",description:"Model validation failures"}),xe=ge.createCounter("copilot_api.model_mapping.mappings",{unit:"{mapping}",description:"Model name normalizations"}),Ae=ge.createCounter("copilot_api.token_refresh.attempts",{unit:"{attempt}",description:"Token refresh attempts"}),Se=ge.createCounter("copilot_api.token_refresh.failures",{unit:"{failure}",description:"Token refresh final failures"}),Ee=ge.createCounter("copilot_api.connectivity.checks",{unit:"{check}",description:"Connectivity probe results"}),Ce=ge.createCounter("copilot_api.connectivity.transitions",{unit:"{transition}",description:"Connectivity state transitions"}),Oe=ge.createCounter("copilot_api.upstream.requests",{unit:"{request}",description:"Upstream API calls"}),Ie=ge.createCounter("copilot_api.stream.chunks",{unit:"{chunk}",description:"Total SSE chunks sent"}),Pe=ge.createCounter("copilot_api.approval.decisions",{unit:"{decision}",description:"Manual approval decisions"}),Re=ge.createCounter("copilot_api.h2_keepalive.pings",{unit:"{ping}",description:"HTTP/2 keepalive pings sent"}),Ne=ge.createCounter("copilot_api.h2.connections",{unit:"{connection}",description:"HTTP/2 connection lifecycle events"}),qe=ge.createCounter("copilot_api.error_capture.decisions",{unit:"{decision}",description:"Per-process daily limiter outcomes (full|suppressed|drop)"}),je=ge.createHistogram("copilot_api.request.duration",{unit:"ms",description:"Total request duration"}),De=ge.createHistogram("copilot_api.copilot.duration",{unit:"ms",description:"Upstream Copilot API call duration"}),Me=ge.createHistogram("copilot_api.stream.duration",{unit:"ms",description:"Duration of SSE streaming phase"}),He=ge.createHistogram("copilot_api.rate_limit.wait_duration",{unit:"ms",description:"Duration of rate limit waits"}),Be=ge.createHistogram("copilot_api.translation.duration",{unit:"ms",description:"Translation layer processing time"}),Fe=ge.createHistogram("copilot_api.token_refresh.duration",{unit:"ms",description:"Token refresh duration"}),Ue=ge.createHistogram("copilot_api.connectivity.probe_duration",{unit:"ms",description:"Individual connectivity probe duration"}),Le=ge.createHistogram("copilot_api.tokens.per_request.input",{unit:"{token}",description:"Input tokens per request distribution"}),Ge=ge.createHistogram("copilot_api.tokens.per_request.output",{unit:"{token}",description:"Output tokens per request distribution"}),ze=ge.createHistogram("copilot_api.stream.chunks_per_request",{unit:"{chunk}",description:"Chunks per streaming request"}),Je=ge.createHistogram("copilot_api.approval.wait_duration",{unit:"ms",description:"Time waiting for manual approval"});function Ke(e,t,o,n,r){let a=d.getActiveSpan()?.spanContext()??r;_e.emit({severityNumber:e,severityText:t,body:o,attributes:{...n,...a&&{"trace.id":a.traceId,"span.id":a.spanId}}})}function We(e,t,o){let n=t instanceof Error?t:Error(String(t));e.setStatus({code:c.ERROR,message:o??n.message}),e.recordException(n)}function Ve(e,t,o){We(e,o),t&&t!==e&&We(t,o)}function Ye(e,t=""){let o={};if(null==e)return o;if("object"!=typeof e)return("string"==typeof e||"number"==typeof e||"boolean"==typeof e)&&t&&(o[t]=e),o;if(Array.isArray(e))return t&&(o[t]=JSON.stringify(e)),o;for(let[n,r]of Object.entries(e)){let e=t?`${t}.${n}`:n;void 0===r||"function"==typeof r||(null===r?o[e]="null":"object"!=typeof r||Array.isArray(r)?Array.isArray(r)?o[e]=JSON.stringify(r):("string"==typeof r||"number"==typeof r||"boolean"==typeof r)&&(o[e]=r):Object.assign(o,Ye(r,e)))}return o}ge.createObservableGauge("copilot_api.connectivity.status",{unit:"{status}",description:"1 = online, 0 = offline"}).addCallback(e=>{e.observe(+!!tt.getConnectivityStats().isOnline)}),ge.createObservableGauge("copilot_api.connectivity.consecutive_failures",{unit:"{failure}",description:"Current consecutive connectivity failure count"}).addCallback(e=>{e.observe(tt.getConnectivityStats().consecutiveFailures)}),ge.createObservableGauge("copilot_api.models.available",{unit:"{model}",description:"Number of available models"}).addCallback(e=>{e.observe(X.models?.data.length??0)}),ge.createObservableGauge("copilot_api.completion_logger.pending",{unit:"{callback}",description:"Number of pending completion callbacks"}).addCallback(e=>{e.observe(ce.completionCallbacks.size)}),ge.createObservableGauge("copilot_api.uptime",{unit:"s",description:"Server uptime in seconds"}).addCallback(e=>{e.observe((Date.now()-de)/1e3)});const Xe=new Set(["authorization","cookie","set-cookie","x-honeycomb-team","x-api-key","proxy-authorization"]);function Ze(e,t,o){for(let[n,r]of Object.entries(o)){let o=n.toLowerCase();Xe.has(o)||e.setAttribute(`http.${t}.header.${o}`,r)}}async function Qe(e){let{spanName:t,url:o,target:n,method:r="GET",headers:a,body:i,signal:s,extraAttributes:u}=e,p=he.startSpan(t,{kind:l.CLIENT,attributes:{"http.method":r,"url.full":o,"copilot_api.target":n,...u}});a&&Ze(p,"request",a);try{let e=await fetch(o,{method:r,headers:a,body:i,signal:s});return p.setAttribute("http.response.status_code",e.status),function(e,t){t.headers.forEach((t,o)=>{let n=o.toLowerCase();Xe.has(n)||e.setAttribute(`http.response.header.${n}`,t)})}(p,e),Oe.add(1,{target:n,status_code:String(e.status)}),e.ok||p.setStatus({code:c.ERROR,message:`HTTP ${e.status}`}),{response:e,span:p}}catch(e){throw We(p,e),p.end(),e}}async function et(e){let{spanName:t,url:o,target:n,method:r="POST",headers:a,body:i,signal:s,headersTimeout:u,bodyTimeout:p,extraAttributes:d,dispatcher:m}=e,f=he.startSpan(t,{kind:l.CLIENT,attributes:{"http.method":r,"url.full":o,"copilot_api.target":n,"copilot_api.h2.enabled":void 0!==m,...d}});Ze(f,"request",a);try{let{statusCode:e,headers:t,body:l}=await O(o,{method:r,headers:a,body:i,signal:s,headersTimeout:u,bodyTimeout:p,dispatcher:m});f.setAttribute("http.response.status_code",e);for(let[e,o]of Object.entries(t)){let t=e.toLowerCase();void 0!==o&&!Xe.has(t)&&f.setAttribute(`http.response.header.${t}`,Array.isArray(o)?o.join(", "):o)}return Oe.add(1,{target:n,status_code:String(e)}),e>=400&&f.setStatus({code:c.ERROR,message:`HTTP ${e}`}),{statusCode:e,headers:t,body:l,span:f}}catch(e){throw We(f,e),f.end(),e}}const tt=new class extends EventTarget{isOnline=!0;lastChecked=(new Date).toISOString();consecutiveFailures=0;lastErrorType;lastErrorMessage;lastSuccessfulEndpoint;endpointFailureStats={};checkInterval;abortController;on(e,t){return this.addEventListener(e,t),this}off(e,t){return this.removeEventListener(e,t),this}start(){o.debug("Starting connectivity monitor",{probeEndpoints:X.connectivity.probeEndpoints,fastInterval:X.connectivity.fastProbeInterval}),this.scheduleNextCheck()}stop(){o.debug("Stopping connectivity monitor"),this.checkInterval&&=void clearTimeout(this.checkInterval),this.abortController&&=void this.abortController.abort()}scheduleNextCheck(){this.checkInterval&&clearTimeout(this.checkInterval);let e=(this.isOnline?X.connectivity.slowProbeInterval:X.connectivity.fastProbeInterval)+Math.random()*X.connectivity.jitterMaxMs;this.checkInterval=setTimeout(()=>{this.performConnectivityCheck().catch(e=>{o.error("Connectivity check failed:",e)})},e)}async performConnectivityCheck(){let e=he.startSpan("copilot_api.connectivity.probe");this.abortController=new AbortController;let t=setTimeout(()=>this.abortController?.abort(),X.connectivity.timeoutMs);try{let n=!1;for(let e of X.connectivity.probeEndpoints)try{let t=performance.now(),o=await fetch(e,{method:"HEAD",signal:this.abortController.signal,headers:{"User-Agent":"copilot-api-connectivity-monitor/1.0",...X.connectivity.dnsCache&&{"Cache-Control":"max-age=300"}}}),r=performance.now()-t;if(o.ok){n=!0,this.lastSuccessfulEndpoint=e,Ue.record(r,{endpoint:e,result:"success"});break}Ue.record(r,{endpoint:e,result:"failed"})}catch(t){this.endpointFailureStats[e]=(this.endpointFailureStats[e]||0)+1,o.debug(`Probe failed for ${e}:`,t)}this.updateConnectivityState(n);let r=n?"online":"offline";e.setAttribute("copilot_api.connectivity.result",r),e.setAttribute("copilot_api.connectivity.consecutive_failures",this.consecutiveFailures),this.lastSuccessfulEndpoint&&e.setAttribute("copilot_api.connectivity.successful_endpoint",this.lastSuccessfulEndpoint),Ee.add(1,{result:n?"online":"offline"})}catch(e){this.handleConnectivityError(e)}finally{clearTimeout(t),e.end(),this.scheduleNextCheck()}}updateConnectivityState(e){let t=this.isOnline;if(this.isOnline=e,this.lastChecked=(new Date).toISOString(),e){let e=this.consecutiveFailures;this.consecutiveFailures>0&&o.info(`Connectivity restored after ${this.consecutiveFailures} failures`),this.consecutiveFailures=0,this.lastErrorType=void 0,this.lastErrorMessage=void 0,t||(this.dispatchEvent(new CustomEvent("online")),Ce.add(1,{from:"offline",to:"online"}),Ke(_.INFO,"INFO","Connectivity restored",{"copilot_api.connectivity.consecutive_failures_before_recovery":e}))}else this.consecutiveFailures++,t&&(o.warn("Connectivity lost"),this.dispatchEvent(new CustomEvent("offline")),Ce.add(1,{from:"online",to:"offline"}),Ke(_.WARN,"WARN","Connectivity lost",{"copilot_api.connectivity.consecutive_failures":this.consecutiveFailures}))}handleConnectivityError(e){this.lastErrorType=e.name,this.lastErrorMessage=e.message,o.error("Connectivity check failed:",e),this.updateConnectivityState(!1)}getConnectivityStats(){return{isOnline:this.isOnline,lastChecked:this.lastChecked,consecutiveFailures:this.consecutiveFailures,lastErrorType:this.lastErrorType,lastErrorMessage:this.lastErrorMessage}}getPerformanceStats(){let e=this.isOnline?X.connectivity.slowProbeInterval:X.connectivity.fastProbeInterval;return{currentInterval:e,nextCheckEstimate:new Date(Date.now()+e+Math.random()*X.connectivity.jitterMaxMs).toISOString(),lastSuccessfulEndpoint:this.lastSuccessfulEndpoint,endpointFailureStats:{...this.endpointFailureStats},jitterEnabled:X.connectivity.jitterMaxMs>0,connectionPooling:X.connectivity.connectionPooling,dnsCache:X.connectivity.dnsCache}}},ot=()=>({"content-type":"application/json",accept:"application/json"}),nt="0.48.1",rt=`copilot-chat/${nt}`,at=`GitHubCopilotChat/${nt}`,it=async e=>{let t=(e=>{let t=e.replaceAll(/[^\w.-]/g,"_").trim();if(0===t.length||"."===t||".."===t||/^[_.]+$/.test(t))throw Error("Invalid GitHub username: cannot be empty or consist only of special characters after sanitization");return`${K.MACHINE_ID_PATH}_${t}`})(e);try{let e=await a.readFile(t,"utf8");if(e.trim())return e.trim()}catch{}let o=(e=>{let t=I("sha256");return t.update(process.platform),t.update(process.arch),t.update(process.env.USER||process.env.USERNAME||"anonymous"),t.update(i.hostname()),t.update(e),t.update(Date.now().toString()),t.update(P(16)),t.digest("hex")})(e);return await a.writeFile(t,o),await a.chmod(t,384),o},st=async(e,t)=>{e.machineId||=await it(t),e.sessionId||=await(async()=>{try{let e=await a.readFile(K.SESSION_ID_PATH,"utf8");if(e.trim())return e.trim()}catch{}let e=R();return await a.writeFile(K.SESSION_ID_PATH,e),await a.chmod(K.SESSION_ID_PATH,384),e})()},lt=e=>"individual"===e.accountType?"https://api.githubcopilot.com":`https://api.${e.accountType}.githubcopilot.com`,ct=(e,t=!1)=>{if(!e.machineId||!e.sessionId)throw Error("VSCode identifiers not initialized. Call initializeVSCodeIdentifiers() during startup.");let o=R(),n={Authorization:`Bearer ${e._t1}`,"Content-Type":"application/json",accept:"*/*","accept-encoding":"br, gzip, deflate","accept-language":"*","sec-fetch-mode":"cors","Copilot-Integration-Id":"vscode-chat","Editor-Version":`vscode/${e._v1}`,"Editor-Plugin-Version":rt,"User-Agent":at,"VScode-MachineId":e.machineId,"VScode-SessionId":e.sessionId,"OpenAI-Intent":"conversation-agent","X-Interaction-Type":"conversation-agent","X-Agent-Task-Id":o,"X-VSCode-User-Agent-Library-Version":"node-fetch","X-GitHub-Api-Version":"2025-05-01","X-Interaction-Id":R(),"X-Request-Id":o};return t&&(n["copilot-vision-request"]="true"),n},ut=["interleaved-thinking","context-management","advanced-tool-use","redact-thinking"];const pt=(e,t,o)=>{let n=ct(e);delete n["Copilot-Integration-Id"],n["anthropic-version"]=t?.anthropicVersion??"2023-06-01";let r=new Set,a=t?.anthropicBeta?function(e){let t=e.split(",").map(e=>e.trim()).filter(e=>e&&ut.some(t=>e.startsWith(`${t}-`)));return t.length>0?t.join(","):void 0}(t.anthropicBeta):void 0;if(a)for(let e of a.split(","))r.add(e);if(o)for(let e of o)r.add(e);return r.size>0&&(n["anthropic-beta"]=[...r].join(",")),n},dt="https://api.github.com",mt=e=>({"content-type":"application/json",accept:"application/json",authorization:`token ${e._t2}`,"editor-version":`vscode/${e._v1}`,"editor-plugin-version":rt,"user-agent":at,"x-github-api-version":"2025-04-01","x-vscode-user-agent-library-version":"node-fetch"}),ft="https://github.com",ht="01ab8ac9400c4e429b23",gt=["user:email"].join(" ");function _t(e){return e.includes("/messages")?"anthropic":e.includes("/chat/completions")?"openai":e.includes("/embeddings")?"embeddings":e.includes("/responses")?"responses":e.includes("/models")?"models":e.includes("/usage")?"usage":e.includes("/token")?"token":"unknown"}const yt=32768,kt=[{regex:/Bearer\s+[\w.-]{20,}/g,mask:"Bearer ***"},{regex:/\bghu_[A-Za-z0-9]{20,}/g,mask:"ghu_***"},{regex:/\bghp_[A-Za-z0-9]{20,}/g,mask:"ghp_***"},{regex:/\bgho_[A-Za-z0-9]{20,}/g,mask:"gho_***"},{regex:/\bghs_[A-Za-z0-9]{20,}/g,mask:"ghs_***"},{regex:/\bghr_[A-Za-z0-9]{20,}/g,mask:"ghr_***"},{regex:/\bsk-[A-Za-z0-9-]{20,}/g,mask:"sk-***"},{regex:/\bhcaik_[A-Za-z0-9]{20,}/g,mask:"hcaik_***"}],wt=new Set(["authorization","cookie","set-cookie","x-api-key","proxy-authorization"]);function bt(e){let t=e;for(let{regex:e,mask:o}of kt)t=t.replace(e,o);return t}const vt=new Map;function Tt(e){let t=function(e=new Date){return e.toISOString().slice(0,10)}(e.now),o=e.upstreamErrorType??"unknown",n=(e.model??"unknown").slice(0,100);return`${e.endpointType}:${e.statusCode}:${o}:${n}:${t}`}function $t(e,t,o){let n=bt(o),r=8*yt,a=n.length>r,i=a?n.slice(0,r):n,s=I("sha256").update(n).digest("hex");if(i.length<=yt)e.setAttribute(t,i),e.setAttribute(`${t}.parts`,1);else{for(let o=0;o<i.length;o+=yt)e.setAttribute(`${t}.part_${o/yt}`,i.slice(o,o+yt));e.setAttribute(`${t}.parts`,Math.ceil(i.length/yt))}e.setAttribute(`${t}.bytes`,n.length),e.setAttribute(`${t}.sha256`,s),a&&(e.setAttribute(`${t}.truncated`,!0),e.setAttribute(`${t}.dropped_bytes`,n.length-i.length))}function xt(e,t){let o=function(e){if(vt.size>=1e3&&!vt.has(e)){let e=vt.keys().next().value;void 0!==e&&vt.delete(e)}let t,o=(vt.get(e)??0)+1;return vt.set(e,o),t=o<=2?"full":3===o?"suppressed":"drop",qe.add(1,{decision:t}),t}(t.signatureKey);if(e.setAttribute("copilot_api.error_capture.decision",o),e.setAttribute("copilot_api.error_capture.signature_key",t.signatureKey),"drop"===o)return{decision:o};if("suppressed"===o)return e.setAttribute("copilot_api.error_capture.suppressed_today",!0),{decision:o};let n=t.c.get("rawBody");n&&$t(e,"copilot_api.incoming_request_body",n);let r=At(t.c.req.header());return r&&$t(e,"copilot_api.incoming_headers",r),void 0!==t.outgoingBody&&$t(e,"copilot_api.outgoing_request_body",t.outgoingBody),void 0!==t.outgoingHeaders&&$t(e,"copilot_api.outgoing_headers",At(t.outgoingHeaders)),void 0!==t.upstreamResponseBody&&$t(e,"copilot_api.upstream_response_body",t.upstreamResponseBody),{decision:o}}function At(e){let t={};for(let[o,n]of Object.entries(e))wt.has(o.toLowerCase())||(t[o]=n);return JSON.stringify(t)}async function St(){try{let e=new URL("../package.json",import.meta.url).pathname,t=await a.readFile(e);return JSON.parse(t.toString()).version}catch{return"unknown"}}function Et(){let e=typeof Bun<"u";return{name:e?"bun":"node",version:e?Bun.version:process.version.slice(1),platform:i.platform(),arch:i.arch()}}async function Ct(){try{return!!(await a.stat(K.GITHUB_TOKEN_PATH)).isFile()&&(await a.readFile(K.GITHUB_TOKEN_PATH,"utf8")).trim().length>0}catch{return!1}}async function Ot(e){let t=await async function(){let[e,t]=await Promise.all([St(),Ct()]);return{version:e,runtime:Et(),paths:{APP_DIR:K.APP_DIR,GITHUB_TOKEN_PATH:K.GITHUB_TOKEN_PATH},tokenExists:t}}();e.json?function(e){console.log(JSON.stringify(e,null,2))}(t):function(e){o.info(`service debug\n\nVersion: ${e.version}\nRuntime: ${e.runtime.name} ${e.runtime.version} (${e.runtime.platform} ${e.runtime.arch})\n\nPaths:\n- APP_DIR: ${e.paths.APP_DIR}\n- GITHUB_TOKEN_PATH: ${e.paths.GITHUB_TOKEN_PATH}\n\nToken exists: ${e.tokenExists?"Yes":"No"}`)}(t)}const It=e({meta:{name:"debug",description:"Print debug information about the application"},args:{json:{type:"boolean",default:!1,description:"Output debug information as JSON"}},run:({args:e})=>Ot({json:e.json})}),Pt=process.env.COPILOT_API_REPORT_ENDPOINT??"https://copilot-api.barazany.dev/report",Rt=process.env.COPILOT_API_REPORT_KEY??"cai_60fc3498226c9121cbf0da949ab207cddd93e2d74faabbbb",Nt=new Set;let qt;function jt(e){if(X.errorReporting&&!(e.statusCode<500)&&!Nt.has(e.signature)){if(Nt.size>=1e3){let e=Nt.values().next().value;void 0!==e&&Nt.delete(e)}Nt.add(e.signature),async function(e){qt??=St();let t=await qt,o=Et(),n=void 0===e.upstreamErrorMessage?void 0:function(e){return e.replaceAll(/(\/(?:home|Users)\/|\\Users\\)[^/\\\s]+/g,(e,t)=>`${t}***`)}(bt(e.upstreamErrorMessage)).slice(0,600),r={proxyVersion:t,signature:e.signature,errorClass:e.errorClass,statusCode:e.statusCode,upstreamErrorType:e.upstreamErrorType,upstreamErrorMessage:n,endpointType:_t(e.route),route:e.route,model:e.model?.slice(0,100),platform:`${o.platform}/${o.arch}`,runtime:`${o.name}/${o.version}`,timestamp:(new Date).toISOString()},a=new AbortController,i=setTimeout(()=>a.abort(),4e3);try{await fetch(Pt,{method:"POST",headers:{"content-type":"application/json","x-ingest-key":Rt},body:JSON.stringify(r),signal:a.signal})}finally{clearTimeout(i)}}(e).catch(e=>{o.debug("Error report submission failed:",e)})}}var Dt=class extends Error{response;outgoingBody;outgoingHeaders;constructor(e,t,o){super(e),this.response=t,this.outgoingBody=o?.outgoingBody,this.outgoingHeaders=o?.outgoingHeaders}},Mt=class extends Error{name="RequestTimeoutError";constructor(e){super(`Upstream request timed out after ${e}ms`)}};function Ht(e,t){return setTimeout(()=>e.abort(new Mt(t)),t)}const Bt=new Set(["UND_ERR_CONNECT_TIMEOUT","ECONNREFUSED","ENOTFOUND","EAI_AGAIN","ETIMEDOUT","EADDRNOTAVAIL","EPIPE","ECONNRESET"]),Ft=RegExp(`\\b(?:${[...Bt].join("|")})\\b`);function Ut(e){return e instanceof Error?e.code:void 0}function Lt(e){return e.req.path.startsWith("/v1/messages")}function Gt(e,t){if(Lt(t)){try{let t=JSON.parse(e);if("message"in t&&"string"==typeof t.message&&!("error"in t))return{type:"error",error:{type:"invalid_request_error",message:t.message}};if("error"in t&&"object"==typeof t.error){let e=t.error;return{type:"error",error:{type:"string"==typeof e.type&&e.type||"string"==typeof e.code&&e.code||"api_error",message:"string"==typeof e.message&&e.message||"Unknown error"}}}}catch{}return{type:"error",error:{type:"api_error",message:e}}}try{return JSON.parse(e)}catch{return{error:{message:e,type:"error"}}}}function zt(e){let t=e.error,o={};return t&&"object"==typeof t&&("string"==typeof t.type?o.type=t.type:"string"==typeof t.code&&(o.type=t.code),"string"==typeof t.message&&(o.message=t.message)),!o.message&&"string"==typeof e.message&&(o.message=e.message),o}function Jt(e,t){e&&(t.type&&e.setAttribute("copilot_api.upstream.error_type",t.type),t.message&&e.setAttribute("copilot_api.upstream.error_message",t.message))}function Kt(e){let t={};return e.type&&(t["copilot_api.upstream.error_type"]=e.type),e.message&&(t["copilot_api.upstream.error_message"]=e.message),t}function Wt(e){let{c:t,error:o,errorText:n,upstream:r}=e,a=d.getActiveSpan();if(!a)return;let i=Tt({endpointType:_t(t.req.path),statusCode:o.response.status,upstreamErrorType:r.type,model:t.get("requestData")?.model});xt(a,{c:t,outgoingBody:o.outgoingBody,outgoingHeaders:o.outgoingHeaders,upstreamResponseBody:n,signatureKey:i})}function Vt(e,t,o){let n=e.get("requestId"),r=ce.completionCallbacks.get(n);r&&(ce.logError(r,t,o),ce.completionCallbacks.delete(n))}async function Yt(e,t){if(t instanceof Dt&&429===t.response.status)return async function(e,t){let o=d.getActiveSpan(),n=e.get("requestId"),r=ce.completionCallbacks.get(n);r&&(ce.logRateLimit(r,t.response),ce.completionCallbacks.delete(n)),Te.add(1,{action:"rejected",source:"upstream"});let a=await t.response.text(),i=Gt(a,e),s=zt(i);return o?.setStatus({code:c.ERROR,message:"Rate limited by upstream"}),o?.setAttribute("copilot_api.error_type","rate_limit_upstream"),Jt(o,s),Ke(_.WARN,"WARN","Upstream rate limit hit",{"copilot_api.status_code":429,"http.path":e.req.path,"copilot_api.error_type":"rate_limit_upstream",...Kt(s)}),Wt({c:e,error:t,errorText:a,upstream:s}),e.json(i,429)}(e,t);if(t instanceof SyntaxError){d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_json_body"),Ke(_.WARN,"WARN",`Invalid JSON in request body: ${t.message}`,{"copilot_api.status_code":400,"http.path":e.req.path,"copilot_api.error_type":"invalid_json_body"});let o=Lt(e)?{type:"error",error:{type:"invalid_request_error",message:"Invalid JSON in request body"}}:{error:{message:"Invalid JSON in request body",type:"invalid_request_error"}};return Vt(e,400,"Invalid JSON in request body"),e.json(o,400)}if(t instanceof Dt)return async function(e,t){let o=d.getActiveSpan(),n=await t.response.text(),r=Gt(n,e),a=zt(r);return Vt(e,t.response.status,a.message??t.message),o?.setStatus({code:c.ERROR,message:t.message}),o?.recordException(t),o?.setAttribute("copilot_api.error_type","HTTPError"),Jt(o,a),Ke(_.ERROR,"ERROR",`HTTP error: ${t.message}`,{"copilot_api.status_code":t.response.status,"http.path":e.req.path,"copilot_api.error_type":"HTTPError",...Kt(a)}),Wt({c:e,error:t,errorText:n,upstream:a}),t.response.status>=500&&jt({route:e.req.path,statusCode:t.response.status,errorClass:"HTTPError",signature:Tt({endpointType:_t(e.req.path),statusCode:t.response.status,upstreamErrorType:a.type,model:e.get("requestData")?.model}),model:e.get("requestData")?.model,upstreamErrorType:a.type,upstreamErrorMessage:a.message}),e.json(r,t.response.status)}(e,t);if(function(e){return e instanceof Mt||e instanceof Error&&"AbortError"===e.name&&e.cause instanceof Mt}(t))return function(e,t){let o=d.getActiveSpan();o?.setStatus({code:c.ERROR,message:"Upstream request timed out"}),t instanceof Error&&o?.recordException(t),o?.setAttribute("copilot_api.error_type","request_timeout");let n="Upstream request timed out (gateway timeout). Increase the timeout or retry.";Ke(_.ERROR,"ERROR",n,{"copilot_api.status_code":504,"http.path":e.req.path,"copilot_api.error_type":"request_timeout"});let r=Lt(e)?{type:"error",error:{type:"api_error",message:n}}:{error:{message:n,type:"timeout_error"}};return Vt(e,504,t instanceof Error?t.message:n),e.json(r,504)}(e,t);if(function(e){if(!(e instanceof Error))return!1;let t=e.cause,o=Ut(e)??Ut(t);return o?Bt.has(o):Ft.test(e.message)||t instanceof Error&&Ft.test(t.message)}(t))return function(e,t){let o=d.getActiveSpan();o?.setStatus({code:c.ERROR,message:"Transient upstream connection failure"}),t instanceof Error&&o?.recordException(t),o?.setAttribute("copilot_api.error_type","transient_transport");let n="Temporary upstream connection failure. Please retry.";Ke(_.WARN,"WARN",n,{"copilot_api.status_code":503,"http.path":e.req.path,"copilot_api.error_type":"transient_transport"}),e.header("Retry-After","1");let r=Lt(e)?{type:"error",error:{type:"api_error",message:n}}:{error:{message:n,type:"service_unavailable"}};return Vt(e,503,t instanceof Error?t.message:n),e.json(r,503)}(e,t);let n=d.getActiveSpan(),r=t instanceof Error?t:Error(String(t));n?.setStatus({code:c.ERROR,message:r.message}),n?.recordException(r),n?.setAttribute("copilot_api.error_type",r.name),Ke(_.ERROR,"ERROR",`Unhandled error: ${r.message}`,{"copilot_api.status_code":500,"http.path":e.req.path,"copilot_api.error_type":r.name}),jt({route:e.req.path,statusCode:500,errorClass:r.name,signature:Tt({endpointType:_t(e.req.path),statusCode:500,upstreamErrorType:r.name,model:e.get("requestData")?.model}),model:e.get("requestData")?.model,upstreamErrorType:r.name,upstreamErrorMessage:r.message}),Vt(e,500,r.message),o.error(r);let a=Lt(e)?{type:"error",error:{type:"api_error",message:r.message}}:{error:{message:r.message,type:"error"}};return e.json(a,500)}const Xt=async()=>{let e=`${dt}/copilot_internal/v2/token`,t=X.timeoutMs,o=new AbortController,n=setTimeout(()=>o.abort(),t);try{let{response:t,span:n}=await Qe({spanName:"github GET /copilot_internal/v2/token",url:e,target:"copilot_token",headers:mt(X),signal:o.signal});try{if(!t.ok)throw new Dt("Failed to get Service token",t);return await t.json()}catch(e){throw We(n,e),e}finally{n.end()}}finally{clearTimeout(n)}};async function Zt(){let e=`${dt}/user`,t=X.timeoutMs,o=new AbortController,n=setTimeout(()=>o.abort(),t);try{let{response:t,span:n}=await Qe({spanName:"github GET /user",url:e,target:"github_user",headers:{authorization:`token ${X._t2}`,"content-type":"application/json",accept:"application/json"},signal:o.signal});try{if(!t.ok)throw new Dt("Failed to get GitHub user",t);return await t.json()}catch(e){throw We(n,e),e}finally{n.end()}}finally{clearTimeout(n)}}let Qt=null;function eo(){return Qt||=Xt().then(({token:e})=>{X._t1=e,o.debug("Service token refreshed on upstream 401")}).finally(()=>{Qt=null}),Qt}const to=async()=>{let e=`${lt(X)}/models`,t=ct(X),o=X.timeoutMs,n=new AbortController,r=Ht(n,o);try{let{response:o,span:r}=await Qe({spanName:"copilot GET /models",url:e,target:"models",headers:t,signal:n.signal});try{if(!o.ok)throw new Dt("Failed to get models",o);let e=await o.json();return r.setAttribute("copilot_api.models_count",e.data.length),e}catch(e){throw We(r,e),e}finally{r.end()}}finally{clearTimeout(r)}};const oo=e=>new Promise(t=>{setTimeout(t,e)}),no=e=>null==e;async function ro(){X.models=await(async()=>{try{return await to()}catch(e){if(e instanceof Dt&&401===e.response.status)return await eo(),to();throw e}})()}const ao=()=>{X._v1="1.135.0-insider"};var io=class extends Error{constructor(e){super(e),this.name="AuthorizationError"}};let so,lo,co,uo,po,mo=!1;function fo(){return ho()?po:void 0}function ho(){return void 0!==po&&Date.now()-po.at<6e4}function go(e){let{span:t,error:n,reason:r,refreshStart:a,attempt:i}=e,s=n.response.status,l=401===s?"Auth token is invalid or expired":"GitHub Copilot subscription not found or not active";X._t1=void 0,po={status:s,message:l,at:Date.now()},clearInterval(so),so=void 0,o.error(`Token refresh received terminal HTTP ${s} — ${l}. Scheduled refresh halted. Re-authenticate to resume.`),Ae.add(1,{reason:r,success:"false"}),Se.add(1,{reason:r}),t.setAttribute("copilot_api.token_refresh.success",!1),t.setAttribute("copilot_api.token_refresh.terminal_status",s),t.setStatus({code:c.ERROR,message:n.message}),t.recordException(n),Fe.record(performance.now()-a,{reason:r}),Ke(_.ERROR,"ERROR",`Token refresh terminated — HTTP ${s} (${l})`,{"copilot_api.token_refresh.reason":r,"copilot_api.token_refresh.attempt":i,"copilot_api.token_refresh.terminal_status":s})}function _o(e){let{span:t,error:n,reason:r,refreshStart:a,maxRetries:i}=e;X._t1=void 0,o.error("All token refresh attempts failed. Stale token has been cleared — next request will trigger re-authentication or fail with a clear 'no token' error.");let s=n instanceof Error?n:Error(String(n));t.setAttribute("copilot_api.token_refresh.success",!1),t.setStatus({code:c.ERROR,message:s.message}),t.recordException(s),Se.add(1,{reason:r}),Fe.record(performance.now()-a,{reason:r}),Ke(_.ERROR,"ERROR",`Token refresh failed after ${i} attempts (${r})`,{"copilot_api.token_refresh.reason":r,"copilot_api.token_refresh.attempts":i})}const yo=async(e=5,t=1e3,n="scheduled")=>mo?(o.debug("Token refresh already in progress, coalescing"),lo):(mo=!0,lo=he.startActiveSpan("copilot_api.token.refresh",async r=>{let a=performance.now();r.setAttribute("copilot_api.token_refresh.reason",n),r.setAttribute("copilot_api.token_refresh.max_retries",e);try{for(let i=1;i<=e;i++)try{r.setAttribute("copilot_api.token_refresh.attempt",i),o.debug(`Refreshing Service token (${n}, attempt ${i}/${e})`);let{token:t}=await Xt();return X._t1=t,po=void 0,o.debug("Service token refreshed successfully"),X.showToken&&o.info("Refreshed Service token:",t),r.setAttribute("copilot_api.token_refresh.success",!0),Ae.add(1,{reason:n,success:"true"}),Fe.record(performance.now()-a,{reason:n}),void Ke(_.INFO,"INFO",`Token refreshed successfully (${n})`,{"copilot_api.token_refresh.reason":n,"copilot_api.token_refresh.attempt":i})}catch(s){if(s instanceof Dt&&(401===s.response.status||403===s.response.status))return void go({span:r,error:s,reason:n,refreshStart:a,attempt:i});let l=i===e;if(o.error(`Failed to refresh Service token (attempt ${i}/${e}):`,s),Ae.add(1,{reason:n,success:"false"}),l)return void _o({span:r,error:s,reason:n,refreshStart:a,maxRetries:e});let c=t*2**(i-1);o.debug(`Retrying token refresh in ${c}ms...`),await new Promise(e=>setTimeout(e,c))}}finally{r.end(),mo=!1,lo=void 0}}),lo);async function ko(){return!!X._t1||!ho()&&(await yo(3,250,"on-demand"),!!X._t1)}async function wo(e){try{let t=await a.readFile(K.GITHUB_TOKEN_PATH,"utf8");if(t&&!e?.force)return X._t2=t,X.showToken&&o.info("Auth token:",t),void await bo();o.info("Authentication required");let n=await async function(){let e=new AbortController,t=X.timeoutMs,o=setTimeout(()=>{e.abort()},t);try{let t=await fetch(`${ft}/login/device/code`,{method:"POST",headers:{"content-type":"application/json",accept:"application/json"},body:JSON.stringify({client_id:ht,scope:gt}),signal:e.signal});if(!t.ok)throw new Dt("Failed to get device code",t);return await t.json()}finally{clearTimeout(o)}}();o.debug("Device code response:",n),o.info(`Please enter the code "${n.user_code}" at ${n.verification_uri}`);try{m.writeSync(n.user_code),o.success("Code copied to clipboard — opening browser...")}catch{o.info("Open the link above and enter the code to authenticate")}!function(e){try{let t,o=g.platform;t="darwin"===o?"open":"win32"===o?"start":"xdg-open",f(t,[e],()=>{})}catch{}}(n.verification_uri);let r=await async function(e){let t=1e3*(e.interval+1);o.debug(`Polling access token with interval of ${t}ms`),o.start("Waiting for authorization...");let n=Date.now(),r=1e3*e.expires_in;for(;;){if(Date.now()-n>=r)throw new io("Authorization timed out — the code expired. Please run the command again.");let a=new AbortController,i=X.timeoutMs,s=setTimeout(()=>{a.abort()},i);try{let n=await fetch(`${ft}/login/oauth/access_token`,{method:"POST",headers:ot(),body:JSON.stringify({client_id:ht,device_code:e.device_code,grant_type:"urn:ietf:params:oauth:grant-type:device_code"}),signal:a.signal});if(!n.ok){await oo(t),o.error("Failed to poll access token:",await n.text());continue}let r=await n.json();if(o.debug("Polling access token response:",r),r.error){if("expired_token"===r.error)throw new io("Authorization timed out — the code expired. Please run the command again.");if("access_denied"===r.error)throw new io("Authorization was denied. Please run the command again and approve the request.");"authorization_pending"!==r.error&&"slow_down"!==r.error&&o.warn(`Unexpected auth error: ${r.error}`),await oo(t);continue}if(r.access_token)return r.access_token;await oo(t)}catch(e){if(e instanceof io)throw e;if(e instanceof Error&&"AbortError"===e.name){o.error("Access token polling timed out"),await oo(t);continue}throw e}finally{clearTimeout(s)}}}(n);await(e=>a.writeFile(K.GITHUB_TOKEN_PATH,e,{mode:384}))(r),X._t2=r,X.showToken&&o.info("Auth token:",r),await bo()}catch(e){throw e instanceof Dt?(o.error("Failed to get Auth token:",await e.response.json()),e):(o.error("Failed to get Auth token:",e),e)}}async function bo(){let e=await Zt();o.success(`Authenticated as ${e.login}`)}async function vo(e){e.verbose&&(o.level=5,o.info("Verbose logging enabled")),X.showToken=e.showToken,await W(),await wo({force:!0}),console.log([""," Get started:",""," $ npx copilot-api-node20@latest start --claude-code"," $ npx copilot-api-node20@latest start --codex",""," Full docs: https://www.npmjs.com/package/copilot-api-node20",""].join("\n")),process.exit(0)}const To=e({meta:{name:"auth",description:"Run authentication flow"},args:{verbose:{alias:"v",type:"boolean",default:!1,description:"Enable verbose logging"},"show-token":{type:"boolean",default:!1,description:"Show token on auth"}},run:({args:e})=>vo({verbose:e.verbose,showToken:e["show-token"]})}),$o=async()=>{let e=`${dt}/copilot_internal/user`,t=X.timeoutMs,o=new AbortController,n=setTimeout(()=>o.abort(),t);try{let{response:t,span:n}=await Qe({spanName:"github GET /copilot_internal/user",url:e,target:"usage",headers:mt(X),signal:o.signal});try{if(!t.ok)throw new Dt("Failed to get usage",t);return await t.json()}catch(e){throw We(n,e),e}finally{n.end()}}finally{clearTimeout(n)}},xo=e({meta:{name:"check-usage",description:"Show current usage/quota information"},async run(){await W(),await wo();try{let e=await $o(),t=e.quota_snapshots.premium_interactions,n=t.entitlement,r=n-t.remaining,a=n>0?r/n*100:0,i=t.percent_remaining;function s(e,t){if(!t)return`${e}: N/A`;let o=t.entitlement,n=o-t.remaining,r=o>0?n/o*100:0,a=t.percent_remaining;return`${e}: ${n}/${o} used (${r.toFixed(1)}% used, ${a.toFixed(1)}% remaining)`}let l=`Premium: ${r}/${n} used (${a.toFixed(1)}% used, ${i.toFixed(1)}% remaining)`,c=s("Chat",e.quota_snapshots.chat),u=s("Completions",e.quota_snapshots.completions);o.box(`Usage (plan: ${e.copilot_plan})\nQuota resets: ${e.quota_reset_date}\n\nQuotas:\n ${l}\n ${c}\n ${u}`)}catch(p){o.error("Failed to fetch usage:",p),process.exit(1)}}}),Ao=N(f);async function So(){let e="win32"===g.platform?"where.exe":"which";try{return await Ao(e,["tailscale"]),!0}catch{return!1}}async function Eo(){try{let{stdout:e}=await Ao("tailscale",["status","--self","--json"]);return JSON.parse(e).Self}catch{return}}function Co(e){return e.replace(/\.$/,"")}async function Oo(){let e=await Eo();if(e?.Online)return Co(e.DNSName)}const Io=N(f),Po=e=>`[1m${e}[0m`,Ro=e=>`[2m${e}[0m`,No=e=>`[36m${e}[0m`,qo=e=>`[32m${e}[0m`,jo=e=>`[31m${e}[0m`,Do=e=>`[33m${e}[0m`,Mo=Ro(" ─────────────────────────────────────────────────────────────"),Ho=s.join(K.APP_DIR,"certs","tailscale"),Bo=s.join(Ho,"cert.pem"),Fo=s.join(Ho,"key.pem"),Uo={certDir:Ho,certPath:Bo,keyPath:Fo};function Lo(){switch(g.platform){case"darwin":return[` ${Ro("Install Tailscale for macOS:")}`,` ${No("https://tailscale.com/download/mac")}`,` ${Ro("(Use the Mac App Store or .pkg download — not brew)")}`,"",` ${Ro("After installing, open the Tailscale app and sign in.")}`,` ${Ro("Then re-run this command.")}`].join("\n");case"linux":return[` ${Ro("Install Tailscale for Linux:")}`,` ${No("curl -fsSL https://tailscale.com/install.sh | sh")}`,` ${No("sudo tailscale up")}`,` ${Ro("or")} ${No("https://tailscale.com/download/linux")}`].join("\n");case"win32":return[` ${Ro("Install Tailscale for Windows:")}`,` ${No("https://tailscale.com/download/windows")}`,"",` ${Ro("After installing, open the Tailscale app and sign in.")}`].join("\n");default:return` ${Ro("Install Tailscale:")} ${No("https://tailscale.com/download")}`}}function Go(){let e=[` ${jo("Tailscale is not running.")}`];return"darwin"===g.platform?e.push(` ${Ro("Open the Tailscale app from Applications and sign in.")}`,` ${Ro("Download:")} ${No("https://tailscale.com/download/mac")}`):"win32"===g.platform?e.push(` ${Ro("Open the Tailscale app and sign in.")}`,` ${Ro("Download:")} ${No("https://tailscale.com/download/windows")}`):e.push(` ${Ro("Connect with:")} ${No("sudo tailscale up")}`),e.push("",` ${Ro("Then re-run this command.")}`),e.join("\n")}async function zo(){try{return await a.access(Bo),await a.access(Fo),!0}catch{return!1}}function Jo(e){console.log(""),console.log(Mo),console.log(` ${Po("Claude Cowork Setup")} ${Ro("— Diagnostic")}`),console.log(Mo),console.log("");for(let t of function(e){let t=[];for(let[o,n]of Object.entries(e)){let e;e="ok"===n.status?qo("✅"):"missing"===n.status?jo("❌"):Do("❓");let r=n.detail?Ro(` ${n.detail}`):"";t.push(` ${e} ${o}${r}`)}return t}(e))console.log(t);console.log("");let t=Object.values(e).filter(e=>"missing"===e.status);0===t.length?console.log(` ${qo("All checks passed.")}`):console.log(` ${jo(`${t.length} issue(s).`)} Run ${No("copilot-api cowork-setup install")} to fix.`),console.log("")}const Ko={alias:"y",type:"boolean",default:!1,description:"Skip confirmation prompts (non-interactive mode)"},Wo=e({meta:{name:"cowork-setup",description:"Set up Tailscale-based HTTPS for Claude Cowork to reach the proxy."},subCommands:{doctor:e({meta:{name:"doctor",description:"Diagnose Tailscale + cert status"},async run(){await async function(){let e={},t=await So();if(e["tailscale-installed"]=t?{status:"ok"}:{status:"missing",detail:"tailscale not found in PATH"},!t)return Jo(e),console.log(""),console.log(Lo()),void console.log("");let o=await Eo();if(!o||!o.Online)return e["tailscale-running"]={status:"missing",detail:"not connected"},Jo(e),console.log(Go()),void console.log("");let n=Co(o.DNSName);e["tailscale-running"]={status:"ok",detail:n};let r=await zo();e["tailscale-cert"]=r?{status:"ok",detail:Bo}:{status:"missing",detail:'Run "copilot-api cowork-setup install" to generate'},r&&(e.ready={status:"ok",detail:`https://${n}:<port>`}),Jo(e)}(),g.exit(0)}}),install:e({meta:{name:"install",description:"Generate a Tailscale TLS certificate for Cowork (interactive, or pass --yes)"},args:{yes:Ko},async run({args:e}){await async function(e){if(console.log(""),console.log(Mo),console.log(` ${Po("Claude Cowork Setup")} ${Ro("— Install")}`),console.log(Mo),console.log(""),!await So())return console.log(` ${jo("Tailscale is not installed.")}`),console.log(""),console.log(Lo()),console.log(""),console.log(` ${Ro("After installing, run")} ${No("tailscale up")} ${Ro("to connect, then re-run this command.")}`),void console.log("");let t=await Eo();if(!t||!t.Online)return console.log(Go()),void console.log("");let n=Co(t.DNSName);if(console.log(` ${Ro("Tailscale hostname:")} ${Po(n)}`),console.log(""),console.log(` ${Po("Generating TLS certificate via Tailscale…")}`),console.log(` ${Ro("This requests a real Let's Encrypt cert for your Tailscale hostname.")}`),console.log(` ${No(`$ tailscale cert --cert-file ${Bo} --key-file ${Fo} ${n}`)}`),console.log(""),e||await o.prompt("Generate the certificate?",{type:"confirm",initial:!0})){try{await a.mkdir(Ho,{recursive:!0}),o.start("Generating certificate (this may take a few seconds)…"),await Io("tailscale",["cert","--cert-file",Bo,"--key-file",Fo,n]),console.log(` ${qo("✓ Certificate generated")}`)}catch(e){let t=e instanceof Error?e.message:String(e);return void o.error(`Failed to generate cert: ${t}`)}console.log(""),console.log(Mo),console.log(` ${Po("Next steps")}`),console.log(Mo),console.log(""),console.log(` ${Po("1.")} Start the proxy:`),console.log(` ${No("copilot-api start --claude-cowork")}`),console.log(""),console.log(` ${Po("2.")} In Cowork ${Ro("→")} Settings ${Ro("→")} Inference Provider, set:`),console.log(` ${Po("inferenceGatewayBaseUrl")} = ${No(`https://${n}:<port>`)}`),console.log(` ${Ro("(replace <port> with the port you start the proxy on, default 4141)")}`),console.log(""),console.log(` ${Po("3.")} Restart Cowork ${Ro("(Cmd+Q and reopen)")}`),console.log(""),console.log(` ${Ro("For Cowork's own configuration docs, see:")}`),console.log(` ${No("https://claude.com/docs/cowork/3p/installation")}`),console.log("")}else o.info("Skipped.")}(e.yes),g.exit(0)}}),revert:e({meta:{name:"revert",description:"Remove the generated Tailscale cert files"},args:{yes:Ko},async run({args:e}){await async function(e){if(console.log(""),console.log(Mo),console.log(` ${Po("Claude Cowork Setup")} ${Ro("— Revert")}`),console.log(Mo),console.log(""),!await zo())return console.log(` ${Ro("No Tailscale cert found. Nothing to revert.")}`),void console.log("");if(console.log(` ${Po("Remove Tailscale cert files:")}`),console.log(` ${Ro(Bo)}`),console.log(` ${Ro(Fo)}`),console.log(""),e||await o.prompt("Delete these files?",{type:"confirm",initial:!0})){try{await a.rm(Ho,{recursive:!0}),console.log(` ${qo("✓ Cert files removed.")}`)}catch(e){let t=e instanceof Error?e.message:String(e);o.warn(`Could not remove: ${t}`)}console.log(""),console.log(` ${Ro("Don't forget to update Cowork's inferenceGatewayBaseUrl setting.")}`),console.log("")}else o.info("Skipped.")}(e.yes),g.exit(0)}})}});function Vo(e){let t=e,o=String.fromCodePoint(27),n=t.split(o);if(n.length>1){t=n[0];for(let e=1;e<n.length;e++){let r=n[e],a=r.match(/^\[[0-9;]*[a-z]/i);t+=a?r.slice(a[0].length):o+r}}return t.replaceAll(/[\u200B-\u200D\uFEFF]/g,"").replaceAll(/[\u2060-\u2064]/g,"").replaceAll(/[\u206A-\u206F]/g,"").replaceAll(/[\u180E\u2000-\u200A\u2028\u2029\u202F\u205F\u3000]/g,"").replaceAll(/[\uFFF0-\uFFFF]/g,"").replaceAll(/[\x00-\x08\v\f\x0E-\x1F]/g,"")}function Yo(e){if("string"==typeof e)return Vo(e);if(Array.isArray(e))return e.map(e=>Yo(e));if(e&&"object"==typeof e){let t={},o="thinking"===e.type;for(let[n,r]of Object.entries(e))t[n]=!o||"thinking"!==n&&"signature"!==n?Yo(r):r;return"object"===t.type&&!("properties"in t)&&(t.properties={}),t}return e}const Xo="x-copilot-api-self-test",Zo=R();const Qo=/\b(?:haiku|mini|flash|nano|small|lite)\b/i;function en(e){return!e.id.startsWith("text-embedding")&&"embeddings"!==e.capabilities.type&&!function(e){let t=e.supported_endpoints;return t?t.includes("/responses")&&!t.includes("/chat/completions"):/gpt-[\d.]+-codex/i.test(e.id)}(e)&&!function(e){return"disabled"===e.policy?.state}(e)}function tn(e){try{!function(e){let{c:t,start:o,span:n}=e,r=t.get("requestData"),a=t.res.status,i=r?.model??"unknown",s=r?.streaming??!1,l=Math.round(performance.now()-o);if(n.setAttribute("http.status_code",a),n.setAttribute("copilot_api.model",i),n.setAttribute("copilot_api.streaming",s),n.setAttribute("copilot_api.duration_ms",l),r?._d1&&n.setAttribute("copilot_api.copilot_duration_ms",r._d1),r?.tokenUsage){let e=r.tokenUsage;n.setAttribute("copilot_api.input_tokens",e.inputTokens),n.setAttribute("copilot_api.output_tokens",e.outputTokens),n.setAttribute("copilot_api.total_tokens",e.totalTokens),e.cachedTokens&&n.setAttribute("copilot_api.cached_tokens",e.cachedTokens)}t.res.headers.forEach((e,t)=>{let o=t.toLowerCase();Xe.has(o)||n.setAttribute(`http.response.header.${o}`,e)}),a>=400&&n.setStatus({code:c.ERROR,message:`HTTP ${a}`})}(e)}catch(e){o.warn("Error enriching span during finalization:",e)}try{!function(e){let{c:t,start:o,method:n,path:r,endpointType:a,requestId:i}=e;if(t.get("isSelfTest"))return;let s=Math.round(performance.now()-o),l=t.get("requestData"),c=t.res.status,u=l?.model??"unknown",p=l?.streaming??!1,d={method:n,path:r,status_code:String(c),model:u,streaming:String(p),endpoint_type:a};if(ye.add(1,d),je.record(s,d),c>=400&&ke.add(1,{method:n,path:r,status_code:String(c),error_type:c>=500?"server_error":"client_error"}),l?.tokenUsage){let e=l.tokenUsage,t={model:u,endpoint_type:a};e.inputTokens&&(we.add(e.inputTokens,t),Le.record(e.inputTokens,t)),e.outputTokens&&(be.add(e.outputTokens,t),Ge.record(e.outputTokens,t)),e.cachedTokens&&ve.add(e.cachedTokens,{model:u})}!p&&l?.tokenUsage&&ce.executeCompletion(i)}(e)}catch(e){o.warn("Error recording metrics during finalization:",e)}try{e.span.end()}catch{}}const on=1048576;const nn=async()=>he.startActiveSpan("copilot_api.approval.await",async e=>{let t=performance.now();try{let n=await o.prompt("Accept incoming request?",{type:"confirm"}),r=performance.now()-t;if(e.setAttribute("copilot_api.approval.wait_duration_ms",r),Je.record(r),!n)throw e.setAttribute("copilot_api.approval.result","rejected"),Pe.add(1,{result:"rejected"}),new Dt("Request rejected",Response.json({message:"Request rejected"},{status:403}));e.setAttribute("copilot_api.approval.result","approved"),Pe.add(1,{result:"approved"})}finally{e.end()}});function rn(e){let t=e.prompt_tokens||0,o=e.completion_tokens||0;return{inputTokens:t,outputTokens:o,totalTokens:e.total_tokens||t+o,cachedTokens:e.prompt_tokens_details?.cached_tokens,acceptedPredictionTokens:e.completion_tokens_details?.accepted_prediction_tokens,rejectedPredictionTokens:e.completion_tokens_details?.rejected_prediction_tokens}}function an(e,t){void 0!==t.prompt_tokens&&e.setAttribute("copilot_api.input_tokens",t.prompt_tokens),void 0!==t.completion_tokens&&e.setAttribute("copilot_api.output_tokens",t.completion_tokens),void 0!==t.total_tokens&&e.setAttribute("copilot_api.total_tokens",t.total_tokens)}const sn=[{pattern:/haiku/i,family:"haiku"},{pattern:/sonnet[.-]?4[.-]6/i,family:"sonnet-4.6"},{pattern:/(sonnet-4[.-]5|[.-]?3[.-]5[.-]?sonnet|[.-]?3[.-]7[.-]?sonnet)/i,family:"sonnet-4.5"},{pattern:/sonnet-4(?![.-]5|[.-]6|[.-]1)/i,family:"sonnet-4"},{pattern:/opus[.-]?4[.-]7/i,family:"opus-4.7"},{pattern:/opus[.-]?4[.-]6/i,family:"opus-4.6"},{pattern:/opus[.-]?4[.-]5/i,family:"opus-4.5"},{pattern:/opus/i,family:"opus"}],ln="claude-haiku-4.5",cn={haiku:ln,"sonnet-4.6":"claude-sonnet-4.6","sonnet-4.5":"claude-sonnet-4.5","sonnet-4":"claude-sonnet-4","opus-4.7":"claude-opus-4.7","opus-4.6":"claude-opus-4.6","opus-4.5":"claude-opus-4.5",opus:"claude-opus-4.5"};function un(e,t){let o=function(e){return e.startsWith("anthropic/")?e.slice(10):e}(e),[n,r]=function(e){let t=e.lastIndexOf("["),o=e.lastIndexOf("]");return-1!==t&&o===e.length-1&&o>t?[e.slice(0,t),e.slice(t+1,o)]:[e,null]}(o);if(t.includes(o))return o;if(r){let e=`${n}-${r}`.replaceAll(/(\d)-(\d)\b/g,"$1.$2");if(t.includes(e))return e}let a=function(e){for(let t of sn)if(t.pattern.test(e))return t.family;return null}(n);if(!a)return null;let i=n.replace(/-\d{8}(?::.*)?$/,""),s=r?`-${r}`:"";for(let e of t){let t=e.replace(/-\d{8}(?::.*)?$/,""),o=`${i}${s}`.toLowerCase().replaceAll(/(\d)-(\d)\b/g,"$1.$2");if(t.toLowerCase().replaceAll(/(\d)-(\d)\b/g,"$1.$2")===o)return e}return function(e,t,o=null){let n=cn[e];if(!n)return null;if(o){let e=`${n}-${o}`;if(t.includes(e))return e}if(t.includes(n))return n;if("sonnet-4.5"===e)for(let e of["claude-3.5-sonnet"]){let n=o?`${e}-${o}`:e;if(t.includes(n))return n}return null}(a,t,r)}const pn=new Map([["none",0],["low",1],["medium",2],["high",3],["xhigh",4]]);function dn(e,t){if(!e||!t||0===t.length)return null;let o=function(e){return"max"===e?"xhigh":e}(e);if(t.includes(o))return o;let n=pn.get(o);if(void 0===n)return t[0]??null;let r=null,a=1/0;for(let e of t){let t=pn.get(e);if(void 0===t)continue;let o=Math.abs(t-n);o<a&&(a=o,r=e)}return r}var mn=class extends Error{statusCode;constructor(e,t=400){super(e),this.name="ModelValidationError",this.statusCode=t}};function fn(e){if(!e||"string"!=typeof e)throw new mn("Model name is required and must be a string");if(!X.models?.data)throw new mn("Models not available. Please try again later.",503);let t=X.models.data.map(e=>e.id);if(t.includes(e))return e;let o=un(e,t);if(!o)throw $e.add(1,{requested_model:e}),new mn(`Invalid model: '${e}'. Available services: ${t.join(", ")}`);return o}async function hn(e){if(void 0===e.rateLimitSeconds)return;let t=e.rateLimitSeconds;return he.startActiveSpan("copilot_api.rate_limit.check",async n=>{try{let r=Date.now();if(n.setAttribute("copilot_api.rate_limit.configured_seconds",t),!e.lastRequestTimestamp)return e.lastRequestTimestamp=r,void n.setAttribute("copilot_api.rate_limit.action","allowed");let a=(r-e.lastRequestTimestamp)/1e3;if(n.setAttribute("copilot_api.rate_limit.elapsed_seconds",a),a>t)return e.lastRequestTimestamp=r,void n.setAttribute("copilot_api.rate_limit.action","allowed");let i=Math.ceil(t-a);if(n.setAttribute("copilot_api.rate_limit.wait_seconds",i),!e.rateLimitWait)throw n.setAttribute("copilot_api.rate_limit.action","rejected"),Te.add(1,{action:"rejected",source:"local"}),o.warn(`Rate limit exceeded. Need to wait ${i} more seconds.`),new Dt("Rate limit exceeded",Response.json({message:"Rate limit exceeded"},{status:429}));let s=1e3*i;n.setAttribute("copilot_api.rate_limit.action","waited"),Te.add(1,{action:"waited",source:"local"}),He.record(s,{source:"local"}),o.warn(`Rate limit reached. Waiting ${i} seconds before proceeding...`),await oo(s),e.lastRequestTimestamp=r,o.info("Rate limit wait completed, proceeding with request")}finally{n.end()}})}function gn(e){if(e instanceof Dt){let t=e.response.status;return{type:529===t?"overloaded_error":`upstream_error_${t}`,message:`Upstream error (${t}) while streaming response`}}return{type:"api_error",message:"Stream interrupted before completion"}}async function _n(e,t){let{type:n,message:r}=gn(t);try{await e.writeSSE({event:"error",data:JSON.stringify({type:"error",error:{type:n,message:r}})})}catch(e){o.debug("Failed to emit Anthropic stream error frame:",e)}}async function yn(e,t){let{type:n,message:r}=gn(t);try{await e.writeSSE({event:"error",data:JSON.stringify({error:{message:r,type:n}})})}catch(e){o.debug("Failed to emit OpenAI stream error frame:",e)}}function kn(e){if("number"==typeof e){if(!Number.isFinite(e))return null;let t=Math.floor(e);return t>0?t:null}if("string"==typeof e){let t=e.trim();if(!t)return null;let o=Number(t);if(!Number.isFinite(o))return null;let n=Math.floor(o);return n>0?n:null}return null}function wn(e,t,o){return Math.min(Math.max(e,t),o)}function bn(e,t=0){if(t>5||!e||"object"!=typeof e)return null;let o=e.error;if(!o||"object"!=typeof o)return null;let n=o.code;if("string"==typeof n)return n;let r=o.message;if("string"!=typeof r)return null;try{return bn(JSON.parse(r),t+1)}catch{return null}}function vn(e,t){let o=e?.data.find(e=>e.id===t);if(!o)return null;let n=kn(o.capabilities.supports.min_thinking_budget),r=kn(o.capabilities.supports.max_thinking_budget);return!n||!r||r<=n?null:{bounds:{min:n,max:r-1},maxOutputTokens:kn(o.capabilities.limits?.max_output_tokens)??void 0}}function Tn(e){let{config:t}=e,o=t.bounds.min,n=t.bounds.max,r=wn(kn(e.requestedBudget)??o,o,n),a=kn(e.maxTokens);if(a||=r+1,t.maxOutputTokens&&a>t.maxOutputTokens&&(a=t.maxOutputTokens),a<=r){let e=Math.min(r,a-1);if(e>=o)r=e;else{let e=o+1;if(t.maxOutputTokens&&e>t.maxOutputTokens)return{thinkingBudget:null,maxTokens:a};a=e,r=o}}return a<=r?{thinkingBudget:null,maxTokens:a}:{thinkingBudget:r,maxTokens:a}}function $n(e,t){if(no(e.thinking_budget))return e;let o=vn(t,e.model);if(!o)return{...e,thinking_budget:void 0};let n=Tn({requestedBudget:e.thinking_budget,maxTokens:e.max_tokens,config:o});return null===n.thinkingBudget?{...e,max_tokens:n.maxTokens,thinking_budget:void 0}:{...e,max_tokens:n.maxTokens,thinking_budget:n.thinkingBudget}}function xn(e){return"invalid_thinking_budget"===bn(e)}async function An(e){let{payload:t,error:o,models:n,errorBodyText:r}=e;if(no(t.thinking_budget)||!(o instanceof Error))return null;let a,i,s=o;if(!(s.response instanceof Response)||400!==s.response.status)return null;if(void 0!==r)a=r;else try{a=await s.response.clone().text()}catch{return null}try{i=JSON.parse(a)}catch{return null}if(!xn(i))return null;let l=vn(n,t.model);return l?function(e,t){let o=Tn({requestedBudget:e.thinking_budget,maxTokens:e.max_tokens,config:t});if(null===o.thinkingBudget)return{...e,max_tokens:o.maxTokens,thinking_budget:void 0};let n=o.thinkingBudget,r=kn(e.thinking_budget);if(r&&r===o.thinkingBudget){let e=n+1;e<=t.bounds.max&&(!o.maxTokens||e<o.maxTokens)&&(n=e)}let a=o.maxTokens;if((!a||a<=n)&&(a=n+1),t.maxOutputTokens&&a>t.maxOutputTokens){if(!(t.maxOutputTokens>n))return{...e,max_tokens:t.maxOutputTokens,thinking_budget:void 0};a=t.maxOutputTokens}return{...e,max_tokens:a,thinking_budget:n}}(t,l):{...t,thinking_budget:void 0}}function Sn(e,t){let o=!1;return()=>{if(o)return;o=!0;let n=e.get("requestData")||{};n.upstreamTtfbMs=performance.now()-t,e.set("requestData",n)}}function En(e,t){let o=e.get("requestData")||{};o.upstreamTotalMs=performance.now()-t,o._d1=o.upstreamTotalMs,e.set("requestData",o)}const Cn=new Map,On=new Map,In=new Set;let Pn,Rn,Nn;function qn(e){return!e.closed&&!e.destroyed}function jn(e){o.debug(`Creating HTTP/2 client for ${e}`);let t=new C(e,{allowH2:!0,pipelining:0,keepAliveTimeout:6e4,initialWindowSize:4194304,connectionWindowSize:16777216});return Cn.set(t,Date.now()),Ne.add(1,{event:"created",origin:e}),Ke(_.INFO,"INFO",`HTTP/2 client created for ${e}`,{"copilot_api.h2.event":"created","copilot_api.h2.origin":e}),t.on("connect",()=>{o.debug(`HTTP/2 client connected to ${e}`)}),t.on("error",t=>{o.debug(`HTTP/2 client error for ${e}:`,t.message)}),t.on("disconnect",(n,r,a)=>{o.debug(`HTTP/2 client disconnected from ${e}:`,a.message);let i=In.has(t);Ne.add(1,{event:"goaway",origin:e}),Ke(i?_.WARN:_.DEBUG,i?"WARN":"DEBUG",`HTTP/2 client disconnected from ${e}: ${a.message}`,{"copilot_api.h2.event":"goaway","copilot_api.h2.origin":e,"copilot_api.h2.error":a.message}),On.delete(t),In.delete(t),Cn.delete(t),qn(t)&&t.close().catch(e=>{o.debug("Error closing GOAWAY'd HTTP/2 client:",e)})}),t}function Dn(e){if(!X.connectivity.h2)return;Pn&&Pn!==e&&function(){for(let e of[...On.keys(),...In])qn(e)&&e.close().catch(e=>{o.debug("Error closing HTTP/2 pool entry:",e)});On.clear(),In.clear(),Cn.clear()}(),Pn=e;let t=Date.now();for(let[n]of On)if(t-(Cn.get(n)??0)>=6e5)On.delete(n),Cn.delete(n),qn(n)&&n.close().catch(e=>{o.debug("Error closing rotated HTTP/2 client:",e)}),Ne.add(1,{event:"rotated",origin:e}),Ke(_.INFO,"INFO",`HTTP/2 client rotated for ${e} (max lifetime reached)`,{"copilot_api.h2.event":"rotated","copilot_api.h2.origin":e});else{if(qn(n))return On.delete(n),In.add(n),n;On.delete(n),Cn.delete(n)}let n=jn(e);return In.add(n),n}function Mn(e){e&&In.delete(e)&&(qn(e)?On.set(e,Date.now()):Cn.delete(e))}function Hn(){Nn||(Nn=setInterval(()=>{!function(){let e=Date.now(),t=X.connectivity.h2Keepalive,n=On.size;for(let[r,a]of On)e-a<6e4||t&&n<=1||(On.delete(r),Cn.delete(r),n--,qn(r)&&r.close().catch(e=>{o.debug("Error closing idle HTTP/2 client:",e)}),Ne.add(1,{event:"idle_reaped",origin:Pn??""}),Ke(_.INFO,"INFO",`HTTP/2 idle connection reaped for ${Pn}`,{"copilot_api.h2.event":"idle_reaped","copilot_api.h2.origin":Pn??""}))}()},3e4),Nn.unref())}function Bn(){Rn||(o.debug("Starting HTTP/2 keepalive (every 45s)"),Rn=setInterval(()=>{(async function(){if(0===On.size&&0===In.size){if(Pn){let e=jn(Pn);On.set(e,Date.now())}return}let e=[...On.keys()];for(let t of e)On.delete(t);await Promise.allSettled(e.map(async e=>{if(qn(e))try{let{statusCode:t,body:n}=await e.request({path:"/models",method:"GET",headers:ct(X)});await n.dump(),Re.add(1,{result:"success"}),o.debug(`HTTP/2 keepalive: GET /models → ${t}`),On.set(e,Date.now())}catch(t){Re.add(1,{result:"error"}),o.warn("HTTP/2 keepalive failed:",t instanceof Error?t.message:t),Ne.add(1,{event:"error",origin:Pn??""}),Cn.delete(e),qn(e)&&e.close().catch(e=>{o.debug("Error closing broken HTTP/2 client:",e)})}else Cn.delete(e)}))})().catch(e=>{o.debug("Unexpected error in HTTP/2 keepalive:",e)})},45e3),Rn.unref(),Hn())}function Fn(e){return function(e){if(!(e instanceof Error))return!1;let t=e.code;return(!t||"UND_ERR_SOCKET"===t)&&/GOAWAY/i.test(e.message)}(e)||function(e){if(!(e instanceof Error))return!1;let t=e.code;return"ECONNRESET"===t||(!t||"UND_ERR_SOCKET"===t)&&(/ECONNRESET/i.test(e.message)||/other side closed/i.test(e.message))}(e)||function(e){if(!(e instanceof Error))return!1;let t=e.code;return"UND_ERR_DESTROYED"===t||"UND_ERR_CLOSED"===t}(e)||function(e){return e instanceof Error&&"UND_ERR_CONNECT_TIMEOUT"===e.code}(e)}async function Un(){return new Promise(e=>setTimeout(e,100))}async function Ln(e,t,o){try{if(!e.ok)throw new Dt("Failed to create chat completions",e,{outgoingBody:o.outgoingBody,outgoingHeaders:o.outgoingHeaders});let n=await e.json();return n.id&&t.setAttribute("copilot_api.response.id",n.id),n.usage&&an(t,n.usage),n}catch(e){throw We(t,e),e}finally{t.end()}}const Gn=async e=>{let t=Yo(e);try{return await zn(t)}catch(e){if(e instanceof Dt&&401===e.response.status)return await eo(),zn(t);let n;if(e instanceof Dt)try{n=await e.response.clone().text()}catch{n=void 0}let r=await An({payload:t,error:e,models:X.models,errorBodyText:n});if(r)return e instanceof Dt&&void 0!==n&&o.warn(`Upstream rejected thinking_budget (status ${e.response.status}): ${n.slice(0,500)}`),o.warn("Adjusting thinking_budget payload and retrying once..."),await zn(Yo(r));throw e}},zn=async e=>{if(!X._t1)throw Error("Service token not found");let t=e.messages.some(e=>"string"!=typeof e.content&&e.content?.some(e=>"image_url"===e.type)),n=e.messages.some(e=>["assistant","tool"].includes(e.role)),r={...ct(X,t),"X-Initiator":n?"agent":"user"},a=lt(X),i=`${a}/chat/completions`,s=X.timeoutMs,l=function(e,t){if(!function(e,t){return(t?.data.find(t=>t.id===e)?.capabilities.family??e).startsWith("gpt-5")}(e.model,t))return{...e};let{max_tokens:o,stop:n,...r}=e;return null==o?{...r}:{...r,max_completion_tokens:o}}(e,X.models),c=JSON.stringify(l),u={"copilot_api.model":e.model,"copilot_api.streaming":!!e.stream,"copilot_api.timeout_ms":s,"copilot_api.has_tools":!!e.tools?.length,"copilot_api.tool_count":e.tools?.length??0,"copilot_api.message_count":e.messages.length,"copilot_api.max_tokens":e.max_tokens??0,"copilot_api.vision_enabled":t,"copilot_api.initiator":n?"agent":"user"};for(let t=0;t<=1;t++){let n=Dn(a),l=new AbortController,p=Ht(l,s);try{let{statusCode:o,headers:a,body:p,span:d}=await et({spanName:"copilot POST /chat/completions",url:i,target:"chat_completions",headers:r,body:c,signal:l.signal,headersTimeout:s,bodyTimeout:3*s,extraAttributes:{...u,"copilot_api.h2.retry_attempt":t},dispatcher:n}),m=new Response(p,{status:o,headers:a});if(e.stream){if(!m.ok)throw d.end(),new Dt("Failed to create chat completions",m,{outgoingBody:c,outgoingHeaders:r});return{events:M(m),span:d,release:()=>Mn(n)}}try{return await Ln(m,d,{outgoingBody:c,outgoingHeaders:r})}finally{Mn(n)}}catch(e){if(Mn(n),Fn(e)&&t<1){o.warn(`HTTP/2 connection error during chat completions, retrying (attempt ${t+1}): ${e instanceof Error?e.message:String(e)}`),await Un();continue}throw e}finally{clearTimeout(p)}}throw Error("Unexpected: exhausted GOAWAY retries without result")};function Jn(e,t){if(!e.data)return e;try{let o=JSON.parse(e.data);if(o.usage&&t(o.usage),void 0!==o.usage?.prompt_tokens_details?.cached_tokens)return{...e,data:JSON.stringify({...o,usage:{...o.usage,prompt_tokens_details:void 0}})}}catch(t){o.warn("Failed to parse streaming chunk:",e.data.slice(0,200),t)}return e}async function Kn(e){let t=!0===e.get("isSelfTest");t||await hn(X);let n=await e.req.json();o.debug("Request payload:",JSON.stringify(n).slice(-400));try{n=function(e){return he.startActiveSpan("copilot_api.model.validate",t=>{try{t.setAttribute("copilot_api.model.requested",e.model);let n=fn(e.model);return t.setAttribute("copilot_api.model.normalized",n),n===e.model?(t.setAttribute("copilot_api.model.was_mapped",!1),e):(t.setAttribute("copilot_api.model.was_mapped",!0),xe.add(1,{from_model:e.model,to_model:n}),o.debug(`Normalized model from '${e.model}' to '${n}'`),{...e,model:n})}finally{t.end()}})}(n)}catch(t){if(t instanceof mn)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_model"),e.json({error:{message:t.message,type:"invalid_request_error",code:"invalid_model"}},t.statusCode);throw t}if(e.set("requestData",{model:n.model,streaming:!!n.stream}),X.manualApprove&&!t&&await nn(),no(n.max_tokens)){let e=X.models?.data.find(e=>e.id===n.model);n={...n,max_tokens:e?.capabilities.limits?.max_output_tokens},o.debug("Set max_tokens to:",JSON.stringify(n.max_tokens))}n=$n(n,X.models),no(n.thinking_budget)||o.debug("Normalized thinking_budget to:",JSON.stringify(n.thinking_budget));let r=performance.now(),a=await Gn(n),i=performance.now()-r;if(De.record(i,{model:n.model,target:"chat_completions",streaming:String(!!n.stream)}),Wn(a)){let t=e.get("requestData")||{};return a.usage&&(t.tokenUsage=rn(a.usage)),t._d1=i,t.upstreamTtfbMs=i,t.upstreamTotalMs=i,e.set("requestData",t),o.debug("Non-streaming response:",JSON.stringify(a)),e.json(a)}let{events:s,span:l,release:c}=a;return D(e,async t=>{let o={value:null},a=0,u=performance.now(),p=Sn(e,r);try{try{for await(let r of s){p();let s=r;r.data&&"[DONE]"!==r.data&&(a++,Ie.add(1,{model:n.model,endpoint_type:"openai"}),s=Jn(r,t=>{o.value=t;let n=e.get("requestData")||{};n.tokenUsage=rn(t),n._d1=i,e.set("requestData",n)})),await t.writeSSE(s)}let l=performance.now()-u,c={model:n.model,endpoint_type:"openai"};if(Me.record(l,c),ze.record(a,c),En(e,r),o.value){let t=e.get("requestData")||{};t.tokenUsage||(t.tokenUsage=rn(o.value),t._d1=i,e.set("requestData",t))}}catch(o){throw Ve(l,e.get("requestSpan"),o),await yn(t,o),o}finally{o.value&&an(l,o.value),l.end(),c()}let d=e.get("requestId");d&&ce.executeCompletion(d)}finally{e.get("resolveStreamComplete")?.()}})}const Wn=e=>Object.hasOwn(e,"choices"),Vn=new q;Vn.post("/",async e=>{try{return await Kn(e)}catch(t){return await Yt(e,t)}});const Yn=new q;Yn.post("/",async e=>{try{let t=await e.req.json();try{t.model=fn(t.model)}catch(t){if(t instanceof mn)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_model"),e.json({error:{message:t.message,type:"invalid_request_error",code:"invalid_model"}},t.statusCode);throw t}e.set("requestData",{model:t.model});let o=performance.now(),n=await(async e=>{if(!X._t1)throw Error("Service token not found");let t=`${lt(X)}/embeddings`,o=ct(X),n=X.timeoutMs,r=new AbortController,a=Ht(r,n),i=JSON.stringify(e);try{let{response:n,span:a}=await Qe({spanName:"copilot POST /embeddings",url:t,target:"embeddings",method:"POST",headers:o,body:i,signal:r.signal,extraAttributes:{"copilot_api.model":e.model,"copilot_api.input_count":Array.isArray(e.input)?e.input.length:1}});try{if(!n.ok)throw new Dt("Failed to create embeddings",n,{outgoingBody:i,outgoingHeaders:o});return await n.json()}catch(e){throw We(a,e),e}finally{a.end()}}finally{clearTimeout(a)}})(t),r=performance.now()-o;De.record(r,{model:t.model,target:"embeddings",streaming:"false"});let a=e.get("requestData")||{};return a.tokenUsage=rn(n.usage),a._d1=r,e.set("requestData",a),e.json(n)}catch(t){return await Yt(e,t)}});const Xn=new q;let Zn=null,Qn=null;function er(e){return"type"in e&&"string"==typeof e.type&&e.type.startsWith("web_search")}function tr(e){return!er(e)}Xn.get("/",async e=>{let t,o=function(){let e=X._t1;if(!e)return"missing";try{let t=e.split(".");if(t.length<2)return"expired";let o=(t[1]??"").replaceAll("-","+").replaceAll("_","/"),n=JSON.parse(atob(o)),r="object"==typeof n&&n&&"exp"in n&&"number"==typeof n.exp?n.exp:void 0;return void 0!==r&&1e3*r<Date.now()?"expired":"valid"}catch{return"expired"}}(),n=await async function(){let e=Date.now(),t=Zn;return t&&e-t.timestamp<3e4?{result:t.result}:Qn||(Qn=(async()=>{let e=new AbortController,t=setTimeout(()=>e.abort(),5e3),o=performance.now();try{let t=`${lt(X)}/models`,n=await fetch(t,{method:"GET",headers:ct(X),signal:e.signal}),r=Math.round(performance.now()-o),a=n.ok?"reachable":"unreachable";return Zn={result:a,timestamp:Date.now()},{result:a,latencyMs:r}}catch{let e=Math.round(performance.now()-o);return Zn={result:"unreachable",timestamp:Date.now()},{result:"unreachable",latencyMs:e}}finally{clearTimeout(t),Qn=null}})(),Qn)}();t="valid"===o&&"reachable"===n.result?"ok":"valid"!==o&&"reachable"!==n.result?"unhealthy":"degraded";let r={status:t,copilot_token:o,upstream:n.result,version:"0.40.4",timestamp:(new Date).toISOString()};void 0!==n.latencyMs&&(r.upstream_latency_ms=n.latencyMs);let a="ok"===t?200:503;return e.json(r,a)});const or=new H(F),nr={...B["anthropic/claude-sonnet-4"].tokens,baseOverhead:4,perTool:27};function rr(e){return or.encode(e).length}function ar(e){let t=0;for(let o of e)switch(o.type){case"text":t+=rr(o.text)*nr.contentMultiplier;break;case"tool_use":t+=rr(o.name+JSON.stringify(o.input))*nr.contentMultiplier;break;case"tool_result":o.content&&(t+=rr("string"==typeof o.content?o.content:JSON.stringify(o.content))*nr.contentMultiplier);break;case"thinking":t+=rr(o.thinking)*nr.contentMultiplier;break;case"image":t+=1600}return t}function ir(e){let t=0,o=e.properties;if(!o)return t;let n=Object.entries(o);for(let[e,[o,r]]of n.entries()){if(t+=0===e?nr.perFirstProp:nr.perAdditionalProp,t+=rr(o),r.description&&(t+=nr.perPropDesc+rr(r.description)),r.enum&&Array.isArray(r.enum)){t+=nr.perEnum;for(let e of r.enum)t+=rr(String(e))}if("object"===r.type&&r.properties&&(t+=nr.perNestedObject,t+=ir(r)),"array"===r.type&&r.items){let e=r.items;"object"===e.type&&e.properties&&(t+=nr.perArrayOfObjects,t+=ir(e))}}return t}function sr(e,t){let o={"copilot_api.context_1m_beta":/context-1m/i.test(t??"")};return e.thinking&&(o["copilot_api.thinking.type"]=e.thinking.type,"budget_tokens"in e.thinking&&e.thinking.budget_tokens&&(o["copilot_api.thinking.budget_tokens"]=e.thinking.budget_tokens)),e.output_config?.effort&&(o["copilot_api.output_config.effort"]=e.output_config.effort),o}function lr(e,t,o){let n=sr(t,o);for(let[t,o]of Object.entries(n))void 0!==o&&e.setAttribute(t,o)}const cr=async(e,t,n)=>{try{return await pr(e,t)}catch(r){if(r instanceof Dt&&401===r.response.status)return await eo(),pr(e,t);if(r instanceof Dt&&400===r.response.status&&n?.onStructuredOutputFallback){let a;try{a=await r.response.clone().text()}catch{a=void 0}let i=n.onStructuredOutputFallback(e,a);if(i)return o.warn(`Upstream rejected structured outputs on ${e.model}; retrying once against ${i.model}`),pr(i,t)}throw r}};function ur(e){return e.context_management?["context-management-2025-06-27"]:[]}const pr=async(e,t)=>{if(!X._t1)throw Error("Service token not found");let{metadata:n,...r}=Yo(e),a={...pt(X,t,ur(r)),"X-Initiator":"agent"},i=lt(X),s=`${i}/v1/messages`,l=X.timeoutMs,c=JSON.stringify(r),u=function(e,t,o){return{"copilot_api.model":e.model,"copilot_api.streaming":!!e.stream,"copilot_api.timeout_ms":o,"copilot_api.has_tools":!!e.tools?.length,"copilot_api.tool_count":e.tools?.length||0,"copilot_api.max_tokens":e.max_tokens||0,"copilot_api.api_type":"anthropic_passthrough",...sr(e,t?.anthropicBeta)}}(r,t,l);for(let e=0;e<=1;e++){let t=Dn(i),p=new AbortController,d=Ht(p,l);try{let{statusCode:o,headers:n,body:i,span:d}=await et({spanName:"copilot POST /v1/messages",url:s,target:"anthropic_messages",headers:a,body:c,signal:p.signal,headersTimeout:l,bodyTimeout:3*l,extraAttributes:{...u,"copilot_api.h2.retry_attempt":e},dispatcher:t}),m=new Response(i,{status:o,headers:n});if(!m.ok)throw d.end(),new Dt("Failed to create anthropic messages",m,{outgoingBody:c,outgoingHeaders:a});if(r.stream)return{events:M(m),span:d,release:()=>Mn(t)};try{let e=await m.json();"string"==typeof e.id&&d.setAttribute("copilot_api.response.id",e.id);let t=e.usage;return t&&an(d,{prompt_tokens:t.input_tokens??0,completion_tokens:t.output_tokens??0,total_tokens:(t.input_tokens??0)+(t.output_tokens??0)}),e}finally{d.end(),Mn(t)}}catch(n){if(Mn(t),Fn(n)&&e<1){o.warn(`HTTP/2 connection error during anthropic messages, retrying (attempt ${e+1}): ${n instanceof Error?n.message:String(n)}`),await Un();continue}throw n}finally{clearTimeout(d)}}throw Error("Unexpected: exhausted GOAWAY retries without result")};async function dr(e,t,o){try{if(!e.ok)throw new Dt("Failed to create responses",e,{outgoingBody:o.outgoingBody,outgoingHeaders:o.outgoingHeaders});let n=await e.json();return n.id&&t.setAttribute("copilot_api.response.id",n.id),n.usage&&an(t,{prompt_tokens:n.usage.input_tokens,completion_tokens:n.usage.output_tokens,total_tokens:n.usage.total_tokens}),n}catch(e){throw We(t,e),e}finally{t.end()}}const mr=async e=>{try{return await fr(e)}catch(t){if(t instanceof Dt&&401===t.response.status)return await eo(),fr(e);throw t}},fr=async e=>{if(!X._t1)throw Error("Service token not found");let t=Yo(e),n={...ct(X),"X-Initiator":"agent"},r=lt(X),a=`${r}/responses`,i=X.timeoutMs,s=JSON.stringify(t),l={"copilot_api.model":t.model,"copilot_api.streaming":!!t.stream,"copilot_api.timeout_ms":i,"copilot_api.has_tools":!!t.tools?.length,"copilot_api.tool_count":t.tools?.length??0,"copilot_api.max_output_tokens":t.max_output_tokens??0,"copilot_api.api_type":"responses"};for(let e=0;e<=1;e++){let c=Dn(r),u=new AbortController,p=Ht(u,i);try{let{statusCode:o,headers:r,body:p,span:d}=await et({spanName:"copilot POST /responses",url:a,target:"responses",headers:n,body:s,signal:u.signal,headersTimeout:i,bodyTimeout:3*i,extraAttributes:{...l,"copilot_api.h2.retry_attempt":e},dispatcher:c}),m=new Response(p,{status:o,headers:r});if(t.stream){if(!m.ok)throw d.end(),new Dt("Failed to create responses",m,{outgoingBody:s,outgoingHeaders:n});return{events:M(m),span:d,release:()=>Mn(c)}}try{return await dr(m,d,{outgoingBody:s,outgoingHeaders:n})}finally{Mn(c)}}catch(t){if(Mn(c),Fn(t)&&e<1){o.warn(`HTTP/2 connection error during responses, retrying (attempt ${e+1}): ${t instanceof Error?t.message:String(t)}`),await Un();continue}throw t}finally{clearTimeout(p)}}throw Error("Unexpected: exhausted GOAWAY retries without result")},hr=new Set(["low","medium","high","max","xhigh"]);function gr(e,t,n){let r=t.includes(e.model)?e.model:un(e.model,t)??e.model,a=r===e.model?e:{...e,model:r},i=function(e,t,o={}){let n=un(e,t);if(!n)return null;let r=new Set(t);if(o.context1m){let e=function(e,t){let o=`${e}-1m`;if(t.has(o))return o;let n=`${e}-1m-`;for(let e of t)if(e.startsWith(n))return e;return null}(n,r);if(e)return e}if(o.effort){let e=function(e,t,o){let n=null;if("high"===o?n="high":("max"===o||"xhigh"===o)&&(n="xhigh"),!n)return null;let r=`${e}-${n}`;return t.has(r)?r:null}(n,r,o.effort);if(e)return e}return null}(a.model,t,{context1m:n.context1m,effort:a.output_config?.effort}),s=a;if(i&&i!==a.model){o.debug(`Resolved model variant: ${a.model} → ${i}`);let e=d.getActiveSpan();e?.setAttribute("copilot_api.model.variant_resolved_from",a.model),e?.setAttribute("copilot_api.model.variant_resolved_to",i),s={...a,model:i}}return function(e){let t=e.output_config?.effort;if(!t)return e;let n=X.models?.data.find(t=>t.id===e.model)?.capabilities.supports.reasoning_effort,r=dn(t,n);if(!r||!hr.has(r))return e;let a=r;if(a===t)return e;o.debug(`Effort clamp: ${t} → ${a}`);let i=d.getActiveSpan();return i?.setAttribute("copilot_api.effort.requested",t),i?.setAttribute("copilot_api.effort.clamped_to",a),{...e,output_config:{...e.output_config,effort:a}}}(s)}function _r(e){return null===e?null:{stop:"end_turn",length:"max_tokens",tool_calls:"tool_use",content_filter:"end_turn"}[e]}function yr(e,t){let o={model:e.model,messages:kr(e.messages,e.system),max_tokens:e.max_tokens,stop:e.stop_sequences,stream:e.stream,temperature:e.temperature,top_p:e.top_p,user:e.metadata?.user_id,tools:$r(e.tools),tool_choice:xr(e.tool_choice)},n=e.thinking;if("enabled"===n?.type||"adaptive"===n?.type){let r=vn(t,o.model);if(r){let a="enabled"===n.type&&"number"==typeof n.budget_tokens?n.budget_tokens:function(e,t,o){let n=function(e,t){return"max"===e||"xhigh"===e?t:"high"===e?16e3:"medium"===e?8e3:1024}(e,o.max),r=kn(t),a=r&&r>1?r-1:o.min;return wn(Math.min(n,a),o.min,o.max)}(e.output_config?.effort??"high",o.max_tokens,r.bounds);o=$n({...o,thinking_budget:a},t)}}return o}function kr(e,t){let o=function(e){return e?"string"==typeof e?[{role:"system",content:wr(e)}]:[{role:"system",content:wr(e.map(e=>e.text).join("\n\n"))}]:[]}(t),n=e.flatMap(e=>"user"===e.role?function(e){let t=[];if(Array.isArray(e.content)){let o=e.content.filter(e=>"tool_result"===e.type),n=e.content.filter(e=>"tool_result"!==e.type);for(let e of o)t.push({role:"tool",tool_call_id:e.tool_use_id,content:Tr(e.content)});n.length>0&&t.push({role:"user",content:Tr(n)})}else t.push({role:"user",content:Tr(e.content)});return t}(e):function(e){let t=function(e){return{reasoning_text:vr(e.reasoning_text),reasoning_opaque:vr(e.reasoning_opaque)}}(e);if(!Array.isArray(e.content))return[{role:"assistant",content:Tr(e.content),...t}];let o=e.content.filter(e=>"tool_use"===e.type),n=e.content.filter(e=>"text"===e.type),r=e.content.filter(e=>"thinking"===e.type),a=[...n.map(e=>e.text),...r.map(e=>e.thinking)].join("\n\n");return o.length>0?[{role:"assistant",content:a||null,...t,tool_calls:o.map(e=>({id:e.id,type:"function",function:{name:e.name,arguments:JSON.stringify(e.input)}}))}]:[{role:"assistant",content:Tr(e.content),...t}]}(e));return[...o,...n]}function wr(e){return e.startsWith("x-anthropic-billing-header")?e.replace(/^x-_an1-billing-header:[^\n]*\n+/,""):e}const br=32768;function vr(e){if("string"==typeof e)return e.length<=br?e:e.slice(0,br)}function Tr(e){if("string"==typeof e)return e;if(!Array.isArray(e))return null;if(!e.some(e=>"image"===e.type))return e.filter(e=>"text"===e.type||"thinking"===e.type).map(e=>"text"===e.type?e.text:e.thinking).join("\n\n");let t=[];for(let o of e)switch(o.type){case"text":t.push({type:"text",text:o.text});break;case"thinking":t.push({type:"text",text:o.thinking});break;case"image":t.push({type:"image_url",image_url:{url:`data:${o.source.media_type};base64,${o.source.data}`}})}return t}function $r(e){if(e)return e.filter(tr).map(e=>({type:"function",function:{name:e.name,description:e.description,parameters:e.input_schema}}))}function xr(e){if(e)switch(e.type){case"auto":return"auto";case"any":return"required";case"tool":return e.name?{type:"function",function:{name:e.name}}:void 0;case"none":return"none";default:return}}function Ar(e){return"string"==typeof e?[{type:"text",text:e}]:Array.isArray(e)?e.filter(e=>"text"===e.type).map(e=>({type:"text",text:e.text})):[]}function Sr(e){return e.reasoning_text?[{type:"thinking",thinking:e.reasoning_text}]:[]}function Er(e){return e?e.map(e=>{let t={};try{t=JSON.parse(e.function.arguments)}catch{r.warn(`Failed to parse tool call arguments for "${e.function.name}": ${e.function.arguments.slice(0,200)}`)}return{type:"tool_use",id:e.id,name:e.function.name,input:t}}):[]}const Cr=new Set(["low","medium","high","max","xhigh"]);function Or(e,t){let o=e.thinking;if(!o||"enabled"!==o.type)return e;let n=t?.data.find(t=>t.id===e.model);if(!n||!n.capabilities.supports.adaptive_thinking)return e;let r={...e,thinking:{type:"adaptive"}};if(!e.output_config?.effort){let t=(e=>null!==e&&Cr.has(e)?e:null)(dn(function(e){return!e||e<=0?"medium":e<8e3?"low":e<24e3?"medium":"high"}(o.budget_tokens),n.capabilities.supports.reasoning_effort));t&&(r.output_config={...e.output_config,effort:t})}return r}function Ir(e){return"string"!=typeof e&&Array.isArray(e)?e.map(e=>{let t=e;if(!t.cache_control||"object"!=typeof t.cache_control)return e;let o=t.cache_control;if("string"!=typeof o.type){let{cache_control:e,...o}=t;return o}let n={type:o.type};return void 0!==o.ttl&&(n.ttl=o.ttl),{...t,cache_control:n}}):e}const Pr=/[^\w-]/g;function Rr(e){return e.replaceAll(Pr,"_")}function Nr(e,t){let o=function(e,t){if(!e.output_config?.effort)return e;let o=t?.data.find(t=>t.id===e.model);if(!o)return e;let n=o.capabilities.supports.reasoning_effort;if(Array.isArray(n)&&n.length>0)return e;let{effort:r,...a}=e.output_config;if(0===Object.keys(a).length){let{output_config:t,...o}=e;return o}return{...e,output_config:a}}(e,t);return o=Or(o,t),o=function(e,t){let o=e.max_tokens;if("number"!=typeof o)return e;let n=t?.data.find(t=>t.id===e.model);if(!n)return e;let r=n.capabilities.limits;if(!r)return e;let a=(!1===e.stream?r.max_non_streaming_output_tokens:void 0)??r.max_output_tokens;if("number"!=typeof a||a<=0)return e;let i=Math.max(Math.min(o,a),16);return i===o?e:{...e,max_tokens:i}}(o,t),o={...o,system:Ir(o.system)},o=function(e){let t=e.messages.map(e=>{if(!Array.isArray(e.content))return e;let t=e.content.map(e=>{let t=e;return"tool_use"===t.type&&"string"==typeof t.id?{...t,id:Rr(t.id)}:"tool_result"===t.type&&"string"==typeof t.tool_use_id?{...t,tool_use_id:Rr(t.tool_use_id)}:e});return{...e,content:t}});return{...e,messages:t}}(o),o}function qr(e){return function(e){let t=e.thinking;if(null==t)return null;if("object"!=typeof t)return"thinking must be an object";let o=t,n=new Set(["enabled","adaptive","disabled"]);return"string"==typeof o.type&&n.has(o.type)?"enabled"!==o.type||void 0===o.budget_tokens||"number"==typeof o.budget_tokens&&Number.isFinite(o.budget_tokens)&&!(o.budget_tokens<=0)&&Number.isInteger(o.budget_tokens)?null:"thinking.budget_tokens must be a positive integer":"thinking.type must be one of: enabled, adaptive, disabled"}(e)??function(e){let t=e.output_config;if(null==t)return null;if("object"!=typeof t)return"output_config must be an object";let o=t;if(void 0===o.effort)return null;let n=new Set(["low","medium","high","max","xhigh"]);return"string"==typeof o.effort&&n.has(o.effort)?null:"output_config.effort must be one of: low, medium, high, max, xhigh"}(e)}function jr(e,t){return he.startActiveSpan("copilot_api.model.validate",n=>{try{n.setAttribute("copilot_api.model.requested",t.model),lr(n,t,e.req.header("anthropic-beta"));let r=fn(t.model);n.setAttribute("copilot_api.model.normalized",r);let a=qr(t);return a?(d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_request"),{ok:!1,response:e.json({type:"error",error:{type:"invalid_request_error",message:a}},400)}):r===t.model?(n.setAttribute("copilot_api.model.was_mapped",!1),{ok:!0,payload:t}):(n.setAttribute("copilot_api.model.was_mapped",!0),xe.add(1,{from_model:t.model,to_model:r}),o.debug(`Model mapping: '${t.model}' → '${r}'`),{ok:!0,payload:{...t,model:r}})}catch(t){if(t instanceof mn)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_model"),{ok:!1,response:e.json({type:"error",error:{type:"invalid_request_error",message:t.message}},t.statusCode)};throw t}finally{n.end()}})}function Dr(e){let t=function(e){let t=[];for(let o of e)"user"===o.role?t.push(...Hr(o)):t.push(...Fr(o));return t}(e.messages);if(0===t.length)throw new Dt("request has no translatable message content",Response.json({type:"error",error:{type:"invalid_request_error",message:"request has no translatable message content"}},{status:400}));let o={model:e.model,input:t,max_output_tokens:Math.max(e.max_tokens,16),stream:e.stream,temperature:e.temperature,top_p:e.top_p,store:!1,user:e.metadata?.user_id?.slice(0,64)},n=function(e){return e?function(e){return e.startsWith("x-anthropic-billing-header")?e.replace(/^x-_an1-billing-header:[^\n]*\n+/,""):e}("string"==typeof e?e:e.map(e=>e.text).join("\n\n")):null}(e.system);return n&&(o.instructions=n),e.tools?.length&&(o.tools=e.tools.filter(tr).map(e=>({type:"function",name:e.name,description:e.description,parameters:e.input_schema}))),e.tool_choice&&(o.tool_choice=function(e){switch(e.type){case"auto":return"auto";case"any":return"required";case"none":return"none";case"tool":return e.name?{type:"function",name:e.name}:void 0;default:return}}(e.tool_choice)),"adaptive"===e.thinking?.type?o.reasoning={effort:Mr(e.output_config?.effort??"high")}:"enabled"===e.thinking?.type&&e.thinking.budget_tokens&&(o.reasoning=function(e){return e<5e3?{effort:"low"}:e<2e4?{effort:"medium"}:e<32e3?{effort:"high"}:{effort:"xhigh"}}(e.thinking.budget_tokens)),o}function Mr(e){switch(e){case"low":return"low";case"medium":return"medium";case"max":case"xhigh":return"xhigh";default:return"high"}}function Hr(e){if("string"==typeof e.content)return[{type:"message",role:"user",content:e.content}];let t=[],o=e.content.filter(e=>"tool_result"===e.type),n=e.content.filter(e=>"tool_result"!==e.type);for(let e of o)t.push(Br(e));if(n.length>0)if(n.some(e=>"image"===e.type)){let e=[];for(let t of n)"text"===t.type?e.push({type:"input_text",text:t.text}):e.push({type:"input_image",image_url:`data:${t.source.media_type};base64,${t.source.data}`});t.push({type:"message",role:"user",content:e})}else{let e=n.filter(e=>"text"===e.type).map(e=>e.text).join("\n\n");e&&t.push({type:"message",role:"user",content:e})}return t}function Br(e){let t;return t="string"==typeof e.content?e.content:Array.isArray(e.content)?e.content.filter(e=>"text"===e.type).map(e=>e.text).join("\n"):"",e.is_error&&(t=`[ERROR] ${t}`),{type:"function_call_output",call_id:e.tool_use_id,output:t}}function Fr(e){if("string"==typeof e.content)return[{type:"message",role:"assistant",content:e.content}];let t=[],o=e.content.filter(e=>"text"===e.type),n=e.content.filter(e=>"thinking"===e.type),r=e.content.filter(e=>"tool_use"===e.type),a=[...o.map(e=>e.text),...n.map(e=>e.thinking)].join("\n\n");a&&t.push({type:"message",role:"assistant",content:a});for(let e of r)t.push({type:"function_call",call_id:e.id,name:e.name,arguments:JSON.stringify(e.input)});return t}function Ur(e,t){if(t)return"tool_use";switch(e){case"completed":case"cancelled":case"failed":return"end_turn";case"incomplete":return"max_tokens";default:return null}}function Lr(e,t){e.contentBlockOpen&&=(t.push({type:"content_block_stop",index:e.contentBlockIndex}),e.contentBlockIndex++,!1)}function Gr(e,t,o){e.messageStartSent||=(e.responseId=o?.responseId??e.responseId,e.model=o?.model??e.model,t.push({type:"message_start",message:{id:e.responseId,type:"message",role:"assistant",content:[],model:e.model,stop_reason:null,stop_sequence:null,usage:{input_tokens:0,output_tokens:0}}}),!0)}function zr(e,t){let o=[];switch(e.type){case"response.created":Gr(t,o,{responseId:e.response.id,model:e.response.model});break;case"response.in_progress":case"response.output_text.done":case"response.function_call_arguments.done":case"response.refusal.done":case"response.reasoning_summary_text.delta":case"response.reasoning_summary_text.done":default:break;case"response.output_item.added":if("function_call"===e.item.type){Gr(t,o),Lr(t,o);let n=e.item;t.toolCalls[e.output_index]={call_id:n.call_id,name:n.name,_bi1:t.contentBlockIndex},o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"tool_use",id:n.call_id,name:n.name,input:{}}}),t.contentBlockOpen=!0}break;case"response.content_part.added":Gr(t,o),Lr(t,o),o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"text",text:""}}),t.contentBlockOpen=!0;break;case"response.output_text.delta":o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"text_delta",text:e.delta}});break;case"response.content_part.done":Lr(t,o);break;case"response.function_call_arguments.delta":{let n=t.toolCalls[e.output_index];n&&o.push({type:"content_block_delta",index:n._bi1,delta:{type:"input_json_delta",partial_json:e.delta}});break}case"response.output_item.done":if("function_call"===e.item.type){let n=t.toolCalls[e.output_index];n&&t.contentBlockOpen&&(o.push({type:"content_block_stop",index:n._bi1}),t.contentBlockIndex++,t.contentBlockOpen=!1)}break;case"response.completed":{Lr(t,o);let n=e.response.output.some(e=>"function_call"===e.type),r=e.response.usage;o.push({type:"message_delta",delta:{stop_reason:Ur(e.response.status,n),stop_sequence:null},usage:{input_tokens:r?.input_tokens??0,output_tokens:r?.output_tokens??0}},{type:"message_stop"});break}case"response.incomplete":{Gr(t,o),Lr(t,o);let n=e.response.usage;o.push({type:"message_delta",delta:{stop_reason:"max_tokens",stop_sequence:null},usage:{input_tokens:n?.input_tokens??0,output_tokens:n?.output_tokens??0}},{type:"message_stop"});break}case"response.failed":Gr(t,o),Lr(t,o),o.push({type:"error",error:{type:e.response.error?.code??"api_error",message:e.response.error?.message??"Response generation failed"}});break;case"response.cancelled":Gr(t,o),Lr(t,o),o.push({type:"message_delta",delta:{stop_reason:"end_turn",stop_sequence:null},usage:{input_tokens:0,output_tokens:0}},{type:"message_stop"});break;case"response.refusal.delta":Gr(t,o),t.contentBlockOpen||=(o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"text",text:""}}),!0),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"text_delta",text:e.delta}})}return o}function Jr(e,t){e.thinkingBlockOpen||(e.contentBlockOpen&&=(t.push({type:"content_block_stop",index:e.contentBlockIndex}),e.contentBlockIndex++,!1),t.push({type:"content_block_start",index:e.contentBlockIndex,content_block:{type:"thinking",thinking:""}}),e.thinkingBlockOpen=!0,e.contentBlockOpen=!0)}function Kr(e,t){e.thinkingBlockOpen&&(t.push({type:"content_block_stop",index:e.contentBlockIndex}),e.contentBlockIndex++,e.thinkingBlockOpen=!1,e.contentBlockOpen=!1)}function Wr(e,t){let o=[];if(0===e.choices.length)return o;let n=e.choices[0],{delta:r}=n;if(t.messageStartSent||=(o.push({type:"message_start",message:{id:e.id,type:"message",role:"assistant",content:[],model:e.model,stop_reason:null,stop_sequence:null,usage:{input_tokens:e.usage?.prompt_tokens??0,output_tokens:0}}}),!0),"string"==typeof r.reasoning_text&&""!==r.reasoning_text&&(Jr(t,o),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"thinking_delta",thinking:r.reasoning_text}})),"string"==typeof r.reasoning_opaque&&""!==r.reasoning_opaque&&(Jr(t,o),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"signature_delta",signature:r.reasoning_opaque}}),Kr(t,o)),r.content&&(Kr(t,o),function(e){return!!e.contentBlockOpen&&Object.values(e.toolCalls).some(t=>t._bi1===e.contentBlockIndex)}(t)&&(o.push({type:"content_block_stop",index:t.contentBlockIndex}),t.contentBlockIndex++,t.contentBlockOpen=!1),t.contentBlockOpen||=(o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"text",text:""}}),!0),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"text_delta",text:r.content}})),r.tool_calls){Kr(t,o);for(let e of r.tool_calls){if(e.id&&e.function?.name){t.contentBlockOpen&&=(o.push({type:"content_block_stop",index:t.contentBlockIndex}),t.contentBlockIndex++,!1);let n=t.contentBlockIndex;t.toolCalls[e.index]={id:e.id,name:e.function.name,_bi1:n},o.push({type:"content_block_start",index:n,content_block:{type:"tool_use",id:e.id,name:e.function.name,input:{}}}),t.contentBlockOpen=!0}if(e.function?.arguments){let n=t.toolCalls[e.index];n&&o.push({type:"content_block_delta",index:n._bi1,delta:{type:"input_json_delta",partial_json:e.function.arguments}})}}}return n.finish_reason&&(Kr(t,o),t.contentBlockOpen&&=(o.push({type:"content_block_stop",index:t.contentBlockIndex}),!1),o.push({type:"message_delta",delta:{stop_reason:_r(n.finish_reason),stop_sequence:null},usage:{input_tokens:e.usage?.prompt_tokens??0,output_tokens:e.usage?.completion_tokens??0}},{type:"message_stop"})),o}const Vr=/structured_outputs|output_config\.format/i;function Yr(e,t,o){return function(e,t,o){return!(!e.output_config?.format||"claude-haiku-4.5"===o||!t)&&Vr.test(t)}(e,t,e.model)&&o?.data.some(e=>"claude-haiku-4.5"===e.id)?Nr({...e,model:ln},o):null}var Xr=class extends Error{constructor(){super("Exa web search timed out after 15000ms. The search endpoint may be slow or unreachable."),this.name="ExaTimeoutError"}};var Zr=class extends Error{constructor(){super("Tavily web search timed out after 15000ms. The search endpoint may be slow or unreachable."),this.name="TavilyTimeoutError"}};const Qr={tavily:async function(e,t,n){let r=function(e,t){let o={query:e,max_results:t?.maxResults??5};return t?.includeDomains?.length&&(o.include_domains=t.includeDomains),t?.excludeDomains?.length&&(o.exclude_domains=t.excludeDomains),o}(t,n);o.debug("Tavily search request:",JSON.stringify(r));let a=new AbortController,i=setTimeout(()=>a.abort(),15e3);try{let{response:t,span:i}=await Qe({spanName:"tavily POST /search",url:"https://api.tavily.com/search",target:"tavily_search",method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${e}`},body:JSON.stringify(r),signal:a.signal,extraAttributes:{"tavily.max_results":n?.maxResults??5,"tavily.has_include_domains":!!n?.includeDomains?.length,"tavily.has_exclude_domains":!!n?.excludeDomains?.length}});try{let e=await async function(e){if(!e.ok){let t=await e.text();throw Error(`Tavily API error: ${e.status} ${t}`)}return await e.json()}(t);return i.setAttribute("tavily.results_count",e.results.length),o.debug(`Tavily returned ${e.results.length} results`),e.results}catch(e){throw We(i,e),e}finally{i.end()}}catch(e){throw e instanceof DOMException&&"AbortError"===e.name?new Zr:e}finally{clearTimeout(i)}},exa:async function(e,t,n){let r=function(e,t){let o={query:e,numResults:t?.maxResults??5,contents:{text:!0}};return t?.includeDomains?.length&&(o.includeDomains=t.includeDomains),t?.excludeDomains?.length&&(o.excludeDomains=t.excludeDomains),o}(t,n);o.debug("Exa search request:",JSON.stringify(r));let a=new AbortController,i=setTimeout(()=>a.abort(),15e3);try{let{response:t,span:i}=await Qe({spanName:"exa POST /search",url:"https://api.exa.ai/search",target:"exa_search",method:"POST",headers:{"Content-Type":"application/json","x-api-key":e},body:JSON.stringify(r),signal:a.signal,extraAttributes:{"exa.max_results":n?.maxResults??5,"exa.has_include_domains":!!n?.includeDomains?.length,"exa.has_exclude_domains":!!n?.excludeDomains?.length}});try{let e=await async function(e){if(!e.ok){let t=await e.text();throw Error(`Exa API error: ${e.status} ${t}`)}return await e.json()}(t);return i.setAttribute("exa.results_count",e.results.length),o.debug(`Exa returned ${e.results.length} results`),e.results.map(e=>({title:e.title??"",url:e.url,content:e.text??""}))}catch(e){throw We(i,e),e}finally{i.end()}}catch(e){throw e instanceof DOMException&&"AbortError"===e.name?new Xr:e}finally{clearTimeout(i)}}},ea=["tavily","exa"];function ta(e){return"tavily"===e||"exa"===e}function oa(){return X.webSearchProviders.length>0}async function na(e,t){return async function(e,t,n){let{providers:r,searchFns:a=Qr}=n;if(0===r.length)throw Error("No web search provider configured");let i,s=[];for(let[n,l]of r.entries())try{let n=await a[l.name](l.key,e,t);return s.length>0&&o.info(`Web search recovered: served by "${l.name}" after ${s.join(", ")} failed.`),n}catch(e){i=e,s.push(l.name);let t=e instanceof Error?e.message:String(e);n!==r.length-1&&o.warn(`Web search provider "${l.name}" failed (${t}); falling over to "${r[n+1].name}".`)}let l=i instanceof Error?i.message:String(i);throw o.error(`Web search failed: all providers exhausted (${s.join(", ")}). Last error: ${l}`),i instanceof Error?i:Error("All web search providers failed")}(e,t,{providers:X.webSearchProviders})}function ra(){let e="";for(let t=0;t<24;t++)e+="abcdefghijklmnopqrstuvwxyz0123456789"[Math.floor(36*Math.random())];return e}function aa(e){return e.searchFailed?[{type:"web_search_tool_result_error",error_code:e.errorCode??"unavailable"}]:e.results}async function ia(e,t){let n=function(e){let t,o=e.messages[0];if(!o||"user"!==o.role)return null;if("string"==typeof o.content)t=o.content;else{if(!Array.isArray(o.content))return null;{let e=o.content.find(e=>"text"===e.type);if(!e)return null;t=e.text}}return t.startsWith("Perform a web search for the query: ")?t.slice(36).trim():t.trim()||null}(t);if(!n)return e.set("requestData",{model:t.model,streaming:!1}),e.json({type:"error",error:{type:"invalid_request_error",message:"Could not extract search query from web search request"}},400);let r=function(e){let t=e.tools?.[0];return t&&er(t)?{maxResults:"number"==typeof t.max_uses?t.max_uses:5,allowedDomains:t.allowed_domains,blockedDomains:t.blocked_domains}:{maxResults:5}}(t);o.info(`Web search intercepted: "${n}"`);let a,i=[],s=!1;try{if(!oa())throw s=!0,a="unavailable",Error("No web search provider configured");i=(await na(n,{maxResults:Math.min(r.maxResults,10),includeDomains:r.allowedDomains,excludeDomains:r.blockedDomains})).map(e=>({type:"web_search_result",url:e.url,title:e.title,encrypted_content:Buffer.from(e.content).toString("base64"),page_age:null}))}catch(e){o.error("Web search failed:",e),s=!0,a??="unavailable"}let l={query:n,results:i,model:t.model,searchFailed:s,errorCode:a};if(!t.stream)return e.set("requestData",{model:t.model,streaming:!1}),e.json(function(e){let{query:t,model:o}=e,n=`srvtoolu_${ra()}`,r=[{type:"text",text:"I'll search for that."},{type:"server_tool_use",id:n,name:"web_search",input:{query:t}},{type:"web_search_tool_result",tool_use_id:n,content:aa(e)}];return{id:`msg_ws_${ra()}`,type:"message",role:"assistant",model:o,content:r,stop_reason:"end_turn",stop_sequence:null,usage:{input_tokens:0,output_tokens:0}}}(l));let c=function(e){let{query:t,model:o}=e,n=`srvtoolu_${ra()}`,r=`msg_ws_${ra()}`,a=[];return a.push({type:"message_start",message:{id:r,type:"message",role:"assistant",content:[],model:o,stop_reason:null,stop_sequence:null,usage:{input_tokens:0,output_tokens:0}}},{type:"content_block_start",index:0,content_block:{type:"text",text:""}},{type:"content_block_delta",index:0,delta:{type:"text_delta",text:"I'll search for that."}},{type:"content_block_stop",index:0},{type:"content_block_start",index:1,content_block:{type:"server_tool_use",id:n,name:"web_search",input:{}}},{type:"content_block_delta",index:1,delta:{type:"input_json_delta",partial_json:JSON.stringify({query:t})}},{type:"content_block_stop",index:1},{type:"content_block_start",index:2,content_block:{type:"web_search_tool_result",tool_use_id:n,content:aa(e)}},{type:"content_block_stop",index:2},{type:"message_delta",delta:{stop_reason:"end_turn",stop_sequence:null},usage:{output_tokens:0}},{type:"message_stop"}),a}(l);return e.set("requestData",{model:t.model,streaming:!0}),D(e,async t=>{for(let e of c)await t.writeSSE({event:e.type,data:JSON.stringify(e)});e.get("resolveStreamComplete")?.()})}const sa=(e,t)=>!(!e||!t||e===t);async function la(e){if(X._t1||await ko())return null;let t=fo();return t?(d.getActiveSpan()?.setAttribute("copilot_api.error_type","authentication_error"),e.json({type:"error",error:{type:"authentication_error",message:`${t.message}; re-authenticate with \`copilot-api auth\`, then restart the proxy`}},401)):(d.getActiveSpan()?.setAttribute("copilot_api.error_type","service_unavailable"),e.header("Retry-After","1"),e.json({type:"error",error:{type:"service_unavailable",message:"Service token not yet available; retry shortly"}},503))}async function ca(e){let t=await e.req.json();if(function(e){let t=e.tools;return!(!t||1!==t.length)&&er(t[0])}(t))return ia(e,t);await hn(X),o.debug("Anthropic request payload:",t);let r=t.output_config?.effort;t=function(e,t){return gr(t,X.models?.data.map(e=>e.id)??[],{context1m:/context-1m/i.test(e.req.header("anthropic-beta")??"")})}(e,t);let a=jr(e,t);if(!a.ok)return a.response;t=a.payload;let i=await la(e);if(i)return i;if(function(e){let t=X.models?.data.find(t=>t.id===e)?.supported_endpoints;return t?t.includes("/responses")&&!t.includes("/chat/completions"):/gpt-[\d.]+-codex/i.test(e)}(t.model))return ha(e,t);if(function(e){return e.toLowerCase().startsWith("claude-")}(t.model))return async function(e,t,o){let n=Nr(t,X.models),r={anthropicBeta:e.req.header("anthropic-beta"),anthropicVersion:e.req.header("anthropic-version")},a=n.output_config?.effort;return e.set("requestData",{model:n.model,reasoningEffort:a,effortClamped:sa(o,a),streaming:!!n.stream}),X.manualApprove&&await nn(),he.startActiveSpan("copilot_api.anthropic_passthrough",async t=>{t.setAttribute("copilot_api.route","anthropic_passthrough"),t.setAttribute("copilot_api.model",n.model),t.setAttribute("copilot_api.streaming",!!n.stream),lr(t,n,r.anthropicBeta);try{let o=performance.now(),a=await cr(n,r,{onStructuredOutputFallback:(e,o)=>{let n=Yr(e,o,X.models);return n&&(t.setAttribute("copilot_api.structured_output_fallback",!0),t.setAttribute("copilot_api.structured_output_fallback.model",n.model)),n}}),i=performance.now()-o;if(De.record(i,{model:n.model,target:"anthropic_messages",streaming:String(!!n.stream)}),!n.stream){let o=a,n=o.usage;if(n){let t={input_tokens:n.input_tokens||0,output_tokens:n.output_tokens||0,cache_read_input_tokens:n.cache_read_input_tokens||0,cache_creation_input_tokens:n.cache_creation_input_tokens||0},o=e.get("requestData")||{};o.tokenUsage=rn(ma(t)),o._d1=i,o.upstreamTtfbMs=i,o.upstreamTotalMs=i,e.set("requestData",o)}return t.end(),e.json(o)}let{events:s,span:l,release:c}=a;return D(e,async r=>{let a=0,i=performance.now(),u={input_tokens:0,output_tokens:0,cache_read_input_tokens:0,cache_creation_input_tokens:0},p=!1,d=Sn(e,o);try{try{for await(let e of s)d(),e.data&&"[DONE]"!==e.data?(a++,Ie.add(1,{model:n.model,endpoint_type:"anthropic_messages"}),fa(e.data,u)&&(p=!0),await r.writeSSE(e)):await r.writeSSE(e);let e=performance.now()-i,t={model:n.model,endpoint_type:"anthropic_messages"};Me.record(e,t),ze.record(a,t)}catch(t){throw Ve(l,e.get("requestSpan"),t),await _n(r,t),t}finally{if(En(e,o),p){let t=ma(u);an(l,t);let o=e.get("requestData")||{};o.tokenUsage=rn(t),e.set("requestData",o)}l.end(),c()}let t=e.get("requestId");t&&ce.executeCompletion(t)}finally{t.end(),e.get("resolveStreamComplete")?.()}})}catch(e){throw We(t,e),t.end(),e}})}(e,t,r);let s=performance.now(),l=he.startActiveSpan("copilot_api.translate.anthropic_to_openai",o=>{try{o.setAttribute("copilot_api.translation.direction","anthropic_to_openai"),o.setAttribute("copilot_api.translation.message_count",t.messages.length),o.setAttribute("copilot_api.translation.has_tools",!!t.tools?.length),o.setAttribute("copilot_api.translation.has_system",!!t.system),o.setAttribute("copilot_api.translation.context_1m_beta",/context-1m/i.test(e.req.header("anthropic-beta")??""));let n=t.messages.some(e=>Array.isArray(e.content)&&e.content.some(e=>"image"===e.type)),r=t.messages.some(e=>Array.isArray(e.content)&&e.content.some(e=>"thinking"===e.type));return o.setAttribute("copilot_api.translation.has_images",n),o.setAttribute("copilot_api.translation.has_thinking",r),yr(t,X.models)}finally{o.end()}});Be.record(performance.now()-s,{direction:"anthropic_to_openai"}),l=$n(l,X.models),o.debug("Translated OpenAI request payload:",l);let c=t.output_config?.effort;e.set("requestData",{model:l.model,reasoningEffort:c,effortClamped:sa(r,c),streaming:!!l.stream});let u=performance.now();X.manualApprove&&await nn();let p=await Gn(l),d=performance.now()-u;if(De.record(d,{model:l.model,target:"chat_completions",streaming:String(!!l.stream)}),pa(p)){let t=e.get("requestData")||{};p.usage&&(t.tokenUsage=rn(p.usage)),t._d1=d,t.upstreamTtfbMs=d,t.upstreamTotalMs=d,e.set("requestData",t),o.level>=n.debug&&o.debug("Non-streaming response:",JSON.stringify(p).slice(-400));let r=performance.now(),a=he.startActiveSpan("copilot_api.translate.openai_to_anthropic",e=>{try{e.setAttribute("copilot_api.translation.direction","openai_to_anthropic");let t=function(e){let t=[],o=[],n=[],r=null;r=e.choices[0]?.finish_reason??r;for(let a of e.choices){let e=Sr(a.message),i=Ar(a.message.content),s=Er(a.message.tool_calls);t.push(...e),o.push(...i),n.push(...s),("tool_calls"===a.finish_reason||"stop"===r)&&(r=a.finish_reason)}return{id:e.id,type:"message",role:"assistant",model:e.model,content:[...t,...o,...n],stop_reason:_r(r),stop_sequence:null,usage:{input_tokens:e.usage?.prompt_tokens??0,output_tokens:e.usage?.completion_tokens??0}}}(p);return e.setAttribute("copilot_api.translation.content_blocks",t.content.length),e.setAttribute("copilot_api.translation.stop_reason",t.stop_reason??"null"),e.setAttribute("copilot_api.translation.has_tool_use",t.content.some(e=>"tool_use"===e.type)),t}finally{e.end()}});return Be.record(performance.now()-r,{direction:"openai_to_anthropic"}),o.debug("Translated Anthropic response:",a),e.json(a)}o.debug("Streaming response from service");let{events:m,span:f,release:h}=p;return D(e,async t=>{let n=null,r=0,a=performance.now(),i=Sn(e,u),s={messageStartSent:!1,contentBlockIndex:0,contentBlockOpen:!1,thinkingBlockOpen:!1,toolCalls:{}};try{try{for await(let a of m){if(i(),o.debug("Raw stream event:",a),"[DONE]"===a.data)break;if(!a.data)continue;let c;try{c=JSON.parse(a.data)}catch(e){o.warn("Failed to parse streaming chunk:",a.data.slice(0,200),e);continue}if(r++,Ie.add(1,{model:l.model,endpoint_type:"anthropic"}),c.usage){n=c.usage;let t=e.get("requestData")||{};t.tokenUsage=rn(n),t._d1=d,e.set("requestData",t)}let u=Wr(c,s);for(let e of u)o.debug("Translated Anthropic event:",e),await t.writeSSE({event:e.type,data:JSON.stringify(e)})}let c=performance.now()-a,p={model:l.model,endpoint_type:"anthropic"};if(Me.record(c,p),ze.record(r,p),En(e,u),n){let t=e.get("requestData")||{};t.tokenUsage||(t.tokenUsage=rn(n),t._d1=d,e.set("requestData",t))}}catch(o){throw Ve(f,e.get("requestSpan"),o),await _n(t,o),o}finally{n&&an(f,n),f.end(),h()}let c=e.get("requestId");c&&ce.executeCompletion(c)}finally{e.get("resolveStreamComplete")?.()}})}function ua(e){if("response.completed"!==e.type&&"response.incomplete"!==e.type)return null;let t=e.response.usage;return t?{prompt_tokens:t.input_tokens,completion_tokens:t.output_tokens,total_tokens:t.total_tokens}:null}const pa=e=>Object.hasOwn(e,"choices"),da=e=>Object.hasOwn(e,"output");function ma(e){let t=e.input_tokens+e.cache_read_input_tokens+e.cache_creation_input_tokens;return{prompt_tokens:t,completion_tokens:e.output_tokens,total_tokens:t+e.output_tokens,prompt_tokens_details:{cached_tokens:e.cache_read_input_tokens}}}function fa(e,t){try{let o=JSON.parse(e);if("message_start"===o.type){let e=o.message?.usage;if(e)return t.input_tokens=e.input_tokens||0,t.cache_read_input_tokens=e.cache_read_input_tokens||0,t.cache_creation_input_tokens=e.cache_creation_input_tokens||0,!0}if("message_delta"===o.type){let e=o.usage;if(e)return t.output_tokens=e.output_tokens||0,!0}}catch{}return!1}async function ha(e,t){let r=performance.now(),a=he.startActiveSpan("copilot_api.translate.anthropic_to_responses",e=>{try{return e.setAttribute("copilot_api.translation.direction","anthropic_to_responses"),e.setAttribute("copilot_api.translation.message_count",t.messages.length),Dr(t)}finally{e.end()}});Be.record(performance.now()-r,{direction:"anthropic_to_responses"}),o.debug("Translated Responses API payload:",a),e.set("requestData",{model:a.model,streaming:!!a.stream}),X.manualApprove&&await nn();let i=performance.now(),s=await mr(a),l=performance.now()-i;if(De.record(l,{model:a.model,target:"responses",streaming:String(!!a.stream)}),da(s)){let t=e.get("requestData")||{};if(s.usage&&(t.tokenUsage=rn({prompt_tokens:s.usage.input_tokens,completion_tokens:s.usage.output_tokens,total_tokens:s.usage.total_tokens})),t._d1=l,t.upstreamTtfbMs=l,t.upstreamTotalMs=l,e.set("requestData",t),o.level>=n.debug&&o.debug("Non-streaming Responses API response:",JSON.stringify(s).slice(-400)),"failed"===s.status)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","upstream_failure"),e.json({type:"error",error:{type:s.error?.code??"api_error",message:s.error?.message??"Response generation failed"}},500);let r=performance.now(),a=he.startActiveSpan("copilot_api.translate.responses_to_anthropic",e=>{try{return e.setAttribute("copilot_api.translation.direction","responses_to_anthropic"),function(e){let t=[],o=!1;for(let n of e.output)if("message"===n.type)for(let e of n.content)e.text&&t.push({type:"text",text:e.text});else if("function_call"===n.type){o=!0;let e={};try{e=JSON.parse(n.arguments)}catch{}t.push({type:"tool_use",id:n.call_id,name:n.name,input:e})}return{id:e.id,type:"message",role:"assistant",model:e.model,content:t,stop_reason:Ur(e.status,o),stop_sequence:null,usage:{input_tokens:e.usage?.input_tokens??0,output_tokens:e.usage?.output_tokens??0}}}(s)}finally{e.end()}});return Be.record(performance.now()-r,{direction:"responses_to_anthropic"}),e.json(a)}o.debug("Streaming Responses API response");let{events:c,span:u,release:p}=s;return D(e,async t=>{let n=null,r=0,s=performance.now(),d=Sn(e,i),m={messageStartSent:!1,contentBlockIndex:0,contentBlockOpen:!1,responseId:"",model:"",toolCalls:{}};try{try{for await(let i of c){if(d(),o.debug("Responses API raw stream event:",i),!i.data)continue;let s;try{s=JSON.parse(i.data)}catch(e){o.warn("Failed to parse streaming chunk:",i.data.slice(0,200),e);continue}r++,Ie.add(1,{model:a.model,endpoint_type:"responses"});let c=ua(s);if(c){n=c;let t=e.get("requestData")||{};t.tokenUsage=rn(n),t._d1=l,e.set("requestData",t)}let u=zr(s,m);for(let e of u)o.debug("Translated Anthropic event:",e),await t.writeSSE({event:e.type,data:JSON.stringify(e)})}let u=performance.now()-s,p={model:a.model,endpoint_type:"responses"};Me.record(u,p),ze.record(r,p),En(e,i)}catch(o){throw Ve(u,e.get("requestSpan"),o),await _n(t,o),o}finally{n&&an(u,n),u.end(),p()}let f=e.get("requestId");f&&ce.executeCompletion(f)}finally{e.get("resolveStreamComplete")?.()}})}const ga=new q;ga.post("/",async e=>{try{return await ca(e)}catch(t){return await Yt(e,t)}});const _a=new q;function ya(e){return he.startActiveSpan("copilot_api.model.validate",t=>{try{t.setAttribute("copilot_api.model.requested",e.model);let n=fn(e.model);return t.setAttribute("copilot_api.model.normalized",n),n===e.model?(t.setAttribute("copilot_api.model.was_mapped",!1),e):(t.setAttribute("copilot_api.model.was_mapped",!0),xe.add(1,{from_model:e.model,to_model:n}),o.debug(`Normalized model from '${e.model}' to '${n}'`),{...e,model:n})}finally{t.end()}})}function ka(e,t){let o=function(e){try{let t=JSON.parse(e);if(("response.completed"===t.type||"response.incomplete"===t.type)&&t.response?.usage){let e=t.response.usage;return{prompt_tokens:e.input_tokens,completion_tokens:e.output_tokens,total_tokens:e.total_tokens}}}catch{}return null}(e);if(!o)return;t.usageRef.value=o;let n=t.c.get("requestData")||{};n.tokenUsage=rn(o),n._d1=t._d1,t.c.set("requestData",n)}_a.get("/",async e=>{try{X.models||await ro();let t=X.models?.data.map(e=>({id:e.id,object:"model",type:"model",created:0,created_at:new Date(0).toISOString(),owned_by:e.vendor,display_name:e.name,context_length:e.capabilities.limits?.max_context_window_tokens}));return e.json({object:"list",data:t,has_more:!1})}catch(t){return await Yt(e,t)}});const wa=new Set(["message","function_call","function_call_output"]),ba=new Set(["type","name","description","parameters"]);async function va(e){if(!e)return!1;let t=e.sources;if(t&&t.length>0)return!1;let n=e.query??e.queries?.[0];return!(!n||!oa())&&(o.info(`Enriching web search: "${n}"`),e.sources=(await na(n,{maxResults:5})).map(e=>({type:"url",url:e.url,title:e.title,content:e.content})),!0)}async function Ta(e){if(oa())try{for(let t of e.output){let e=t;"web_search_call"===e.type&&await va(e.action)}}catch(e){o.error("Failed to enrich non-streaming web search:",e)}}async function $a(e){if(!oa())return e;try{let t=JSON.parse(e);if("response.output_item.done"===t.type){let e=t.item;if("web_search_call"===e?.type&&await va(e.action))return JSON.stringify(t)}}catch(e){o.error("Failed to enrich web search:",e)}return e}function xa(e,t){if("function_call"!==e.type||!t.has(e.name))return!1;if(e.type="custom_tool_call","string"==typeof e.arguments){try{e.input=JSON.parse(e.arguments).input??e.arguments}catch{e.input=e.arguments}delete e.arguments}return!0}function Aa(e,t){if(0===t.size)return e;try{let o=JSON.parse(e),n=o.type;if("response.output_item.added"===n||"response.output_item.done"===n){let e=o.item;if(e&&xa(e,t))return JSON.stringify(o)}if("response.completed"===n){let n=o.response?.output;if(!n)return e;let r=!1;for(let e of n)xa(e,t)&&(r=!0);if(r)return JSON.stringify(o)}}catch{}return e}function Sa(e){return null!=e}function Ea(e){let t=e.input,o="string"==typeof t?t:t.map(e=>function(e){switch(e.type){case"custom_tool_call":{let t=e.input;return{type:"function_call",call_id:e.call_id,name:e.name,arguments:JSON.stringify("string"==typeof t?{input:t}:t)}}case"custom_tool_call_output":return{type:"function_call_output",call_id:e.call_id,output:e.output};default:return wa.has(e.type)||"web_search_call"===e.type?e:null}}(e)).filter(e=>null!==e),n={model:e.model,input:o};for(let t of["instructions","max_output_tokens","temperature","top_p","stream","tool_choice","parallel_tool_calls","user"])Sa(e[t])&&(n[t]=e[t]);let r=new Set;if(Sa(e.tools)){let t=function(e){let t=new Set;return{tools:e.filter(e=>{let t=e.type;return"function"===t||"custom"===t||"web_search"===t||t.startsWith("web_search_")}).map(e=>{let o=e.type;if("web_search"===o||o.startsWith("web_search_"))return{type:e.type};let n={};for(let t of Object.keys(e))ba.has(t)&&(n[t]=e[t]);return"custom"===n.type&&(n.type="function",t.add(n.name),n.parameters||={type:"object",properties:{input:{type:"string",description:"The freeform tool input content"}},required:["input"],additionalProperties:!1}),n}),customToolNames:t}}(e.tools);n.tools=t.tools,r=t.customToolNames}if(Sa(e.reasoning)&&"object"==typeof e.reasoning){let t=e.reasoning;n.reasoning={},Sa(t.effort)&&(n.reasoning.effort=t.effort),Sa(t.summary)&&(n.reasoning.summary=t.summary)}if(Sa(e.text)&&"object"==typeof e.text){let t=e.text;Sa(t.format)&&(n.text={format:t.format})}return{payload:n,customToolNames:r}}async function Ca(e){if(X._t1)return null;if(!await ko()){let t=fo();return t?(d.getActiveSpan()?.setAttribute("copilot_api.error_type","authentication_error"),e.json({error:{message:`${t.message}; re-authenticate with \`copilot-api auth\`, then restart the proxy`,type:"authentication_error"}},401)):(d.getActiveSpan()?.setAttribute("copilot_api.error_type","service_unavailable"),e.header("Retry-After","1"),e.json({error:{message:"Service token not yet available; retry shortly",type:"service_unavailable"}},503))}return null}async function Oa(e){await hn(X);let{payload:t,customToolNames:n}=Ea(await e.req.json()),r=t;o.debug(`Responses API [${Array.isArray(r.input)?r.input.length:1} items]`),n.size>0&&o.debug(`Custom tools detected: ${[...n].join(", ")}`);let a=function(e,t){try{return{ok:!0,payload:ya(t)}}catch(t){if(t instanceof mn)return{ok:!1,response:e.json({error:{message:t.message,type:"invalid_request_error",code:"invalid_model"}},t.statusCode)};throw t}}(e,r);if(!a.ok)return a.response;r=a.payload;let i=await Ca(e);if(i)return i;e.set("requestData",{model:r.model,reasoningEffort:r.reasoning?.effort,streaming:!!r.stream}),X.manualApprove&&await nn();let s=performance.now(),l=await mr(r),c=performance.now()-s;if(De.record(c,{model:r.model,target:"responses",streaming:String(!!r.stream)}),Ia(l))return async function(e,t,o){await Ta(t);let n=e.get("requestData")||{};return t.usage&&(n.tokenUsage=rn({prompt_tokens:t.usage.input_tokens,completion_tokens:t.usage.output_tokens,total_tokens:t.usage.total_tokens})),n._d1=o,n.upstreamTtfbMs=o,n.upstreamTotalMs=o,e.set("requestData",n),e.json(t)}(e,l,c);let{events:u,span:p,release:d}=l;return D(e,async t=>{let o={value:null},a=0,i=performance.now(),l=Sn(e,s);try{try{for await(let i of u)if(l(),i.data&&"[DONE]"!==i.data){a++;let s=Aa(i.data,n);s=await $a(s);let l=s===i.data?i:{...i,data:s};Ie.add(1,{model:r.model,endpoint_type:"responses"}),ka(s,{usageRef:o,c:e,_d1:c}),await t.writeSSE(l)}else await t.writeSSE(i);let p=performance.now()-i,d={model:r.model,endpoint_type:"responses"};Me.record(p,d),ze.record(a,d),En(e,s)}catch(o){throw Ve(p,e.get("requestSpan"),o),await yn(t,o),o}finally{o.value&&an(p,o.value),p.end(),d()}let m=e.get("requestId");m&&ce.executeCompletion(m)}finally{e.get("resolveStreamComplete")?.()}})}const Ia=e=>Object.hasOwn(e,"output"),Pa=new q;Pa.post("/",async e=>{try{return await Oa(e)}catch(t){return await Yt(e,t)}});const Ra=new q;Ra.get("/",e=>{try{return X.showToken?e.json({token:X._t1}):e.json({error:"Token endpoint disabled. Restart with --show-token to enable it.",token:null},403)}catch(t){return o.error("Error fetching token:",t),e.json({error:"Failed to fetch token",token:null},500)}});const Na=new q;Na.get("/",async e=>{try{let t=await $o();return e.json(t)}catch(t){return o.error("Error fetching usage:",t),e.json({error:"Failed to fetch usage"},500)}});const qa=new q;function ja(){return function(e){let t=e.filter(e=>en(e));if(0===t.length)return;let o=t.find(e=>Qo.test(e.id));return o?o.id:(t.find(e=>"Anthropic"===e.vendor)??t[0]).id}(X.models?.data??[])}function Da(e,t,o){let n=function(e){if(!e)return;try{let t=JSON.parse(e),o=t.error?.message??t.message;if("string"==typeof o&&o.length>0)return Vo(o).slice(0,200)}catch{}let t=Vo(e).trim();return t.length>0?t.slice(0,200):void 0}(t),r=n?` (upstream: ${n})`:"";switch(!0){case 401===e:case 403===e:return`Authentication/entitlement failed (HTTP ${e}). Your GitHub Copilot subscription may be inactive, or the Auth token is invalid. Run \`copilot-api auth\` to re-authenticate; if it persists, this account has no active Copilot access${r}.`;case 402===e:return`Premium monthly quota exhausted (HTTP 402). Switch to a non-premium model (e.g. claude-haiku-4.5) or wait for the monthly quota reset${r}.`;case 400===e:return`Model '${o}' was rejected (HTTP 400). On individual plans only some models are entitled — try claude-haiku-4.5, or run \`copilot-api doctor\` to see what works${r}.`;case 413===e:return`Request too large (HTTP 413)${r}.`;case 429===e:return`Rate limited upstream (HTTP 429) — wait and retry${r}.`;case 503===e:return`Service not ready (HTTP 503) — the model catalog or Service token is still warming up. Retry in a few seconds${r}.`;case e>=500:return`Upstream error (HTTP ${e})${r}.`;default:return`Unexpected response (HTTP ${e})${r}.`}}async function Ma(e={}){let t=performance.now(),o=e.model&&function(e){let t=X.models?.data.find(t=>t.id===e);return void 0!==t&&en(t)}(e.model)?e.model:ja();if(!o)return{ok:!1,durationMs:0,reason:"No models available — the catalog is empty (upstream /models failed at startup). Check connectivity and authentication."};let n,r=e.timeoutMs??3e4,a=()=>Math.round(performance.now()-t),i=(async()=>{try{let e=await qa.request("/chat/completions",{method:"POST",headers:{"content-type":"application/json",[Xo]:Zo},body:JSON.stringify({model:o,messages:[{role:"user",content:"ping"}],max_tokens:1,stream:!1})});if(e.ok)return{ok:!0,model:o,status:e.status,durationMs:a()};let t=await e.text().catch(()=>"");return{ok:!1,model:o,status:e.status,durationMs:a(),reason:Da(e.status,t,o),detail:t.slice(0,400)||void 0}}catch(e){let t=e instanceof Error?e.message:String(e);return{ok:!1,model:o,durationMs:a(),reason:`Request failed before a usable response: ${t}`,detail:t}}})(),s=new Promise(e=>{n=setTimeout(()=>{e({ok:!1,model:o,durationMs:a(),reason:`Did not complete within ${r}ms. If you started with --manual, approve the request or use --no-smoke-test; otherwise the upstream may be slow or unreachable.`})},r)});try{return await Promise.race([i,s])}finally{n&&clearTimeout(n)}}qa.use(async(e,t)=>{let n=performance.now(),r=`req_${Date.now()}_${Math.random().toString(36).slice(2,11)}`,a=e.req.method,i=e.req.path,s=_t(i),p=function(e){return e===Zo}(e.req.header(Xo));e.set("requestId",r),e.set("isSelfTest",p),e.header("x-request-id",r);let m=he.startSpan("copilot_api.handle_request",{kind:l.SERVER,attributes:{"http.method":a,"http.url":e.req.url,"http.route":i,"copilot_api.request_id":r,"copilot_api.endpoint_type":s}});e.set("requestSpan",m),e.set("requestTraceContext",m.spanContext()),p&&m.setAttribute("copilot_api.self_test",!0);for(let[t,o]of Object.entries(e.req.header())){let e=t.toLowerCase();Xe.has(e)||"x-copilot-api-self-test"!==e&&m.setAttribute(`http.request.header.${e}`,o)}await async function(e,t){let{method:n,path:r,endpointType:a}=t;if("POST"===n&&("anthropic"===a||"openai"===a||"embeddings"===a||r.includes("/responses")))try{let t=await e.req.raw.clone().text();e.set("rawBody",t.length>on?t.slice(0,on):t)}catch(e){o.warn("Failed to cache incoming request body for error capture:",e)}}(e,{method:a,path:i,endpointType:s});let f,h=new Promise(e=>{f=e});e.set("streamComplete",h),e.set("resolveStreamComplete",f);let g=d.setSpan(u.active(),m);await u.with(g,async()=>{p||ce.registerCompletion(r,e,n);try{await t()}catch(e){let t=e instanceof Error?e:Error(String(e));throw m.setStatus({code:c.ERROR,message:t.message}),m.recordException(t),e}});let _=e.get("requestData"),y={c:e,start:n,method:a,path:i,endpointType:s,requestId:r,span:m};_?.streaming&&e.res.status<400?h.then(()=>tn(y)).catch(e=>{o.warn("Error finalizing streaming request:",e);let t=e instanceof Error?e:Error(String(e));try{m.recordException(t),m.setStatus({code:c.ERROR,message:`Stream finalization failed: ${t.message}`})}catch{}try{m.end()}catch{}}):tn(y)}),qa.use(j()),qa.use(async(e,t)=>{let o=e.req.header("content-length");if(o){let t=Number(o);if(Number.isFinite(t)&&t>33554432)return r.warn(`Rejected oversized request: ${t} bytes on ${e.req.path} (UA: ${e.req.header("user-agent")??"unknown"})`),e.json({type:"error",error:{type:"request_too_large",message:`Request body exceeds 32 MB limit (got ${t} bytes).`}},413)}await t()}),qa.get("/",e=>e.text("Server running")),qa.route("/health",Xn),qa.route("/chat/completions",Vn),qa.route("/models",_a),qa.route("/embeddings",Yn),qa.route("/usage",Na),qa.route("/token",Ra),qa.route("/v1/chat/completions",Vn),qa.route("/v1/models",_a),qa.route("/v1/embeddings",Yn),qa.route("/v1/messages",ga),qa.post("/v1/messages/count_tokens",async function(e){let t;try{t=await e.req.json()}catch{return e.json({error:{type:"invalid_request_error",message:"Invalid JSON"}},400)}if(!Array.isArray(t.messages))return e.json({error:{type:"invalid_request_error",message:"messages is required"}},400);let o=nr.baseOverhead;if(t.system){let e="string"==typeof t.system?t.system:t.system.map(e=>e.text).join("\n\n");o+=nr.perMessage+rr(e)*nr.contentMultiplier}for(let e of t.messages)o+=nr.perMessage,o+=rr(e.role),"string"==typeof e.content?o+=rr(e.content)*nr.contentMultiplier:Array.isArray(e.content)&&(o+=ar(e.content));let n=t.tools?.filter(tr);return n&&n.length>0&&(o+=function(e){let t=nr.toolsExist;for(let[o,n]of e.entries())o>0&&(t+=nr.perTool),t+=rr(n.name),n.description&&(t+=nr.perDesc+rr(n.description)),t+=ir(n.input_schema);return t}(n)),e.json({input_tokens:Math.round(o)})}),qa.route("/v1/responses",Pa),qa.route("/responses",Pa),qa.onError((e,t)=>Yt(t,e));const Ha=e=>`[1m${e}[0m`,Ba=e=>`[2m${e}[0m`,Fa=e=>`[32m${e}[0m`,Ua=e=>`[31m${e}[0m`,La=e=>`[33m${e}[0m`,Ga=Ba(" ─────────────────────────────────────────────────────────────");function za(e,t,o){console.log(` ${function(e){return"ok"===e?Fa("✓"):"warn"===e?La("⚠"):Ua("✗")}(e)} ${Ha(t.padEnd(14))} ${o}`)}function Ja(e){console.log(` ${Ba("↳")} ${Ba(e)}`)}function Ka(e){return e instanceof Dt?`HTTP ${e.response.status} ${e.message}`:e instanceof Error?e.message:String(e)}async function Wa(){let e=g.env.GH_TOKEN;if(e&&e.trim().length>0)return{token:e.trim(),source:"GH_TOKEN env"};let t=await async function(){try{let e=(await a.readFile(K.GITHUB_TOKEN_PATH,"utf8")).trim();return e.length>0?e:void 0}catch{return}}();return t?{token:t,source:"stored file"}:void 0}async function Va(){try{await ro();let e=(X.models?.data.length??0)>0;return za(e?"ok":"warn","Model catalog",e?function(){let e=X.models?.data??[],t={Claude:0,OpenAI:0,Gemini:0,Embedding:0};for(let o of e)o.id.startsWith("text-embedding")?t.Embedding++:"Anthropic"===o.vendor?t.Claude++:"Google"===o.vendor?t.Gemini++:t.OpenAI++;let o=Object.entries(t).filter(([,e])=>e>0).map(([e,t])=>`${e}: ${t}`);return`${e.length} models (${o.join(", ")})`}():"empty"),e}catch(e){return za("fail","Model catalog",Ka(e)),Ja("Could not fetch /models — check connectivity/auth."),!1}}async function Ya(e){X.accountType=e.accountType;let t=await St(),o=Et();if(console.log(""),console.log(` ${Ha("COPILOT-API DOCTOR")} ${Ba(`v${t}`)}`),console.log(Ga),za("ok","Runtime",`${o.name} ${o.version} (${o.platform}-${o.arch})`),await W(),ao(),!await async function(){let e=await Wa();if(!e)return za("fail","Auth token","not found"),void Ja("Run `copilot-api auth` (or `copilot-api start`) to authenticate.");X._t2=e.token,za("ok","Auth token",`found (${e.source})`);try{let e=await Zt();return await st(X,e.login),za("ok","GitHub auth",`logged in as ${e.login}`),e.login}catch(e){return za("fail","GitHub auth",Ka(e)),void Ja("Token looks invalid/expired. Re-run `copilot-api auth`.")}}())return console.log(Ga),console.log(` ${Ua("✗")} ${Ha("Authentication failed")} — cannot continue.`),console.log(""),1;let n=await async function(){try{let{token:e}=await Xt();return X._t1=e,za("ok","Service token","acquired"),!0}catch(e){let t=e instanceof Dt?e.response.status:0;return za("fail","Service token",Ka(e)),Ja(401===t?"Auth token is invalid/expired — run `copilot-api auth`.":403===t?"No active GitHub Copilot subscription on this account. Re-auth won't help.":"Transient/network issue — check connectivity and retry."),!1}}(),r=!!n&&await Va();await async function(){try{let e=await $o(),t=e.quota_snapshots.premium_interactions;za("ok","Copilot plan",`${e.copilot_plan} · premium ${t.percent_remaining.toFixed(0)}% remaining `+Ba(`(resets ${e.quota_reset_date})`))}catch(e){za("warn","Copilot plan",`unavailable (${Ka(e)})`)}}();let a=!1;return n&&r?a=await async function(){let e=await Ma();return e.ok?(za("ok","Generation",`works via ${e.model} ${Ba(`(${e.durationMs}ms)`)}`),!0):(za("fail","Generation",`${e.reason}${e.status?Ba(` [HTTP ${e.status}]`):""}`),!1)}():za("warn","Generation","skipped (no token or empty catalog)"),function(){let e=[],t="ok";for(let o of["ANTHROPIC_BASE_URL","OPENAI_BASE_URL"]){let n=g.env[o];n&&("ANTHROPIC_BASE_URL"===o&&/\/v1\/*$/.test(n)&&(t="warn",e.push(`${o}=${n} ends in /v1 — Claude Code appends /v1/messages, producing a doubled /v1/v1/... path (404). Drop the trailing /v1.`)),/\/v1\/v1(?:\/|$)/.test(n)&&(t="warn",e.push(`${o}=${n} contains a doubled /v1/v1 path (404).`)))}if(e.length>0){za(t,"Client config","potential base-URL issue");for(let t of e)Ja(t)}else za("ok","Client config","no base-URL issues detected");Ja("Point clients at http://127.0.0.1:4141. For Docker/LAN, start with --hostname 0.0.0.0.")}(),console.log(Ga),a?(console.log(` ${Fa("✓")} ${Ha("All systems go")} — your proxy can generate. Point your client at it and go.`),console.log(""),0):(console.log(` ${La("⚠")} ${Ha("Some checks need attention")} — see the ${Ua("✗")}/${La("⚠")} lines above.`),console.log(""),2)}const Xa=e({meta:{name:"doctor",description:"Diagnose your setup end-to-end: token, auth, entitlement, model catalog, and one real generation. Tells you exactly what's wrong and how to fix it."},args:{"account-type":{alias:"a",type:"string",default:"individual",description:"Account type to check against (individual, business, enterprise)"}},async run({args:e}){let t=await Ya({accountType:e["account-type"]});g.exit(t)}});function Za(e){return{log(t,r){let a=o.level>=n.debug;if(t.level!==n.warn||a)for(let o of e)o.log(t,r)}}}let Qa=!1;const ei="copilot-api-node20",ti=`https://registry.npmjs.org/${ei}/latest`,oi=e=>`[1m${e}[0m`,ni=e=>`[33m${e}[0m`;async function ri(){let e=new AbortController,t=setTimeout(()=>e.abort(),5e3);"object"==typeof t&&"unref"in t&&t.unref();try{let t=await fetch(ti,{signal:e.signal});return t.ok?(await t.json()).version??null:null}catch{return null}finally{clearTimeout(t)}}function ai(e,t){let o=Math.max(0,t-function(e){return e.replaceAll(/\x1b\[[0-9;]*m/g,"").length}(e));return e+" ".repeat(o)}function ii(e,t=""){let o,n=function(){let{platform:e,ppid:t,env:o}=g;if("win32"===e){try{if(h(`wmic process get ParentProcessId,Name | findstr "${t}"`,{stdio:"pipe"}).toString().toLowerCase().includes("powershell.exe"))return"powershell"}catch{return"cmd"}return"cmd"}{let e=o.SHELL;if(e){if(e.endsWith("zsh"))return"zsh";if(e.endsWith("fish"))return"fish";if(e.endsWith("bash"))return"bash"}return"sh"}}(),r=Object.entries(e).filter(([,e])=>void 0!==e);switch(n){case"powershell":o=r.map(([e,t])=>`$env:${e} = ${t}`).join("; ");break;case"cmd":o=r.map(([e,t])=>`set ${e}=${t}`).join(" & ");break;case"fish":o=r.map(([e,t])=>`set -gx ${e} ${t}`).join("; ");break;default:{let e=r.map(([e,t])=>`${e}=${t}`).join(" ");o=r.length>0?`export ${e}`:"";break}}return o&&t?`${o}${"cmd"===n?" & ":" && "}${t}`:o||t}const si=e=>`[1m${e}[0m`,li=e=>`[2m${e}[0m`,ci=e=>`[36m${e}[0m`,ui=e=>`[32m${e}[0m`,pi=e=>`[33m${e}[0m`,di=e=>`[4m${e}[0m`,mi=(e,t)=>`]8;;${e}\\${t}]8;;\\`,fi="?utm_source=copilot-cli&utm_medium=terminal&utm_campaign=startup_banner",hi="https://github.com/johnib/copilot-api-issues/issues",gi=li(" ─────────────────────────────────────────────────────────────");function _i(e){return void 0===e?"":e>=1e6?`${(e/1e6).toFixed(0)}M`:`${(e/1e3).toFixed(0)}K`}function yi(e){return e&&0!==e.length?e.join("·"):"—"}const ki=[{title:"I Had Claude Mine 30 Days of My Own Messages. What It Found Was Uncomfortably Accurate.",teaser:"I had Claude read a month of my messages. It nailed me.",url:"https://barazany.dev/blog/mining-claude-history-ultracode"},{title:"The 5-Hour Quota, Boris's Tweet, and What the Source Code Actually Reveals",teaser:"Claude Code's caching story — decoded from the source.",url:"https://barazany.dev/blog/claude-code-token-caching"},{title:"Claude Code's Compaction Engine: What the Source Code Actually Reveals",teaser:"What's actually running beneath every long session.",url:"https://barazany.dev/blog/claude-codes-compaction-engine"}];function wi(e){if(0===e.length)return[];let t=["",gi,` ${si("BARAZANY.DEV")} ${li("— Recent Posts")}`,gi,""];for(let[o,n]of e.entries()){let e=mi(`${n.url}${fi}`,si(di(`[${o+1}]`)));t.push(` ${e} ${ci(n.title)}`,` ${li("→")} ${li(n.teaser)}`,"")}return t.push(gi,` ${mi(`https://barazany.dev/blog${fi}`,"barazany.dev/blog")}`,gi),t}function bi(e){let t=[];X.connectivity.h2Keepalive?t.push("HTTP/2 keepalive"):X.connectivity.h2&&t.push("HTTP/2"),t.push(`timeout ${e.timeout/1e3}s`);let o=e.webSearchProviders.length>0?`${e.webSearchProviders.map(e=>(e=>e&&e[0].toUpperCase()+e.slice(1))(e)).join(li(" → "))} ${ui("✓")}`:li("off"),n=["",` ${si("COPILOT-API")} ${li(`v${e.version}`)}`,gi,` ${li("Runtime")} ${e.runtime.name} ${e.runtime.version} (${e.runtime.platform}-${e.runtime.arch})`,` ${li("User")} ${e.user} ${li("·")} ${e.accountType}`];return X._v1&&n.push(` ${li("Client")} VSCode ${X._v1}`),n.push(` ${li("Network")} ${t.join(li(" · "))}`,` ${li("Search")} ${o}`),e.clipboardCopied&&n.push(` ${li("Clipboard")} Claude Code command ${ui("✓")}`),n.push(gi),n}function vi(e){if(!e.model&&!e.smallModel)return[];let t=["",` ${si("Active")}`];if(e.model){let o=X.models?.data.find(t=>t.id===e.model),n=_i(o?.capabilities.limits?.max_context_window_tokens),r=yi(o?.capabilities.supports.reasoning_effort);t.push(` ${ci(e.model.padEnd(32))} ${li("ctx")} ${si(n.padStart(5))} ${li("effort")} ${li(r)} ${pi("← main")}`)}if(e.smallModel){let o=X.models?.data.find(t=>t.id===e.smallModel),n=_i(o?.capabilities.limits?.max_context_window_tokens),r=yi(o?.capabilities.supports.reasoning_effort);t.push(` ${e.smallModel.padEnd(32)} ${li("ctx")} ${n.padStart(5)} ${li("effort")} ${li(r)} ${pi("← small")}`)}return t}function Ti(e){let t=[];for(let[o,n]of function(){let e=[],t=[],o=[],n=[];for(let r of X.models?.data??[]){let a=r.capabilities.limits?.max_context_window_tokens,i={id:r.id,ctx:a,effort:r.capabilities.supports.reasoning_effort};r.id.startsWith("text-embedding")?n.push(i):"Anthropic"===r.vendor?e.push(i):"Google"===r.vendor?o.push(i):t.push(i)}return[["Claude",e],["OpenAI",t],["Gemini",o],["Embedding",n]]}())if(0!==n.length){t.push("",` ${si(o)}`);for(let r of n){let n=r.id===e.model||r.id===e.smallModel,a=n?ci("●"):li("·"),i=n?ci(r.id.padEnd(34)):r.id.padEnd(34),s=r.ctx?_i(r.ctx).padStart(5):"".padStart(5),l="Embedding"===o?"":` ${yi(r.effort)}`;t.push(` ${a} ${i} ${li(s)}${li(l)}`)}}return t}function $i(){let e=hi.replace(/^https:\/\//,""),t=mi(`${hi}?utm_source=copilot-cli&utm_medium=terminal&utm_campaign=issues_banner`,e);return["",gi,` ${si("FOUND A BUG?")} ${li("— Report it on GitHub")}`,gi,"",` ${ci("→")} ${ci(t)}`,` ${li("Bug reports, feature requests, and questions welcome.")}`,"",gi]}function xi(e){if(!e.endpoints)return[];let{scheme:t,port:o,hostname:n}=e.endpoints,r=n?`${t}://${n}:${o}`:`${t}://<your-tailscale-hostname>:${o}`,a=["",gi,` ${si("Claude Cowork")} ${li("— Settings → Inference Provider")}`,gi,"",` ${li("Paste into")} ${si("inferenceGatewayBaseUrl")}${li(":")}`,` ${si(ci(r))}`];return n||a.push("",` ${li("Your Tailscale hostname is shown by:")} ${ci("tailscale status --self")}`),a.push("",` ${li("Docs:")} ${ci("https://claude.com/docs/cowork/3p/installation")}`),a}function Ai(e){if(!e.https||!e.https.selfSigned)return[];let{certPath:t}=e.https,o=["",gi,` ${si("HTTPS")} ${li("— self-signed cert")}`,gi,"",` ${li("Cert")} ${t}`];switch(o.push("",` ${si("Trust this cert")} ${li("(one-time setup)")}`),g.platform){case"darwin":o.push(` ${li("macOS:")}`,` ${ci("sudo security add-trusted-cert -d -r trustRoot \\")}`,` ${ci(`-k /Library/Keychains/System.keychain "${t}"`)}`);break;case"win32":o.push(` ${li("Windows (PowerShell as Administrator):")}`,` ${ci(`Import-Certificate -FilePath "${t}" \``)}`,` ${ci("-CertStoreLocation Cert:\\LocalMachine\\Root")}`);break;case"linux":o.push(` ${li("Linux (Debian/Ubuntu):")}`,` ${ci(`sudo cp "${t}" /usr/local/share/ca-certificates/copilot-api.crt`)}`,` ${ci("sudo update-ca-certificates")}`,` ${li("Linux (Fedora/RHEL/Arch):")}`,` ${ci(`sudo cp "${t}" /etc/pki/ca-trust/source/anchors/copilot-api.crt`)}`,` ${ci("sudo update-ca-trust")}`);break;default:o.push(` ${li("(Unknown platform — see Node fallback below.)")}`)}return o.push("",` ${li("Or, for Node CLIs only (no admin needed):")}`,` ${ci(`export NODE_EXTRA_CA_CERTS="${t}"`)}`,gi),o}function Si(e){let t=Math.floor(e/1e3),o=Math.floor(t/3600),n=Math.floor(t%3600/60);return o>0?`${o}h ${n}m`:n>0?`${n}m`:`${t}s`}const Ei=s.join(K.APP_DIR,"certs"),Ci=s.join(Ei,"cert.pem"),Oi=s.join(Ei,"key.pem"),Ii=s.join(Ei,"cert.meta.json");async function Pi(e){try{return await a.readFile(e,"utf8")}catch{return}}async function Ri(e){let t=await Pi(Ci),o=await Pi(Oi),n=await async function(){let e=await Pi(Ii);if(e)try{let t=JSON.parse(e);return Array.isArray(t.hosts)&&"string"==typeof t.notAfter?t:void 0}catch{return}}();if(!t||!o||!n)return!1;let r=new Set(n.hosts);for(let t of e)if(!r.has(t))return!1;let a=Date.parse(n.notAfter);return!Number.isNaN(a)&&a-Date.now()>2592e6}function Ni(e){return 0!==G(e)}async function qi(e){await a.mkdir(Ei,{recursive:!0});let t=new Date,o=new Date;o.setDate(o.getDate()+825);let n=["127.0.0.1","::1"],r=new Set(["localhost"]),i=new Set(n);for(let t of e)Ni(t)?i.add(t):r.add(t);let s=await z([{name:"commonName",value:"localhost"},{name:"organizationName",value:"copilot-api"}],{keyType:"ec",curve:"P-256",algorithm:"sha256",notBeforeDate:t,notAfterDate:o,extensions:[{name:"basicConstraints",cA:!1},{name:"keyUsage",digitalSignature:!0,keyEncipherment:!0,critical:!0},{name:"extKeyUsage",serverAuth:!0,clientAuth:!0},{name:"subjectAltName",altNames:[...[...r].map(e=>({type:2,value:e})),...[...i].map(e=>({type:7,ip:e}))]}]});return await a.writeFile(Ci,s.cert,{mode:420}),await a.writeFile(Oi,s.private,{mode:384}),await async function(e){await a.writeFile(Ii,JSON.stringify(e,null,2),{mode:420})}({hosts:[...r,...i].sort(),notAfter:o.toISOString()}),{cert:s.cert,key:s.private,certPath:Ci,keyPath:Oi,generated:!0}}const ji=[],Di=Date.now();let Mi="";function Hi(){let e=async(e,t=0)=>{let n=he.startSpan("copilot_api.server.shutdown",{kind:l.INTERNAL,attributes:{"copilot_api.shutdown.reason":e,"copilot_api.shutdown.exit_code":t,"copilot_api.uptime_seconds":(Date.now()-Di)/1e3}});for(let t of ji)try{await t()}catch(e){o.error("Error during cleanup:",e)}n.end(),function(e,t){let o=mi("https://barazany.dev?utm_source=copilot-cli&utm_medium=terminal&utm_campaign=goodbye_banner","barazany.dev"),n=["",gi,` ${si("COPILOT-API")} ${li(`v${e}`)} ${li("·")} ${Si(t)} uptime`,gi,""," Check in from time to time on",` ${ci(o)}`,"",gi,""];console.log(n.join("\n"))}(Mi,Date.now()-Di),g.exit(t)};g.on("SIGINT",()=>e("SIGINT")),g.on("SIGTERM",()=>e("SIGTERM")),g.on("uncaughtException",t=>{o.error("Uncaught exception:",t),e("uncaughtException",1)}),g.on("unhandledRejection",(t,n)=>{o.error("Unhandled promise rejection at:",n,"reason:",t),e("unhandledRejection",1)})}function Bi(e){return e._t2?"cli_arg":g.env.GH_TOKEN?"env_var":"stored"}function Fi(e){let{options:t,version:o,runtime:n,_u1:r}=e,a=he.startSpan("copilot_api.server.startup",{kind:l.INTERNAL,attributes:Ye({config:{version:o,port:t.port,accountType:t.accountType,verbose:t.verbose,manualApprove:t.manual,rateLimitSeconds:t.rateLimit??0,rateLimitWait:t.rateLimitWait,timeoutMs:t.timeout,showToken:t.showToken,_cc1:t._cc1,model:t.model,smallModel:t.smallModel,_t3:Bi(t)},runtime:n,identity:{_u1:r.login,machineId:X.machineId,sessionId:X.sessionId,_v1:X._v1},connectivity:X.connectivity,modelsCount:X.models?.data.length??0,startupDurationMs:Date.now()-Di},"copilot_api")});if(X.models?.data)for(let e of X.models.data)a.addEvent("copilot_api.model.available",Ye(e,"model"));a.end(),Ke(_.INFO,"INFO","Server started",Ye({version:o,port:t.port,accountType:t.accountType,_u1:r.login,modelsCount:X.models?.data.length??0,startupDurationMs:Date.now()-Di},"copilot_api"))}async function Ui(e){if(e.https){if(e.httpsCert&&e.httpsKey)return async function(e,t){let[o,n]=await Promise.all([a.readFile(e,"utf8"),a.readFile(t,"utf8")]);return{cert:o,key:n,certPath:e,keyPath:t,generated:!1}}(e.httpsCert,e.httpsKey);if(e.httpsCert||e.httpsKey)throw Error("Both --https-cert and --https-key must be provided together");return async function(e=[]){if(await Ri(e)){let e=await Pi(Ci),t=await Pi(Oi);if(e&&t)return{cert:e,key:t,certPath:Ci,keyPath:Oi,generated:!1}}return o.info("Generating new self-signed TLS certificate…"),qi(e)}(e.httpsHosts)}}async function Li(e){let t=function(e){if(!e.claudeCowork)return e;if(e.httpsCert&&e.httpsKey)return{...e,https:!0};let{certPath:t,keyPath:n}=Uo;try{U(t),U(n)}catch{throw o.error("Tailscale cert not found. Run `copilot-api cowork-setup install` first."),Error("Tailscale cert not found")}return{...e,https:!0,httpsCert:t,httpsKey:n}}(e);if(Hi(),ji.push(()=>{o.debug("Cleaning up connectivity monitor"),tt.stop()},()=>{o.debug("Cleaning up token management"),o.debug("Cleaning up token management"),so&&=void clearInterval(so),co&&=void tt.off("online",co),uo&&=void tt.off("offline",uo),lo=void 0,po=void 0},async()=>{o.debug("Cleaning up HTTP/2 client"),await async function(){o.debug("Stopping HTTP/2 pool"),Rn&&=void clearInterval(Rn),Nn&&=void clearInterval(Nn);let e=[...On.keys(),...In];On.clear(),In.clear(),Cn.clear(),Pn=void 0;for(let t of e)qn(t)&&(Ne.add(1,{event:"closed"}),await t.close())}()},async()=>{o.debug("Shutting down OTel SDK"),await async function(){if(!ue)return;let e=5e3,t=new Promise(e=>{setTimeout(()=>e("timeout"),5e3).unref()});try{"timeout"===await Promise.race([ue.shutdown(),t])&&o.warn("OTel SDK shutdown timed out after 5000ms; continuing exit")}catch(e){o.warn("OTel SDK shutdown failed; continuing exit",e)}}()}),t.verbose&&(o.level=5,o.info("Verbose logging enabled")),t._cc1&&t.codex)throw Error("Cannot use --claude-code and --codex together");X.accountType=t.accountType,X.manualApprove=t.manual,X.rateLimitSeconds=t.rateLimit,X.rateLimitWait=t.rateLimitWait,X.showToken=t.showToken,X.timeoutMs=t.timeout,X.connectivity.timeoutMs=t.connectTimeout,X.webSearchProviders=t.webSearchProviders,X.errorReporting=function(e){let t=g.env.COPILOT_API_ERROR_REPORTING;return(void 0===t||!["0","false","no","off"].includes(t.trim().toLowerCase()))&&e}(t.errorReporting),function(){let e="1"===g.env.COPILOT_H2_KEEPALIVE||"true"===g.env.COPILOT_H2_KEEPALIVE,t=e||"1"===g.env.COPILOT_H2||"true"===g.env.COPILOT_H2;X.connectivity.h2=t,X.connectivity.h2Keepalive=e}(),await W(),ao();let n=await St();Mi=n;let r=Et();(function(e,t){t&&(de=t),pe=crypto.randomUUID();let o=v({[S]:"copilot-api",[E]:e,[A]:pe}),{endpoint:n,headers:r}=fe();ue=new x({resource:o,traceExporter:new b({url:`${n}/v1/traces`,headers:r}),metricReader:new $({exporter:new w({url:`${n}/v1/metrics`,headers:r}),exportIntervalMillis:15e3}),logRecordProcessors:[new T({exporter:new k({url:`${n}/v1/logs`,headers:r})})],instrumentations:[]}),ue.start()})(n,Di),t._t2&&o.warn("Passing the Auth token via --github-token / -g exposes it to other processes on this host (visible in ps/proc). Prefer the GH_TOKEN environment variable instead.");let a,i=t._t2||g.env.GH_TOKEN;i?(X._t2=i,o.info("Using provided Auth token")):await wo();try{a=await Zt(),await st(X,a.login)}catch(e){throw o.error("Failed to get user info for machine ID generation:",e),Error("Cannot proceed without user information",{cause:e})}await(async()=>{let{token:e,refresh_in:t}=await Xt();X._t1=e,o.debug("Service token fetched successfully!"),X.showToken&&o.info("Service token:",e),so=setInterval(()=>{yo(5,1e3,"scheduled").catch(e=>{o.error("Unexpected error in scheduled token refresh:",e)})},1e3*(t-60)),tt.start(),co=()=>{o.debug("Network connectivity restored, attempting immediate token refresh"),yo(3,500,"network-restored").catch(e=>{o.error("Unexpected error in network-restored token refresh:",e)})},uo=()=>{o.debug("Network connectivity lost")},tt.on("online",co),tt.on("offline",uo)})(),await async function(){try{return await ro(),!0}catch(e){let t="object"==typeof e&&e&&"statusCode"in e&&"number"==typeof e.statusCode?e.statusCode:void 0,n=e instanceof Error?e.message:"Unknown error occurred",r=void 0===t?"":` (HTTP ${t})`;return o.warn(`Could not fetch model list from Copilot${r}: ${n}. This is likely a transient network or authentication issue. The proxy will start anyway; model listing endpoints may return empty until the cache is populated.`),!1}}()||function(e){let t=setTimeout(()=>{ro().then(()=>{o.info("Model cache populated successfully on deferred retry")}).catch(()=>{})},e);t.unref()}(3e4);let s=function(e=18e5){let t=setInterval(()=>{ro().then(()=>o.debug("Model list refreshed successfully")).catch(e=>{o.warn("Failed to refresh model list; keeping existing cache:",e)})},e);return t.unref(),()=>{clearInterval(t)}}();ji.push(()=>{o.debug("Cleaning up model refresh interval"),s()}),X.connectivity.h2&&(Mn(Dn(lt(X))),X.connectivity.h2Keepalive&&Bn()),Fi({options:t,version:n,runtime:r,_u1:a});let l=await Ui(t),c=l?"https":"http",u=`${c}://localhost:${t.port}`,p=await async function(e,t,n){if(!e._cc1)return!1;let r,a;if(X.models||(o.error("Cannot apply --claude-code defaults: model cache is empty (Copilot API was unreachable at startup). Retry once the network/API is back, or run without --claude-code."),g.exit(1)),e.model&&e.smallModel){let t=X.models.data.map(e=>e.id);if(!t.includes(e.model))throw o.info(`Available services: \n${t.join("\n")}`),Error(`Invalid model: ${e.model}`);if(!t.includes(e.smallModel))throw o.info(`Available services: \n${t.join("\n")}`),Error(`Invalid small model: ${e.smallModel}`);r=e.model,a=e.smallModel}else{if(e.model||e.smallModel)throw Error("Both --model and --small-model must be specified for model selection");r=await o.prompt("Select a model to use",{type:"select",options:X.models.data.map(e=>e.id)}),a=await o.prompt("Select a small model to use",{type:"select",options:X.models.data.map(e=>e.id)})}let i=ii({ANTHROPIC_BASE_URL:t,ANTHROPIC_AUTH_TOKEN:"dummy",ANTHROPIC_MODEL:r,ANTHROPIC_SMALL_FAST_MODEL:a,NODE_EXTRA_CA_CERTS:n?.certPath},"claude");try{return m.writeSync(i),!0}catch{return o.warn("Failed to copy to clipboard. Here is the command:"),o.log(i),!1}}(t,u,l)||await async function(e,t,n){if(!e.codex)return!1;let r;if(X.models||(o.error("Cannot apply --codex defaults: model cache is empty (Copilot API was unreachable at startup). Retry once the network/API is back, or run without --codex."),g.exit(1)),e.model){let t=X.models.data.map(e=>e.id);if(!t.includes(e.model))throw o.info(`Available services: \n${t.join("\n")}`),Error(`Invalid model: ${e.model}`);r=e.model}else r=await o.prompt("Select a model to use with Codex CLI",{type:"select",options:X.models.data.map(e=>e.id)});let a=ii({OPENAI_BASE_URL:t,OPENAI_API_KEY:"dummy",NODE_EXTRA_CA_CERTS:n?.certPath},`codex --model ${r}`);try{return m.writeSync(a),!0}catch{return o.warn("Failed to copy to clipboard. Here is the Codex CLI command:"),o.log(a),!1}}(t,u,l);(function(e){let t=[...bi(e),...vi(e),...Ti(e),...$i(),"",...wi(ki),...xi(e),...Ai(e),""];console.log(t.join("\n"))})(await async function(e){let{options:t,version:o,runtime:n,user:r,clipboardCopied:a,tls:i}=e,s=i?"https":"http";return{version:o,runtime:n,user:r,accountType:t.accountType,port:t.port,timeout:t.timeout,webSearchProviders:t.webSearchProviders.map(e=>e.name),model:t.model,smallModel:t.smallModel,clipboardCopied:a,https:i?{certPath:i.certPath,keyPath:i.keyPath,generated:i.generated,selfSigned:!t.httpsCert}:void 0,endpoints:t.claudeCowork?{scheme:s,port:t.port,hostname:await Oo()}:void 0}}({options:t,version:n,runtime:r,user:a.login,clipboardCopied:p,tls:l})),L({fetch:qa.fetch,port:t.port,hostname:t.hostname,tls:l?{cert:l.cert,key:l.key}:void 0,bun:{idleTimeout:255}}),function(e,t,n){o.info(`Server listening on ${e}://${t}:${n}`)}(c,t.hostname,t.port),t.smokeTest&&await async function(e,t,n){try{o.start("Running first-run self-test (one tiny generation)…");let r=await Ma({model:t});if(r.ok){let t=void 0===n||["::1","127.0.0.1","localhost"].includes(n)?`Point your client at ${e}`:`Point your client at ${e} — you bound ${n}, so from another machine/container replace \`localhost\` with this host's reachable IP/hostname.`;return void o.success(`Self-test passed — generation works via ${r.model} (${r.durationMs}ms). ${t}`)}let a=r.status?` (HTTP ${r.status})`:"";o.warn(`Self-test FAILED${a}: ${r.reason??"unknown error"}`),r.detail&&o.info(` detail: ${Vo(r.detail)}`),o.info(" The server is still running. Run `copilot-api doctor` to diagnose, or `--no-smoke-test` to skip this check.")}catch(e){o.warn("First-run self-test could not run:",e instanceof Error?e.message:String(e))}}(u,t.smallModel??t.model,t.hostname)}function Gi(e,t){let o=Number.parseInt(e,10);if(Number.isNaN(o))throw Error(`${t} must be a number, got: "${e}"`);return o}const zi=e({meta:{name:"start",description:"Start the API server"},args:{port:{alias:"p",type:"string",default:"4141",description:"Port to listen on"},hostname:{alias:"H",type:"string",default:"127.0.0.1",description:"Hostname/IP to bind the server to. Defaults to 127.0.0.1 (localhost only) for security. Use 0.0.0.0 only when you intentionally need LAN/network/Docker exposure."},verbose:{alias:"v",type:"boolean",default:!1,description:"Enable verbose logging"},"account-type":{alias:"a",type:"string",default:"individual",description:"Account type (individual, business, enterprise)"},manual:{type:"boolean",default:!1,description:"Enable manual request approval"},"rate-limit":{alias:"r",type:"string",description:"Rate limit in seconds between requests"},wait:{alias:"w",type:"boolean",default:!1,description:"Wait instead of error when rate limit is hit. Has no effect if rate limit is not set"},"github-token":{alias:"g",type:"string",description:"Auth token (visible in process list — prefer GH_TOKEN env var)"},"claude-code":{alias:"c",type:"boolean",default:!1,description:"Generate a command to launch with API config"},codex:{type:"boolean",default:!1,description:"Generate a command to launch Codex CLI with Copilot API config"},model:{alias:"m",type:"string",description:"Model to use (with --claude-code or --codex)"},"small-model":{alias:"s",type:"string",description:"Small/fast model to use (requires --claude-code)"},"show-token":{type:"boolean",default:!1,description:"Show tokens on fetch and refresh"},"error-reporting":{type:"boolean",default:!0,description:"Send anonymous, sanitized error reports to the maintainer to help fix bugs (no prompts, completions, or tokens). Use --no-error-reporting or COPILOT_API_ERROR_REPORTING=0 to disable."},timeout:{alias:"t",type:"string",description:"API timeout in milliseconds (default: 600000)"},"connect-timeout":{type:"string",description:"Connectivity probe timeout in milliseconds (default: 15000). Overrides COPILOT_CONNECT_TIMEOUT_MS env var."},"tavily-api-key":{type:"string",description:"[DEPRECATED — set the TAVILY_API_KEY env var instead] Tavily API key for web search."},"web-search-provider":{type:"string",description:'Web search failover order, e.g. "exa,tavily" (first = primary, rest = fallbacks). Web search turns on when TAVILY_API_KEY and/or EXA_API_KEY are set; this flag is optional and only orders the providers you configured.'},https:{type:"boolean",default:!1,description:"Serve over HTTPS using a self-signed certificate (auto-generated and persisted)"},"https-cert":{type:"string",description:"Path to a PEM-encoded TLS certificate (use with --https-key to bring your own cert)"},"https-key":{type:"string",description:"Path to a PEM-encoded TLS private key (use with --https-cert to bring your own cert)"},"https-hosts":{type:"string",description:"Extra hostnames or IPs to include in the self-signed cert's SANs (comma-separated). Example: --https-hosts host.docker.internal,192.168.1.42"},"claude-cowork":{type:"boolean",default:!1,description:"Print Claude Cowork-specific setup hints (inference endpoint URLs to paste into Cowork's apiHost setting)"},"smoke-test":{type:"boolean",default:!0,description:"After startup, run one tiny self-test generation to verify the proxy works end-to-end and print a clear PASS/FAIL. Disable with --no-smoke-test (or COPILOT_API_NO_SMOKE_TEST=1)."}},run({args:e}){let t=e["rate-limit"],n=void 0===t?void 0:Gi(t,"--rate-limit"),r=e.timeout,a=void 0===r?Y:Gi(r,"--timeout"),i=e["connect-timeout"]??g.env.COPILOT_CONNECT_TIMEOUT_MS,s=void 0===i?15e3:Gi(i,"--connect-timeout");if(s<1e3)throw Error(`--connect-timeout must be at least 1000ms, got: ${s}`);let l=e["https-hosts"],c=l?l.split(",").map(e=>e.trim()).filter(Boolean):[],u=e["web-search-provider"]??g.env.WEB_SEARCH_PROVIDER,p=u?u.split(",").map(e=>e.trim()).filter(Boolean):[];e["tavily-api-key"]&&o.warn("--tavily-api-key is deprecated; set the TAVILY_API_KEY environment variable instead.");let d=function(e){let t={tavily:e.tavilyApiKey,exa:e.exaApiKey},n=(e.order??[]).map(e=>e.toLowerCase());for(let e of n)if(!ta(e))throw Error(`Unknown web search provider: "${e}". Valid providers: ${ea.join(", ")}`);let r=n.length>0?n:ea,a=new Set,i=n.length>0,s=[];for(let e of r){if(!ta(e)||a.has(e))continue;a.add(e);let n=t[e];n?s.push({name:e,key:n}):i&&o.warn(`Web search provider "${e}" was requested but no API key is configured — skipping.`)}return s}({tavilyApiKey:e["tavily-api-key"]||g.env.TAVILY_API_KEY,exaApiKey:g.env.EXA_API_KEY,order:p}),m=(g.env.COPILOT_API_NO_SMOKE_TEST??"").trim().toLowerCase(),f=""!==m&&"0"!==m&&"false"!==m;return Li({port:Gi(e.port,"--port"),hostname:e.hostname,verbose:e.verbose,accountType:e["account-type"],manual:e.manual,rateLimit:n,rateLimitWait:e.wait,_t2:e["github-token"],_cc1:e["claude-code"],codex:e.codex,model:e.model,smallModel:e["small-model"],showToken:e["show-token"],timeout:a,connectTimeout:s,webSearchProviders:d,https:e.https,httpsCert:e["https-cert"],httpsKey:e["https-key"],httpsHosts:c,claudeCowork:e["claude-cowork"],errorReporting:e["error-reporting"],smokeTest:e["smoke-test"]&&!f})}});Qa||(Qa=!0,o.setReporters([Za(o.options.reporters)])),await async function(){try{if("1"===process.env.COPILOT_API_SKIP_UPDATE_CHECK)return;let[e,t]=await Promise.all([St(),ri()]);if("unknown"===e||!t||!function(e,t){let o=e.split(".").map(Number),n=t.split(".").map(Number),r=Math.max(o.length,n.length);for(let e=0;e<r;e++){let t=o[e]??0,r=n[e]??0;if(t<r)return!0;if(t>r)return!1}return!1}(e,t))return;!function(e,t){let o=`npx ${ei}@latest`,n=ni("│"),r=` ${oi("Update available!")} ${(e=>`[2m${e}[0m`)(e)} → ${(e=>`[32m${e}[0m`)(t)}`,a=` Run ${oi(o)} to update`,i=" ".repeat(54),s=ni(`╭${"─".repeat(54)}╮`),l=ni(`╰${"─".repeat(54)}╯`),c=["",s,`${n}${i}${n}`,`${n}${ai(r,54)}${n}`,`${n}${i}${n}`,`${n}${ai(a,54)}${n}`,`${n}${i}${n}`,l,""];console.log(c.join("\n"))}(e,t)}catch{}}(),await t(e({meta:{name:"copilot-api",description:"API proxy server for tool integration."},subCommands:{auth:To,start:zi,"check-usage":xo,debug:It,doctor:Xa,"cowork-setup":Wo}}));export{};
|
|
2
|
+
import{defineCommand as e,runMain as t}from"citty";import o,{LogLevels as n,consola as r}from"consola";import a from"node:fs/promises";import i from"node:os";import s from"node:path";import{SpanKind as l,SpanStatusCode as c,context as u,metrics as p,trace as d}from"@opentelemetry/api";import m from"clipboardy";import{execFile as f,execSync as h}from"node:child_process";import g from"node:process";import{SeverityNumber as _,logs as y}from"@opentelemetry/api-logs";import{OTLPLogExporter as w}from"@opentelemetry/exporter-logs-otlp-http";import{OTLPMetricExporter as k}from"@opentelemetry/exporter-metrics-otlp-http";import{OTLPTraceExporter as b}from"@opentelemetry/exporter-trace-otlp-http";import{resourceFromAttributes as v}from"@opentelemetry/resources";import{BatchLogRecordProcessor as $}from"@opentelemetry/sdk-logs";import{PeriodicExportingMetricReader as T}from"@opentelemetry/sdk-metrics";import{NodeSDK as x}from"@opentelemetry/sdk-node";import{ATTR_SERVICE_INSTANCE_ID as A,ATTR_SERVICE_NAME as S,ATTR_SERVICE_VERSION as E}from"@opentelemetry/semantic-conventions";import{Client as C,request as O}from"undici";import{createHash as I,randomBytes as P,randomUUID as R}from"node:crypto";import{promisify as N}from"node:util";import{Hono as q}from"hono";import{cors as D}from"hono/cors";import{streamSSE as j}from"hono/streaming";import{events as M}from"fetch-event-stream";import{Tokenizer as H,models as B}from"ai-tokenizer";import*as F from"ai-tokenizer/encoding/claude";import{accessSync as U}from"node:fs";import{serve as L}from"srvx";import{isIP as G}from"node:net";import{generate as z}from"selfsigned";const J=s.join(i.homedir(),".local","share","copilot-api"),K={APP_DIR:J,GITHUB_TOKEN_PATH:s.join(J,"github_token"),MACHINE_ID_PATH:s.join(J,"machine_id"),SESSION_ID_PATH:s.join(J,"session_id")};async function W(){await a.mkdir(K.APP_DIR,{recursive:!0}),await V(K.GITHUB_TOKEN_PATH),await V(K.SESSION_ID_PATH)}async function V(e){try{await a.access(e,a.constants.W_OK)}catch{await a.writeFile(e,""),await a.chmod(e,384)}}const Y=6e5,X={accountType:"individual",manualApprove:!1,rateLimitWait:!1,showToken:!1,timeoutMs:Y,webSearchProviders:[],errorReporting:!0,connectivity:{probeEndpoints:["https://api.github.com","https://www.google.com","https://1.1.1.1"],fastProbeInterval:5e3,slowProbeInterval:1e4,timeoutMs:15e3,jitterMaxMs:1e3,connectionPooling:!0,dnsCache:!0,h2:!1,h2Keepalive:!1}},Z=" │ ",Q=e=>{if(e>=1e6){let t=e/1e6;return Number.isInteger(t)?`${t}M`:`${t.toFixed(1)}M`}return e>=1e4?`${Math.round(e/1e3)}K`:e>=1e3?`${(e/1e3).toFixed(1)}K`:e.toString()},ee=(e,t)=>e.padEnd(t),te=e=>`${(e/1e3).toFixed(1)}s`.padStart(6),oe=(e,t,o)=>` --\x3e ${ee(e,4)} ${ee(t,21)} ${ee(o,3)}`,ne=e=>{let t=(e.reasoningEffort??"-")+(e.effortClamped?"*":"");return(e=>ee(e.length>21?`${e.slice(0,20)}…`:e,22))(e.model??"—")+ee(t,8)},re=e=>{let t=e?.inputTokens??0,o=e?.cachedTokens??0,n=e?Q(Math.max(t-o,0)):"—",r=e?Q(e.outputTokens??0):"—",a=o?Q(o):"—";return`↑${n.padStart(5)} ⚡${a.padStart(5)} ↓${r.padStart(5)}`},ae=(e,t)=>{if(!e?.inputTokens||!t)return`ctx ${ee("—",10)}`;let o=Math.round(e.inputTokens/t*100),n=Q(e.inputTokens).padStart(5),r=`${o}%`;return`ctx ${n}${r.padStart(Math.max(10-n.length,r.length+1))}`},ie=e=>{if(void 0===e.ttfbMs)return`e2e ${te(e.e2eMs)}`;let t=`(+${((e.e2eMs-e.ttfbMs)/1e3).toFixed(1)}s)`.padStart(8);return`ttfb ${te(e.ttfbMs)} → e2e ${te(e.e2eMs)} ${t}`},se=e=>e?X.models?.data.find(t=>t.id===e)?.capabilities.limits?.max_context_window_tokens:void 0,le=e=>({...e?.inputTokens&&{"copilot_api.input_tokens":e.inputTokens},...e?.inputTokens&&{"copilot_api.fresh_input_tokens":Math.max(e.inputTokens-(e.cachedTokens??0),0)},...e?.outputTokens&&{"copilot_api.output_tokens":e.outputTokens},...e?.cachedTokens&&{"copilot_api.cached_tokens":e.cachedTokens}}),ce={completionCallbacks:new Map,registerCompletion(e,t,o){this.completionCallbacks.set(e,{context:t,startTime:o,requestId:e})},executeCompletion(e){let t=this.completionCallbacks.get(e);t&&(this.logCompletion(t),this.completionCallbacks.delete(e))},logCompletion(e){let{context:t,startTime:n}=e,r=Math.round(performance.now()-n),a=t.get("requestData"),i=a?.upstreamTotalMs??a?._d1,s=(e=>[oe(e.method,e.path,e.status),ne(e),re(e.tokenUsage),ae(e.tokenUsage,e.maxContextTokens),ie({ttfbMs:e.ttfbMs,e2eMs:e.e2eMs})].join(Z))({method:t.req.method,path:t.req.path,status:t.res.status.toString(),model:a?.model,reasoningEffort:a?.reasoningEffort,effortClamped:a?.effortClamped,tokenUsage:a?.tokenUsage,maxContextTokens:se(a?.model),ttfbMs:a?.upstreamTtfbMs,e2eMs:r});o.info(s),Ke(_.INFO,"INFO","Request completed",(e=>{let{c:t,requestData:o,duration:n,upstreamTotal:r}=e;return{"http.method":t.req.method,"http.path":t.req.path,"http.status_code":t.res.status,"copilot_api.duration_ms":n,...o?.model&&{"copilot_api.model":o.model},...o?.reasoningEffort&&{"copilot_api.reasoning_effort":o.reasoningEffort},...o?.effortClamped&&{"copilot_api.effort_clamped":!0},...void 0!==o?.upstreamTtfbMs&&{"copilot_api.upstream_ttfb_ms":Math.round(o.upstreamTtfbMs)},...void 0!==r&&{"copilot_api.upstream_total_ms":Math.round(r),"copilot_api.copilot_duration_ms":Math.round(r)},...le(o?.tokenUsage)}})({c:t,requestData:a,duration:r,upstreamTotal:i}),t.get("requestTraceContext"))},logRateLimit(e,t){let{context:n,startTime:r}=e,a=Math.round(performance.now()-r),i=(t.headers.get("x-ratelimit-exceeded")||"").split(":")[1]||"unknown",s=t.headers.get("retry-after")||t.headers.get("x-ratelimit-user-retry-after")||"?",l=n.get("requestData");o.warn((e=>[oe(e.method,e.path,"429"),ne(e),`rate-limited retry ${e.retry}s (${e.rateLimitType})`.padEnd(37),`e2e ${te(e.e2eMs)}`].join(Z))({method:n.req.method,path:n.req.path,model:l?.model,reasoningEffort:l?.reasoningEffort,effortClamped:l?.effortClamped,retry:s,rateLimitType:i,e2eMs:a}))},logError(e,t,n){let{context:r,startTime:a}=e,i=Math.round(performance.now()-a),s=r.get("requestData");o.error((e=>{let t=oe(e.method,e.path,e.status.toString()),o=ne(e),n=e.message.replaceAll(/\s+/g," ").trim();return[t,o,(n.length>37?`${n.slice(0,36)}…`:n).padEnd(37),`e2e ${te(e.e2eMs)}`].join(Z)})({method:r.req.method,path:r.req.path,status:t,model:s?.model,reasoningEffort:s?.reasoningEffort,effortClamped:s?.effortClamped,message:n,e2eMs:i}))},cleanup(){let e=performance.now()-12e5;for(let[t,o]of this.completionCallbacks)o.startTime<e&&this.completionCallbacks.delete(t);if(this.completionCallbacks.size>1e3){let e=Array.from(this.completionCallbacks.entries()).sort(([,e],[,t])=>e.startTime-t.startTime),t=e.slice(0,e.length-1e3);for(let[e]of t)this.completionCallbacks.delete(e)}}};setInterval(()=>ce.cleanup(),6e4);let ue,pe,de=Date.now();const me={"x-honeycomb-team":"hcaik_01km2y7yf1rrn70xvxce5kx9dyz936dwm21b9bgvnwf3pxq0cmqkcwha8n"};function fe(){let e=process.env.OTEL_EXPORTER_OTLP_ENDPOINT??"https://api.honeycomb.io",t=process.env.OTEL_EXPORTER_OTLP_HEADERS?function(e){return e?Object.fromEntries(e.split(",").map(e=>e.trim()).filter(Boolean).map(e=>{let t=e.indexOf("=");return-1===t?[e,""]:[decodeURIComponent(e.slice(0,t)),decodeURIComponent(e.slice(t+1))]})):{}}(process.env.OTEL_EXPORTER_OTLP_HEADERS):me;return{endpoint:e.replace(/\/$/,""),headers:t}}const he=d.getTracer("copilot-api"),ge=p.getMeter("copilot-api"),_e=y.getLogger("copilot-api"),ye=ge.createCounter("copilot_api.requests.total",{unit:"{request}",description:"Total requests received"}),we=ge.createCounter("copilot_api.requests.errors",{unit:"{error}",description:"Total error responses"}),ke=ge.createCounter("copilot_api.tokens.input",{unit:"{token}",description:"Total input tokens consumed"}),be=ge.createCounter("copilot_api.tokens.output",{unit:"{token}",description:"Total output tokens generated"}),ve=ge.createCounter("copilot_api.tokens.cached",{unit:"{token}",description:"Total cached prompt tokens"}),$e=ge.createCounter("copilot_api.rate_limit.triggers",{unit:"{trigger}",description:"Rate limit trigger count"}),Te=ge.createCounter("copilot_api.model_validation.errors",{unit:"{error}",description:"Model validation failures"}),xe=ge.createCounter("copilot_api.model_mapping.mappings",{unit:"{mapping}",description:"Model name normalizations"}),Ae=ge.createCounter("copilot_api.token_refresh.attempts",{unit:"{attempt}",description:"Token refresh attempts"}),Se=ge.createCounter("copilot_api.token_refresh.failures",{unit:"{failure}",description:"Token refresh final failures"}),Ee=ge.createCounter("copilot_api.connectivity.checks",{unit:"{check}",description:"Connectivity probe results"}),Ce=ge.createCounter("copilot_api.connectivity.transitions",{unit:"{transition}",description:"Connectivity state transitions"}),Oe=ge.createCounter("copilot_api.upstream.requests",{unit:"{request}",description:"Upstream API calls"}),Ie=ge.createCounter("copilot_api.stream.chunks",{unit:"{chunk}",description:"Total SSE chunks sent"}),Pe=ge.createCounter("copilot_api.approval.decisions",{unit:"{decision}",description:"Manual approval decisions"}),Re=ge.createCounter("copilot_api.h2_keepalive.pings",{unit:"{ping}",description:"HTTP/2 keepalive pings sent"}),Ne=ge.createCounter("copilot_api.h2.connections",{unit:"{connection}",description:"HTTP/2 connection lifecycle events"}),qe=ge.createCounter("copilot_api.error_capture.decisions",{unit:"{decision}",description:"Per-process daily limiter outcomes (full|suppressed|drop)"}),De=ge.createHistogram("copilot_api.request.duration",{unit:"ms",description:"Total request duration"}),je=ge.createHistogram("copilot_api.copilot.duration",{unit:"ms",description:"Upstream Copilot API call duration"}),Me=ge.createHistogram("copilot_api.stream.duration",{unit:"ms",description:"Duration of SSE streaming phase"}),He=ge.createHistogram("copilot_api.rate_limit.wait_duration",{unit:"ms",description:"Duration of rate limit waits"}),Be=ge.createHistogram("copilot_api.translation.duration",{unit:"ms",description:"Translation layer processing time"}),Fe=ge.createHistogram("copilot_api.token_refresh.duration",{unit:"ms",description:"Token refresh duration"}),Ue=ge.createHistogram("copilot_api.connectivity.probe_duration",{unit:"ms",description:"Individual connectivity probe duration"}),Le=ge.createHistogram("copilot_api.tokens.per_request.input",{unit:"{token}",description:"Input tokens per request distribution"}),Ge=ge.createHistogram("copilot_api.tokens.per_request.output",{unit:"{token}",description:"Output tokens per request distribution"}),ze=ge.createHistogram("copilot_api.stream.chunks_per_request",{unit:"{chunk}",description:"Chunks per streaming request"}),Je=ge.createHistogram("copilot_api.approval.wait_duration",{unit:"ms",description:"Time waiting for manual approval"});function Ke(e,t,o,n,r){let a=d.getActiveSpan()?.spanContext()??r;_e.emit({severityNumber:e,severityText:t,body:o,attributes:{...n,...a&&{"trace.id":a.traceId,"span.id":a.spanId}}})}function We(e,t,o){let n=t instanceof Error?t:Error(String(t));e.setStatus({code:c.ERROR,message:o??n.message}),e.recordException(n)}function Ve(e,t,o){We(e,o),t&&t!==e&&We(t,o)}function Ye(e,t=""){let o={};if(null==e)return o;if("object"!=typeof e)return("string"==typeof e||"number"==typeof e||"boolean"==typeof e)&&t&&(o[t]=e),o;if(Array.isArray(e))return t&&(o[t]=JSON.stringify(e)),o;for(let[n,r]of Object.entries(e)){let e=t?`${t}.${n}`:n;void 0===r||"function"==typeof r||(null===r?o[e]="null":"object"!=typeof r||Array.isArray(r)?Array.isArray(r)?o[e]=JSON.stringify(r):("string"==typeof r||"number"==typeof r||"boolean"==typeof r)&&(o[e]=r):Object.assign(o,Ye(r,e)))}return o}ge.createObservableGauge("copilot_api.connectivity.status",{unit:"{status}",description:"1 = online, 0 = offline"}).addCallback(e=>{e.observe(+!!tt.getConnectivityStats().isOnline)}),ge.createObservableGauge("copilot_api.connectivity.consecutive_failures",{unit:"{failure}",description:"Current consecutive connectivity failure count"}).addCallback(e=>{e.observe(tt.getConnectivityStats().consecutiveFailures)}),ge.createObservableGauge("copilot_api.models.available",{unit:"{model}",description:"Number of available models"}).addCallback(e=>{e.observe(X.models?.data.length??0)}),ge.createObservableGauge("copilot_api.completion_logger.pending",{unit:"{callback}",description:"Number of pending completion callbacks"}).addCallback(e=>{e.observe(ce.completionCallbacks.size)}),ge.createObservableGauge("copilot_api.uptime",{unit:"s",description:"Server uptime in seconds"}).addCallback(e=>{e.observe((Date.now()-de)/1e3)});const Xe=new Set(["authorization","cookie","set-cookie","x-honeycomb-team","x-api-key","proxy-authorization"]);function Ze(e,t,o){for(let[n,r]of Object.entries(o)){let o=n.toLowerCase();Xe.has(o)||e.setAttribute(`http.${t}.header.${o}`,r)}}async function Qe(e){let{spanName:t,url:o,target:n,method:r="GET",headers:a,body:i,signal:s,extraAttributes:u}=e,p=he.startSpan(t,{kind:l.CLIENT,attributes:{"http.method":r,"url.full":o,"copilot_api.target":n,...u}});a&&Ze(p,"request",a);try{let e=await fetch(o,{method:r,headers:a,body:i,signal:s});return p.setAttribute("http.response.status_code",e.status),function(e,t){t.headers.forEach((t,o)=>{let n=o.toLowerCase();Xe.has(n)||e.setAttribute(`http.response.header.${n}`,t)})}(p,e),Oe.add(1,{target:n,status_code:String(e.status)}),e.ok||p.setStatus({code:c.ERROR,message:`HTTP ${e.status}`}),{response:e,span:p}}catch(e){throw We(p,e),p.end(),e}}async function et(e){let{spanName:t,url:o,target:n,method:r="POST",headers:a,body:i,signal:s,headersTimeout:u,bodyTimeout:p,extraAttributes:d,dispatcher:m}=e,f=he.startSpan(t,{kind:l.CLIENT,attributes:{"http.method":r,"url.full":o,"copilot_api.target":n,"copilot_api.h2.enabled":void 0!==m,...d}});Ze(f,"request",a);try{let{statusCode:e,headers:t,body:l}=await O(o,{method:r,headers:a,body:i,signal:s,headersTimeout:u,bodyTimeout:p,dispatcher:m});f.setAttribute("http.response.status_code",e);for(let[e,o]of Object.entries(t)){let t=e.toLowerCase();void 0!==o&&!Xe.has(t)&&f.setAttribute(`http.response.header.${t}`,Array.isArray(o)?o.join(", "):o)}return Oe.add(1,{target:n,status_code:String(e)}),e>=400&&f.setStatus({code:c.ERROR,message:`HTTP ${e}`}),{statusCode:e,headers:t,body:l,span:f}}catch(e){throw We(f,e),f.end(),e}}const tt=new class extends EventTarget{isOnline=!0;lastChecked=(new Date).toISOString();consecutiveFailures=0;lastErrorType;lastErrorMessage;lastSuccessfulEndpoint;endpointFailureStats={};checkInterval;abortController;on(e,t){return this.addEventListener(e,t),this}off(e,t){return this.removeEventListener(e,t),this}start(){o.debug("Starting connectivity monitor",{probeEndpoints:X.connectivity.probeEndpoints,fastInterval:X.connectivity.fastProbeInterval}),this.scheduleNextCheck()}stop(){o.debug("Stopping connectivity monitor"),this.checkInterval&&=void clearTimeout(this.checkInterval),this.abortController&&=void this.abortController.abort()}scheduleNextCheck(){this.checkInterval&&clearTimeout(this.checkInterval);let e=(this.isOnline?X.connectivity.slowProbeInterval:X.connectivity.fastProbeInterval)+Math.random()*X.connectivity.jitterMaxMs;this.checkInterval=setTimeout(()=>{this.performConnectivityCheck().catch(e=>{o.error("Connectivity check failed:",e)})},e)}async performConnectivityCheck(){let e=he.startSpan("copilot_api.connectivity.probe");this.abortController=new AbortController;let t=setTimeout(()=>this.abortController?.abort(),X.connectivity.timeoutMs);try{let n=!1;for(let e of X.connectivity.probeEndpoints)try{let t=performance.now(),o=await fetch(e,{method:"HEAD",signal:this.abortController.signal,headers:{"User-Agent":"copilot-api-connectivity-monitor/1.0",...X.connectivity.dnsCache&&{"Cache-Control":"max-age=300"}}}),r=performance.now()-t;if(o.ok){n=!0,this.lastSuccessfulEndpoint=e,Ue.record(r,{endpoint:e,result:"success"});break}Ue.record(r,{endpoint:e,result:"failed"})}catch(t){this.endpointFailureStats[e]=(this.endpointFailureStats[e]||0)+1,o.debug(`Probe failed for ${e}:`,t)}this.updateConnectivityState(n);let r=n?"online":"offline";e.setAttribute("copilot_api.connectivity.result",r),e.setAttribute("copilot_api.connectivity.consecutive_failures",this.consecutiveFailures),this.lastSuccessfulEndpoint&&e.setAttribute("copilot_api.connectivity.successful_endpoint",this.lastSuccessfulEndpoint),Ee.add(1,{result:n?"online":"offline"})}catch(e){this.handleConnectivityError(e)}finally{clearTimeout(t),e.end(),this.scheduleNextCheck()}}updateConnectivityState(e){let t=this.isOnline;if(this.isOnline=e,this.lastChecked=(new Date).toISOString(),e){let e=this.consecutiveFailures;this.consecutiveFailures>0&&o.info(`Connectivity restored after ${this.consecutiveFailures} failures`),this.consecutiveFailures=0,this.lastErrorType=void 0,this.lastErrorMessage=void 0,t||(this.dispatchEvent(new CustomEvent("online")),Ce.add(1,{from:"offline",to:"online"}),Ke(_.INFO,"INFO","Connectivity restored",{"copilot_api.connectivity.consecutive_failures_before_recovery":e}))}else this.consecutiveFailures++,t&&(o.warn("Connectivity lost"),this.dispatchEvent(new CustomEvent("offline")),Ce.add(1,{from:"online",to:"offline"}),Ke(_.WARN,"WARN","Connectivity lost",{"copilot_api.connectivity.consecutive_failures":this.consecutiveFailures}))}handleConnectivityError(e){this.lastErrorType=e.name,this.lastErrorMessage=e.message,o.error("Connectivity check failed:",e),this.updateConnectivityState(!1)}getConnectivityStats(){return{isOnline:this.isOnline,lastChecked:this.lastChecked,consecutiveFailures:this.consecutiveFailures,lastErrorType:this.lastErrorType,lastErrorMessage:this.lastErrorMessage}}getPerformanceStats(){let e=this.isOnline?X.connectivity.slowProbeInterval:X.connectivity.fastProbeInterval;return{currentInterval:e,nextCheckEstimate:new Date(Date.now()+e+Math.random()*X.connectivity.jitterMaxMs).toISOString(),lastSuccessfulEndpoint:this.lastSuccessfulEndpoint,endpointFailureStats:{...this.endpointFailureStats},jitterEnabled:X.connectivity.jitterMaxMs>0,connectionPooling:X.connectivity.connectionPooling,dnsCache:X.connectivity.dnsCache}}},ot=()=>({"content-type":"application/json",accept:"application/json"}),nt="0.48.1",rt=`copilot-chat/${nt}`,at=`GitHubCopilotChat/${nt}`,it=async e=>{let t=(e=>{let t=e.replaceAll(/[^\w.-]/g,"_").trim();if(0===t.length||"."===t||".."===t||/^[_.]+$/.test(t))throw Error("Invalid GitHub username: cannot be empty or consist only of special characters after sanitization");return`${K.MACHINE_ID_PATH}_${t}`})(e);try{let e=await a.readFile(t,"utf8");if(e.trim())return e.trim()}catch{}let o=(e=>{let t=I("sha256");return t.update(process.platform),t.update(process.arch),t.update(process.env.USER||process.env.USERNAME||"anonymous"),t.update(i.hostname()),t.update(e),t.update(Date.now().toString()),t.update(P(16)),t.digest("hex")})(e);return await a.writeFile(t,o),await a.chmod(t,384),o},st=async(e,t)=>{e.machineId||=await it(t),e.sessionId||=await(async()=>{try{let e=await a.readFile(K.SESSION_ID_PATH,"utf8");if(e.trim())return e.trim()}catch{}let e=R();return await a.writeFile(K.SESSION_ID_PATH,e),await a.chmod(K.SESSION_ID_PATH,384),e})()},lt=e=>"individual"===e.accountType?"https://api.githubcopilot.com":`https://api.${e.accountType}.githubcopilot.com`,ct=(e,t=!1)=>{if(!e.machineId||!e.sessionId)throw Error("VSCode identifiers not initialized. Call initializeVSCodeIdentifiers() during startup.");let o=R(),n={Authorization:`Bearer ${e._t1}`,"Content-Type":"application/json",accept:"*/*","accept-encoding":"br, gzip, deflate","accept-language":"*","sec-fetch-mode":"cors","Copilot-Integration-Id":"vscode-chat","Editor-Version":`vscode/${e._v1}`,"Editor-Plugin-Version":rt,"User-Agent":at,"VScode-MachineId":e.machineId,"VScode-SessionId":e.sessionId,"OpenAI-Intent":"conversation-agent","X-Interaction-Type":"conversation-agent","X-Agent-Task-Id":o,"X-VSCode-User-Agent-Library-Version":"node-fetch","X-GitHub-Api-Version":"2025-05-01","X-Interaction-Id":R(),"X-Request-Id":o};return t&&(n["copilot-vision-request"]="true"),n},ut=["interleaved-thinking","context-management","advanced-tool-use","redact-thinking"];const pt=(e,t,o)=>{let n=ct(e);delete n["Copilot-Integration-Id"],n["anthropic-version"]=t?.anthropicVersion??"2023-06-01";let r=new Set,a=t?.anthropicBeta?function(e){let t=e.split(",").map(e=>e.trim()).filter(e=>e&&ut.some(t=>e.startsWith(`${t}-`)));return t.length>0?t.join(","):void 0}(t.anthropicBeta):void 0;if(a)for(let e of a.split(","))r.add(e);if(o)for(let e of o)r.add(e);return r.size>0&&(n["anthropic-beta"]=[...r].join(",")),n},dt="https://api.github.com",mt=e=>({"content-type":"application/json",accept:"application/json",authorization:`token ${e._t2}`,"editor-version":`vscode/${e._v1}`,"editor-plugin-version":rt,"user-agent":at,"x-github-api-version":"2025-04-01","x-vscode-user-agent-library-version":"node-fetch"}),ft="https://github.com",ht="01ab8ac9400c4e429b23",gt=["user:email"].join(" ");function _t(e){return e.includes("/messages")?"anthropic":e.includes("/chat/completions")?"openai":e.includes("/embeddings")?"embeddings":e.includes("/responses")?"responses":e.includes("/models")?"models":e.includes("/usage")?"usage":e.includes("/token")?"token":"unknown"}const yt=32768,wt=[{regex:/Bearer\s+[\w.-]{20,}/g,mask:"Bearer ***"},{regex:/\bghu_[A-Za-z0-9]{20,}/g,mask:"ghu_***"},{regex:/\bghp_[A-Za-z0-9]{20,}/g,mask:"ghp_***"},{regex:/\bgho_[A-Za-z0-9]{20,}/g,mask:"gho_***"},{regex:/\bghs_[A-Za-z0-9]{20,}/g,mask:"ghs_***"},{regex:/\bghr_[A-Za-z0-9]{20,}/g,mask:"ghr_***"},{regex:/\bsk-[A-Za-z0-9-]{20,}/g,mask:"sk-***"},{regex:/\bhcaik_[A-Za-z0-9]{20,}/g,mask:"hcaik_***"}],kt=new Set(["authorization","cookie","set-cookie","x-api-key","proxy-authorization"]);function bt(e){let t=e;for(let{regex:e,mask:o}of wt)t=t.replace(e,o);return t}const vt=new Map;function $t(e){let t=function(e=new Date){return e.toISOString().slice(0,10)}(e.now),o=e.upstreamErrorType??"unknown",n=(e.model??"unknown").slice(0,100);return`${e.endpointType}:${e.statusCode}:${o}:${n}:${t}`}function Tt(e,t,o){let n=bt(o),r=8*yt,a=n.length>r,i=a?n.slice(0,r):n,s=I("sha256").update(n).digest("hex");if(i.length<=yt)e.setAttribute(t,i),e.setAttribute(`${t}.parts`,1);else{for(let o=0;o<i.length;o+=yt)e.setAttribute(`${t}.part_${o/yt}`,i.slice(o,o+yt));e.setAttribute(`${t}.parts`,Math.ceil(i.length/yt))}e.setAttribute(`${t}.bytes`,n.length),e.setAttribute(`${t}.sha256`,s),a&&(e.setAttribute(`${t}.truncated`,!0),e.setAttribute(`${t}.dropped_bytes`,n.length-i.length))}function xt(e,t){let o=function(e){if(vt.size>=1e3&&!vt.has(e)){let e=vt.keys().next().value;void 0!==e&&vt.delete(e)}let t,o=(vt.get(e)??0)+1;return vt.set(e,o),t=o<=2?"full":3===o?"suppressed":"drop",qe.add(1,{decision:t}),t}(t.signatureKey);if(e.setAttribute("copilot_api.error_capture.decision",o),e.setAttribute("copilot_api.error_capture.signature_key",t.signatureKey),"drop"===o)return{decision:o};if("suppressed"===o)return e.setAttribute("copilot_api.error_capture.suppressed_today",!0),{decision:o};let n=t.c.get("rawBody");n&&Tt(e,"copilot_api.incoming_request_body",n);let r=At(t.c.req.header());return r&&Tt(e,"copilot_api.incoming_headers",r),void 0!==t.outgoingBody&&Tt(e,"copilot_api.outgoing_request_body",t.outgoingBody),void 0!==t.outgoingHeaders&&Tt(e,"copilot_api.outgoing_headers",At(t.outgoingHeaders)),void 0!==t.upstreamResponseBody&&Tt(e,"copilot_api.upstream_response_body",t.upstreamResponseBody),{decision:o}}function At(e){let t={};for(let[o,n]of Object.entries(e))kt.has(o.toLowerCase())||(t[o]=n);return JSON.stringify(t)}async function St(){try{let e=new URL("../package.json",import.meta.url).pathname,t=await a.readFile(e);return JSON.parse(t.toString()).version}catch{return"unknown"}}function Et(){let e=typeof Bun<"u";return{name:e?"bun":"node",version:e?Bun.version:process.version.slice(1),platform:i.platform(),arch:i.arch()}}async function Ct(){try{return!!(await a.stat(K.GITHUB_TOKEN_PATH)).isFile()&&(await a.readFile(K.GITHUB_TOKEN_PATH,"utf8")).trim().length>0}catch{return!1}}async function Ot(e){let t=await async function(){let[e,t]=await Promise.all([St(),Ct()]);return{version:e,runtime:Et(),paths:{APP_DIR:K.APP_DIR,GITHUB_TOKEN_PATH:K.GITHUB_TOKEN_PATH},tokenExists:t}}();e.json?function(e){console.log(JSON.stringify(e,null,2))}(t):function(e){o.info(`service debug\n\nVersion: ${e.version}\nRuntime: ${e.runtime.name} ${e.runtime.version} (${e.runtime.platform} ${e.runtime.arch})\n\nPaths:\n- APP_DIR: ${e.paths.APP_DIR}\n- GITHUB_TOKEN_PATH: ${e.paths.GITHUB_TOKEN_PATH}\n\nToken exists: ${e.tokenExists?"Yes":"No"}`)}(t)}const It=e({meta:{name:"debug",description:"Print debug information about the application"},args:{json:{type:"boolean",default:!1,description:"Output debug information as JSON"}},run:({args:e})=>Ot({json:e.json})}),Pt=process.env.COPILOT_API_REPORT_ENDPOINT??"https://copilot-api.barazany.dev/report",Rt=process.env.COPILOT_API_REPORT_KEY??"cai_60fc3498226c9121cbf0da949ab207cddd93e2d74faabbbb",Nt=new Set;let qt;function Dt(e){if(X.errorReporting&&!(e.statusCode<500)&&!Nt.has(e.signature)){if(Nt.size>=1e3){let e=Nt.values().next().value;void 0!==e&&Nt.delete(e)}Nt.add(e.signature),async function(e){qt??=St();let t=await qt,o=Et(),n=void 0===e.upstreamErrorMessage?void 0:function(e){return e.replaceAll(/(\/(?:home|Users)\/|\\Users\\)[^/\\\s]+/g,(e,t)=>`${t}***`)}(bt(e.upstreamErrorMessage)).slice(0,600),r={proxyVersion:t,signature:e.signature,errorClass:e.errorClass,statusCode:e.statusCode,upstreamErrorType:e.upstreamErrorType,upstreamErrorMessage:n,endpointType:_t(e.route),route:e.route,model:e.model?.slice(0,100),platform:`${o.platform}/${o.arch}`,runtime:`${o.name}/${o.version}`,timestamp:(new Date).toISOString()},a=new AbortController,i=setTimeout(()=>a.abort(),4e3);try{await fetch(Pt,{method:"POST",headers:{"content-type":"application/json","x-ingest-key":Rt},body:JSON.stringify(r),signal:a.signal})}finally{clearTimeout(i)}}(e).catch(e=>{o.debug("Error report submission failed:",e)})}}var jt=class extends Error{response;outgoingBody;outgoingHeaders;constructor(e,t,o){super(e),this.response=t,this.outgoingBody=o?.outgoingBody,this.outgoingHeaders=o?.outgoingHeaders}},Mt=class extends Error{name="RequestTimeoutError";constructor(e){super(`Upstream request timed out after ${e}ms`)}};function Ht(e,t){return setTimeout(()=>e.abort(new Mt(t)),t)}const Bt=new Set(["UND_ERR_CONNECT_TIMEOUT","ECONNREFUSED","ENOTFOUND","EAI_AGAIN","ETIMEDOUT","EADDRNOTAVAIL","EPIPE","ECONNRESET"]),Ft=RegExp(`\\b(?:${[...Bt].join("|")})\\b`);function Ut(e){return e instanceof Error?e.code:void 0}function Lt(e){return e.req.path.startsWith("/v1/messages")}function Gt(e,t){if(Lt(t)){try{let t=JSON.parse(e);if("message"in t&&"string"==typeof t.message&&!("error"in t))return{type:"error",error:{type:"invalid_request_error",message:t.message}};if("error"in t&&"object"==typeof t.error){let e=t.error;return{type:"error",error:{type:"string"==typeof e.type&&e.type||"string"==typeof e.code&&e.code||"api_error",message:"string"==typeof e.message&&e.message||"Unknown error"}}}}catch{}return{type:"error",error:{type:"api_error",message:e}}}try{return JSON.parse(e)}catch{return{error:{message:e,type:"error"}}}}function zt(e){let t=e.error,o={};return t&&"object"==typeof t&&("string"==typeof t.type?o.type=t.type:"string"==typeof t.code&&(o.type=t.code),"string"==typeof t.message&&(o.message=t.message)),!o.message&&"string"==typeof e.message&&(o.message=e.message),o}function Jt(e,t){e&&(t.type&&e.setAttribute("copilot_api.upstream.error_type",t.type),t.message&&e.setAttribute("copilot_api.upstream.error_message",t.message))}function Kt(e){let t={};return e.type&&(t["copilot_api.upstream.error_type"]=e.type),e.message&&(t["copilot_api.upstream.error_message"]=e.message),t}function Wt(e){let{c:t,error:o,errorText:n,upstream:r}=e,a=d.getActiveSpan();if(!a)return;let i=$t({endpointType:_t(t.req.path),statusCode:o.response.status,upstreamErrorType:r.type,model:t.get("requestData")?.model});xt(a,{c:t,outgoingBody:o.outgoingBody,outgoingHeaders:o.outgoingHeaders,upstreamResponseBody:n,signatureKey:i})}function Vt(e,t,o){let n=e.get("requestId"),r=ce.completionCallbacks.get(n);r&&(ce.logError(r,t,o),ce.completionCallbacks.delete(n))}async function Yt(e,t){if(t instanceof jt&&429===t.response.status)return async function(e,t){let o=d.getActiveSpan(),n=e.get("requestId"),r=ce.completionCallbacks.get(n);r&&(ce.logRateLimit(r,t.response),ce.completionCallbacks.delete(n)),$e.add(1,{action:"rejected",source:"upstream"});let a=await t.response.text(),i=Gt(a,e),s=zt(i);return o?.setStatus({code:c.ERROR,message:"Rate limited by upstream"}),o?.setAttribute("copilot_api.error_type","rate_limit_upstream"),Jt(o,s),Ke(_.WARN,"WARN","Upstream rate limit hit",{"copilot_api.status_code":429,"http.path":e.req.path,"copilot_api.error_type":"rate_limit_upstream",...Kt(s)}),Wt({c:e,error:t,errorText:a,upstream:s}),e.json(i,429)}(e,t);if(t instanceof SyntaxError){d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_json_body"),Ke(_.WARN,"WARN",`Invalid JSON in request body: ${t.message}`,{"copilot_api.status_code":400,"http.path":e.req.path,"copilot_api.error_type":"invalid_json_body"});let o=Lt(e)?{type:"error",error:{type:"invalid_request_error",message:"Invalid JSON in request body"}}:{error:{message:"Invalid JSON in request body",type:"invalid_request_error"}};return Vt(e,400,"Invalid JSON in request body"),e.json(o,400)}if(t instanceof jt)return async function(e,t){let o=d.getActiveSpan(),n=await t.response.text(),r=Gt(n,e),a=zt(r);return Vt(e,t.response.status,a.message??t.message),o?.setStatus({code:c.ERROR,message:t.message}),o?.recordException(t),o?.setAttribute("copilot_api.error_type","HTTPError"),Jt(o,a),Ke(_.ERROR,"ERROR",`HTTP error: ${t.message}`,{"copilot_api.status_code":t.response.status,"http.path":e.req.path,"copilot_api.error_type":"HTTPError",...Kt(a)}),Wt({c:e,error:t,errorText:n,upstream:a}),t.response.status>=500&&Dt({route:e.req.path,statusCode:t.response.status,errorClass:"HTTPError",signature:$t({endpointType:_t(e.req.path),statusCode:t.response.status,upstreamErrorType:a.type,model:e.get("requestData")?.model}),model:e.get("requestData")?.model,upstreamErrorType:a.type,upstreamErrorMessage:a.message}),e.json(r,t.response.status)}(e,t);if(function(e){return e instanceof Mt||e instanceof Error&&"AbortError"===e.name&&e.cause instanceof Mt}(t))return function(e,t){let o=d.getActiveSpan();o?.setStatus({code:c.ERROR,message:"Upstream request timed out"}),t instanceof Error&&o?.recordException(t),o?.setAttribute("copilot_api.error_type","request_timeout");let n="Upstream request timed out (gateway timeout). Increase the timeout or retry.";Ke(_.ERROR,"ERROR",n,{"copilot_api.status_code":504,"http.path":e.req.path,"copilot_api.error_type":"request_timeout"});let r=Lt(e)?{type:"error",error:{type:"api_error",message:n}}:{error:{message:n,type:"timeout_error"}};return Vt(e,504,t instanceof Error?t.message:n),e.json(r,504)}(e,t);if(function(e){if(!(e instanceof Error))return!1;let t=e.cause,o=Ut(e)??Ut(t);return o?Bt.has(o):Ft.test(e.message)||t instanceof Error&&Ft.test(t.message)}(t))return function(e,t){let o=d.getActiveSpan();o?.setStatus({code:c.ERROR,message:"Transient upstream connection failure"}),t instanceof Error&&o?.recordException(t),o?.setAttribute("copilot_api.error_type","transient_transport");let n="Temporary upstream connection failure. Please retry.";Ke(_.WARN,"WARN",n,{"copilot_api.status_code":503,"http.path":e.req.path,"copilot_api.error_type":"transient_transport"}),e.header("Retry-After","1");let r=Lt(e)?{type:"error",error:{type:"api_error",message:n}}:{error:{message:n,type:"service_unavailable"}};return Vt(e,503,t instanceof Error?t.message:n),e.json(r,503)}(e,t);let n=d.getActiveSpan(),r=t instanceof Error?t:Error(String(t));n?.setStatus({code:c.ERROR,message:r.message}),n?.recordException(r),n?.setAttribute("copilot_api.error_type",r.name),Ke(_.ERROR,"ERROR",`Unhandled error: ${r.message}`,{"copilot_api.status_code":500,"http.path":e.req.path,"copilot_api.error_type":r.name}),Dt({route:e.req.path,statusCode:500,errorClass:r.name,signature:$t({endpointType:_t(e.req.path),statusCode:500,upstreamErrorType:r.name,model:e.get("requestData")?.model}),model:e.get("requestData")?.model,upstreamErrorType:r.name,upstreamErrorMessage:r.message}),Vt(e,500,r.message),o.error(r);let a=Lt(e)?{type:"error",error:{type:"api_error",message:r.message}}:{error:{message:r.message,type:"error"}};return e.json(a,500)}const Xt=async()=>{let e=`${dt}/copilot_internal/v2/token`,t=X.timeoutMs,o=new AbortController,n=setTimeout(()=>o.abort(),t);try{let{response:t,span:n}=await Qe({spanName:"github GET /copilot_internal/v2/token",url:e,target:"copilot_token",headers:mt(X),signal:o.signal});try{if(!t.ok)throw new jt("Failed to get Service token",t);return await t.json()}catch(e){throw We(n,e),e}finally{n.end()}}finally{clearTimeout(n)}};async function Zt(){let e=`${dt}/user`,t=X.timeoutMs,o=new AbortController,n=setTimeout(()=>o.abort(),t);try{let{response:t,span:n}=await Qe({spanName:"github GET /user",url:e,target:"github_user",headers:{authorization:`token ${X._t2}`,"content-type":"application/json",accept:"application/json"},signal:o.signal});try{if(!t.ok)throw new jt("Failed to get GitHub user",t);return await t.json()}catch(e){throw We(n,e),e}finally{n.end()}}finally{clearTimeout(n)}}let Qt=null;function eo(){return Qt||=Xt().then(({token:e})=>{X._t1=e,o.debug("Service token refreshed on upstream 401")}).finally(()=>{Qt=null}),Qt}const to=async()=>{let e=`${lt(X)}/models`,t=ct(X),o=X.timeoutMs,n=new AbortController,r=Ht(n,o);try{let{response:o,span:r}=await Qe({spanName:"copilot GET /models",url:e,target:"models",headers:t,signal:n.signal});try{if(!o.ok)throw new jt("Failed to get models",o);let e=await o.json();return r.setAttribute("copilot_api.models_count",e.data.length),e}catch(e){throw We(r,e),e}finally{r.end()}}finally{clearTimeout(r)}};const oo=e=>new Promise(t=>{setTimeout(t,e)}),no=e=>null==e;async function ro(){X.models=await(async()=>{try{return await to()}catch(e){if(e instanceof jt&&401===e.response.status)return await eo(),to();throw e}})()}const ao=()=>{X._v1="1.135.0-insider"};var io=class extends Error{constructor(e){super(e),this.name="AuthorizationError"}};let so,lo,co,uo,po,mo=!1;function fo(){return ho()?po:void 0}function ho(){return void 0!==po&&Date.now()-po.at<6e4}function go(e){let{span:t,error:n,reason:r,refreshStart:a,attempt:i}=e,s=n.response.status,l=401===s?"Auth token is invalid or expired":"GitHub Copilot subscription not found or not active";X._t1=void 0,po={status:s,message:l,at:Date.now()},clearInterval(so),so=void 0,o.error(`Token refresh received terminal HTTP ${s} — ${l}. Scheduled refresh halted. Re-authenticate to resume.`),Ae.add(1,{reason:r,success:"false"}),Se.add(1,{reason:r}),t.setAttribute("copilot_api.token_refresh.success",!1),t.setAttribute("copilot_api.token_refresh.terminal_status",s),t.setStatus({code:c.ERROR,message:n.message}),t.recordException(n),Fe.record(performance.now()-a,{reason:r}),Ke(_.ERROR,"ERROR",`Token refresh terminated — HTTP ${s} (${l})`,{"copilot_api.token_refresh.reason":r,"copilot_api.token_refresh.attempt":i,"copilot_api.token_refresh.terminal_status":s})}function _o(e){let{span:t,error:n,reason:r,refreshStart:a,maxRetries:i}=e;X._t1=void 0,o.error("All token refresh attempts failed. Stale token has been cleared — next request will trigger re-authentication or fail with a clear 'no token' error.");let s=n instanceof Error?n:Error(String(n));t.setAttribute("copilot_api.token_refresh.success",!1),t.setStatus({code:c.ERROR,message:s.message}),t.recordException(s),Se.add(1,{reason:r}),Fe.record(performance.now()-a,{reason:r}),Ke(_.ERROR,"ERROR",`Token refresh failed after ${i} attempts (${r})`,{"copilot_api.token_refresh.reason":r,"copilot_api.token_refresh.attempts":i})}const yo=async(e=5,t=1e3,n="scheduled")=>mo?(o.debug("Token refresh already in progress, coalescing"),lo):(mo=!0,lo=he.startActiveSpan("copilot_api.token.refresh",async r=>{let a=performance.now();r.setAttribute("copilot_api.token_refresh.reason",n),r.setAttribute("copilot_api.token_refresh.max_retries",e);try{for(let i=1;i<=e;i++)try{r.setAttribute("copilot_api.token_refresh.attempt",i),o.debug(`Refreshing Service token (${n}, attempt ${i}/${e})`);let{token:t}=await Xt();return X._t1=t,po=void 0,o.debug("Service token refreshed successfully"),X.showToken&&o.info("Refreshed Service token:",t),r.setAttribute("copilot_api.token_refresh.success",!0),Ae.add(1,{reason:n,success:"true"}),Fe.record(performance.now()-a,{reason:n}),void Ke(_.INFO,"INFO",`Token refreshed successfully (${n})`,{"copilot_api.token_refresh.reason":n,"copilot_api.token_refresh.attempt":i})}catch(s){if(s instanceof jt&&(401===s.response.status||403===s.response.status))return void go({span:r,error:s,reason:n,refreshStart:a,attempt:i});let l=i===e;if(o.error(`Failed to refresh Service token (attempt ${i}/${e}):`,s),Ae.add(1,{reason:n,success:"false"}),l)return void _o({span:r,error:s,reason:n,refreshStart:a,maxRetries:e});let c=t*2**(i-1);o.debug(`Retrying token refresh in ${c}ms...`),await new Promise(e=>setTimeout(e,c))}}finally{r.end(),mo=!1,lo=void 0}}),lo);async function wo(){return!!X._t1||!ho()&&(await yo(3,250,"on-demand"),!!X._t1)}async function ko(e){try{let t=await a.readFile(K.GITHUB_TOKEN_PATH,"utf8");if(t&&!e?.force)return X._t2=t,X.showToken&&o.info("Auth token:",t),void await bo();o.info("Authentication required");let n=await async function(){let e=new AbortController,t=X.timeoutMs,o=setTimeout(()=>{e.abort()},t);try{let t=await fetch(`${ft}/login/device/code`,{method:"POST",headers:{"content-type":"application/json",accept:"application/json"},body:JSON.stringify({client_id:ht,scope:gt}),signal:e.signal});if(!t.ok)throw new jt("Failed to get device code",t);return await t.json()}finally{clearTimeout(o)}}();o.debug("Device code response:",n),o.info(`Please enter the code "${n.user_code}" at ${n.verification_uri}`);try{m.writeSync(n.user_code),o.success("Code copied to clipboard — opening browser...")}catch{o.info("Open the link above and enter the code to authenticate")}!function(e){try{let t,o=g.platform;t="darwin"===o?"open":"win32"===o?"start":"xdg-open",f(t,[e],()=>{})}catch{}}(n.verification_uri);let r=await async function(e){let t=1e3*(e.interval+1);o.debug(`Polling access token with interval of ${t}ms`),o.start("Waiting for authorization...");let n=Date.now(),r=1e3*e.expires_in;for(;;){if(Date.now()-n>=r)throw new io("Authorization timed out — the code expired. Please run the command again.");let a=new AbortController,i=X.timeoutMs,s=setTimeout(()=>{a.abort()},i);try{let n=await fetch(`${ft}/login/oauth/access_token`,{method:"POST",headers:ot(),body:JSON.stringify({client_id:ht,device_code:e.device_code,grant_type:"urn:ietf:params:oauth:grant-type:device_code"}),signal:a.signal});if(!n.ok){await oo(t),o.error("Failed to poll access token:",await n.text());continue}let r=await n.json();if(o.debug("Polling access token response:",r),r.error){if("expired_token"===r.error)throw new io("Authorization timed out — the code expired. Please run the command again.");if("access_denied"===r.error)throw new io("Authorization was denied. Please run the command again and approve the request.");"authorization_pending"!==r.error&&"slow_down"!==r.error&&o.warn(`Unexpected auth error: ${r.error}`),await oo(t);continue}if(r.access_token)return r.access_token;await oo(t)}catch(e){if(e instanceof io)throw e;if(e instanceof Error&&"AbortError"===e.name){o.error("Access token polling timed out"),await oo(t);continue}throw e}finally{clearTimeout(s)}}}(n);await(e=>a.writeFile(K.GITHUB_TOKEN_PATH,e,{mode:384}))(r),X._t2=r,X.showToken&&o.info("Auth token:",r),await bo()}catch(e){throw e instanceof jt?(o.error("Failed to get Auth token:",await e.response.json()),e):(o.error("Failed to get Auth token:",e),e)}}async function bo(){let e=await Zt();o.success(`Authenticated as ${e.login}`)}async function vo(e){e.verbose&&(o.level=5,o.info("Verbose logging enabled")),X.showToken=e.showToken,await W(),await ko({force:!0}),console.log([""," Get started:",""," $ npx copilot-api-node20@latest start --claude-code"," $ npx copilot-api-node20@latest start --codex",""," Full docs: https://www.npmjs.com/package/copilot-api-node20",""].join("\n")),process.exit(0)}const $o=e({meta:{name:"auth",description:"Run authentication flow"},args:{verbose:{alias:"v",type:"boolean",default:!1,description:"Enable verbose logging"},"show-token":{type:"boolean",default:!1,description:"Show token on auth"}},run:({args:e})=>vo({verbose:e.verbose,showToken:e["show-token"]})}),To=.01,xo=864e5,Ao=new Intl.NumberFormat("en-US",{style:"currency",currency:"USD"}),So=new Intl.NumberFormat("en-US"),Eo=e=>Ao.format(e*To),Co=e=>e.credits_used??e.entitlement-e.remaining,Oo=(e,t,o)=>{let n=(e=>{let t=new Date(`${e}T00:00:00Z`);return new Date(Date.UTC(t.getUTCFullYear(),t.getUTCMonth()-1,1))})(t),r=(o.getTime()-n.getTime())/xo;if(r<.5)return;let a=Co(e),i=a*To/r,s=a>=e.entitlement;if(s||i<=0)return{usdPerDay:i,exhaustsOn:void 0,exhausted:s};let l=e.entitlement*To,c=new Date(n.getTime()+l/i*xo);return{usdPerDay:i,exhaustsOn:c<new Date(`${t}T00:00:00Z`)?c:void 0,exhausted:!1}},Io=e=>e?e.unlimited?"unlimited":e.entitlement<=0?"not metered":`${So.format(Co(e))} of ${So.format(e.entitlement)} used`:"n/a",Po=e=>e.padEnd(14),Ro=(e,t=new Date)=>{let o=e.quota_snapshots.premium_interactions,n=[`Usage — ${e.login??"unknown"} (${e.copilot_plan})`,""];if(o.unlimited)n.push(`${Po("AI credits")}unlimited`);else{let e=Co(o),t=o.percent_remaining;n.push(`${Po("AI credits")}${Eo(e)} / ${Eo(o.entitlement)} ${t.toFixed(1)}% left`,`${Po("")}${(e=>{let t=Math.round(32*Math.min(Math.max(e,0),1));return"█".repeat(t)+"░".repeat(32-t)})(1-t/100)}`,`${Po("")}${So.format(e)} of ${So.format(o.entitlement)} credits`)}if(n.push("",`${Po("Chat")}${Io(e.quota_snapshots.chat)}`,`${Po("Completions")}${Io(e.quota_snapshots.completions)}`,"",`${Po("Resets")}${e.quota_reset_date} (in ${((e,t)=>Math.max(0,Math.ceil((new Date(`${e}T00:00:00Z`).getTime()-t.getTime())/xo)))(e.quota_reset_date,t)} days)`),!o.unlimited){let r=Oo(o,e.quota_reset_date,t);r&&n.push(`${Po("Burn rate")}~${Ao.format(r.usdPerDay)}/day${(e=>e.exhausted?" — allowance already exhausted":e.exhaustsOn?` — on track to exhaust ${(e=>e.toLocaleDateString("en-US",{month:"short",day:"numeric",timeZone:"UTC"}))(e.exhaustsOn)}`:" — within allowance")(r)}`);let a=o.overage_permitted?"permitted, "+(o.overage_count>0?`${So.format(o.overage_count)} used`:"none used"):"not permitted";n.push(`${Po("Overage")}${a}`)}return n.join("\n")},No=async()=>{let e=`${dt}/copilot_internal/user`,t=X.timeoutMs,o=new AbortController,n=setTimeout(()=>o.abort(),t);try{let{response:t,span:n}=await Qe({spanName:"github GET /copilot_internal/user",url:e,target:"usage",headers:mt(X),signal:o.signal});try{if(!t.ok)throw new jt("Failed to get usage",t);return await t.json()}catch(e){throw We(n,e),e}finally{n.end()}}finally{clearTimeout(n)}},qo=e({meta:{name:"check-usage",description:"Show current usage/quota information"},async run(){await W(),await ko();try{let e=await No();o.box(Ro(e))}catch(e){o.error("Failed to fetch usage:",e),process.exit(1)}}}),Do=N(f);async function jo(){let e="win32"===g.platform?"where.exe":"which";try{return await Do(e,["tailscale"]),!0}catch{return!1}}async function Mo(){try{let{stdout:e}=await Do("tailscale",["status","--self","--json"]);return JSON.parse(e).Self}catch{return}}function Ho(e){return e.replace(/\.$/,"")}async function Bo(){let e=await Mo();if(e?.Online)return Ho(e.DNSName)}const Fo=N(f),Uo=e=>`[1m${e}[0m`,Lo=e=>`[2m${e}[0m`,Go=e=>`[36m${e}[0m`,zo=e=>`[32m${e}[0m`,Jo=e=>`[31m${e}[0m`,Ko=e=>`[33m${e}[0m`,Wo=Lo(" ─────────────────────────────────────────────────────────────"),Vo=s.join(K.APP_DIR,"certs","tailscale"),Yo=s.join(Vo,"cert.pem"),Xo=s.join(Vo,"key.pem"),Zo={certDir:Vo,certPath:Yo,keyPath:Xo};function Qo(){switch(g.platform){case"darwin":return[` ${Lo("Install Tailscale for macOS:")}`,` ${Go("https://tailscale.com/download/mac")}`,` ${Lo("(Use the Mac App Store or .pkg download — not brew)")}`,"",` ${Lo("After installing, open the Tailscale app and sign in.")}`,` ${Lo("Then re-run this command.")}`].join("\n");case"linux":return[` ${Lo("Install Tailscale for Linux:")}`,` ${Go("curl -fsSL https://tailscale.com/install.sh | sh")}`,` ${Go("sudo tailscale up")}`,` ${Lo("or")} ${Go("https://tailscale.com/download/linux")}`].join("\n");case"win32":return[` ${Lo("Install Tailscale for Windows:")}`,` ${Go("https://tailscale.com/download/windows")}`,"",` ${Lo("After installing, open the Tailscale app and sign in.")}`].join("\n");default:return` ${Lo("Install Tailscale:")} ${Go("https://tailscale.com/download")}`}}function en(){let e=[` ${Jo("Tailscale is not running.")}`];return"darwin"===g.platform?e.push(` ${Lo("Open the Tailscale app from Applications and sign in.")}`,` ${Lo("Download:")} ${Go("https://tailscale.com/download/mac")}`):"win32"===g.platform?e.push(` ${Lo("Open the Tailscale app and sign in.")}`,` ${Lo("Download:")} ${Go("https://tailscale.com/download/windows")}`):e.push(` ${Lo("Connect with:")} ${Go("sudo tailscale up")}`),e.push("",` ${Lo("Then re-run this command.")}`),e.join("\n")}async function tn(){try{return await a.access(Yo),await a.access(Xo),!0}catch{return!1}}function on(e){console.log(""),console.log(Wo),console.log(` ${Uo("Claude Cowork Setup")} ${Lo("— Diagnostic")}`),console.log(Wo),console.log("");for(let t of function(e){let t=[];for(let[o,n]of Object.entries(e)){let e;e="ok"===n.status?zo("✅"):"missing"===n.status?Jo("❌"):Ko("❓");let r=n.detail?Lo(` ${n.detail}`):"";t.push(` ${e} ${o}${r}`)}return t}(e))console.log(t);console.log("");let t=Object.values(e).filter(e=>"missing"===e.status);0===t.length?console.log(` ${zo("All checks passed.")}`):console.log(` ${Jo(`${t.length} issue(s).`)} Run ${Go("copilot-api cowork-setup install")} to fix.`),console.log("")}const nn={alias:"y",type:"boolean",default:!1,description:"Skip confirmation prompts (non-interactive mode)"},rn=e({meta:{name:"cowork-setup",description:"Set up Tailscale-based HTTPS for Claude Cowork to reach the proxy."},subCommands:{doctor:e({meta:{name:"doctor",description:"Diagnose Tailscale + cert status"},async run(){await async function(){let e={},t=await jo();if(e["tailscale-installed"]=t?{status:"ok"}:{status:"missing",detail:"tailscale not found in PATH"},!t)return on(e),console.log(""),console.log(Qo()),void console.log("");let o=await Mo();if(!o||!o.Online)return e["tailscale-running"]={status:"missing",detail:"not connected"},on(e),console.log(en()),void console.log("");let n=Ho(o.DNSName);e["tailscale-running"]={status:"ok",detail:n};let r=await tn();e["tailscale-cert"]=r?{status:"ok",detail:Yo}:{status:"missing",detail:'Run "copilot-api cowork-setup install" to generate'},r&&(e.ready={status:"ok",detail:`https://${n}:<port>`}),on(e)}(),g.exit(0)}}),install:e({meta:{name:"install",description:"Generate a Tailscale TLS certificate for Cowork (interactive, or pass --yes)"},args:{yes:nn},async run({args:e}){await async function(e){if(console.log(""),console.log(Wo),console.log(` ${Uo("Claude Cowork Setup")} ${Lo("— Install")}`),console.log(Wo),console.log(""),!await jo())return console.log(` ${Jo("Tailscale is not installed.")}`),console.log(""),console.log(Qo()),console.log(""),console.log(` ${Lo("After installing, run")} ${Go("tailscale up")} ${Lo("to connect, then re-run this command.")}`),void console.log("");let t=await Mo();if(!t||!t.Online)return console.log(en()),void console.log("");let n=Ho(t.DNSName);if(console.log(` ${Lo("Tailscale hostname:")} ${Uo(n)}`),console.log(""),console.log(` ${Uo("Generating TLS certificate via Tailscale…")}`),console.log(` ${Lo("This requests a real Let's Encrypt cert for your Tailscale hostname.")}`),console.log(` ${Go(`$ tailscale cert --cert-file ${Yo} --key-file ${Xo} ${n}`)}`),console.log(""),e||await o.prompt("Generate the certificate?",{type:"confirm",initial:!0})){try{await a.mkdir(Vo,{recursive:!0}),o.start("Generating certificate (this may take a few seconds)…"),await Fo("tailscale",["cert","--cert-file",Yo,"--key-file",Xo,n]),console.log(` ${zo("✓ Certificate generated")}`)}catch(e){let t=e instanceof Error?e.message:String(e);return void o.error(`Failed to generate cert: ${t}`)}console.log(""),console.log(Wo),console.log(` ${Uo("Next steps")}`),console.log(Wo),console.log(""),console.log(` ${Uo("1.")} Start the proxy:`),console.log(` ${Go("copilot-api start --claude-cowork")}`),console.log(""),console.log(` ${Uo("2.")} In Cowork ${Lo("→")} Settings ${Lo("→")} Inference Provider, set:`),console.log(` ${Uo("inferenceGatewayBaseUrl")} = ${Go(`https://${n}:<port>`)}`),console.log(` ${Lo("(replace <port> with the port you start the proxy on, default 4141)")}`),console.log(""),console.log(` ${Uo("3.")} Restart Cowork ${Lo("(Cmd+Q and reopen)")}`),console.log(""),console.log(` ${Lo("For Cowork's own configuration docs, see:")}`),console.log(` ${Go("https://claude.com/docs/cowork/3p/installation")}`),console.log("")}else o.info("Skipped.")}(e.yes),g.exit(0)}}),revert:e({meta:{name:"revert",description:"Remove the generated Tailscale cert files"},args:{yes:nn},async run({args:e}){await async function(e){if(console.log(""),console.log(Wo),console.log(` ${Uo("Claude Cowork Setup")} ${Lo("— Revert")}`),console.log(Wo),console.log(""),!await tn())return console.log(` ${Lo("No Tailscale cert found. Nothing to revert.")}`),void console.log("");if(console.log(` ${Uo("Remove Tailscale cert files:")}`),console.log(` ${Lo(Yo)}`),console.log(` ${Lo(Xo)}`),console.log(""),e||await o.prompt("Delete these files?",{type:"confirm",initial:!0})){try{await a.rm(Vo,{recursive:!0}),console.log(` ${zo("✓ Cert files removed.")}`)}catch(e){let t=e instanceof Error?e.message:String(e);o.warn(`Could not remove: ${t}`)}console.log(""),console.log(` ${Lo("Don't forget to update Cowork's inferenceGatewayBaseUrl setting.")}`),console.log("")}else o.info("Skipped.")}(e.yes),g.exit(0)}})}});function an(e){let t=e,o=String.fromCodePoint(27),n=t.split(o);if(n.length>1){t=n[0];for(let e=1;e<n.length;e++){let r=n[e],a=r.match(/^\[[0-9;]*[a-z]/i);t+=a?r.slice(a[0].length):o+r}}return t.replaceAll(/[\u200B-\u200D\uFEFF]/g,"").replaceAll(/[\u2060-\u2064]/g,"").replaceAll(/[\u206A-\u206F]/g,"").replaceAll(/[\u180E\u2000-\u200A\u2028\u2029\u202F\u205F\u3000]/g,"").replaceAll(/[\uFFF0-\uFFFF]/g,"").replaceAll(/[\x00-\x08\v\f\x0E-\x1F]/g,"")}function sn(e){if("string"==typeof e)return an(e);if(Array.isArray(e))return e.map(e=>sn(e));if(e&&"object"==typeof e){let t={},o="thinking"===e.type;for(let[n,r]of Object.entries(e))t[n]=!o||"thinking"!==n&&"signature"!==n?sn(r):r;return"object"===t.type&&!("properties"in t)&&(t.properties={}),t}return e}const ln="x-copilot-api-self-test",cn=R();const un=/\b(?:haiku|mini|flash|nano|small|lite)\b/i;function pn(e){return!e.id.startsWith("text-embedding")&&"embeddings"!==e.capabilities.type&&!function(e){let t=e.supported_endpoints;return t?t.includes("/responses")&&!t.includes("/chat/completions"):/gpt-[\d.]+-codex/i.test(e.id)}(e)&&!function(e){return"disabled"===e.policy?.state}(e)}function dn(e){try{!function(e){let{c:t,start:o,span:n}=e,r=t.get("requestData"),a=t.res.status,i=r?.model??"unknown",s=r?.streaming??!1,l=Math.round(performance.now()-o);if(n.setAttribute("http.status_code",a),n.setAttribute("copilot_api.model",i),n.setAttribute("copilot_api.streaming",s),n.setAttribute("copilot_api.duration_ms",l),r?._d1&&n.setAttribute("copilot_api.copilot_duration_ms",r._d1),r?.tokenUsage){let e=r.tokenUsage;n.setAttribute("copilot_api.input_tokens",e.inputTokens),n.setAttribute("copilot_api.output_tokens",e.outputTokens),n.setAttribute("copilot_api.total_tokens",e.totalTokens),e.cachedTokens&&n.setAttribute("copilot_api.cached_tokens",e.cachedTokens)}t.res.headers.forEach((e,t)=>{let o=t.toLowerCase();Xe.has(o)||n.setAttribute(`http.response.header.${o}`,e)}),a>=400&&n.setStatus({code:c.ERROR,message:`HTTP ${a}`})}(e)}catch(e){o.warn("Error enriching span during finalization:",e)}try{!function(e){let{c:t,start:o,method:n,path:r,endpointType:a,requestId:i}=e;if(t.get("isSelfTest"))return;let s=Math.round(performance.now()-o),l=t.get("requestData"),c=t.res.status,u=l?.model??"unknown",p=l?.streaming??!1,d={method:n,path:r,status_code:String(c),model:u,streaming:String(p),endpoint_type:a};if(ye.add(1,d),De.record(s,d),c>=400&&we.add(1,{method:n,path:r,status_code:String(c),error_type:c>=500?"server_error":"client_error"}),l?.tokenUsage){let e=l.tokenUsage,t={model:u,endpoint_type:a};e.inputTokens&&(ke.add(e.inputTokens,t),Le.record(e.inputTokens,t)),e.outputTokens&&(be.add(e.outputTokens,t),Ge.record(e.outputTokens,t)),e.cachedTokens&&ve.add(e.cachedTokens,{model:u})}!p&&l?.tokenUsage&&ce.executeCompletion(i)}(e)}catch(e){o.warn("Error recording metrics during finalization:",e)}try{e.span.end()}catch{}}const mn=1048576;const fn=async()=>he.startActiveSpan("copilot_api.approval.await",async e=>{let t=performance.now();try{let n=await o.prompt("Accept incoming request?",{type:"confirm"}),r=performance.now()-t;if(e.setAttribute("copilot_api.approval.wait_duration_ms",r),Je.record(r),!n)throw e.setAttribute("copilot_api.approval.result","rejected"),Pe.add(1,{result:"rejected"}),new jt("Request rejected",Response.json({message:"Request rejected"},{status:403}));e.setAttribute("copilot_api.approval.result","approved"),Pe.add(1,{result:"approved"})}finally{e.end()}});function hn(e){let t=e.prompt_tokens||0,o=e.completion_tokens||0;return{inputTokens:t,outputTokens:o,totalTokens:e.total_tokens||t+o,cachedTokens:e.prompt_tokens_details?.cached_tokens,acceptedPredictionTokens:e.completion_tokens_details?.accepted_prediction_tokens,rejectedPredictionTokens:e.completion_tokens_details?.rejected_prediction_tokens}}function gn(e,t){void 0!==t.prompt_tokens&&e.setAttribute("copilot_api.input_tokens",t.prompt_tokens),void 0!==t.completion_tokens&&e.setAttribute("copilot_api.output_tokens",t.completion_tokens),void 0!==t.total_tokens&&e.setAttribute("copilot_api.total_tokens",t.total_tokens)}const _n=[{pattern:/haiku/i,family:"haiku"},{pattern:/sonnet[.-]?4[.-]6/i,family:"sonnet-4.6"},{pattern:/(sonnet-4[.-]5|[.-]?3[.-]5[.-]?sonnet|[.-]?3[.-]7[.-]?sonnet)/i,family:"sonnet-4.5"},{pattern:/sonnet-4(?![.-]5|[.-]6|[.-]1)/i,family:"sonnet-4"},{pattern:/opus[.-]?4[.-]7/i,family:"opus-4.7"},{pattern:/opus[.-]?4[.-]6/i,family:"opus-4.6"},{pattern:/opus[.-]?4[.-]5/i,family:"opus-4.5"},{pattern:/opus/i,family:"opus"}],yn="claude-haiku-4.5",wn={haiku:yn,"sonnet-4.6":"claude-sonnet-4.6","sonnet-4.5":"claude-sonnet-4.5","sonnet-4":"claude-sonnet-4","opus-4.7":"claude-opus-4.7","opus-4.6":"claude-opus-4.6","opus-4.5":"claude-opus-4.5",opus:"claude-opus-4.5"};function kn(e,t){let o=function(e){return e.startsWith("anthropic/")?e.slice(10):e}(e),[n,r]=function(e){let t=e.lastIndexOf("["),o=e.lastIndexOf("]");return-1!==t&&o===e.length-1&&o>t?[e.slice(0,t),e.slice(t+1,o)]:[e,null]}(o);if(t.includes(o))return o;if(r){let e=`${n}-${r}`.replaceAll(/(\d)-(\d)\b/g,"$1.$2");if(t.includes(e))return e}let a=function(e){for(let t of _n)if(t.pattern.test(e))return t.family;return null}(n);if(!a)return null;let i=n.replace(/-\d{8}(?::.*)?$/,""),s=r?`-${r}`:"";for(let e of t){let t=e.replace(/-\d{8}(?::.*)?$/,""),o=`${i}${s}`.toLowerCase().replaceAll(/(\d)-(\d)\b/g,"$1.$2");if(t.toLowerCase().replaceAll(/(\d)-(\d)\b/g,"$1.$2")===o)return e}return function(e,t,o=null){let n=wn[e];if(!n)return null;if(o){let e=`${n}-${o}`;if(t.includes(e))return e}if(t.includes(n))return n;if("sonnet-4.5"===e)for(let e of["claude-3.5-sonnet"]){let n=o?`${e}-${o}`:e;if(t.includes(n))return n}return null}(a,t,r)}const bn=new Map([["none",0],["low",1],["medium",2],["high",3],["xhigh",4]]);function vn(e,t){if(!e||!t||0===t.length)return null;let o=function(e){return"max"===e?"xhigh":e}(e);if(t.includes(o))return o;let n=bn.get(o);if(void 0===n)return t[0]??null;let r=null,a=1/0;for(let e of t){let t=bn.get(e);if(void 0===t)continue;let o=Math.abs(t-n);o<a&&(a=o,r=e)}return r}var $n=class extends Error{statusCode;constructor(e,t=400){super(e),this.name="ModelValidationError",this.statusCode=t}};function Tn(e){if(!e||"string"!=typeof e)throw new $n("Model name is required and must be a string");if(!X.models?.data)throw new $n("Models not available. Please try again later.",503);let t=X.models.data.map(e=>e.id);if(t.includes(e))return e;let o=kn(e,t);if(!o)throw Te.add(1,{requested_model:e}),new $n(`Invalid model: '${e}'. Available services: ${t.join(", ")}`);return o}async function xn(e){if(void 0===e.rateLimitSeconds)return;let t=e.rateLimitSeconds;return he.startActiveSpan("copilot_api.rate_limit.check",async n=>{try{let r=Date.now();if(n.setAttribute("copilot_api.rate_limit.configured_seconds",t),!e.lastRequestTimestamp)return e.lastRequestTimestamp=r,void n.setAttribute("copilot_api.rate_limit.action","allowed");let a=(r-e.lastRequestTimestamp)/1e3;if(n.setAttribute("copilot_api.rate_limit.elapsed_seconds",a),a>t)return e.lastRequestTimestamp=r,void n.setAttribute("copilot_api.rate_limit.action","allowed");let i=Math.ceil(t-a);if(n.setAttribute("copilot_api.rate_limit.wait_seconds",i),!e.rateLimitWait)throw n.setAttribute("copilot_api.rate_limit.action","rejected"),$e.add(1,{action:"rejected",source:"local"}),o.warn(`Rate limit exceeded. Need to wait ${i} more seconds.`),new jt("Rate limit exceeded",Response.json({message:"Rate limit exceeded"},{status:429}));let s=1e3*i;n.setAttribute("copilot_api.rate_limit.action","waited"),$e.add(1,{action:"waited",source:"local"}),He.record(s,{source:"local"}),o.warn(`Rate limit reached. Waiting ${i} seconds before proceeding...`),await oo(s),e.lastRequestTimestamp=r,o.info("Rate limit wait completed, proceeding with request")}finally{n.end()}})}function An(e){if(e instanceof jt){let t=e.response.status;return{type:529===t?"overloaded_error":`upstream_error_${t}`,message:`Upstream error (${t}) while streaming response`}}return{type:"api_error",message:"Stream interrupted before completion"}}async function Sn(e,t){let{type:n,message:r}=An(t);try{await e.writeSSE({event:"error",data:JSON.stringify({type:"error",error:{type:n,message:r}})})}catch(e){o.debug("Failed to emit Anthropic stream error frame:",e)}}async function En(e,t){let{type:n,message:r}=An(t);try{await e.writeSSE({event:"error",data:JSON.stringify({error:{message:r,type:n}})})}catch(e){o.debug("Failed to emit OpenAI stream error frame:",e)}}function Cn(e){if("number"==typeof e){if(!Number.isFinite(e))return null;let t=Math.floor(e);return t>0?t:null}if("string"==typeof e){let t=e.trim();if(!t)return null;let o=Number(t);if(!Number.isFinite(o))return null;let n=Math.floor(o);return n>0?n:null}return null}function On(e,t,o){return Math.min(Math.max(e,t),o)}function In(e,t=0){if(t>5||!e||"object"!=typeof e)return null;let o=e.error;if(!o||"object"!=typeof o)return null;let n=o.code;if("string"==typeof n)return n;let r=o.message;if("string"!=typeof r)return null;try{return In(JSON.parse(r),t+1)}catch{return null}}function Pn(e,t){let o=e?.data.find(e=>e.id===t);if(!o)return null;let n=Cn(o.capabilities.supports.min_thinking_budget),r=Cn(o.capabilities.supports.max_thinking_budget);return!n||!r||r<=n?null:{bounds:{min:n,max:r-1},maxOutputTokens:Cn(o.capabilities.limits?.max_output_tokens)??void 0}}function Rn(e){let{config:t}=e,o=t.bounds.min,n=t.bounds.max,r=On(Cn(e.requestedBudget)??o,o,n),a=Cn(e.maxTokens);if(a||=r+1,t.maxOutputTokens&&a>t.maxOutputTokens&&(a=t.maxOutputTokens),a<=r){let e=Math.min(r,a-1);if(e>=o)r=e;else{let e=o+1;if(t.maxOutputTokens&&e>t.maxOutputTokens)return{thinkingBudget:null,maxTokens:a};a=e,r=o}}return a<=r?{thinkingBudget:null,maxTokens:a}:{thinkingBudget:r,maxTokens:a}}function Nn(e,t){if(no(e.thinking_budget))return e;let o=Pn(t,e.model);if(!o)return{...e,thinking_budget:void 0};let n=Rn({requestedBudget:e.thinking_budget,maxTokens:e.max_tokens,config:o});return null===n.thinkingBudget?{...e,max_tokens:n.maxTokens,thinking_budget:void 0}:{...e,max_tokens:n.maxTokens,thinking_budget:n.thinkingBudget}}function qn(e){return"invalid_thinking_budget"===In(e)}async function Dn(e){let{payload:t,error:o,models:n,errorBodyText:r}=e;if(no(t.thinking_budget)||!(o instanceof Error))return null;let a,i,s=o;if(!(s.response instanceof Response)||400!==s.response.status)return null;if(void 0!==r)a=r;else try{a=await s.response.clone().text()}catch{return null}try{i=JSON.parse(a)}catch{return null}if(!qn(i))return null;let l=Pn(n,t.model);return l?function(e,t){let o=Rn({requestedBudget:e.thinking_budget,maxTokens:e.max_tokens,config:t});if(null===o.thinkingBudget)return{...e,max_tokens:o.maxTokens,thinking_budget:void 0};let n=o.thinkingBudget,r=Cn(e.thinking_budget);if(r&&r===o.thinkingBudget){let e=n+1;e<=t.bounds.max&&(!o.maxTokens||e<o.maxTokens)&&(n=e)}let a=o.maxTokens;if((!a||a<=n)&&(a=n+1),t.maxOutputTokens&&a>t.maxOutputTokens){if(!(t.maxOutputTokens>n))return{...e,max_tokens:t.maxOutputTokens,thinking_budget:void 0};a=t.maxOutputTokens}return{...e,max_tokens:a,thinking_budget:n}}(t,l):{...t,thinking_budget:void 0}}function jn(e,t){let o=!1;return()=>{if(o)return;o=!0;let n=e.get("requestData")||{};n.upstreamTtfbMs=performance.now()-t,e.set("requestData",n)}}function Mn(e,t){let o=e.get("requestData")||{};o.upstreamTotalMs=performance.now()-t,o._d1=o.upstreamTotalMs,e.set("requestData",o)}const Hn=new Map,Bn=new Map,Fn=new Set;let Un,Ln,Gn;function zn(e){return!e.closed&&!e.destroyed}function Jn(e){o.debug(`Creating HTTP/2 client for ${e}`);let t=new C(e,{allowH2:!0,pipelining:0,keepAliveTimeout:6e4,initialWindowSize:4194304,connectionWindowSize:16777216});return Hn.set(t,Date.now()),Ne.add(1,{event:"created",origin:e}),Ke(_.INFO,"INFO",`HTTP/2 client created for ${e}`,{"copilot_api.h2.event":"created","copilot_api.h2.origin":e}),t.on("connect",()=>{o.debug(`HTTP/2 client connected to ${e}`)}),t.on("error",t=>{o.debug(`HTTP/2 client error for ${e}:`,t.message)}),t.on("disconnect",(n,r,a)=>{o.debug(`HTTP/2 client disconnected from ${e}:`,a.message);let i=Fn.has(t);Ne.add(1,{event:"goaway",origin:e}),Ke(i?_.WARN:_.DEBUG,i?"WARN":"DEBUG",`HTTP/2 client disconnected from ${e}: ${a.message}`,{"copilot_api.h2.event":"goaway","copilot_api.h2.origin":e,"copilot_api.h2.error":a.message}),Bn.delete(t),Fn.delete(t),Hn.delete(t),zn(t)&&t.close().catch(e=>{o.debug("Error closing GOAWAY'd HTTP/2 client:",e)})}),t}function Kn(e){if(!X.connectivity.h2)return;Un&&Un!==e&&function(){for(let e of[...Bn.keys(),...Fn])zn(e)&&e.close().catch(e=>{o.debug("Error closing HTTP/2 pool entry:",e)});Bn.clear(),Fn.clear(),Hn.clear()}(),Un=e;let t=Date.now();for(let[n]of Bn)if(t-(Hn.get(n)??0)>=6e5)Bn.delete(n),Hn.delete(n),zn(n)&&n.close().catch(e=>{o.debug("Error closing rotated HTTP/2 client:",e)}),Ne.add(1,{event:"rotated",origin:e}),Ke(_.INFO,"INFO",`HTTP/2 client rotated for ${e} (max lifetime reached)`,{"copilot_api.h2.event":"rotated","copilot_api.h2.origin":e});else{if(zn(n))return Bn.delete(n),Fn.add(n),n;Bn.delete(n),Hn.delete(n)}let n=Jn(e);return Fn.add(n),n}function Wn(e){e&&Fn.delete(e)&&(zn(e)?Bn.set(e,Date.now()):Hn.delete(e))}function Vn(){Gn||(Gn=setInterval(()=>{!function(){let e=Date.now(),t=X.connectivity.h2Keepalive,n=Bn.size;for(let[r,a]of Bn)e-a<6e4||t&&n<=1||(Bn.delete(r),Hn.delete(r),n--,zn(r)&&r.close().catch(e=>{o.debug("Error closing idle HTTP/2 client:",e)}),Ne.add(1,{event:"idle_reaped",origin:Un??""}),Ke(_.INFO,"INFO",`HTTP/2 idle connection reaped for ${Un}`,{"copilot_api.h2.event":"idle_reaped","copilot_api.h2.origin":Un??""}))}()},3e4),Gn.unref())}function Yn(){Ln||(o.debug("Starting HTTP/2 keepalive (every 45s)"),Ln=setInterval(()=>{(async function(){if(0===Bn.size&&0===Fn.size){if(Un){let e=Jn(Un);Bn.set(e,Date.now())}return}let e=[...Bn.keys()];for(let t of e)Bn.delete(t);await Promise.allSettled(e.map(async e=>{if(zn(e))try{let{statusCode:t,body:n}=await e.request({path:"/models",method:"GET",headers:ct(X)});await n.dump(),Re.add(1,{result:"success"}),o.debug(`HTTP/2 keepalive: GET /models → ${t}`),Bn.set(e,Date.now())}catch(t){Re.add(1,{result:"error"}),o.warn("HTTP/2 keepalive failed:",t instanceof Error?t.message:t),Ne.add(1,{event:"error",origin:Un??""}),Hn.delete(e),zn(e)&&e.close().catch(e=>{o.debug("Error closing broken HTTP/2 client:",e)})}else Hn.delete(e)}))})().catch(e=>{o.debug("Unexpected error in HTTP/2 keepalive:",e)})},45e3),Ln.unref(),Vn())}function Xn(e){return function(e){if(!(e instanceof Error))return!1;let t=e.code;return(!t||"UND_ERR_SOCKET"===t)&&/GOAWAY/i.test(e.message)}(e)||function(e){if(!(e instanceof Error))return!1;let t=e.code;return"ECONNRESET"===t||(!t||"UND_ERR_SOCKET"===t)&&(/ECONNRESET/i.test(e.message)||/other side closed/i.test(e.message))}(e)||function(e){if(!(e instanceof Error))return!1;let t=e.code;return"UND_ERR_DESTROYED"===t||"UND_ERR_CLOSED"===t}(e)||function(e){return e instanceof Error&&"UND_ERR_CONNECT_TIMEOUT"===e.code}(e)}async function Zn(){return new Promise(e=>setTimeout(e,100))}async function Qn(e,t,o){try{if(!e.ok)throw new jt("Failed to create chat completions",e,{outgoingBody:o.outgoingBody,outgoingHeaders:o.outgoingHeaders});let n=await e.json();return n.id&&t.setAttribute("copilot_api.response.id",n.id),n.usage&&gn(t,n.usage),n}catch(e){throw We(t,e),e}finally{t.end()}}const er=async e=>{let t=sn(e);try{return await tr(t)}catch(e){if(e instanceof jt&&401===e.response.status)return await eo(),tr(t);let n;if(e instanceof jt)try{n=await e.response.clone().text()}catch{n=void 0}let r=await Dn({payload:t,error:e,models:X.models,errorBodyText:n});if(r)return e instanceof jt&&void 0!==n&&o.warn(`Upstream rejected thinking_budget (status ${e.response.status}): ${n.slice(0,500)}`),o.warn("Adjusting thinking_budget payload and retrying once..."),await tr(sn(r));throw e}},tr=async e=>{if(!X._t1)throw Error("Service token not found");let t=e.messages.some(e=>"string"!=typeof e.content&&e.content?.some(e=>"image_url"===e.type)),n=e.messages.some(e=>["assistant","tool"].includes(e.role)),r={...ct(X,t),"X-Initiator":n?"agent":"user"},a=lt(X),i=`${a}/chat/completions`,s=X.timeoutMs,l=function(e,t){if(!function(e,t){return(t?.data.find(t=>t.id===e)?.capabilities.family??e).startsWith("gpt-5")}(e.model,t))return{...e};let{max_tokens:o,stop:n,...r}=e;return null==o?{...r}:{...r,max_completion_tokens:o}}(e,X.models),c=JSON.stringify(l),u={"copilot_api.model":e.model,"copilot_api.streaming":!!e.stream,"copilot_api.timeout_ms":s,"copilot_api.has_tools":!!e.tools?.length,"copilot_api.tool_count":e.tools?.length??0,"copilot_api.message_count":e.messages.length,"copilot_api.max_tokens":e.max_tokens??0,"copilot_api.vision_enabled":t,"copilot_api.initiator":n?"agent":"user"};for(let t=0;t<=1;t++){let n=Kn(a),l=new AbortController,p=Ht(l,s);try{let{statusCode:o,headers:a,body:p,span:d}=await et({spanName:"copilot POST /chat/completions",url:i,target:"chat_completions",headers:r,body:c,signal:l.signal,headersTimeout:s,bodyTimeout:3*s,extraAttributes:{...u,"copilot_api.h2.retry_attempt":t},dispatcher:n}),m=new Response(p,{status:o,headers:a});if(e.stream){if(!m.ok)throw d.end(),new jt("Failed to create chat completions",m,{outgoingBody:c,outgoingHeaders:r});return{events:M(m),span:d,release:()=>Wn(n)}}try{return await Qn(m,d,{outgoingBody:c,outgoingHeaders:r})}finally{Wn(n)}}catch(e){if(Wn(n),Xn(e)&&t<1){o.warn(`HTTP/2 connection error during chat completions, retrying (attempt ${t+1}): ${e instanceof Error?e.message:String(e)}`),await Zn();continue}throw e}finally{clearTimeout(p)}}throw Error("Unexpected: exhausted GOAWAY retries without result")};function or(e,t){if(!e.data)return e;try{let o=JSON.parse(e.data);if(o.usage&&t(o.usage),void 0!==o.usage?.prompt_tokens_details?.cached_tokens)return{...e,data:JSON.stringify({...o,usage:{...o.usage,prompt_tokens_details:void 0}})}}catch(t){o.warn("Failed to parse streaming chunk:",e.data.slice(0,200),t)}return e}async function nr(e){let t=!0===e.get("isSelfTest");t||await xn(X);let n=await e.req.json();o.debug("Request payload:",JSON.stringify(n).slice(-400));try{n=function(e){return he.startActiveSpan("copilot_api.model.validate",t=>{try{t.setAttribute("copilot_api.model.requested",e.model);let n=Tn(e.model);return t.setAttribute("copilot_api.model.normalized",n),n===e.model?(t.setAttribute("copilot_api.model.was_mapped",!1),e):(t.setAttribute("copilot_api.model.was_mapped",!0),xe.add(1,{from_model:e.model,to_model:n}),o.debug(`Normalized model from '${e.model}' to '${n}'`),{...e,model:n})}finally{t.end()}})}(n)}catch(t){if(t instanceof $n)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_model"),e.json({error:{message:t.message,type:"invalid_request_error",code:"invalid_model"}},t.statusCode);throw t}if(e.set("requestData",{model:n.model,streaming:!!n.stream}),X.manualApprove&&!t&&await fn(),no(n.max_tokens)){let e=X.models?.data.find(e=>e.id===n.model);n={...n,max_tokens:e?.capabilities.limits?.max_output_tokens},o.debug("Set max_tokens to:",JSON.stringify(n.max_tokens))}n=Nn(n,X.models),no(n.thinking_budget)||o.debug("Normalized thinking_budget to:",JSON.stringify(n.thinking_budget));let r=performance.now(),a=await er(n),i=performance.now()-r;if(je.record(i,{model:n.model,target:"chat_completions",streaming:String(!!n.stream)}),rr(a)){let t=e.get("requestData")||{};return a.usage&&(t.tokenUsage=hn(a.usage)),t._d1=i,t.upstreamTtfbMs=i,t.upstreamTotalMs=i,e.set("requestData",t),o.debug("Non-streaming response:",JSON.stringify(a)),e.json(a)}let{events:s,span:l,release:c}=a;return j(e,async t=>{let o={value:null},a=0,u=performance.now(),p=jn(e,r);try{try{for await(let r of s){p();let s=r;r.data&&"[DONE]"!==r.data&&(a++,Ie.add(1,{model:n.model,endpoint_type:"openai"}),s=or(r,t=>{o.value=t;let n=e.get("requestData")||{};n.tokenUsage=hn(t),n._d1=i,e.set("requestData",n)})),await t.writeSSE(s)}let l=performance.now()-u,c={model:n.model,endpoint_type:"openai"};if(Me.record(l,c),ze.record(a,c),Mn(e,r),o.value){let t=e.get("requestData")||{};t.tokenUsage||(t.tokenUsage=hn(o.value),t._d1=i,e.set("requestData",t))}}catch(o){throw Ve(l,e.get("requestSpan"),o),await En(t,o),o}finally{o.value&&gn(l,o.value),l.end(),c()}let d=e.get("requestId");d&&ce.executeCompletion(d)}finally{e.get("resolveStreamComplete")?.()}})}const rr=e=>Object.hasOwn(e,"choices"),ar=new q;ar.post("/",async e=>{try{return await nr(e)}catch(t){return await Yt(e,t)}});const ir=new q;ir.post("/",async e=>{try{let t=await e.req.json();try{t.model=Tn(t.model)}catch(t){if(t instanceof $n)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_model"),e.json({error:{message:t.message,type:"invalid_request_error",code:"invalid_model"}},t.statusCode);throw t}e.set("requestData",{model:t.model});let o=performance.now(),n=await(async e=>{if(!X._t1)throw Error("Service token not found");let t=`${lt(X)}/embeddings`,o=ct(X),n=X.timeoutMs,r=new AbortController,a=Ht(r,n),i=JSON.stringify(e);try{let{response:n,span:a}=await Qe({spanName:"copilot POST /embeddings",url:t,target:"embeddings",method:"POST",headers:o,body:i,signal:r.signal,extraAttributes:{"copilot_api.model":e.model,"copilot_api.input_count":Array.isArray(e.input)?e.input.length:1}});try{if(!n.ok)throw new jt("Failed to create embeddings",n,{outgoingBody:i,outgoingHeaders:o});return await n.json()}catch(e){throw We(a,e),e}finally{a.end()}}finally{clearTimeout(a)}})(t),r=performance.now()-o;je.record(r,{model:t.model,target:"embeddings",streaming:"false"});let a=e.get("requestData")||{};return a.tokenUsage=hn(n.usage),a._d1=r,e.set("requestData",a),e.json(n)}catch(t){return await Yt(e,t)}});const sr=new q;let lr=null,cr=null;function ur(e){return"type"in e&&"string"==typeof e.type&&e.type.startsWith("web_search")}function pr(e){return!ur(e)}sr.get("/",async e=>{let t,o=function(){let e=X._t1;if(!e)return"missing";try{let t=e.split(".");if(t.length<2)return"expired";let o=(t[1]??"").replaceAll("-","+").replaceAll("_","/"),n=JSON.parse(atob(o)),r="object"==typeof n&&n&&"exp"in n&&"number"==typeof n.exp?n.exp:void 0;return void 0!==r&&1e3*r<Date.now()?"expired":"valid"}catch{return"expired"}}(),n=await async function(){let e=Date.now(),t=lr;return t&&e-t.timestamp<3e4?{result:t.result}:cr||(cr=(async()=>{let e=new AbortController,t=setTimeout(()=>e.abort(),5e3),o=performance.now();try{let t=`${lt(X)}/models`,n=await fetch(t,{method:"GET",headers:ct(X),signal:e.signal}),r=Math.round(performance.now()-o),a=n.ok?"reachable":"unreachable";return lr={result:a,timestamp:Date.now()},{result:a,latencyMs:r}}catch{let e=Math.round(performance.now()-o);return lr={result:"unreachable",timestamp:Date.now()},{result:"unreachable",latencyMs:e}}finally{clearTimeout(t),cr=null}})(),cr)}();t="valid"===o&&"reachable"===n.result?"ok":"valid"!==o&&"reachable"!==n.result?"unhealthy":"degraded";let r={status:t,copilot_token:o,upstream:n.result,version:"0.41.0",timestamp:(new Date).toISOString()};void 0!==n.latencyMs&&(r.upstream_latency_ms=n.latencyMs);let a="ok"===t?200:503;return e.json(r,a)});const dr=new H(F),mr={...B["anthropic/claude-sonnet-4"].tokens,baseOverhead:4,perTool:27};function fr(e){return dr.encode(e).length}function hr(e){let t=0;for(let o of e)switch(o.type){case"text":t+=fr(o.text)*mr.contentMultiplier;break;case"tool_use":t+=fr(o.name+JSON.stringify(o.input))*mr.contentMultiplier;break;case"tool_result":o.content&&(t+=fr("string"==typeof o.content?o.content:JSON.stringify(o.content))*mr.contentMultiplier);break;case"thinking":t+=fr(o.thinking)*mr.contentMultiplier;break;case"image":t+=1600}return t}function gr(e){let t=0,o=e.properties;if(!o)return t;let n=Object.entries(o);for(let[e,[o,r]]of n.entries()){if(t+=0===e?mr.perFirstProp:mr.perAdditionalProp,t+=fr(o),r.description&&(t+=mr.perPropDesc+fr(r.description)),r.enum&&Array.isArray(r.enum)){t+=mr.perEnum;for(let e of r.enum)t+=fr(String(e))}if("object"===r.type&&r.properties&&(t+=mr.perNestedObject,t+=gr(r)),"array"===r.type&&r.items){let e=r.items;"object"===e.type&&e.properties&&(t+=mr.perArrayOfObjects,t+=gr(e))}}return t}function _r(e,t){let o={"copilot_api.context_1m_beta":/context-1m/i.test(t??"")};return e.thinking&&(o["copilot_api.thinking.type"]=e.thinking.type,"budget_tokens"in e.thinking&&e.thinking.budget_tokens&&(o["copilot_api.thinking.budget_tokens"]=e.thinking.budget_tokens)),e.output_config?.effort&&(o["copilot_api.output_config.effort"]=e.output_config.effort),o}function yr(e,t,o){let n=_r(t,o);for(let[t,o]of Object.entries(n))void 0!==o&&e.setAttribute(t,o)}const wr=async(e,t,n)=>{try{return await br(e,t)}catch(r){if(r instanceof jt&&401===r.response.status)return await eo(),br(e,t);if(r instanceof jt&&400===r.response.status&&n?.onStructuredOutputFallback){let a;try{a=await r.response.clone().text()}catch{a=void 0}let i=n.onStructuredOutputFallback(e,a);if(i)return o.warn(`Upstream rejected structured outputs on ${e.model}; retrying once against ${i.model}`),br(i,t)}throw r}};function kr(e){return e.context_management?["context-management-2025-06-27"]:[]}const br=async(e,t)=>{if(!X._t1)throw Error("Service token not found");let{metadata:n,...r}=sn(e),a={...pt(X,t,kr(r)),"X-Initiator":"agent"},i=lt(X),s=`${i}/v1/messages`,l=X.timeoutMs,c=JSON.stringify(r),u=function(e,t,o){return{"copilot_api.model":e.model,"copilot_api.streaming":!!e.stream,"copilot_api.timeout_ms":o,"copilot_api.has_tools":!!e.tools?.length,"copilot_api.tool_count":e.tools?.length||0,"copilot_api.max_tokens":e.max_tokens||0,"copilot_api.api_type":"anthropic_passthrough",..._r(e,t?.anthropicBeta)}}(r,t,l);for(let e=0;e<=1;e++){let t=Kn(i),p=new AbortController,d=Ht(p,l);try{let{statusCode:o,headers:n,body:i,span:d}=await et({spanName:"copilot POST /v1/messages",url:s,target:"anthropic_messages",headers:a,body:c,signal:p.signal,headersTimeout:l,bodyTimeout:3*l,extraAttributes:{...u,"copilot_api.h2.retry_attempt":e},dispatcher:t}),m=new Response(i,{status:o,headers:n});if(!m.ok)throw d.end(),new jt("Failed to create anthropic messages",m,{outgoingBody:c,outgoingHeaders:a});if(r.stream)return{events:M(m),span:d,release:()=>Wn(t)};try{let e=await m.json();"string"==typeof e.id&&d.setAttribute("copilot_api.response.id",e.id);let t=e.usage;return t&&gn(d,{prompt_tokens:t.input_tokens??0,completion_tokens:t.output_tokens??0,total_tokens:(t.input_tokens??0)+(t.output_tokens??0)}),e}finally{d.end(),Wn(t)}}catch(n){if(Wn(t),Xn(n)&&e<1){o.warn(`HTTP/2 connection error during anthropic messages, retrying (attempt ${e+1}): ${n instanceof Error?n.message:String(n)}`),await Zn();continue}throw n}finally{clearTimeout(d)}}throw Error("Unexpected: exhausted GOAWAY retries without result")};async function vr(e,t,o){try{if(!e.ok)throw new jt("Failed to create responses",e,{outgoingBody:o.outgoingBody,outgoingHeaders:o.outgoingHeaders});let n=await e.json();return n.id&&t.setAttribute("copilot_api.response.id",n.id),n.usage&&gn(t,{prompt_tokens:n.usage.input_tokens,completion_tokens:n.usage.output_tokens,total_tokens:n.usage.total_tokens}),n}catch(e){throw We(t,e),e}finally{t.end()}}const $r=async e=>{try{return await Tr(e)}catch(t){if(t instanceof jt&&401===t.response.status)return await eo(),Tr(e);throw t}},Tr=async e=>{if(!X._t1)throw Error("Service token not found");let t=sn(e),n={...ct(X),"X-Initiator":"agent"},r=lt(X),a=`${r}/responses`,i=X.timeoutMs,s=JSON.stringify(t),l={"copilot_api.model":t.model,"copilot_api.streaming":!!t.stream,"copilot_api.timeout_ms":i,"copilot_api.has_tools":!!t.tools?.length,"copilot_api.tool_count":t.tools?.length??0,"copilot_api.max_output_tokens":t.max_output_tokens??0,"copilot_api.api_type":"responses"};for(let e=0;e<=1;e++){let c=Kn(r),u=new AbortController,p=Ht(u,i);try{let{statusCode:o,headers:r,body:p,span:d}=await et({spanName:"copilot POST /responses",url:a,target:"responses",headers:n,body:s,signal:u.signal,headersTimeout:i,bodyTimeout:3*i,extraAttributes:{...l,"copilot_api.h2.retry_attempt":e},dispatcher:c}),m=new Response(p,{status:o,headers:r});if(t.stream){if(!m.ok)throw d.end(),new jt("Failed to create responses",m,{outgoingBody:s,outgoingHeaders:n});return{events:M(m),span:d,release:()=>Wn(c)}}try{return await vr(m,d,{outgoingBody:s,outgoingHeaders:n})}finally{Wn(c)}}catch(t){if(Wn(c),Xn(t)&&e<1){o.warn(`HTTP/2 connection error during responses, retrying (attempt ${e+1}): ${t instanceof Error?t.message:String(t)}`),await Zn();continue}throw t}finally{clearTimeout(p)}}throw Error("Unexpected: exhausted GOAWAY retries without result")},xr=new Set(["low","medium","high","max","xhigh"]);function Ar(e,t,n){let r=t.includes(e.model)?e.model:kn(e.model,t)??e.model,a=r===e.model?e:{...e,model:r},i=function(e,t,o={}){let n=kn(e,t);if(!n)return null;let r=new Set(t);if(o.context1m){let e=function(e,t){let o=`${e}-1m`;if(t.has(o))return o;let n=`${e}-1m-`;for(let e of t)if(e.startsWith(n))return e;return null}(n,r);if(e)return e}if(o.effort){let e=function(e,t,o){let n=null;if("high"===o?n="high":("max"===o||"xhigh"===o)&&(n="xhigh"),!n)return null;let r=`${e}-${n}`;return t.has(r)?r:null}(n,r,o.effort);if(e)return e}return null}(a.model,t,{context1m:n.context1m,effort:a.output_config?.effort}),s=a;if(i&&i!==a.model){o.debug(`Resolved model variant: ${a.model} → ${i}`);let e=d.getActiveSpan();e?.setAttribute("copilot_api.model.variant_resolved_from",a.model),e?.setAttribute("copilot_api.model.variant_resolved_to",i),s={...a,model:i}}return function(e){let t=e.output_config?.effort;if(!t)return e;let n=X.models?.data.find(t=>t.id===e.model)?.capabilities.supports.reasoning_effort,r=vn(t,n);if(!r||!xr.has(r))return e;let a=r;if(a===t)return e;o.debug(`Effort clamp: ${t} → ${a}`);let i=d.getActiveSpan();return i?.setAttribute("copilot_api.effort.requested",t),i?.setAttribute("copilot_api.effort.clamped_to",a),{...e,output_config:{...e.output_config,effort:a}}}(s)}function Sr(e){return null===e?null:{stop:"end_turn",length:"max_tokens",tool_calls:"tool_use",content_filter:"end_turn"}[e]}function Er(e,t){let o={model:e.model,messages:Cr(e.messages,e.system),max_tokens:e.max_tokens,stop:e.stop_sequences,stream:e.stream,temperature:e.temperature,top_p:e.top_p,user:e.metadata?.user_id,tools:Nr(e.tools),tool_choice:qr(e.tool_choice)},n=e.thinking;if("enabled"===n?.type||"adaptive"===n?.type){let r=Pn(t,o.model);if(r){let a="enabled"===n.type&&"number"==typeof n.budget_tokens?n.budget_tokens:function(e,t,o){let n=function(e,t){return"max"===e||"xhigh"===e?t:"high"===e?16e3:"medium"===e?8e3:1024}(e,o.max),r=Cn(t),a=r&&r>1?r-1:o.min;return On(Math.min(n,a),o.min,o.max)}(e.output_config?.effort??"high",o.max_tokens,r.bounds);o=Nn({...o,thinking_budget:a},t)}}return o}function Cr(e,t){let o=function(e){return e?"string"==typeof e?[{role:"system",content:Or(e)}]:[{role:"system",content:Or(e.map(e=>e.text).join("\n\n"))}]:[]}(t),n=e.flatMap(e=>"user"===e.role?function(e){let t=[];if(Array.isArray(e.content)){let o=e.content.filter(e=>"tool_result"===e.type),n=e.content.filter(e=>"tool_result"!==e.type);for(let e of o)t.push({role:"tool",tool_call_id:e.tool_use_id,content:Rr(e.content)});n.length>0&&t.push({role:"user",content:Rr(n)})}else t.push({role:"user",content:Rr(e.content)});return t}(e):function(e){let t=function(e){return{reasoning_text:Pr(e.reasoning_text),reasoning_opaque:Pr(e.reasoning_opaque)}}(e);if(!Array.isArray(e.content))return[{role:"assistant",content:Rr(e.content),...t}];let o=e.content.filter(e=>"tool_use"===e.type),n=e.content.filter(e=>"text"===e.type),r=e.content.filter(e=>"thinking"===e.type),a=[...n.map(e=>e.text),...r.map(e=>e.thinking)].join("\n\n");return o.length>0?[{role:"assistant",content:a||null,...t,tool_calls:o.map(e=>({id:e.id,type:"function",function:{name:e.name,arguments:JSON.stringify(e.input)}}))}]:[{role:"assistant",content:Rr(e.content),...t}]}(e));return[...o,...n]}function Or(e){return e.startsWith("x-anthropic-billing-header")?e.replace(/^x-_an1-billing-header:[^\n]*\n+/,""):e}const Ir=32768;function Pr(e){if("string"==typeof e)return e.length<=Ir?e:e.slice(0,Ir)}function Rr(e){if("string"==typeof e)return e;if(!Array.isArray(e))return null;if(!e.some(e=>"image"===e.type))return e.filter(e=>"text"===e.type||"thinking"===e.type).map(e=>"text"===e.type?e.text:e.thinking).join("\n\n");let t=[];for(let o of e)switch(o.type){case"text":t.push({type:"text",text:o.text});break;case"thinking":t.push({type:"text",text:o.thinking});break;case"image":t.push({type:"image_url",image_url:{url:`data:${o.source.media_type};base64,${o.source.data}`}})}return t}function Nr(e){if(e)return e.filter(pr).map(e=>({type:"function",function:{name:e.name,description:e.description,parameters:e.input_schema}}))}function qr(e){if(e)switch(e.type){case"auto":return"auto";case"any":return"required";case"tool":return e.name?{type:"function",function:{name:e.name}}:void 0;case"none":return"none";default:return}}function Dr(e){return"string"==typeof e?[{type:"text",text:e}]:Array.isArray(e)?e.filter(e=>"text"===e.type).map(e=>({type:"text",text:e.text})):[]}function jr(e){return e.reasoning_text?[{type:"thinking",thinking:e.reasoning_text}]:[]}function Mr(e){return e?e.map(e=>{let t={};try{t=JSON.parse(e.function.arguments)}catch{r.warn(`Failed to parse tool call arguments for "${e.function.name}": ${e.function.arguments.slice(0,200)}`)}return{type:"tool_use",id:e.id,name:e.function.name,input:t}}):[]}const Hr=new Set(["low","medium","high","max","xhigh"]);function Br(e,t){let o=e.thinking;if(!o||"enabled"!==o.type)return e;let n=t?.data.find(t=>t.id===e.model);if(!n||!n.capabilities.supports.adaptive_thinking)return e;let r={...e,thinking:{type:"adaptive"}};if(!e.output_config?.effort){let t=(e=>null!==e&&Hr.has(e)?e:null)(vn(function(e){return!e||e<=0?"medium":e<8e3?"low":e<24e3?"medium":"high"}(o.budget_tokens),n.capabilities.supports.reasoning_effort));t&&(r.output_config={...e.output_config,effort:t})}return r}function Fr(e){return"string"!=typeof e&&Array.isArray(e)?e.map(e=>{let t=e;if(!t.cache_control||"object"!=typeof t.cache_control)return e;let o=t.cache_control;if("string"!=typeof o.type){let{cache_control:e,...o}=t;return o}let n={type:o.type};return void 0!==o.ttl&&(n.ttl=o.ttl),{...t,cache_control:n}}):e}const Ur=/[^\w-]/g;function Lr(e){return e.replaceAll(Ur,"_")}function Gr(e,t){let o=function(e,t){if(!e.output_config?.effort)return e;let o=t?.data.find(t=>t.id===e.model);if(!o)return e;let n=o.capabilities.supports.reasoning_effort;if(Array.isArray(n)&&n.length>0)return e;let{effort:r,...a}=e.output_config;if(0===Object.keys(a).length){let{output_config:t,...o}=e;return o}return{...e,output_config:a}}(e,t);return o=Br(o,t),o=function(e,t){let o=e.max_tokens;if("number"!=typeof o)return e;let n=t?.data.find(t=>t.id===e.model);if(!n)return e;let r=n.capabilities.limits;if(!r)return e;let a=(!1===e.stream?r.max_non_streaming_output_tokens:void 0)??r.max_output_tokens;if("number"!=typeof a||a<=0)return e;let i=Math.max(Math.min(o,a),16);return i===o?e:{...e,max_tokens:i}}(o,t),o={...o,system:Fr(o.system)},o=function(e){let t=e.messages.map(e=>{if(!Array.isArray(e.content))return e;let t=e.content.map(e=>{let t=e;return"tool_use"===t.type&&"string"==typeof t.id?{...t,id:Lr(t.id)}:"tool_result"===t.type&&"string"==typeof t.tool_use_id?{...t,tool_use_id:Lr(t.tool_use_id)}:e});return{...e,content:t}});return{...e,messages:t}}(o),o}function zr(e){return function(e){let t=e.thinking;if(null==t)return null;if("object"!=typeof t)return"thinking must be an object";let o=t,n=new Set(["enabled","adaptive","disabled"]);return"string"==typeof o.type&&n.has(o.type)?"enabled"!==o.type||void 0===o.budget_tokens||"number"==typeof o.budget_tokens&&Number.isFinite(o.budget_tokens)&&!(o.budget_tokens<=0)&&Number.isInteger(o.budget_tokens)?null:"thinking.budget_tokens must be a positive integer":"thinking.type must be one of: enabled, adaptive, disabled"}(e)??function(e){let t=e.output_config;if(null==t)return null;if("object"!=typeof t)return"output_config must be an object";let o=t;if(void 0===o.effort)return null;let n=new Set(["low","medium","high","max","xhigh"]);return"string"==typeof o.effort&&n.has(o.effort)?null:"output_config.effort must be one of: low, medium, high, max, xhigh"}(e)}function Jr(e,t){return he.startActiveSpan("copilot_api.model.validate",n=>{try{n.setAttribute("copilot_api.model.requested",t.model),yr(n,t,e.req.header("anthropic-beta"));let r=Tn(t.model);n.setAttribute("copilot_api.model.normalized",r);let a=zr(t);return a?(d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_request"),{ok:!1,response:e.json({type:"error",error:{type:"invalid_request_error",message:a}},400)}):r===t.model?(n.setAttribute("copilot_api.model.was_mapped",!1),{ok:!0,payload:t}):(n.setAttribute("copilot_api.model.was_mapped",!0),xe.add(1,{from_model:t.model,to_model:r}),o.debug(`Model mapping: '${t.model}' → '${r}'`),{ok:!0,payload:{...t,model:r}})}catch(t){if(t instanceof $n)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","invalid_model"),{ok:!1,response:e.json({type:"error",error:{type:"invalid_request_error",message:t.message}},t.statusCode)};throw t}finally{n.end()}})}function Kr(e){let t=function(e){let t=[];for(let o of e)"user"===o.role?t.push(...Vr(o)):t.push(...Xr(o));return t}(e.messages);if(0===t.length)throw new jt("request has no translatable message content",Response.json({type:"error",error:{type:"invalid_request_error",message:"request has no translatable message content"}},{status:400}));let o={model:e.model,input:t,max_output_tokens:Math.max(e.max_tokens,16),stream:e.stream,temperature:e.temperature,top_p:e.top_p,store:!1,user:e.metadata?.user_id?.slice(0,64)},n=function(e){return e?function(e){return e.startsWith("x-anthropic-billing-header")?e.replace(/^x-_an1-billing-header:[^\n]*\n+/,""):e}("string"==typeof e?e:e.map(e=>e.text).join("\n\n")):null}(e.system);return n&&(o.instructions=n),e.tools?.length&&(o.tools=e.tools.filter(pr).map(e=>({type:"function",name:e.name,description:e.description,parameters:e.input_schema}))),e.tool_choice&&(o.tool_choice=function(e){switch(e.type){case"auto":return"auto";case"any":return"required";case"none":return"none";case"tool":return e.name?{type:"function",name:e.name}:void 0;default:return}}(e.tool_choice)),"adaptive"===e.thinking?.type?o.reasoning={effort:Wr(e.output_config?.effort??"high")}:"enabled"===e.thinking?.type&&e.thinking.budget_tokens&&(o.reasoning=function(e){return e<5e3?{effort:"low"}:e<2e4?{effort:"medium"}:e<32e3?{effort:"high"}:{effort:"xhigh"}}(e.thinking.budget_tokens)),o}function Wr(e){switch(e){case"low":return"low";case"medium":return"medium";case"max":case"xhigh":return"xhigh";default:return"high"}}function Vr(e){if("string"==typeof e.content)return[{type:"message",role:"user",content:e.content}];let t=[],o=e.content.filter(e=>"tool_result"===e.type),n=e.content.filter(e=>"tool_result"!==e.type);for(let e of o)t.push(Yr(e));if(n.length>0)if(n.some(e=>"image"===e.type)){let e=[];for(let t of n)"text"===t.type?e.push({type:"input_text",text:t.text}):e.push({type:"input_image",image_url:`data:${t.source.media_type};base64,${t.source.data}`});t.push({type:"message",role:"user",content:e})}else{let e=n.filter(e=>"text"===e.type).map(e=>e.text).join("\n\n");e&&t.push({type:"message",role:"user",content:e})}return t}function Yr(e){let t;return t="string"==typeof e.content?e.content:Array.isArray(e.content)?e.content.filter(e=>"text"===e.type).map(e=>e.text).join("\n"):"",e.is_error&&(t=`[ERROR] ${t}`),{type:"function_call_output",call_id:e.tool_use_id,output:t}}function Xr(e){if("string"==typeof e.content)return[{type:"message",role:"assistant",content:e.content}];let t=[],o=e.content.filter(e=>"text"===e.type),n=e.content.filter(e=>"thinking"===e.type),r=e.content.filter(e=>"tool_use"===e.type),a=[...o.map(e=>e.text),...n.map(e=>e.thinking)].join("\n\n");a&&t.push({type:"message",role:"assistant",content:a});for(let e of r)t.push({type:"function_call",call_id:e.id,name:e.name,arguments:JSON.stringify(e.input)});return t}function Zr(e,t){if(t)return"tool_use";switch(e){case"completed":case"cancelled":case"failed":return"end_turn";case"incomplete":return"max_tokens";default:return null}}function Qr(e,t){e.contentBlockOpen&&=(t.push({type:"content_block_stop",index:e.contentBlockIndex}),e.contentBlockIndex++,!1)}function ea(e,t,o){e.messageStartSent||=(e.responseId=o?.responseId??e.responseId,e.model=o?.model??e.model,t.push({type:"message_start",message:{id:e.responseId,type:"message",role:"assistant",content:[],model:e.model,stop_reason:null,stop_sequence:null,usage:{input_tokens:0,output_tokens:0}}}),!0)}function ta(e,t){let o=[];switch(e.type){case"response.created":ea(t,o,{responseId:e.response.id,model:e.response.model});break;case"response.in_progress":case"response.output_text.done":case"response.function_call_arguments.done":case"response.refusal.done":case"response.reasoning_summary_text.delta":case"response.reasoning_summary_text.done":default:break;case"response.output_item.added":if("function_call"===e.item.type){ea(t,o),Qr(t,o);let n=e.item;t.toolCalls[e.output_index]={call_id:n.call_id,name:n.name,_bi1:t.contentBlockIndex},o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"tool_use",id:n.call_id,name:n.name,input:{}}}),t.contentBlockOpen=!0}break;case"response.content_part.added":ea(t,o),Qr(t,o),o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"text",text:""}}),t.contentBlockOpen=!0;break;case"response.output_text.delta":o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"text_delta",text:e.delta}});break;case"response.content_part.done":Qr(t,o);break;case"response.function_call_arguments.delta":{let n=t.toolCalls[e.output_index];n&&o.push({type:"content_block_delta",index:n._bi1,delta:{type:"input_json_delta",partial_json:e.delta}});break}case"response.output_item.done":if("function_call"===e.item.type){let n=t.toolCalls[e.output_index];n&&t.contentBlockOpen&&(o.push({type:"content_block_stop",index:n._bi1}),t.contentBlockIndex++,t.contentBlockOpen=!1)}break;case"response.completed":{Qr(t,o);let n=e.response.output.some(e=>"function_call"===e.type),r=e.response.usage;o.push({type:"message_delta",delta:{stop_reason:Zr(e.response.status,n),stop_sequence:null},usage:{input_tokens:r?.input_tokens??0,output_tokens:r?.output_tokens??0}},{type:"message_stop"});break}case"response.incomplete":{ea(t,o),Qr(t,o);let n=e.response.usage;o.push({type:"message_delta",delta:{stop_reason:"max_tokens",stop_sequence:null},usage:{input_tokens:n?.input_tokens??0,output_tokens:n?.output_tokens??0}},{type:"message_stop"});break}case"response.failed":ea(t,o),Qr(t,o),o.push({type:"error",error:{type:e.response.error?.code??"api_error",message:e.response.error?.message??"Response generation failed"}});break;case"response.cancelled":ea(t,o),Qr(t,o),o.push({type:"message_delta",delta:{stop_reason:"end_turn",stop_sequence:null},usage:{input_tokens:0,output_tokens:0}},{type:"message_stop"});break;case"response.refusal.delta":ea(t,o),t.contentBlockOpen||=(o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"text",text:""}}),!0),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"text_delta",text:e.delta}})}return o}function oa(e,t){e.thinkingBlockOpen||(e.contentBlockOpen&&=(t.push({type:"content_block_stop",index:e.contentBlockIndex}),e.contentBlockIndex++,!1),t.push({type:"content_block_start",index:e.contentBlockIndex,content_block:{type:"thinking",thinking:""}}),e.thinkingBlockOpen=!0,e.contentBlockOpen=!0)}function na(e,t){e.thinkingBlockOpen&&(t.push({type:"content_block_stop",index:e.contentBlockIndex}),e.contentBlockIndex++,e.thinkingBlockOpen=!1,e.contentBlockOpen=!1)}function ra(e,t){let o=[];if(0===e.choices.length)return o;let n=e.choices[0],{delta:r}=n;if(t.messageStartSent||=(o.push({type:"message_start",message:{id:e.id,type:"message",role:"assistant",content:[],model:e.model,stop_reason:null,stop_sequence:null,usage:{input_tokens:e.usage?.prompt_tokens??0,output_tokens:0}}}),!0),"string"==typeof r.reasoning_text&&""!==r.reasoning_text&&(oa(t,o),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"thinking_delta",thinking:r.reasoning_text}})),"string"==typeof r.reasoning_opaque&&""!==r.reasoning_opaque&&(oa(t,o),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"signature_delta",signature:r.reasoning_opaque}}),na(t,o)),r.content&&(na(t,o),function(e){return!!e.contentBlockOpen&&Object.values(e.toolCalls).some(t=>t._bi1===e.contentBlockIndex)}(t)&&(o.push({type:"content_block_stop",index:t.contentBlockIndex}),t.contentBlockIndex++,t.contentBlockOpen=!1),t.contentBlockOpen||=(o.push({type:"content_block_start",index:t.contentBlockIndex,content_block:{type:"text",text:""}}),!0),o.push({type:"content_block_delta",index:t.contentBlockIndex,delta:{type:"text_delta",text:r.content}})),r.tool_calls){na(t,o);for(let e of r.tool_calls){if(e.id&&e.function?.name){t.contentBlockOpen&&=(o.push({type:"content_block_stop",index:t.contentBlockIndex}),t.contentBlockIndex++,!1);let n=t.contentBlockIndex;t.toolCalls[e.index]={id:e.id,name:e.function.name,_bi1:n},o.push({type:"content_block_start",index:n,content_block:{type:"tool_use",id:e.id,name:e.function.name,input:{}}}),t.contentBlockOpen=!0}if(e.function?.arguments){let n=t.toolCalls[e.index];n&&o.push({type:"content_block_delta",index:n._bi1,delta:{type:"input_json_delta",partial_json:e.function.arguments}})}}}return n.finish_reason&&(na(t,o),t.contentBlockOpen&&=(o.push({type:"content_block_stop",index:t.contentBlockIndex}),!1),o.push({type:"message_delta",delta:{stop_reason:Sr(n.finish_reason),stop_sequence:null},usage:{input_tokens:e.usage?.prompt_tokens??0,output_tokens:e.usage?.completion_tokens??0}},{type:"message_stop"})),o}const aa=/structured_outputs|output_config\.format/i;function ia(e,t,o){return function(e,t,o){return!(!e.output_config?.format||"claude-haiku-4.5"===o||!t)&&aa.test(t)}(e,t,e.model)&&o?.data.some(e=>"claude-haiku-4.5"===e.id)?Gr({...e,model:yn},o):null}var sa=class extends Error{constructor(){super("Exa web search timed out after 15000ms. The search endpoint may be slow or unreachable."),this.name="ExaTimeoutError"}};var la=class extends Error{constructor(){super("Tavily web search timed out after 15000ms. The search endpoint may be slow or unreachable."),this.name="TavilyTimeoutError"}};const ca={tavily:async function(e,t,n){let r=function(e,t){let o={query:e,max_results:t?.maxResults??5};return t?.includeDomains?.length&&(o.include_domains=t.includeDomains),t?.excludeDomains?.length&&(o.exclude_domains=t.excludeDomains),o}(t,n);o.debug("Tavily search request:",JSON.stringify(r));let a=new AbortController,i=setTimeout(()=>a.abort(),15e3);try{let{response:t,span:i}=await Qe({spanName:"tavily POST /search",url:"https://api.tavily.com/search",target:"tavily_search",method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${e}`},body:JSON.stringify(r),signal:a.signal,extraAttributes:{"tavily.max_results":n?.maxResults??5,"tavily.has_include_domains":!!n?.includeDomains?.length,"tavily.has_exclude_domains":!!n?.excludeDomains?.length}});try{let e=await async function(e){if(!e.ok){let t=await e.text();throw Error(`Tavily API error: ${e.status} ${t}`)}return await e.json()}(t);return i.setAttribute("tavily.results_count",e.results.length),o.debug(`Tavily returned ${e.results.length} results`),e.results}catch(e){throw We(i,e),e}finally{i.end()}}catch(e){throw e instanceof DOMException&&"AbortError"===e.name?new la:e}finally{clearTimeout(i)}},exa:async function(e,t,n){let r=function(e,t){let o={query:e,numResults:t?.maxResults??5,contents:{text:!0}};return t?.includeDomains?.length&&(o.includeDomains=t.includeDomains),t?.excludeDomains?.length&&(o.excludeDomains=t.excludeDomains),o}(t,n);o.debug("Exa search request:",JSON.stringify(r));let a=new AbortController,i=setTimeout(()=>a.abort(),15e3);try{let{response:t,span:i}=await Qe({spanName:"exa POST /search",url:"https://api.exa.ai/search",target:"exa_search",method:"POST",headers:{"Content-Type":"application/json","x-api-key":e},body:JSON.stringify(r),signal:a.signal,extraAttributes:{"exa.max_results":n?.maxResults??5,"exa.has_include_domains":!!n?.includeDomains?.length,"exa.has_exclude_domains":!!n?.excludeDomains?.length}});try{let e=await async function(e){if(!e.ok){let t=await e.text();throw Error(`Exa API error: ${e.status} ${t}`)}return await e.json()}(t);return i.setAttribute("exa.results_count",e.results.length),o.debug(`Exa returned ${e.results.length} results`),e.results.map(e=>({title:e.title??"",url:e.url,content:e.text??""}))}catch(e){throw We(i,e),e}finally{i.end()}}catch(e){throw e instanceof DOMException&&"AbortError"===e.name?new sa:e}finally{clearTimeout(i)}}},ua=["tavily","exa"];function pa(e){return"tavily"===e||"exa"===e}function da(){return X.webSearchProviders.length>0}async function ma(e,t){return async function(e,t,n){let{providers:r,searchFns:a=ca}=n;if(0===r.length)throw Error("No web search provider configured");let i,s=[];for(let[n,l]of r.entries())try{let n=await a[l.name](l.key,e,t);return s.length>0&&o.info(`Web search recovered: served by "${l.name}" after ${s.join(", ")} failed.`),n}catch(e){i=e,s.push(l.name);let t=e instanceof Error?e.message:String(e);n!==r.length-1&&o.warn(`Web search provider "${l.name}" failed (${t}); falling over to "${r[n+1].name}".`)}let l=i instanceof Error?i.message:String(i);throw o.error(`Web search failed: all providers exhausted (${s.join(", ")}). Last error: ${l}`),i instanceof Error?i:Error("All web search providers failed")}(e,t,{providers:X.webSearchProviders})}function fa(){let e="";for(let t=0;t<24;t++)e+="abcdefghijklmnopqrstuvwxyz0123456789"[Math.floor(36*Math.random())];return e}function ha(e){return e.searchFailed?[{type:"web_search_tool_result_error",error_code:e.errorCode??"unavailable"}]:e.results}async function ga(e,t){let n=function(e){let t,o=e.messages[0];if(!o||"user"!==o.role)return null;if("string"==typeof o.content)t=o.content;else{if(!Array.isArray(o.content))return null;{let e=o.content.find(e=>"text"===e.type);if(!e)return null;t=e.text}}return t.startsWith("Perform a web search for the query: ")?t.slice(36).trim():t.trim()||null}(t);if(!n)return e.set("requestData",{model:t.model,streaming:!1}),e.json({type:"error",error:{type:"invalid_request_error",message:"Could not extract search query from web search request"}},400);let r=function(e){let t=e.tools?.[0];return t&&ur(t)?{maxResults:"number"==typeof t.max_uses?t.max_uses:5,allowedDomains:t.allowed_domains,blockedDomains:t.blocked_domains}:{maxResults:5}}(t);o.info(`Web search intercepted: "${n}"`);let a,i=[],s=!1;try{if(!da())throw s=!0,a="unavailable",Error("No web search provider configured");i=(await ma(n,{maxResults:Math.min(r.maxResults,10),includeDomains:r.allowedDomains,excludeDomains:r.blockedDomains})).map(e=>({type:"web_search_result",url:e.url,title:e.title,encrypted_content:Buffer.from(e.content).toString("base64"),page_age:null}))}catch(e){o.error("Web search failed:",e),s=!0,a??="unavailable"}let l={query:n,results:i,model:t.model,searchFailed:s,errorCode:a};if(!t.stream)return e.set("requestData",{model:t.model,streaming:!1}),e.json(function(e){let{query:t,model:o}=e,n=`srvtoolu_${fa()}`,r=[{type:"text",text:"I'll search for that."},{type:"server_tool_use",id:n,name:"web_search",input:{query:t}},{type:"web_search_tool_result",tool_use_id:n,content:ha(e)}];return{id:`msg_ws_${fa()}`,type:"message",role:"assistant",model:o,content:r,stop_reason:"end_turn",stop_sequence:null,usage:{input_tokens:0,output_tokens:0}}}(l));let c=function(e){let{query:t,model:o}=e,n=`srvtoolu_${fa()}`,r=`msg_ws_${fa()}`,a=[];return a.push({type:"message_start",message:{id:r,type:"message",role:"assistant",content:[],model:o,stop_reason:null,stop_sequence:null,usage:{input_tokens:0,output_tokens:0}}},{type:"content_block_start",index:0,content_block:{type:"text",text:""}},{type:"content_block_delta",index:0,delta:{type:"text_delta",text:"I'll search for that."}},{type:"content_block_stop",index:0},{type:"content_block_start",index:1,content_block:{type:"server_tool_use",id:n,name:"web_search",input:{}}},{type:"content_block_delta",index:1,delta:{type:"input_json_delta",partial_json:JSON.stringify({query:t})}},{type:"content_block_stop",index:1},{type:"content_block_start",index:2,content_block:{type:"web_search_tool_result",tool_use_id:n,content:ha(e)}},{type:"content_block_stop",index:2},{type:"message_delta",delta:{stop_reason:"end_turn",stop_sequence:null},usage:{output_tokens:0}},{type:"message_stop"}),a}(l);return e.set("requestData",{model:t.model,streaming:!0}),j(e,async t=>{for(let e of c)await t.writeSSE({event:e.type,data:JSON.stringify(e)});e.get("resolveStreamComplete")?.()})}const _a=(e,t)=>!(!e||!t||e===t);async function ya(e){if(X._t1||await wo())return null;let t=fo();return t?(d.getActiveSpan()?.setAttribute("copilot_api.error_type","authentication_error"),e.json({type:"error",error:{type:"authentication_error",message:`${t.message}; re-authenticate with \`copilot-api auth\`, then restart the proxy`}},401)):(d.getActiveSpan()?.setAttribute("copilot_api.error_type","service_unavailable"),e.header("Retry-After","1"),e.json({type:"error",error:{type:"service_unavailable",message:"Service token not yet available; retry shortly"}},503))}async function wa(e){let t=await e.req.json();if(function(e){let t=e.tools;return!(!t||1!==t.length)&&ur(t[0])}(t))return ga(e,t);await xn(X),o.debug("Anthropic request payload:",t);let r=t.output_config?.effort;t=function(e,t){return Ar(t,X.models?.data.map(e=>e.id)??[],{context1m:/context-1m/i.test(e.req.header("anthropic-beta")??"")})}(e,t);let a=Jr(e,t);if(!a.ok)return a.response;t=a.payload;let i=await ya(e);if(i)return i;if(function(e){let t=X.models?.data.find(t=>t.id===e)?.supported_endpoints;return t?t.includes("/responses")&&!t.includes("/chat/completions"):/gpt-[\d.]+-codex/i.test(e)}(t.model))return xa(e,t);if(function(e){return e.toLowerCase().startsWith("claude-")}(t.model))return async function(e,t,o){let n=Gr(t,X.models),r={anthropicBeta:e.req.header("anthropic-beta"),anthropicVersion:e.req.header("anthropic-version")},a=n.output_config?.effort;return e.set("requestData",{model:n.model,reasoningEffort:a,effortClamped:_a(o,a),streaming:!!n.stream}),X.manualApprove&&await fn(),he.startActiveSpan("copilot_api.anthropic_passthrough",async t=>{t.setAttribute("copilot_api.route","anthropic_passthrough"),t.setAttribute("copilot_api.model",n.model),t.setAttribute("copilot_api.streaming",!!n.stream),yr(t,n,r.anthropicBeta);try{let o=performance.now(),a=await wr(n,r,{onStructuredOutputFallback:(e,o)=>{let n=ia(e,o,X.models);return n&&(t.setAttribute("copilot_api.structured_output_fallback",!0),t.setAttribute("copilot_api.structured_output_fallback.model",n.model)),n}}),i=performance.now()-o;if(je.record(i,{model:n.model,target:"anthropic_messages",streaming:String(!!n.stream)}),!n.stream){let o=a,n=o.usage;if(n){let t={input_tokens:n.input_tokens||0,output_tokens:n.output_tokens||0,cache_read_input_tokens:n.cache_read_input_tokens||0,cache_creation_input_tokens:n.cache_creation_input_tokens||0},o=e.get("requestData")||{};o.tokenUsage=hn($a(t)),o._d1=i,o.upstreamTtfbMs=i,o.upstreamTotalMs=i,e.set("requestData",o)}return t.end(),e.json(o)}let{events:s,span:l,release:c}=a;return j(e,async r=>{let a=0,i=performance.now(),u={input_tokens:0,output_tokens:0,cache_read_input_tokens:0,cache_creation_input_tokens:0},p=!1,d=jn(e,o);try{try{for await(let e of s)d(),e.data&&"[DONE]"!==e.data?(a++,Ie.add(1,{model:n.model,endpoint_type:"anthropic_messages"}),Ta(e.data,u)&&(p=!0),await r.writeSSE(e)):await r.writeSSE(e);let e=performance.now()-i,t={model:n.model,endpoint_type:"anthropic_messages"};Me.record(e,t),ze.record(a,t)}catch(t){throw Ve(l,e.get("requestSpan"),t),await Sn(r,t),t}finally{if(Mn(e,o),p){let t=$a(u);gn(l,t);let o=e.get("requestData")||{};o.tokenUsage=hn(t),e.set("requestData",o)}l.end(),c()}let t=e.get("requestId");t&&ce.executeCompletion(t)}finally{t.end(),e.get("resolveStreamComplete")?.()}})}catch(e){throw We(t,e),t.end(),e}})}(e,t,r);let s=performance.now(),l=he.startActiveSpan("copilot_api.translate.anthropic_to_openai",o=>{try{o.setAttribute("copilot_api.translation.direction","anthropic_to_openai"),o.setAttribute("copilot_api.translation.message_count",t.messages.length),o.setAttribute("copilot_api.translation.has_tools",!!t.tools?.length),o.setAttribute("copilot_api.translation.has_system",!!t.system),o.setAttribute("copilot_api.translation.context_1m_beta",/context-1m/i.test(e.req.header("anthropic-beta")??""));let n=t.messages.some(e=>Array.isArray(e.content)&&e.content.some(e=>"image"===e.type)),r=t.messages.some(e=>Array.isArray(e.content)&&e.content.some(e=>"thinking"===e.type));return o.setAttribute("copilot_api.translation.has_images",n),o.setAttribute("copilot_api.translation.has_thinking",r),Er(t,X.models)}finally{o.end()}});Be.record(performance.now()-s,{direction:"anthropic_to_openai"}),l=Nn(l,X.models),o.debug("Translated OpenAI request payload:",l);let c=t.output_config?.effort;e.set("requestData",{model:l.model,reasoningEffort:c,effortClamped:_a(r,c),streaming:!!l.stream});let u=performance.now();X.manualApprove&&await fn();let p=await er(l),d=performance.now()-u;if(je.record(d,{model:l.model,target:"chat_completions",streaming:String(!!l.stream)}),ba(p)){let t=e.get("requestData")||{};p.usage&&(t.tokenUsage=hn(p.usage)),t._d1=d,t.upstreamTtfbMs=d,t.upstreamTotalMs=d,e.set("requestData",t),o.level>=n.debug&&o.debug("Non-streaming response:",JSON.stringify(p).slice(-400));let r=performance.now(),a=he.startActiveSpan("copilot_api.translate.openai_to_anthropic",e=>{try{e.setAttribute("copilot_api.translation.direction","openai_to_anthropic");let t=function(e){let t=[],o=[],n=[],r=null;r=e.choices[0]?.finish_reason??r;for(let a of e.choices){let e=jr(a.message),i=Dr(a.message.content),s=Mr(a.message.tool_calls);t.push(...e),o.push(...i),n.push(...s),("tool_calls"===a.finish_reason||"stop"===r)&&(r=a.finish_reason)}return{id:e.id,type:"message",role:"assistant",model:e.model,content:[...t,...o,...n],stop_reason:Sr(r),stop_sequence:null,usage:{input_tokens:e.usage?.prompt_tokens??0,output_tokens:e.usage?.completion_tokens??0}}}(p);return e.setAttribute("copilot_api.translation.content_blocks",t.content.length),e.setAttribute("copilot_api.translation.stop_reason",t.stop_reason??"null"),e.setAttribute("copilot_api.translation.has_tool_use",t.content.some(e=>"tool_use"===e.type)),t}finally{e.end()}});return Be.record(performance.now()-r,{direction:"openai_to_anthropic"}),o.debug("Translated Anthropic response:",a),e.json(a)}o.debug("Streaming response from service");let{events:m,span:f,release:h}=p;return j(e,async t=>{let n=null,r=0,a=performance.now(),i=jn(e,u),s={messageStartSent:!1,contentBlockIndex:0,contentBlockOpen:!1,thinkingBlockOpen:!1,toolCalls:{}};try{try{for await(let a of m){if(i(),o.debug("Raw stream event:",a),"[DONE]"===a.data)break;if(!a.data)continue;let c;try{c=JSON.parse(a.data)}catch(e){o.warn("Failed to parse streaming chunk:",a.data.slice(0,200),e);continue}if(r++,Ie.add(1,{model:l.model,endpoint_type:"anthropic"}),c.usage){n=c.usage;let t=e.get("requestData")||{};t.tokenUsage=hn(n),t._d1=d,e.set("requestData",t)}let u=ra(c,s);for(let e of u)o.debug("Translated Anthropic event:",e),await t.writeSSE({event:e.type,data:JSON.stringify(e)})}let c=performance.now()-a,p={model:l.model,endpoint_type:"anthropic"};if(Me.record(c,p),ze.record(r,p),Mn(e,u),n){let t=e.get("requestData")||{};t.tokenUsage||(t.tokenUsage=hn(n),t._d1=d,e.set("requestData",t))}}catch(o){throw Ve(f,e.get("requestSpan"),o),await Sn(t,o),o}finally{n&&gn(f,n),f.end(),h()}let c=e.get("requestId");c&&ce.executeCompletion(c)}finally{e.get("resolveStreamComplete")?.()}})}function ka(e){if("response.completed"!==e.type&&"response.incomplete"!==e.type)return null;let t=e.response.usage;return t?{prompt_tokens:t.input_tokens,completion_tokens:t.output_tokens,total_tokens:t.total_tokens}:null}const ba=e=>Object.hasOwn(e,"choices"),va=e=>Object.hasOwn(e,"output");function $a(e){let t=e.input_tokens+e.cache_read_input_tokens+e.cache_creation_input_tokens;return{prompt_tokens:t,completion_tokens:e.output_tokens,total_tokens:t+e.output_tokens,prompt_tokens_details:{cached_tokens:e.cache_read_input_tokens}}}function Ta(e,t){try{let o=JSON.parse(e);if("message_start"===o.type){let e=o.message?.usage;if(e)return t.input_tokens=e.input_tokens||0,t.cache_read_input_tokens=e.cache_read_input_tokens||0,t.cache_creation_input_tokens=e.cache_creation_input_tokens||0,!0}if("message_delta"===o.type){let e=o.usage;if(e)return t.output_tokens=e.output_tokens||0,!0}}catch{}return!1}async function xa(e,t){let r=performance.now(),a=he.startActiveSpan("copilot_api.translate.anthropic_to_responses",e=>{try{return e.setAttribute("copilot_api.translation.direction","anthropic_to_responses"),e.setAttribute("copilot_api.translation.message_count",t.messages.length),Kr(t)}finally{e.end()}});Be.record(performance.now()-r,{direction:"anthropic_to_responses"}),o.debug("Translated Responses API payload:",a),e.set("requestData",{model:a.model,streaming:!!a.stream}),X.manualApprove&&await fn();let i=performance.now(),s=await $r(a),l=performance.now()-i;if(je.record(l,{model:a.model,target:"responses",streaming:String(!!a.stream)}),va(s)){let t=e.get("requestData")||{};if(s.usage&&(t.tokenUsage=hn({prompt_tokens:s.usage.input_tokens,completion_tokens:s.usage.output_tokens,total_tokens:s.usage.total_tokens})),t._d1=l,t.upstreamTtfbMs=l,t.upstreamTotalMs=l,e.set("requestData",t),o.level>=n.debug&&o.debug("Non-streaming Responses API response:",JSON.stringify(s).slice(-400)),"failed"===s.status)return d.getActiveSpan()?.setAttribute("copilot_api.error_type","upstream_failure"),e.json({type:"error",error:{type:s.error?.code??"api_error",message:s.error?.message??"Response generation failed"}},500);let r=performance.now(),a=he.startActiveSpan("copilot_api.translate.responses_to_anthropic",e=>{try{return e.setAttribute("copilot_api.translation.direction","responses_to_anthropic"),function(e){let t=[],o=!1;for(let n of e.output)if("message"===n.type)for(let e of n.content)e.text&&t.push({type:"text",text:e.text});else if("function_call"===n.type){o=!0;let e={};try{e=JSON.parse(n.arguments)}catch{}t.push({type:"tool_use",id:n.call_id,name:n.name,input:e})}return{id:e.id,type:"message",role:"assistant",model:e.model,content:t,stop_reason:Zr(e.status,o),stop_sequence:null,usage:{input_tokens:e.usage?.input_tokens??0,output_tokens:e.usage?.output_tokens??0}}}(s)}finally{e.end()}});return Be.record(performance.now()-r,{direction:"responses_to_anthropic"}),e.json(a)}o.debug("Streaming Responses API response");let{events:c,span:u,release:p}=s;return j(e,async t=>{let n=null,r=0,s=performance.now(),d=jn(e,i),m={messageStartSent:!1,contentBlockIndex:0,contentBlockOpen:!1,responseId:"",model:"",toolCalls:{}};try{try{for await(let i of c){if(d(),o.debug("Responses API raw stream event:",i),!i.data)continue;let s;try{s=JSON.parse(i.data)}catch(e){o.warn("Failed to parse streaming chunk:",i.data.slice(0,200),e);continue}r++,Ie.add(1,{model:a.model,endpoint_type:"responses"});let c=ka(s);if(c){n=c;let t=e.get("requestData")||{};t.tokenUsage=hn(n),t._d1=l,e.set("requestData",t)}let u=ta(s,m);for(let e of u)o.debug("Translated Anthropic event:",e),await t.writeSSE({event:e.type,data:JSON.stringify(e)})}let u=performance.now()-s,p={model:a.model,endpoint_type:"responses"};Me.record(u,p),ze.record(r,p),Mn(e,i)}catch(o){throw Ve(u,e.get("requestSpan"),o),await Sn(t,o),o}finally{n&&gn(u,n),u.end(),p()}let f=e.get("requestId");f&&ce.executeCompletion(f)}finally{e.get("resolveStreamComplete")?.()}})}const Aa=new q;Aa.post("/",async e=>{try{return await wa(e)}catch(t){return await Yt(e,t)}});const Sa=new q;function Ea(e){return he.startActiveSpan("copilot_api.model.validate",t=>{try{t.setAttribute("copilot_api.model.requested",e.model);let n=Tn(e.model);return t.setAttribute("copilot_api.model.normalized",n),n===e.model?(t.setAttribute("copilot_api.model.was_mapped",!1),e):(t.setAttribute("copilot_api.model.was_mapped",!0),xe.add(1,{from_model:e.model,to_model:n}),o.debug(`Normalized model from '${e.model}' to '${n}'`),{...e,model:n})}finally{t.end()}})}function Ca(e,t){let o=function(e){try{let t=JSON.parse(e);if(("response.completed"===t.type||"response.incomplete"===t.type)&&t.response?.usage){let e=t.response.usage;return{prompt_tokens:e.input_tokens,completion_tokens:e.output_tokens,total_tokens:e.total_tokens}}}catch{}return null}(e);if(!o)return;t.usageRef.value=o;let n=t.c.get("requestData")||{};n.tokenUsage=hn(o),n._d1=t._d1,t.c.set("requestData",n)}Sa.get("/",async e=>{try{X.models||await ro();let t=X.models?.data.map(e=>({id:e.id,object:"model",type:"model",created:0,created_at:new Date(0).toISOString(),owned_by:e.vendor,display_name:e.name,context_length:e.capabilities.limits?.max_context_window_tokens}));return e.json({object:"list",data:t,has_more:!1})}catch(t){return await Yt(e,t)}});const Oa=new Set(["message","function_call","function_call_output"]),Ia=new Set(["type","name","description","parameters"]);async function Pa(e){if(!e)return!1;let t=e.sources;if(t&&t.length>0)return!1;let n=e.query??e.queries?.[0];return!(!n||!da())&&(o.info(`Enriching web search: "${n}"`),e.sources=(await ma(n,{maxResults:5})).map(e=>({type:"url",url:e.url,title:e.title,content:e.content})),!0)}async function Ra(e){if(da())try{for(let t of e.output){let e=t;"web_search_call"===e.type&&await Pa(e.action)}}catch(e){o.error("Failed to enrich non-streaming web search:",e)}}async function Na(e){if(!da())return e;try{let t=JSON.parse(e);if("response.output_item.done"===t.type){let e=t.item;if("web_search_call"===e?.type&&await Pa(e.action))return JSON.stringify(t)}}catch(e){o.error("Failed to enrich web search:",e)}return e}function qa(e,t){if("function_call"!==e.type||!t.has(e.name))return!1;if(e.type="custom_tool_call","string"==typeof e.arguments){try{e.input=JSON.parse(e.arguments).input??e.arguments}catch{e.input=e.arguments}delete e.arguments}return!0}function Da(e,t){if(0===t.size)return e;try{let o=JSON.parse(e),n=o.type;if("response.output_item.added"===n||"response.output_item.done"===n){let e=o.item;if(e&&qa(e,t))return JSON.stringify(o)}if("response.completed"===n){let n=o.response?.output;if(!n)return e;let r=!1;for(let e of n)qa(e,t)&&(r=!0);if(r)return JSON.stringify(o)}}catch{}return e}function ja(e){return null!=e}function Ma(e){let t=e.input,o="string"==typeof t?t:t.map(e=>function(e){switch(e.type){case"custom_tool_call":{let t=e.input;return{type:"function_call",call_id:e.call_id,name:e.name,arguments:JSON.stringify("string"==typeof t?{input:t}:t)}}case"custom_tool_call_output":return{type:"function_call_output",call_id:e.call_id,output:e.output};default:return Oa.has(e.type)||"web_search_call"===e.type?e:null}}(e)).filter(e=>null!==e),n={model:e.model,input:o};for(let t of["instructions","max_output_tokens","temperature","top_p","stream","tool_choice","parallel_tool_calls","user"])ja(e[t])&&(n[t]=e[t]);let r=new Set;if(ja(e.tools)){let t=function(e){let t=new Set;return{tools:e.filter(e=>{let t=e.type;return"function"===t||"custom"===t||"web_search"===t||t.startsWith("web_search_")}).map(e=>{let o=e.type;if("web_search"===o||o.startsWith("web_search_"))return{type:e.type};let n={};for(let t of Object.keys(e))Ia.has(t)&&(n[t]=e[t]);return"custom"===n.type&&(n.type="function",t.add(n.name),n.parameters||={type:"object",properties:{input:{type:"string",description:"The freeform tool input content"}},required:["input"],additionalProperties:!1}),n}),customToolNames:t}}(e.tools);n.tools=t.tools,r=t.customToolNames}if(ja(e.reasoning)&&"object"==typeof e.reasoning){let t=e.reasoning;n.reasoning={},ja(t.effort)&&(n.reasoning.effort=t.effort),ja(t.summary)&&(n.reasoning.summary=t.summary)}if(ja(e.text)&&"object"==typeof e.text){let t=e.text;ja(t.format)&&(n.text={format:t.format})}return{payload:n,customToolNames:r}}async function Ha(e){if(X._t1)return null;if(!await wo()){let t=fo();return t?(d.getActiveSpan()?.setAttribute("copilot_api.error_type","authentication_error"),e.json({error:{message:`${t.message}; re-authenticate with \`copilot-api auth\`, then restart the proxy`,type:"authentication_error"}},401)):(d.getActiveSpan()?.setAttribute("copilot_api.error_type","service_unavailable"),e.header("Retry-After","1"),e.json({error:{message:"Service token not yet available; retry shortly",type:"service_unavailable"}},503))}return null}async function Ba(e){await xn(X);let{payload:t,customToolNames:n}=Ma(await e.req.json()),r=t;o.debug(`Responses API [${Array.isArray(r.input)?r.input.length:1} items]`),n.size>0&&o.debug(`Custom tools detected: ${[...n].join(", ")}`);let a=function(e,t){try{return{ok:!0,payload:Ea(t)}}catch(t){if(t instanceof $n)return{ok:!1,response:e.json({error:{message:t.message,type:"invalid_request_error",code:"invalid_model"}},t.statusCode)};throw t}}(e,r);if(!a.ok)return a.response;r=a.payload;let i=await Ha(e);if(i)return i;e.set("requestData",{model:r.model,reasoningEffort:r.reasoning?.effort,streaming:!!r.stream}),X.manualApprove&&await fn();let s=performance.now(),l=await $r(r),c=performance.now()-s;if(je.record(c,{model:r.model,target:"responses",streaming:String(!!r.stream)}),Fa(l))return async function(e,t,o){await Ra(t);let n=e.get("requestData")||{};return t.usage&&(n.tokenUsage=hn({prompt_tokens:t.usage.input_tokens,completion_tokens:t.usage.output_tokens,total_tokens:t.usage.total_tokens})),n._d1=o,n.upstreamTtfbMs=o,n.upstreamTotalMs=o,e.set("requestData",n),e.json(t)}(e,l,c);let{events:u,span:p,release:d}=l;return j(e,async t=>{let o={value:null},a=0,i=performance.now(),l=jn(e,s);try{try{for await(let i of u)if(l(),i.data&&"[DONE]"!==i.data){a++;let s=Da(i.data,n);s=await Na(s);let l=s===i.data?i:{...i,data:s};Ie.add(1,{model:r.model,endpoint_type:"responses"}),Ca(s,{usageRef:o,c:e,_d1:c}),await t.writeSSE(l)}else await t.writeSSE(i);let p=performance.now()-i,d={model:r.model,endpoint_type:"responses"};Me.record(p,d),ze.record(a,d),Mn(e,s)}catch(o){throw Ve(p,e.get("requestSpan"),o),await En(t,o),o}finally{o.value&&gn(p,o.value),p.end(),d()}let m=e.get("requestId");m&&ce.executeCompletion(m)}finally{e.get("resolveStreamComplete")?.()}})}const Fa=e=>Object.hasOwn(e,"output"),Ua=new q;Ua.post("/",async e=>{try{return await Ba(e)}catch(t){return await Yt(e,t)}});const La=new q;La.get("/",e=>{try{return X.showToken?e.json({token:X._t1}):e.json({error:"Token endpoint disabled. Restart with --show-token to enable it.",token:null},403)}catch(t){return o.error("Error fetching token:",t),e.json({error:"Failed to fetch token",token:null},500)}});const Ga=new q;Ga.get("/",async e=>{try{let t=await No();return e.json(t)}catch(t){return o.error("Error fetching usage:",t),e.json({error:"Failed to fetch usage"},500)}});const za=new q;function Ja(){return function(e){let t=e.filter(e=>pn(e));if(0===t.length)return;let o=t.find(e=>un.test(e.id));return o?o.id:(t.find(e=>"Anthropic"===e.vendor)??t[0]).id}(X.models?.data??[])}function Ka(e,t,o){let n=function(e){if(!e)return;try{let t=JSON.parse(e),o=t.error?.message??t.message;if("string"==typeof o&&o.length>0)return an(o).slice(0,200)}catch{}let t=an(e).trim();return t.length>0?t.slice(0,200):void 0}(t),r=n?` (upstream: ${n})`:"";switch(!0){case 401===e:case 403===e:return`Authentication/entitlement failed (HTTP ${e}). Your GitHub Copilot subscription may be inactive, or the Auth token is invalid. Run \`copilot-api auth\` to re-authenticate; if it persists, this account has no active Copilot access${r}.`;case 402===e:return`Premium monthly quota exhausted (HTTP 402). Switch to a non-premium model (e.g. claude-haiku-4.5) or wait for the monthly quota reset${r}.`;case 400===e:return`Model '${o}' was rejected (HTTP 400). On individual plans only some models are entitled — try claude-haiku-4.5, or run \`copilot-api doctor\` to see what works${r}.`;case 413===e:return`Request too large (HTTP 413)${r}.`;case 429===e:return`Rate limited upstream (HTTP 429) — wait and retry${r}.`;case 503===e:return`Service not ready (HTTP 503) — the model catalog or Service token is still warming up. Retry in a few seconds${r}.`;case e>=500:return`Upstream error (HTTP ${e})${r}.`;default:return`Unexpected response (HTTP ${e})${r}.`}}async function Wa(e={}){let t=performance.now(),o=e.model&&function(e){let t=X.models?.data.find(t=>t.id===e);return void 0!==t&&pn(t)}(e.model)?e.model:Ja();if(!o)return{ok:!1,durationMs:0,reason:"No models available — the catalog is empty (upstream /models failed at startup). Check connectivity and authentication."};let n,r=e.timeoutMs??3e4,a=()=>Math.round(performance.now()-t),i=(async()=>{try{let e=await za.request("/chat/completions",{method:"POST",headers:{"content-type":"application/json",[ln]:cn},body:JSON.stringify({model:o,messages:[{role:"user",content:"ping"}],max_tokens:1,stream:!1})});if(e.ok)return{ok:!0,model:o,status:e.status,durationMs:a()};let t=await e.text().catch(()=>"");return{ok:!1,model:o,status:e.status,durationMs:a(),reason:Ka(e.status,t,o),detail:t.slice(0,400)||void 0}}catch(e){let t=e instanceof Error?e.message:String(e);return{ok:!1,model:o,durationMs:a(),reason:`Request failed before a usable response: ${t}`,detail:t}}})(),s=new Promise(e=>{n=setTimeout(()=>{e({ok:!1,model:o,durationMs:a(),reason:`Did not complete within ${r}ms. If you started with --manual, approve the request or use --no-smoke-test; otherwise the upstream may be slow or unreachable.`})},r)});try{return await Promise.race([i,s])}finally{n&&clearTimeout(n)}}za.use(async(e,t)=>{let n=performance.now(),r=`req_${Date.now()}_${Math.random().toString(36).slice(2,11)}`,a=e.req.method,i=e.req.path,s=_t(i),p=function(e){return e===cn}(e.req.header(ln));e.set("requestId",r),e.set("isSelfTest",p),e.header("x-request-id",r);let m=he.startSpan("copilot_api.handle_request",{kind:l.SERVER,attributes:{"http.method":a,"http.url":e.req.url,"http.route":i,"copilot_api.request_id":r,"copilot_api.endpoint_type":s}});e.set("requestSpan",m),e.set("requestTraceContext",m.spanContext()),p&&m.setAttribute("copilot_api.self_test",!0);for(let[t,o]of Object.entries(e.req.header())){let e=t.toLowerCase();Xe.has(e)||"x-copilot-api-self-test"!==e&&m.setAttribute(`http.request.header.${e}`,o)}await async function(e,t){let{method:n,path:r,endpointType:a}=t;if("POST"===n&&("anthropic"===a||"openai"===a||"embeddings"===a||r.includes("/responses")))try{let t=await e.req.raw.clone().text();e.set("rawBody",t.length>mn?t.slice(0,mn):t)}catch(e){o.warn("Failed to cache incoming request body for error capture:",e)}}(e,{method:a,path:i,endpointType:s});let f,h=new Promise(e=>{f=e});e.set("streamComplete",h),e.set("resolveStreamComplete",f);let g=d.setSpan(u.active(),m);await u.with(g,async()=>{p||ce.registerCompletion(r,e,n);try{await t()}catch(e){let t=e instanceof Error?e:Error(String(e));throw m.setStatus({code:c.ERROR,message:t.message}),m.recordException(t),e}});let _=e.get("requestData"),y={c:e,start:n,method:a,path:i,endpointType:s,requestId:r,span:m};_?.streaming&&e.res.status<400?h.then(()=>dn(y)).catch(e=>{o.warn("Error finalizing streaming request:",e);let t=e instanceof Error?e:Error(String(e));try{m.recordException(t),m.setStatus({code:c.ERROR,message:`Stream finalization failed: ${t.message}`})}catch{}try{m.end()}catch{}}):dn(y)}),za.use(D()),za.use(async(e,t)=>{let o=e.req.header("content-length");if(o){let t=Number(o);if(Number.isFinite(t)&&t>33554432)return r.warn(`Rejected oversized request: ${t} bytes on ${e.req.path} (UA: ${e.req.header("user-agent")??"unknown"})`),e.json({type:"error",error:{type:"request_too_large",message:`Request body exceeds 32 MB limit (got ${t} bytes).`}},413)}await t()}),za.get("/",e=>e.text("Server running")),za.route("/health",sr),za.route("/chat/completions",ar),za.route("/models",Sa),za.route("/embeddings",ir),za.route("/usage",Ga),za.route("/token",La),za.route("/v1/chat/completions",ar),za.route("/v1/models",Sa),za.route("/v1/embeddings",ir),za.route("/v1/messages",Aa),za.post("/v1/messages/count_tokens",async function(e){let t;try{t=await e.req.json()}catch{return e.json({error:{type:"invalid_request_error",message:"Invalid JSON"}},400)}if(!Array.isArray(t.messages))return e.json({error:{type:"invalid_request_error",message:"messages is required"}},400);let o=mr.baseOverhead;if(t.system){let e="string"==typeof t.system?t.system:t.system.map(e=>e.text).join("\n\n");o+=mr.perMessage+fr(e)*mr.contentMultiplier}for(let e of t.messages)o+=mr.perMessage,o+=fr(e.role),"string"==typeof e.content?o+=fr(e.content)*mr.contentMultiplier:Array.isArray(e.content)&&(o+=hr(e.content));let n=t.tools?.filter(pr);return n&&n.length>0&&(o+=function(e){let t=mr.toolsExist;for(let[o,n]of e.entries())o>0&&(t+=mr.perTool),t+=fr(n.name),n.description&&(t+=mr.perDesc+fr(n.description)),t+=gr(n.input_schema);return t}(n)),e.json({input_tokens:Math.round(o)})}),za.route("/v1/responses",Ua),za.route("/responses",Ua),za.onError((e,t)=>Yt(t,e));const Va=e=>`[1m${e}[0m`,Ya=e=>`[2m${e}[0m`,Xa=e=>`[32m${e}[0m`,Za=e=>`[31m${e}[0m`,Qa=e=>`[33m${e}[0m`,ei=Ya(" ─────────────────────────────────────────────────────────────");function ti(e,t,o){console.log(` ${function(e){return"ok"===e?Xa("✓"):"warn"===e?Qa("⚠"):Za("✗")}(e)} ${Va(t.padEnd(14))} ${o}`)}function oi(e){console.log(` ${Ya("↳")} ${Ya(e)}`)}function ni(e){return e instanceof jt?`HTTP ${e.response.status} ${e.message}`:e instanceof Error?e.message:String(e)}async function ri(){let e=g.env.GH_TOKEN;if(e&&e.trim().length>0)return{token:e.trim(),source:"GH_TOKEN env"};let t=await async function(){try{let e=(await a.readFile(K.GITHUB_TOKEN_PATH,"utf8")).trim();return e.length>0?e:void 0}catch{return}}();return t?{token:t,source:"stored file"}:void 0}async function ai(){try{await ro();let e=(X.models?.data.length??0)>0;return ti(e?"ok":"warn","Model catalog",e?function(){let e=X.models?.data??[],t={Claude:0,OpenAI:0,Gemini:0,Embedding:0};for(let o of e)o.id.startsWith("text-embedding")?t.Embedding++:"Anthropic"===o.vendor?t.Claude++:"Google"===o.vendor?t.Gemini++:t.OpenAI++;let o=Object.entries(t).filter(([,e])=>e>0).map(([e,t])=>`${e}: ${t}`);return`${e.length} models (${o.join(", ")})`}():"empty"),e}catch(e){return ti("fail","Model catalog",ni(e)),oi("Could not fetch /models — check connectivity/auth."),!1}}async function ii(e){X.accountType=e.accountType;let t=await St(),o=Et();if(console.log(""),console.log(` ${Va("COPILOT-API DOCTOR")} ${Ya(`v${t}`)}`),console.log(ei),ti("ok","Runtime",`${o.name} ${o.version} (${o.platform}-${o.arch})`),await W(),ao(),!await async function(){let e=await ri();if(!e)return ti("fail","Auth token","not found"),void oi("Run `copilot-api auth` (or `copilot-api start`) to authenticate.");X._t2=e.token,ti("ok","Auth token",`found (${e.source})`);try{let e=await Zt();return await st(X,e.login),ti("ok","GitHub auth",`logged in as ${e.login}`),e.login}catch(e){return ti("fail","GitHub auth",ni(e)),void oi("Token looks invalid/expired. Re-run `copilot-api auth`.")}}())return console.log(ei),console.log(` ${Za("✗")} ${Va("Authentication failed")} — cannot continue.`),console.log(""),1;let n=await async function(){try{let{token:e}=await Xt();return X._t1=e,ti("ok","Service token","acquired"),!0}catch(e){let t=e instanceof jt?e.response.status:0;return ti("fail","Service token",ni(e)),oi(401===t?"Auth token is invalid/expired — run `copilot-api auth`.":403===t?"No active GitHub Copilot subscription on this account. Re-auth won't help.":"Transient/network issue — check connectivity and retry."),!1}}(),r=!!n&&await ai();await async function(){try{let e=await No(),t=e.quota_snapshots.premium_interactions,o=t.unlimited?"credits unlimited":`credits ${Eo(Co(t))} of ${Eo(t.entitlement)} · ${t.percent_remaining.toFixed(0)}% left`;ti("ok","Copilot plan",`${e.copilot_plan} · ${o} `+Ya(`(resets ${e.quota_reset_date})`))}catch(e){ti("warn","Copilot plan",`unavailable (${ni(e)})`)}}();let a=!1;return n&&r?a=await async function(){let e=await Wa();return e.ok?(ti("ok","Generation",`works via ${e.model} ${Ya(`(${e.durationMs}ms)`)}`),!0):(ti("fail","Generation",`${e.reason}${e.status?Ya(` [HTTP ${e.status}]`):""}`),!1)}():ti("warn","Generation","skipped (no token or empty catalog)"),function(){let e=[],t="ok";for(let o of["ANTHROPIC_BASE_URL","OPENAI_BASE_URL"]){let n=g.env[o];n&&("ANTHROPIC_BASE_URL"===o&&/\/v1\/*$/.test(n)&&(t="warn",e.push(`${o}=${n} ends in /v1 — Claude Code appends /v1/messages, producing a doubled /v1/v1/... path (404). Drop the trailing /v1.`)),/\/v1\/v1(?:\/|$)/.test(n)&&(t="warn",e.push(`${o}=${n} contains a doubled /v1/v1 path (404).`)))}if(e.length>0){ti(t,"Client config","potential base-URL issue");for(let t of e)oi(t)}else ti("ok","Client config","no base-URL issues detected");oi("Point clients at http://127.0.0.1:4141. For Docker/LAN, start with --hostname 0.0.0.0.")}(),console.log(ei),a?(console.log(` ${Xa("✓")} ${Va("All systems go")} — your proxy can generate. Point your client at it and go.`),console.log(""),0):(console.log(` ${Qa("⚠")} ${Va("Some checks need attention")} — see the ${Za("✗")}/${Qa("⚠")} lines above.`),console.log(""),2)}const si=e({meta:{name:"doctor",description:"Diagnose your setup end-to-end: token, auth, entitlement, model catalog, and one real generation. Tells you exactly what's wrong and how to fix it."},args:{"account-type":{alias:"a",type:"string",default:"individual",description:"Account type to check against (individual, business, enterprise)"}},async run({args:e}){let t=await ii({accountType:e["account-type"]});g.exit(t)}});function li(e){return{log(t,r){let a=o.level>=n.debug;if(t.level!==n.warn||a)for(let o of e)o.log(t,r)}}}let ci=!1;const ui="copilot-api-node20",pi=`https://registry.npmjs.org/${ui}/latest`,di=e=>`[1m${e}[0m`,mi=e=>`[33m${e}[0m`;async function fi(){let e=new AbortController,t=setTimeout(()=>e.abort(),5e3);"object"==typeof t&&"unref"in t&&t.unref();try{let t=await fetch(pi,{signal:e.signal});return t.ok?(await t.json()).version??null:null}catch{return null}finally{clearTimeout(t)}}function hi(e,t){let o=Math.max(0,t-function(e){return e.replaceAll(/\x1b\[[0-9;]*m/g,"").length}(e));return e+" ".repeat(o)}function gi(e,t=""){let o,n=function(){let{platform:e,ppid:t,env:o}=g;if("win32"===e){try{if(h(`wmic process get ParentProcessId,Name | findstr "${t}"`,{stdio:"pipe"}).toString().toLowerCase().includes("powershell.exe"))return"powershell"}catch{return"cmd"}return"cmd"}{let e=o.SHELL;if(e){if(e.endsWith("zsh"))return"zsh";if(e.endsWith("fish"))return"fish";if(e.endsWith("bash"))return"bash"}return"sh"}}(),r=Object.entries(e).filter(([,e])=>void 0!==e);switch(n){case"powershell":o=r.map(([e,t])=>`$env:${e} = ${t}`).join("; ");break;case"cmd":o=r.map(([e,t])=>`set ${e}=${t}`).join(" & ");break;case"fish":o=r.map(([e,t])=>`set -gx ${e} ${t}`).join("; ");break;default:{let e=r.map(([e,t])=>`${e}=${t}`).join(" ");o=r.length>0?`export ${e}`:"";break}}return o&&t?`${o}${"cmd"===n?" & ":" && "}${t}`:o||t}const _i=e=>`[1m${e}[0m`,yi=e=>`[2m${e}[0m`,wi=e=>`[36m${e}[0m`,ki=e=>`[32m${e}[0m`,bi=e=>`[33m${e}[0m`,vi=e=>`[4m${e}[0m`,$i=(e,t)=>`]8;;${e}\\${t}]8;;\\`,Ti="?utm_source=copilot-cli&utm_medium=terminal&utm_campaign=startup_banner",xi="https://github.com/johnib/copilot-api-issues/issues",Ai=yi(" ─────────────────────────────────────────────────────────────");function Si(e){return void 0===e?"":e>=1e6?`${(e/1e6).toFixed(0)}M`:`${(e/1e3).toFixed(0)}K`}function Ei(e){return e&&0!==e.length?e.join("·"):"—"}const Ci=[{title:"I Had Claude Mine 30 Days of My Own Messages. What It Found Was Uncomfortably Accurate.",teaser:"I had Claude read a month of my messages. It nailed me.",url:"https://barazany.dev/blog/mining-claude-history-ultracode"},{title:"The 5-Hour Quota, Boris's Tweet, and What the Source Code Actually Reveals",teaser:"Claude Code's caching story — decoded from the source.",url:"https://barazany.dev/blog/claude-code-token-caching"},{title:"Claude Code's Compaction Engine: What the Source Code Actually Reveals",teaser:"What's actually running beneath every long session.",url:"https://barazany.dev/blog/claude-codes-compaction-engine"}];function Oi(e){if(0===e.length)return[];let t=["",Ai,` ${_i("BARAZANY.DEV")} ${yi("— Recent Posts")}`,Ai,""];for(let[o,n]of e.entries()){let e=$i(`${n.url}${Ti}`,_i(vi(`[${o+1}]`)));t.push(` ${e} ${wi(n.title)}`,` ${yi("→")} ${yi(n.teaser)}`,"")}return t.push(Ai,` ${$i(`https://barazany.dev/blog${Ti}`,"barazany.dev/blog")}`,Ai),t}function Ii(e){let t=[];X.connectivity.h2Keepalive?t.push("HTTP/2 keepalive"):X.connectivity.h2&&t.push("HTTP/2"),t.push(`timeout ${e.timeout/1e3}s`);let o=e.webSearchProviders.length>0?`${e.webSearchProviders.map(e=>(e=>e&&e[0].toUpperCase()+e.slice(1))(e)).join(yi(" → "))} ${ki("✓")}`:yi("off"),n=["",` ${_i("COPILOT-API")} ${yi(`v${e.version}`)}`,Ai,` ${yi("Runtime")} ${e.runtime.name} ${e.runtime.version} (${e.runtime.platform}-${e.runtime.arch})`,` ${yi("User")} ${e.user} ${yi("·")} ${e.accountType}`];return X._v1&&n.push(` ${yi("Client")} VSCode ${X._v1}`),n.push(` ${yi("Network")} ${t.join(yi(" · "))}`,` ${yi("Search")} ${o}`),e.clipboardCopied&&n.push(` ${yi("Clipboard")} Claude Code command ${ki("✓")}`),n.push(Ai),n}function Pi(e){if(!e.model&&!e.smallModel)return[];let t=["",` ${_i("Active")}`];if(e.model){let o=X.models?.data.find(t=>t.id===e.model),n=Si(o?.capabilities.limits?.max_context_window_tokens),r=Ei(o?.capabilities.supports.reasoning_effort);t.push(` ${wi(e.model.padEnd(32))} ${yi("ctx")} ${_i(n.padStart(5))} ${yi("effort")} ${yi(r)} ${bi("← main")}`)}if(e.smallModel){let o=X.models?.data.find(t=>t.id===e.smallModel),n=Si(o?.capabilities.limits?.max_context_window_tokens),r=Ei(o?.capabilities.supports.reasoning_effort);t.push(` ${e.smallModel.padEnd(32)} ${yi("ctx")} ${n.padStart(5)} ${yi("effort")} ${yi(r)} ${bi("← small")}`)}return t}function Ri(e){let t=[];for(let[o,n]of function(){let e=[],t=[],o=[],n=[];for(let r of X.models?.data??[]){let a=r.capabilities.limits?.max_context_window_tokens,i={id:r.id,ctx:a,effort:r.capabilities.supports.reasoning_effort};r.id.startsWith("text-embedding")?n.push(i):"Anthropic"===r.vendor?e.push(i):"Google"===r.vendor?o.push(i):t.push(i)}return[["Claude",e],["OpenAI",t],["Gemini",o],["Embedding",n]]}())if(0!==n.length){t.push("",` ${_i(o)}`);for(let r of n){let n=r.id===e.model||r.id===e.smallModel,a=n?wi("●"):yi("·"),i=n?wi(r.id.padEnd(34)):r.id.padEnd(34),s=r.ctx?Si(r.ctx).padStart(5):"".padStart(5),l="Embedding"===o?"":` ${Ei(r.effort)}`;t.push(` ${a} ${i} ${yi(s)}${yi(l)}`)}}return t}function Ni(){let e=xi.replace(/^https:\/\//,""),t=$i(`${xi}?utm_source=copilot-cli&utm_medium=terminal&utm_campaign=issues_banner`,e);return["",Ai,` ${_i("FOUND A BUG?")} ${yi("— Report it on GitHub")}`,Ai,"",` ${wi("→")} ${wi(t)}`,` ${yi("Bug reports, feature requests, and questions welcome.")}`,"",Ai]}function qi(e){if(!e.endpoints)return[];let{scheme:t,port:o,hostname:n}=e.endpoints,r=n?`${t}://${n}:${o}`:`${t}://<your-tailscale-hostname>:${o}`,a=["",Ai,` ${_i("Claude Cowork")} ${yi("— Settings → Inference Provider")}`,Ai,"",` ${yi("Paste into")} ${_i("inferenceGatewayBaseUrl")}${yi(":")}`,` ${_i(wi(r))}`];return n||a.push("",` ${yi("Your Tailscale hostname is shown by:")} ${wi("tailscale status --self")}`),a.push("",` ${yi("Docs:")} ${wi("https://claude.com/docs/cowork/3p/installation")}`),a}function Di(e){if(!e.https||!e.https.selfSigned)return[];let{certPath:t}=e.https,o=["",Ai,` ${_i("HTTPS")} ${yi("— self-signed cert")}`,Ai,"",` ${yi("Cert")} ${t}`];switch(o.push("",` ${_i("Trust this cert")} ${yi("(one-time setup)")}`),g.platform){case"darwin":o.push(` ${yi("macOS:")}`,` ${wi("sudo security add-trusted-cert -d -r trustRoot \\")}`,` ${wi(`-k /Library/Keychains/System.keychain "${t}"`)}`);break;case"win32":o.push(` ${yi("Windows (PowerShell as Administrator):")}`,` ${wi(`Import-Certificate -FilePath "${t}" \``)}`,` ${wi("-CertStoreLocation Cert:\\LocalMachine\\Root")}`);break;case"linux":o.push(` ${yi("Linux (Debian/Ubuntu):")}`,` ${wi(`sudo cp "${t}" /usr/local/share/ca-certificates/copilot-api.crt`)}`,` ${wi("sudo update-ca-certificates")}`,` ${yi("Linux (Fedora/RHEL/Arch):")}`,` ${wi(`sudo cp "${t}" /etc/pki/ca-trust/source/anchors/copilot-api.crt`)}`,` ${wi("sudo update-ca-trust")}`);break;default:o.push(` ${yi("(Unknown platform — see Node fallback below.)")}`)}return o.push("",` ${yi("Or, for Node CLIs only (no admin needed):")}`,` ${wi(`export NODE_EXTRA_CA_CERTS="${t}"`)}`,Ai),o}function ji(e){let t=Math.floor(e/1e3),o=Math.floor(t/3600),n=Math.floor(t%3600/60);return o>0?`${o}h ${n}m`:n>0?`${n}m`:`${t}s`}const Mi=s.join(K.APP_DIR,"certs"),Hi=s.join(Mi,"cert.pem"),Bi=s.join(Mi,"key.pem"),Fi=s.join(Mi,"cert.meta.json");async function Ui(e){try{return await a.readFile(e,"utf8")}catch{return}}async function Li(e){let t=await Ui(Hi),o=await Ui(Bi),n=await async function(){let e=await Ui(Fi);if(e)try{let t=JSON.parse(e);return Array.isArray(t.hosts)&&"string"==typeof t.notAfter?t:void 0}catch{return}}();if(!t||!o||!n)return!1;let r=new Set(n.hosts);for(let t of e)if(!r.has(t))return!1;let a=Date.parse(n.notAfter);return!Number.isNaN(a)&&a-Date.now()>2592e6}function Gi(e){return 0!==G(e)}async function zi(e){await a.mkdir(Mi,{recursive:!0});let t=new Date,o=new Date;o.setDate(o.getDate()+825);let n=["127.0.0.1","::1"],r=new Set(["localhost"]),i=new Set(n);for(let t of e)Gi(t)?i.add(t):r.add(t);let s=await z([{name:"commonName",value:"localhost"},{name:"organizationName",value:"copilot-api"}],{keyType:"ec",curve:"P-256",algorithm:"sha256",notBeforeDate:t,notAfterDate:o,extensions:[{name:"basicConstraints",cA:!1},{name:"keyUsage",digitalSignature:!0,keyEncipherment:!0,critical:!0},{name:"extKeyUsage",serverAuth:!0,clientAuth:!0},{name:"subjectAltName",altNames:[...[...r].map(e=>({type:2,value:e})),...[...i].map(e=>({type:7,ip:e}))]}]});return await a.writeFile(Hi,s.cert,{mode:420}),await a.writeFile(Bi,s.private,{mode:384}),await async function(e){await a.writeFile(Fi,JSON.stringify(e,null,2),{mode:420})}({hosts:[...r,...i].sort(),notAfter:o.toISOString()}),{cert:s.cert,key:s.private,certPath:Hi,keyPath:Bi,generated:!0}}const Ji=[],Ki=Date.now();let Wi="";function Vi(){let e=async(e,t=0)=>{let n=he.startSpan("copilot_api.server.shutdown",{kind:l.INTERNAL,attributes:{"copilot_api.shutdown.reason":e,"copilot_api.shutdown.exit_code":t,"copilot_api.uptime_seconds":(Date.now()-Ki)/1e3}});for(let t of Ji)try{await t()}catch(e){o.error("Error during cleanup:",e)}n.end(),function(e,t){let o=$i("https://barazany.dev?utm_source=copilot-cli&utm_medium=terminal&utm_campaign=goodbye_banner","barazany.dev"),n=["",Ai,` ${_i("COPILOT-API")} ${yi(`v${e}`)} ${yi("·")} ${ji(t)} uptime`,Ai,""," Check in from time to time on",` ${wi(o)}`,"",Ai,""];console.log(n.join("\n"))}(Wi,Date.now()-Ki),g.exit(t)};g.on("SIGINT",()=>e("SIGINT")),g.on("SIGTERM",()=>e("SIGTERM")),g.on("uncaughtException",t=>{o.error("Uncaught exception:",t),e("uncaughtException",1)}),g.on("unhandledRejection",(t,n)=>{o.error("Unhandled promise rejection at:",n,"reason:",t),e("unhandledRejection",1)})}function Yi(e){return e._t2?"cli_arg":g.env.GH_TOKEN?"env_var":"stored"}function Xi(e){let{options:t,version:o,runtime:n,_u1:r}=e,a=he.startSpan("copilot_api.server.startup",{kind:l.INTERNAL,attributes:Ye({config:{version:o,port:t.port,accountType:t.accountType,verbose:t.verbose,manualApprove:t.manual,rateLimitSeconds:t.rateLimit??0,rateLimitWait:t.rateLimitWait,timeoutMs:t.timeout,showToken:t.showToken,_cc1:t._cc1,model:t.model,smallModel:t.smallModel,_t3:Yi(t)},runtime:n,identity:{_u1:r.login,machineId:X.machineId,sessionId:X.sessionId,_v1:X._v1},connectivity:X.connectivity,modelsCount:X.models?.data.length??0,startupDurationMs:Date.now()-Ki},"copilot_api")});if(X.models?.data)for(let e of X.models.data)a.addEvent("copilot_api.model.available",Ye(e,"model"));a.end(),Ke(_.INFO,"INFO","Server started",Ye({version:o,port:t.port,accountType:t.accountType,_u1:r.login,modelsCount:X.models?.data.length??0,startupDurationMs:Date.now()-Ki},"copilot_api"))}async function Zi(e){if(e.https){if(e.httpsCert&&e.httpsKey)return async function(e,t){let[o,n]=await Promise.all([a.readFile(e,"utf8"),a.readFile(t,"utf8")]);return{cert:o,key:n,certPath:e,keyPath:t,generated:!1}}(e.httpsCert,e.httpsKey);if(e.httpsCert||e.httpsKey)throw Error("Both --https-cert and --https-key must be provided together");return async function(e=[]){if(await Li(e)){let e=await Ui(Hi),t=await Ui(Bi);if(e&&t)return{cert:e,key:t,certPath:Hi,keyPath:Bi,generated:!1}}return o.info("Generating new self-signed TLS certificate…"),zi(e)}(e.httpsHosts)}}async function Qi(e){let t=function(e){if(!e.claudeCowork)return e;if(e.httpsCert&&e.httpsKey)return{...e,https:!0};let{certPath:t,keyPath:n}=Zo;try{U(t),U(n)}catch{throw o.error("Tailscale cert not found. Run `copilot-api cowork-setup install` first."),Error("Tailscale cert not found")}return{...e,https:!0,httpsCert:t,httpsKey:n}}(e);if(Vi(),Ji.push(()=>{o.debug("Cleaning up connectivity monitor"),tt.stop()},()=>{o.debug("Cleaning up token management"),o.debug("Cleaning up token management"),so&&=void clearInterval(so),co&&=void tt.off("online",co),uo&&=void tt.off("offline",uo),lo=void 0,po=void 0},async()=>{o.debug("Cleaning up HTTP/2 client"),await async function(){o.debug("Stopping HTTP/2 pool"),Ln&&=void clearInterval(Ln),Gn&&=void clearInterval(Gn);let e=[...Bn.keys(),...Fn];Bn.clear(),Fn.clear(),Hn.clear(),Un=void 0;for(let t of e)zn(t)&&(Ne.add(1,{event:"closed"}),await t.close())}()},async()=>{o.debug("Shutting down OTel SDK"),await async function(){if(!ue)return;let e=5e3,t=new Promise(e=>{setTimeout(()=>e("timeout"),5e3).unref()});try{"timeout"===await Promise.race([ue.shutdown(),t])&&o.warn("OTel SDK shutdown timed out after 5000ms; continuing exit")}catch(e){o.warn("OTel SDK shutdown failed; continuing exit",e)}}()}),t.verbose&&(o.level=5,o.info("Verbose logging enabled")),t._cc1&&t.codex)throw Error("Cannot use --claude-code and --codex together");X.accountType=t.accountType,X.manualApprove=t.manual,X.rateLimitSeconds=t.rateLimit,X.rateLimitWait=t.rateLimitWait,X.showToken=t.showToken,X.timeoutMs=t.timeout,X.connectivity.timeoutMs=t.connectTimeout,X.webSearchProviders=t.webSearchProviders,X.errorReporting=function(e){let t=g.env.COPILOT_API_ERROR_REPORTING;return(void 0===t||!["0","false","no","off"].includes(t.trim().toLowerCase()))&&e}(t.errorReporting),function(){let e="1"===g.env.COPILOT_H2_KEEPALIVE||"true"===g.env.COPILOT_H2_KEEPALIVE,t=e||"1"===g.env.COPILOT_H2||"true"===g.env.COPILOT_H2;X.connectivity.h2=t,X.connectivity.h2Keepalive=e}(),await W(),ao();let n=await St();Wi=n;let r=Et();(function(e,t){t&&(de=t),pe=crypto.randomUUID();let o=v({[S]:"copilot-api",[E]:e,[A]:pe}),{endpoint:n,headers:r}=fe();ue=new x({resource:o,traceExporter:new b({url:`${n}/v1/traces`,headers:r}),metricReader:new T({exporter:new k({url:`${n}/v1/metrics`,headers:r}),exportIntervalMillis:15e3}),logRecordProcessors:[new $({exporter:new w({url:`${n}/v1/logs`,headers:r})})],instrumentations:[]}),ue.start()})(n,Ki),t._t2&&o.warn("Passing the Auth token via --github-token / -g exposes it to other processes on this host (visible in ps/proc). Prefer the GH_TOKEN environment variable instead.");let a,i=t._t2||g.env.GH_TOKEN;i?(X._t2=i,o.info("Using provided Auth token")):await ko();try{a=await Zt(),await st(X,a.login)}catch(e){throw o.error("Failed to get user info for machine ID generation:",e),Error("Cannot proceed without user information",{cause:e})}await(async()=>{let{token:e,refresh_in:t}=await Xt();X._t1=e,o.debug("Service token fetched successfully!"),X.showToken&&o.info("Service token:",e),so=setInterval(()=>{yo(5,1e3,"scheduled").catch(e=>{o.error("Unexpected error in scheduled token refresh:",e)})},1e3*(t-60)),tt.start(),co=()=>{o.debug("Network connectivity restored, attempting immediate token refresh"),yo(3,500,"network-restored").catch(e=>{o.error("Unexpected error in network-restored token refresh:",e)})},uo=()=>{o.debug("Network connectivity lost")},tt.on("online",co),tt.on("offline",uo)})(),await async function(){try{return await ro(),!0}catch(e){let t="object"==typeof e&&e&&"statusCode"in e&&"number"==typeof e.statusCode?e.statusCode:void 0,n=e instanceof Error?e.message:"Unknown error occurred",r=void 0===t?"":` (HTTP ${t})`;return o.warn(`Could not fetch model list from Copilot${r}: ${n}. This is likely a transient network or authentication issue. The proxy will start anyway; model listing endpoints may return empty until the cache is populated.`),!1}}()||function(e){let t=setTimeout(()=>{ro().then(()=>{o.info("Model cache populated successfully on deferred retry")}).catch(()=>{})},e);t.unref()}(3e4);let s=function(e=18e5){let t=setInterval(()=>{ro().then(()=>o.debug("Model list refreshed successfully")).catch(e=>{o.warn("Failed to refresh model list; keeping existing cache:",e)})},e);return t.unref(),()=>{clearInterval(t)}}();Ji.push(()=>{o.debug("Cleaning up model refresh interval"),s()}),X.connectivity.h2&&(Wn(Kn(lt(X))),X.connectivity.h2Keepalive&&Yn()),Xi({options:t,version:n,runtime:r,_u1:a});let l=await Zi(t),c=l?"https":"http",u=`${c}://localhost:${t.port}`,p=await async function(e,t,n){if(!e._cc1)return!1;let r,a;if(X.models||(o.error("Cannot apply --claude-code defaults: model cache is empty (Copilot API was unreachable at startup). Retry once the network/API is back, or run without --claude-code."),g.exit(1)),e.model&&e.smallModel){let t=X.models.data.map(e=>e.id);if(!t.includes(e.model))throw o.info(`Available services: \n${t.join("\n")}`),Error(`Invalid model: ${e.model}`);if(!t.includes(e.smallModel))throw o.info(`Available services: \n${t.join("\n")}`),Error(`Invalid small model: ${e.smallModel}`);r=e.model,a=e.smallModel}else{if(e.model||e.smallModel)throw Error("Both --model and --small-model must be specified for model selection");r=await o.prompt("Select a model to use",{type:"select",options:X.models.data.map(e=>e.id)}),a=await o.prompt("Select a small model to use",{type:"select",options:X.models.data.map(e=>e.id)})}let i=gi({ANTHROPIC_BASE_URL:t,ANTHROPIC_AUTH_TOKEN:"dummy",ANTHROPIC_MODEL:r,ANTHROPIC_SMALL_FAST_MODEL:a,NODE_EXTRA_CA_CERTS:n?.certPath},"claude");try{return m.writeSync(i),!0}catch{return o.warn("Failed to copy to clipboard. Here is the command:"),o.log(i),!1}}(t,u,l)||await async function(e,t,n){if(!e.codex)return!1;let r;if(X.models||(o.error("Cannot apply --codex defaults: model cache is empty (Copilot API was unreachable at startup). Retry once the network/API is back, or run without --codex."),g.exit(1)),e.model){let t=X.models.data.map(e=>e.id);if(!t.includes(e.model))throw o.info(`Available services: \n${t.join("\n")}`),Error(`Invalid model: ${e.model}`);r=e.model}else r=await o.prompt("Select a model to use with Codex CLI",{type:"select",options:X.models.data.map(e=>e.id)});let a=gi({OPENAI_BASE_URL:t,OPENAI_API_KEY:"dummy",NODE_EXTRA_CA_CERTS:n?.certPath},`codex --model ${r}`);try{return m.writeSync(a),!0}catch{return o.warn("Failed to copy to clipboard. Here is the Codex CLI command:"),o.log(a),!1}}(t,u,l);(function(e){let t=[...Ii(e),...Pi(e),...Ri(e),...Ni(),"",...Oi(Ci),...qi(e),...Di(e),""];console.log(t.join("\n"))})(await async function(e){let{options:t,version:o,runtime:n,user:r,clipboardCopied:a,tls:i}=e,s=i?"https":"http";return{version:o,runtime:n,user:r,accountType:t.accountType,port:t.port,timeout:t.timeout,webSearchProviders:t.webSearchProviders.map(e=>e.name),model:t.model,smallModel:t.smallModel,clipboardCopied:a,https:i?{certPath:i.certPath,keyPath:i.keyPath,generated:i.generated,selfSigned:!t.httpsCert}:void 0,endpoints:t.claudeCowork?{scheme:s,port:t.port,hostname:await Bo()}:void 0}}({options:t,version:n,runtime:r,user:a.login,clipboardCopied:p,tls:l})),L({fetch:za.fetch,port:t.port,hostname:t.hostname,tls:l?{cert:l.cert,key:l.key}:void 0,bun:{idleTimeout:255}}),function(e,t,n){o.info(`Server listening on ${e}://${t}:${n}`)}(c,t.hostname,t.port),t.smokeTest&&await async function(e,t,n){try{o.start("Running first-run self-test (one tiny generation)…");let r=await Wa({model:t});if(r.ok){let t=void 0===n||["::1","127.0.0.1","localhost"].includes(n)?`Point your client at ${e}`:`Point your client at ${e} — you bound ${n}, so from another machine/container replace \`localhost\` with this host's reachable IP/hostname.`;return void o.success(`Self-test passed — generation works via ${r.model} (${r.durationMs}ms). ${t}`)}let a=r.status?` (HTTP ${r.status})`:"";o.warn(`Self-test FAILED${a}: ${r.reason??"unknown error"}`),r.detail&&o.info(` detail: ${an(r.detail)}`),o.info(" The server is still running. Run `copilot-api doctor` to diagnose, or `--no-smoke-test` to skip this check.")}catch(e){o.warn("First-run self-test could not run:",e instanceof Error?e.message:String(e))}}(u,t.smallModel??t.model,t.hostname)}function es(e,t){let o=Number.parseInt(e,10);if(Number.isNaN(o))throw Error(`${t} must be a number, got: "${e}"`);return o}const ts=e({meta:{name:"start",description:"Start the API server"},args:{port:{alias:"p",type:"string",default:"4141",description:"Port to listen on"},hostname:{alias:"H",type:"string",default:"127.0.0.1",description:"Hostname/IP to bind the server to. Defaults to 127.0.0.1 (localhost only) for security. Use 0.0.0.0 only when you intentionally need LAN/network/Docker exposure."},verbose:{alias:"v",type:"boolean",default:!1,description:"Enable verbose logging"},"account-type":{alias:"a",type:"string",default:"individual",description:"Account type (individual, business, enterprise)"},manual:{type:"boolean",default:!1,description:"Enable manual request approval"},"rate-limit":{alias:"r",type:"string",description:"Rate limit in seconds between requests"},wait:{alias:"w",type:"boolean",default:!1,description:"Wait instead of error when rate limit is hit. Has no effect if rate limit is not set"},"github-token":{alias:"g",type:"string",description:"Auth token (visible in process list — prefer GH_TOKEN env var)"},"claude-code":{alias:"c",type:"boolean",default:!1,description:"Generate a command to launch with API config"},codex:{type:"boolean",default:!1,description:"Generate a command to launch Codex CLI with Copilot API config"},model:{alias:"m",type:"string",description:"Model to use (with --claude-code or --codex)"},"small-model":{alias:"s",type:"string",description:"Small/fast model to use (requires --claude-code)"},"show-token":{type:"boolean",default:!1,description:"Show tokens on fetch and refresh"},"error-reporting":{type:"boolean",default:!0,description:"Send anonymous, sanitized error reports to the maintainer to help fix bugs (no prompts, completions, or tokens). Use --no-error-reporting or COPILOT_API_ERROR_REPORTING=0 to disable."},timeout:{alias:"t",type:"string",description:"API timeout in milliseconds (default: 600000)"},"connect-timeout":{type:"string",description:"Connectivity probe timeout in milliseconds (default: 15000). Overrides COPILOT_CONNECT_TIMEOUT_MS env var."},"tavily-api-key":{type:"string",description:"[DEPRECATED — set the TAVILY_API_KEY env var instead] Tavily API key for web search."},"web-search-provider":{type:"string",description:'Web search failover order, e.g. "exa,tavily" (first = primary, rest = fallbacks). Web search turns on when TAVILY_API_KEY and/or EXA_API_KEY are set; this flag is optional and only orders the providers you configured.'},https:{type:"boolean",default:!1,description:"Serve over HTTPS using a self-signed certificate (auto-generated and persisted)"},"https-cert":{type:"string",description:"Path to a PEM-encoded TLS certificate (use with --https-key to bring your own cert)"},"https-key":{type:"string",description:"Path to a PEM-encoded TLS private key (use with --https-cert to bring your own cert)"},"https-hosts":{type:"string",description:"Extra hostnames or IPs to include in the self-signed cert's SANs (comma-separated). Example: --https-hosts host.docker.internal,192.168.1.42"},"claude-cowork":{type:"boolean",default:!1,description:"Print Claude Cowork-specific setup hints (inference endpoint URLs to paste into Cowork's apiHost setting)"},"smoke-test":{type:"boolean",default:!0,description:"After startup, run one tiny self-test generation to verify the proxy works end-to-end and print a clear PASS/FAIL. Disable with --no-smoke-test (or COPILOT_API_NO_SMOKE_TEST=1)."}},run({args:e}){let t=e["rate-limit"],n=void 0===t?void 0:es(t,"--rate-limit"),r=e.timeout,a=void 0===r?Y:es(r,"--timeout"),i=e["connect-timeout"]??g.env.COPILOT_CONNECT_TIMEOUT_MS,s=void 0===i?15e3:es(i,"--connect-timeout");if(s<1e3)throw Error(`--connect-timeout must be at least 1000ms, got: ${s}`);let l=e["https-hosts"],c=l?l.split(",").map(e=>e.trim()).filter(Boolean):[],u=e["web-search-provider"]??g.env.WEB_SEARCH_PROVIDER,p=u?u.split(",").map(e=>e.trim()).filter(Boolean):[];e["tavily-api-key"]&&o.warn("--tavily-api-key is deprecated; set the TAVILY_API_KEY environment variable instead.");let d=function(e){let t={tavily:e.tavilyApiKey,exa:e.exaApiKey},n=(e.order??[]).map(e=>e.toLowerCase());for(let e of n)if(!pa(e))throw Error(`Unknown web search provider: "${e}". Valid providers: ${ua.join(", ")}`);let r=n.length>0?n:ua,a=new Set,i=n.length>0,s=[];for(let e of r){if(!pa(e)||a.has(e))continue;a.add(e);let n=t[e];n?s.push({name:e,key:n}):i&&o.warn(`Web search provider "${e}" was requested but no API key is configured — skipping.`)}return s}({tavilyApiKey:e["tavily-api-key"]||g.env.TAVILY_API_KEY,exaApiKey:g.env.EXA_API_KEY,order:p}),m=(g.env.COPILOT_API_NO_SMOKE_TEST??"").trim().toLowerCase(),f=""!==m&&"0"!==m&&"false"!==m;return Qi({port:es(e.port,"--port"),hostname:e.hostname,verbose:e.verbose,accountType:e["account-type"],manual:e.manual,rateLimit:n,rateLimitWait:e.wait,_t2:e["github-token"],_cc1:e["claude-code"],codex:e.codex,model:e.model,smallModel:e["small-model"],showToken:e["show-token"],timeout:a,connectTimeout:s,webSearchProviders:d,https:e.https,httpsCert:e["https-cert"],httpsKey:e["https-key"],httpsHosts:c,claudeCowork:e["claude-cowork"],errorReporting:e["error-reporting"],smokeTest:e["smoke-test"]&&!f})}});ci||(ci=!0,o.setReporters([li(o.options.reporters)])),await async function(){try{if("1"===process.env.COPILOT_API_SKIP_UPDATE_CHECK)return;let[e,t]=await Promise.all([St(),fi()]);if("unknown"===e||!t||!function(e,t){let o=e.split(".").map(Number),n=t.split(".").map(Number),r=Math.max(o.length,n.length);for(let e=0;e<r;e++){let t=o[e]??0,r=n[e]??0;if(t<r)return!0;if(t>r)return!1}return!1}(e,t))return;!function(e,t){let o=`npx ${ui}@latest`,n=mi("│"),r=` ${di("Update available!")} ${(e=>`[2m${e}[0m`)(e)} → ${(e=>`[32m${e}[0m`)(t)}`,a=` Run ${di(o)} to update`,i=" ".repeat(54),s=mi(`╭${"─".repeat(54)}╮`),l=mi(`╰${"─".repeat(54)}╯`),c=["",s,`${n}${i}${n}`,`${n}${hi(r,54)}${n}`,`${n}${i}${n}`,`${n}${hi(a,54)}${n}`,`${n}${i}${n}`,l,""];console.log(c.join("\n"))}(e,t)}catch{}}(),await t(e({meta:{name:"copilot-api",description:"API proxy server for tool integration."},subCommands:{auth:$o,start:ts,"check-usage":qo,debug:It,doctor:si,"cowork-setup":rn}}));export{};
|