backend: fix copilot API paths

Copilot API has no /v1 prefix. Add pathPrefix field to OpenAIBackend
(defaults to /v1) and apply extraHeaders in fetchModels. Copilot sets
pathPrefix to / so it hits /models and /chat/completions directly.
This commit is contained in:
Levi Neely 2026-05-21 19:40:41 +02:00
parent 15d7d3bf50
commit 1485decdbb
2 changed files with 19 additions and 6 deletions

View File

@ -14,6 +14,7 @@ func NewCopilot(token string) (*OpenAIBackend, error) {
baseURL: u,
apiKey: token,
client: &http.Client{},
pathPrefix: "/",
extraHeaders: map[string]string{
"Openai-Intent": "conversation-edits",
"User-Agent": "opencode/local",

View File

@ -23,6 +23,7 @@ type OpenAIBackend struct {
model string
client *http.Client
extraHeaders map[string]string // optional; applied after Authorization
pathPrefix string // API path prefix (default: /v1); set to "/" for no prefix
ctxLength int // cached; 0 = not yet fetched
ctxModel string // model the cached value is for
cachedModels []openAIModelInfo // cached model list
@ -54,10 +55,17 @@ func (b *OpenAIBackend) fetchModels(ctx context.Context) []openAIModelInfo {
if len(b.cachedModels) > 0 {
return b.cachedModels
}
req, _ := http.NewRequestWithContext(ctx, "GET", b.baseURL.JoinPath("/v1/models").String(), nil)
prefix := b.pathPrefix
if prefix == "" {
prefix = "/v1"
}
req, _ := http.NewRequestWithContext(ctx, "GET", b.baseURL.JoinPath(prefix, "models").String(), nil)
if b.apiKey != "" {
req.Header.Set("Authorization", "Bearer "+b.apiKey)
}
for k, v := range b.extraHeaders {
req.Header.Set(k, v)
}
resp, err := b.client.Do(req)
if err != nil || resp.StatusCode != 200 {
if resp != nil {
@ -493,7 +501,11 @@ func (b *OpenAIBackend) ChatStream(ctx context.Context, messages []Message, tool
data, _ := json.Marshal(req)
httpReq, _ := http.NewRequestWithContext(ctx, http.MethodPost, b.baseURL.JoinPath("/v1/chat/completions").String(), bytes.NewReader(data))
pp := b.pathPrefix
if pp == "" {
pp = "/v1"
}
httpReq, _ := http.NewRequestWithContext(ctx, http.MethodPost, b.baseURL.JoinPath(pp, "chat/completions").String(), bytes.NewReader(data))
httpReq.Header.Set("Content-Type", "application/json")
if b.apiKey != "" {
httpReq.Header.Set("Authorization", "Bearer "+b.apiKey)