chore: merge dev into v2 (#34788)
Co-authored-by: Brendan Allan <14191578+Brendonovich@users.noreply.github.com> Co-authored-by: Kit Langton <kit.langton@gmail.com> Co-authored-by: opencode-agent[bot] <opencode-agent[bot]@users.noreply.github.com> Co-authored-by: Affan Ali <93028901+affanali2k3@users.noreply.github.com> Co-authored-by: affanali2k3 <affanalikhanxx@gmail.com> Co-authored-by: Frank <frank@anoma.ly> Co-authored-by: opencode-agent[bot] <219766164+opencode-agent[bot]@users.noreply.github.com> Co-authored-by: 𝓛𝓲𝓽𝓽𝓵𝓮 𝓕𝓻𝓪𝓷𝓴 <little-frank@opencord.local> Co-authored-by: Aiden Cline <63023139+rekram1-node@users.noreply.github.com> Co-authored-by: Jay V <air@live.ca> Co-authored-by: Dax Raad <d@ironbay.co> Co-authored-by: Aarav Sareen <96787824+arvsrn@users.noreply.github.com> Co-authored-by: OpeOginni <107570612+OpeOginni@users.noreply.github.com> Co-authored-by: Luke Parker <10430890+Hona@users.noreply.github.com> Co-authored-by: Ben Guthrie <benjee.012@gmail.com> Co-authored-by: Dax <mail@thdxr.com> Co-authored-by: Filip <34747899+neriousy@users.noreply.github.com> Co-authored-by: Max Anderson <max.a.anderson95@gmail.com> Co-authored-by: Brendan Allan <git@brendonovich.dev> Co-authored-by: Jack <jack@anoma.ly> Co-authored-by: Shoubhit Dash <shoubhit2005@gmail.com> Co-authored-by: Dustin Deus <deusdustin@gmail.com> Co-authored-by: starptech <starptech@starptechs-MBP.fritz.box> Co-authored-by: Aiden Cline <aidenpcline@gmail.com> Co-authored-by: usrnk1 <7547651+usrnk1@users.noreply.github.com> Co-authored-by: Jay <53023+jayair@users.noreply.github.com> Co-authored-by: runvip <164729189+runvip@users.noreply.github.com> Co-authored-by: opencode <opencode@sst.dev> Co-authored-by: Julian Coy <julian@ex-machina.co> Co-authored-by: Vladimir Glafirov <vglafirov@gitlab.com>
This commit is contained in:
@@ -7,8 +7,9 @@ export const ScrapCommand = cmd({
|
||||
builder: (yargs) => yargs,
|
||||
async handler() {
|
||||
const { Project } = await import("@/project/project")
|
||||
const { AppNodeBuilder } = await import("@opencode-ai/core/effect/app-node-builder")
|
||||
const { makeRuntime } = await import("@opencode-ai/core/effect/runtime")
|
||||
const runtime = makeRuntime(Project.Service, Project.defaultLayer)
|
||||
const runtime = makeRuntime(Project.Service, AppNodeBuilder.build(Project.node))
|
||||
const list = await runtime.runPromise((project) => project.list())
|
||||
process.stdout.write(JSON.stringify(list, null, 2) + EOL)
|
||||
},
|
||||
|
||||
@@ -761,7 +761,7 @@ export const McpDebugCommand = effectCmd({
|
||||
}
|
||||
|
||||
if (response.status === 401) {
|
||||
prompts.log.warn("Server returned 401 Unauthorized")
|
||||
prompts.log.info("Initial unauthenticated check returned 401, so this server requires OAuth")
|
||||
|
||||
// Try to discover OAuth metadata
|
||||
const oauthConfig = typeof serverConfig.oauth === "object" ? serverConfig.oauth : undefined
|
||||
|
||||
@@ -233,11 +233,27 @@ export const RunCommand = effectCmd({
|
||||
hidden: true,
|
||||
describe: "cap visible interactive replay to the newest N messages",
|
||||
})
|
||||
.option("dangerously-skip-permissions", {
|
||||
.option("interactive", {
|
||||
alias: ["i"],
|
||||
type: "boolean",
|
||||
describe: "run in direct interactive split-footer mode",
|
||||
default: false,
|
||||
})
|
||||
.option("auto", {
|
||||
type: "boolean",
|
||||
describe: "auto-approve permissions that are not explicitly denied (dangerous!)",
|
||||
default: false,
|
||||
})
|
||||
.option("yolo", {
|
||||
type: "boolean",
|
||||
hidden: true,
|
||||
default: false,
|
||||
})
|
||||
.option("dangerously-skip-permissions", {
|
||||
type: "boolean",
|
||||
hidden: true,
|
||||
default: false,
|
||||
})
|
||||
.option("demo", {
|
||||
type: "boolean",
|
||||
default: false,
|
||||
@@ -255,6 +271,7 @@ export const RunCommand = effectCmd({
|
||||
yield* Effect.promise(async () => {
|
||||
const rawMessage = [...args.message, ...(args["--"] || [])].join(" ")
|
||||
const interactive = args.mini
|
||||
const auto = args.auto || args.yolo || args["dangerously-skip-permissions"]
|
||||
const thinking = interactive ? (args.thinking ?? true) : (args.thinking ?? false)
|
||||
const die = (message: string): never => {
|
||||
UI.error(message)
|
||||
@@ -780,7 +797,7 @@ export const RunCommand = effectCmd({
|
||||
const permission = event.properties
|
||||
if (permission.sessionID !== sessionID) continue
|
||||
|
||||
if (args["dangerously-skip-permissions"]) {
|
||||
if (auto) {
|
||||
await client.permission.reply({
|
||||
requestID: permission.id,
|
||||
reply: "once",
|
||||
@@ -981,9 +998,12 @@ export async function runMini(input: MiniCommandInput) {
|
||||
variant: undefined,
|
||||
thinking: undefined,
|
||||
mini: true,
|
||||
interactive: false,
|
||||
replay: input.replay ?? true,
|
||||
"replay-limit": input.replayLimit,
|
||||
replayLimit: input.replayLimit,
|
||||
auto: false,
|
||||
yolo: false,
|
||||
"dangerously-skip-permissions": false,
|
||||
dangerouslySkipPermissions: false,
|
||||
demo: input.demo ?? false,
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
// variant and the persisted file.
|
||||
import path from "path"
|
||||
import { FSUtil } from "@opencode-ai/core/fs-util"
|
||||
import { AppNodeBuilder } from "@opencode-ai/core/effect/app-node-builder"
|
||||
import { Context, Effect, Layer } from "effect"
|
||||
import { makeRuntime } from "@/effect/run-service"
|
||||
import { Global } from "@opencode-ai/core/global"
|
||||
@@ -135,7 +136,7 @@ function state(value: unknown): ModelState {
|
||||
}
|
||||
}
|
||||
|
||||
function createLayer(fs = FSUtil.defaultLayer) {
|
||||
function createLayer(fs = AppNodeBuilder.build(FSUtil.node)) {
|
||||
return Layer.fresh(
|
||||
Layer.effect(
|
||||
Service,
|
||||
@@ -196,7 +197,7 @@ function createLayer(fs = FSUtil.defaultLayer) {
|
||||
}
|
||||
|
||||
/** @internal Exported for testing. */
|
||||
export function createVariantRuntime(fs = FSUtil.defaultLayer): VariantRuntime {
|
||||
export function createVariantRuntime(fs = AppNodeBuilder.build(FSUtil.node)): VariantRuntime {
|
||||
const runtime = makeRuntime(Service, createLayer(fs))
|
||||
return {
|
||||
resolveSavedVariant: (model) => runtime.runPromise((svc) => svc.resolveSavedVariant(model)).catch(() => undefined),
|
||||
|
||||
@@ -6,11 +6,12 @@ import { fileURLToPath } from "url"
|
||||
import { UI } from "@/cli/ui"
|
||||
import { errorMessage } from "@opencode-ai/tui/util/error"
|
||||
import { withTimeout } from "@/util/timeout"
|
||||
import { withNetworkOptions, resolveNetworkOptionsNoConfig } from "@/cli/network"
|
||||
import { withNetworkOptions, resolveNetworkOptionsNoConfig, hasArg } from "@/cli/network"
|
||||
import { Filesystem } from "@/util/filesystem"
|
||||
import { OpenCode } from "@opencode-ai/client"
|
||||
import { createOpencodeClient } from "@opencode-ai/sdk/v2"
|
||||
import { writeHeapSnapshot } from "v8"
|
||||
import { ServerAuth } from "@/server/auth"
|
||||
import { validateSession } from "../tui/validate-session"
|
||||
import { win32InstallCtrlCGuard } from "@opencode-ai/tui/terminal-win32"
|
||||
|
||||
@@ -74,6 +75,21 @@ export const TuiThreadCommand = cmd({
|
||||
type: "string",
|
||||
describe: "agent to use",
|
||||
})
|
||||
.option("auto", {
|
||||
type: "boolean",
|
||||
describe: "auto-approve permissions that are not explicitly denied (dangerous!)",
|
||||
default: false,
|
||||
})
|
||||
.option("yolo", {
|
||||
type: "boolean",
|
||||
hidden: true,
|
||||
default: false,
|
||||
})
|
||||
.option("dangerously-skip-permissions", {
|
||||
type: "boolean",
|
||||
hidden: true,
|
||||
default: false,
|
||||
})
|
||||
.option("mini", {
|
||||
type: "boolean",
|
||||
describe: "start the minimal interactive interface",
|
||||
@@ -221,6 +237,7 @@ export const TuiThreadCommand = cmd({
|
||||
model: args.model,
|
||||
prompt,
|
||||
fork: args.fork,
|
||||
auto: args.auto || args.yolo || args["dangerously-skip-permissions"],
|
||||
},
|
||||
}),
|
||||
)
|
||||
|
||||
@@ -37,6 +37,22 @@ export type NetworkOptions = InferredOptionTypes<typeof options>
|
||||
export function withNetworkOptions<T>(yargs: Argv<T>) {
|
||||
return yargs.options(options)
|
||||
}
|
||||
|
||||
export function hasArg(name: string) {
|
||||
return networkArgs().some((arg) => arg === name || arg.startsWith(name + "="))
|
||||
}
|
||||
|
||||
function hasBooleanArg(name: string) {
|
||||
return networkArgs().some(
|
||||
(arg) => arg === name || arg === name + "=true" || arg === name + "=false" || arg === "--no-" + name.slice(2),
|
||||
)
|
||||
}
|
||||
|
||||
function networkArgs() {
|
||||
const separator = process.argv.indexOf("--")
|
||||
return process.argv.slice(2, separator === -1 ? undefined : separator)
|
||||
}
|
||||
|
||||
export const resolveNetworkOptions = Effect.fn("Cli.resolveNetworkOptions")(function* (args: NetworkOptions) {
|
||||
const { Config } = yield* Effect.promise(() => import("@/config/config"))
|
||||
const config = yield* Config.Service.use((cfg) => cfg.getGlobal())
|
||||
@@ -44,10 +60,10 @@ export const resolveNetworkOptions = Effect.fn("Cli.resolveNetworkOptions")(func
|
||||
})
|
||||
|
||||
export function resolveNetworkOptionsNoConfig(args: NetworkOptions, config?: ConfigV1.Info) {
|
||||
const portExplicitlySet = process.argv.includes("--port")
|
||||
const hostnameExplicitlySet = process.argv.includes("--hostname")
|
||||
const mdnsExplicitlySet = process.argv.includes("--mdns")
|
||||
const mdnsDomainExplicitlySet = process.argv.includes("--mdns-domain")
|
||||
const portExplicitlySet = hasArg("--port")
|
||||
const hostnameExplicitlySet = hasArg("--hostname")
|
||||
const mdnsExplicitlySet = hasBooleanArg("--mdns")
|
||||
const mdnsDomainExplicitlySet = hasArg("--mdns-domain")
|
||||
const mdns = mdnsExplicitlySet ? args.mdns : (config?.server?.mdns ?? args.mdns)
|
||||
const mdnsDomain = mdnsDomainExplicitlySet ? args["mdns-domain"] : (config?.server?.mdnsDomain ?? args["mdns-domain"])
|
||||
const port = portExplicitlySet ? args.port : (config?.server?.port ?? args.port)
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
import { run as runTui, type TuiInput } from "@opencode-ai/tui"
|
||||
import { Global } from "@opencode-ai/core/global"
|
||||
import { AppNodeBuilder } from "@opencode-ai/core/effect/app-node-builder"
|
||||
import { Effect } from "effect"
|
||||
|
||||
export function run(input: TuiInput) {
|
||||
return runTui(input).pipe(Effect.provide(Global.defaultLayer))
|
||||
return runTui(input).pipe(Effect.provide(AppNodeBuilder.build(Global.node)))
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user