mirror of
https://github.com/anomalyco/opencode.git
synced 2026-08-06 09:10:47 -04:00
Compare commits
5 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 4598e81fd7 | |||
| f4cb3170d4 | |||
| a4ead918f5 | |||
| 64937161aa | |||
| 7a79f3a5ea |
@@ -30,3 +30,4 @@ UPCOMING_CHANGELOG.md
|
||||
logs/
|
||||
*.bun-build
|
||||
tsconfig.tsbuildinfo
|
||||
/packages/opencode/config.json
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
},
|
||||
"packages/app": {
|
||||
"name": "@opencode-ai/app",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@kobalte/core": "catalog:",
|
||||
"@opencode-ai/core": "workspace:*",
|
||||
@@ -85,7 +85,7 @@
|
||||
},
|
||||
"packages/console/app": {
|
||||
"name": "@opencode-ai/console-app",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@cloudflare/vite-plugin": "1.15.2",
|
||||
"@ibm/plex": "6.4.1",
|
||||
@@ -120,7 +120,7 @@
|
||||
},
|
||||
"packages/console/core": {
|
||||
"name": "@opencode-ai/console-core",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@aws-sdk/client-sts": "3.782.0",
|
||||
"@jsx-email/render": "1.1.1",
|
||||
@@ -147,7 +147,7 @@
|
||||
},
|
||||
"packages/console/function": {
|
||||
"name": "@opencode-ai/console-function",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@ai-sdk/anthropic": "3.0.64",
|
||||
"@ai-sdk/openai": "3.0.48",
|
||||
@@ -171,7 +171,7 @@
|
||||
},
|
||||
"packages/console/mail": {
|
||||
"name": "@opencode-ai/console-mail",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@jsx-email/all": "2.2.3",
|
||||
"@jsx-email/cli": "1.4.3",
|
||||
@@ -195,7 +195,7 @@
|
||||
},
|
||||
"packages/core": {
|
||||
"name": "@opencode-ai/core",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"bin": {
|
||||
"opencode": "./bin/opencode",
|
||||
},
|
||||
@@ -229,7 +229,7 @@
|
||||
},
|
||||
"packages/desktop": {
|
||||
"name": "@opencode-ai/desktop",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"drizzle-orm": "catalog:",
|
||||
"effect": "catalog:",
|
||||
@@ -283,7 +283,7 @@
|
||||
},
|
||||
"packages/enterprise": {
|
||||
"name": "@opencode-ai/enterprise",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@opencode-ai/core": "workspace:*",
|
||||
"@opencode-ai/ui": "workspace:*",
|
||||
@@ -313,7 +313,7 @@
|
||||
},
|
||||
"packages/function": {
|
||||
"name": "@opencode-ai/function",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@octokit/auth-app": "8.0.1",
|
||||
"@octokit/rest": "catalog:",
|
||||
@@ -329,7 +329,7 @@
|
||||
},
|
||||
"packages/http-recorder": {
|
||||
"name": "@opencode-ai/http-recorder",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@effect/platform-node": "catalog:",
|
||||
"effect": "catalog:",
|
||||
@@ -342,7 +342,7 @@
|
||||
},
|
||||
"packages/llm": {
|
||||
"name": "@opencode-ai/llm",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@smithy/eventstream-codec": "4.2.14",
|
||||
"@smithy/util-utf8": "4.2.2",
|
||||
@@ -360,7 +360,7 @@
|
||||
},
|
||||
"packages/opencode": {
|
||||
"name": "opencode",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"bin": {
|
||||
"opencode": "./bin/opencode",
|
||||
},
|
||||
@@ -495,7 +495,7 @@
|
||||
},
|
||||
"packages/plugin": {
|
||||
"name": "@opencode-ai/plugin",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@opencode-ai/sdk": "workspace:*",
|
||||
"effect": "catalog:",
|
||||
@@ -533,7 +533,7 @@
|
||||
},
|
||||
"packages/sdk/js": {
|
||||
"name": "@opencode-ai/sdk",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"cross-spawn": "catalog:",
|
||||
},
|
||||
@@ -548,7 +548,7 @@
|
||||
},
|
||||
"packages/slack": {
|
||||
"name": "@opencode-ai/slack",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@opencode-ai/sdk": "workspace:*",
|
||||
"@slack/bolt": "^3.17.1",
|
||||
@@ -583,7 +583,7 @@
|
||||
},
|
||||
"packages/ui": {
|
||||
"name": "@opencode-ai/ui",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@kobalte/core": "catalog:",
|
||||
"@opencode-ai/core": "workspace:*",
|
||||
@@ -632,7 +632,7 @@
|
||||
},
|
||||
"packages/web": {
|
||||
"name": "@opencode-ai/web",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@astrojs/cloudflare": "12.6.3",
|
||||
"@astrojs/markdown-remark": "6.3.1",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/app",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"description": "",
|
||||
"type": "module",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/console-app",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"scripts": {
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"name": "@opencode-ai/console-core",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/console-function",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/console-mail",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"dependencies": {
|
||||
"@jsx-email/all": "2.2.3",
|
||||
"@jsx-email/cli": "1.4.3",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"name": "@opencode-ai/core",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@opencode-ai/desktop",
|
||||
"private": true,
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"homepage": "https://opencode.ai",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/enterprise",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
id = "opencode"
|
||||
name = "OpenCode"
|
||||
description = "The open source coding agent."
|
||||
version = "1.14.44"
|
||||
version = "1.14.45"
|
||||
schema_version = 1
|
||||
authors = ["Anomaly"]
|
||||
repository = "https://github.com/anomalyco/opencode"
|
||||
@@ -11,26 +11,26 @@ name = "OpenCode"
|
||||
icon = "./icons/opencode.svg"
|
||||
|
||||
[agent_servers.opencode.targets.darwin-aarch64]
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.44/opencode-darwin-arm64.zip"
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.45/opencode-darwin-arm64.zip"
|
||||
cmd = "./opencode"
|
||||
args = ["acp"]
|
||||
|
||||
[agent_servers.opencode.targets.darwin-x86_64]
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.44/opencode-darwin-x64.zip"
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.45/opencode-darwin-x64.zip"
|
||||
cmd = "./opencode"
|
||||
args = ["acp"]
|
||||
|
||||
[agent_servers.opencode.targets.linux-aarch64]
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.44/opencode-linux-arm64.tar.gz"
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.45/opencode-linux-arm64.tar.gz"
|
||||
cmd = "./opencode"
|
||||
args = ["acp"]
|
||||
|
||||
[agent_servers.opencode.targets.linux-x86_64]
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.44/opencode-linux-x64.tar.gz"
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.45/opencode-linux-x64.tar.gz"
|
||||
cmd = "./opencode"
|
||||
args = ["acp"]
|
||||
|
||||
[agent_servers.opencode.targets.windows-x86_64]
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.44/opencode-windows-x64.zip"
|
||||
archive = "https://github.com/anomalyco/opencode/releases/download/v1.14.45/opencode-windows-x64.zip"
|
||||
cmd = "./opencode.exe"
|
||||
args = ["acp"]
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/function",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"name": "@opencode-ai/http-recorder",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"name": "@opencode-ai/llm",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"name": "opencode",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1260,6 +1260,47 @@ const scenarios: Scenario[] = [
|
||||
.probe({ path: "/global/upgrade", body: { target: 1 } })
|
||||
.at(() => ({ path: "/global/upgrade", body: { target: 1 } }))
|
||||
.status(400),
|
||||
|
||||
// ─── SDK routing-params drift coverage (replaces httpapi-query-schema-drift.test.ts) ───
|
||||
// Each routing-aware GET endpoint runs through the real SDK client, which
|
||||
// auto-injects `?directory=...&workspace=...`. Pre-#26581 these all 4xx'd
|
||||
// because the typed query schemas didn't accept the SDK's injected fields.
|
||||
// Any future endpoint added under WorkspaceRoutingMiddleware that forgets
|
||||
// WorkspaceRoutingQueryFields will fail its `.viaSdk(...)` scenario on
|
||||
// first run.
|
||||
http.protected
|
||||
.get("/session", "session.list.via_sdk")
|
||||
.viaSdk((sdk) => sdk.session.list({ roots: true }, { throwOnError: true }))
|
||||
.json(200, array, "status"),
|
||||
http.protected
|
||||
.get("/session/{sessionID}/message", "session.messages.via_sdk")
|
||||
.at((ctx) => ({ path: route("/session/{sessionID}/message", { sessionID: "ses_via_sdk_drift" }), headers: ctx.headers() }))
|
||||
.viaSdk((sdk) => sdk.session.messages({ sessionID: "ses_via_sdk_drift", limit: 80 }))
|
||||
.status(404, undefined, "status"),
|
||||
http.protected
|
||||
.get("/find/file", "find.files.via_sdk")
|
||||
.viaSdk((sdk) => sdk.find.files({ query: "foo" }, { throwOnError: true }))
|
||||
.json(200, array, "status"),
|
||||
http.protected
|
||||
.get("/find", "find.text.via_sdk")
|
||||
.viaSdk((sdk) => sdk.find.text({ pattern: "foo" }, { throwOnError: true }))
|
||||
.json(200, array, "status"),
|
||||
http.protected
|
||||
.get("/file/content", "file.read.via_sdk")
|
||||
.viaSdk((sdk) => sdk.file.read({ path: "foo" }, { throwOnError: true }))
|
||||
.json(200, undefined, "status"),
|
||||
http.protected
|
||||
.get("/experimental/session", "experimental.session.list.via_sdk")
|
||||
.viaSdk((sdk) => sdk.experimental.session.list({}, { throwOnError: true }))
|
||||
.json(200, array, "status"),
|
||||
http.protected
|
||||
.get("/experimental/tool", "experimental.tool.list.via_sdk")
|
||||
.viaSdk((sdk) => sdk.tool.list({ provider: "anthropic", model: "claude" }, { throwOnError: true }))
|
||||
.json(200, array, "status"),
|
||||
http.protected
|
||||
.get("/vcs/diff", "vcs.diff.via_sdk")
|
||||
.viaSdk((sdk) => sdk.vcs.diff({ mode: "git" }, { throwOnError: true }))
|
||||
.json(200, array, "status"),
|
||||
]
|
||||
|
||||
const llmScenarios = new Set([
|
||||
|
||||
@@ -1,134 +0,0 @@
|
||||
import { afterEach, describe, expect } from "bun:test"
|
||||
import { Effect } from "effect"
|
||||
import { Flag } from "@opencode-ai/core/flag/flag"
|
||||
import { Server } from "../../src/server/server"
|
||||
import { SessionID } from "../../src/session/schema"
|
||||
import { resetDatabase } from "../fixture/db"
|
||||
import { disposeAllInstances, tmpdir } from "../fixture/fixture"
|
||||
import { it } from "../lib/effect"
|
||||
|
||||
const originalWorkspaces = Flag.OPENCODE_EXPERIMENTAL_WORKSPACES
|
||||
|
||||
function app() {
|
||||
return Server.Default().app
|
||||
}
|
||||
|
||||
function request(url: string, init?: RequestInit) {
|
||||
return Effect.promise(async () => app().request(url, init))
|
||||
}
|
||||
|
||||
function withTmp<A, E, R>(
|
||||
options: Parameters<typeof tmpdir>[0],
|
||||
fn: (tmp: Awaited<ReturnType<typeof tmpdir>>) => Effect.Effect<A, E, R>,
|
||||
) {
|
||||
return Effect.acquireRelease(
|
||||
Effect.promise(() => tmpdir(options)),
|
||||
(tmp) => Effect.promise(() => tmp[Symbol.asyncDispose]()),
|
||||
).pipe(Effect.flatMap(fn))
|
||||
}
|
||||
|
||||
afterEach(async () => {
|
||||
Flag.OPENCODE_EXPERIMENTAL_WORKSPACES = originalWorkspaces
|
||||
await disposeAllInstances()
|
||||
await resetDatabase()
|
||||
})
|
||||
|
||||
// Regression for the "OpenAPI advertises ?directory&workspace, runtime
|
||||
// rejects them" drift class. Each affected route must accept both params
|
||||
// without 400.
|
||||
describe("httpapi query schema drift", () => {
|
||||
const routingParams = (dir: string) =>
|
||||
`directory=${encodeURIComponent(dir)}&workspace=${encodeURIComponent("ws_test")}`
|
||||
|
||||
const expectNotSchemaRejection = (status: number, url: string) => {
|
||||
expect(status, `route ${url} 400'd, query schema is missing routing fields`).not.toBe(400)
|
||||
}
|
||||
|
||||
it.live(
|
||||
"session list accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/session?${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"session messages accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/session/${SessionID.descending()}/message?limit=80&${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"file find/file accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/find/file?query=foo&${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"file find/text accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/find?pattern=foo&${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"file read accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/file?path=foo&${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"experimental session list accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/experimental/session?${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"experimental tool list accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/experimental/tool?provider=anthropic&model=claude&${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
|
||||
it.live(
|
||||
"vcs diff accepts directory and workspace",
|
||||
withTmp({ config: { formatter: false, lsp: false } }, (tmp) =>
|
||||
Effect.gen(function* () {
|
||||
const url = `/vcs/diff?mode=working&${routingParams(tmp.path)}`
|
||||
const response = yield* request(url)
|
||||
expectNotSchemaRejection(response.status, url)
|
||||
}),
|
||||
),
|
||||
)
|
||||
})
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"name": "@opencode-ai/plugin",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"scripts": {
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/package.json",
|
||||
"name": "@opencode-ai/sdk",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"scripts": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/slack",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"scripts": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@opencode-ai/ui",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"exports": {
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
"name": "@opencode-ai/web",
|
||||
"type": "module",
|
||||
"license": "MIT",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"scripts": {
|
||||
"dev": "astro dev",
|
||||
"dev:remote": "VITE_API_URL=https://api.opencode.ai astro dev",
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
"name": "opencode",
|
||||
"displayName": "opencode",
|
||||
"description": "opencode for VS Code",
|
||||
"version": "1.14.44",
|
||||
"version": "1.14.45",
|
||||
"publisher": "sst-dev",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
|
||||
Reference in New Issue
Block a user