get rid of models.dev macro
This commit is contained in:
1
packages/opencode/.gitignore
vendored
1
packages/opencode/.gitignore
vendored
@@ -2,3 +2,4 @@ research
|
||||
dist
|
||||
gen
|
||||
app.log
|
||||
src/provider/models-snapshot.ts
|
||||
|
||||
@@ -15,6 +15,14 @@ process.chdir(dir)
|
||||
import pkg from "../package.json"
|
||||
import { Script } from "@opencode-ai/script"
|
||||
|
||||
// Fetch and generate models.dev snapshot
|
||||
const modelsData = await fetch(`https://models.dev/api.json`).then((x) => x.text())
|
||||
await Bun.write(
|
||||
path.join(dir, "src/provider/models-snapshot.ts"),
|
||||
`// Auto-generated by build.ts - do not edit\nexport const snapshot = ${modelsData} as const\n`,
|
||||
)
|
||||
console.log("Generated models-snapshot.ts")
|
||||
|
||||
const singleFlag = process.argv.includes("--single")
|
||||
const baselineFlag = process.argv.includes("--baseline")
|
||||
const skipInstall = process.argv.includes("--skip-install")
|
||||
|
||||
@@ -46,6 +46,7 @@ export namespace Flag {
|
||||
export const OPENCODE_EXPERIMENTAL_LSP_TOOL = OPENCODE_EXPERIMENTAL || truthy("OPENCODE_EXPERIMENTAL_LSP_TOOL")
|
||||
export const OPENCODE_DISABLE_FILETIME_CHECK = truthy("OPENCODE_DISABLE_FILETIME_CHECK")
|
||||
export const OPENCODE_EXPERIMENTAL_PLAN_MODE = OPENCODE_EXPERIMENTAL || truthy("OPENCODE_EXPERIMENTAL_PLAN_MODE")
|
||||
export const OPENCODE_MODELS_URL = process.env["OPENCODE_MODELS_URL"]
|
||||
|
||||
function number(key: string) {
|
||||
const value = process.env[key]
|
||||
|
||||
@@ -22,10 +22,6 @@ export namespace Global {
|
||||
cache,
|
||||
config,
|
||||
state,
|
||||
// Allow overriding models.dev URL for offline deployments
|
||||
get modelsDevUrl() {
|
||||
return process.env.OPENCODE_MODELS_URL || "https://models.dev"
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,14 +0,0 @@
|
||||
import { Global } from "../global"
|
||||
|
||||
export async function data() {
|
||||
const path = Bun.env.MODELS_DEV_API_JSON
|
||||
if (path) {
|
||||
const file = Bun.file(path)
|
||||
if (await file.exists()) {
|
||||
return await file.text()
|
||||
}
|
||||
}
|
||||
const url = Global.Path.modelsDevUrl
|
||||
const json = await fetch(`${url}/api.json`).then((x) => x.text())
|
||||
return json
|
||||
}
|
||||
@@ -2,9 +2,16 @@ import { Global } from "../global"
|
||||
import { Log } from "../util/log"
|
||||
import path from "path"
|
||||
import z from "zod"
|
||||
import { data } from "./models-macro" with { type: "macro" }
|
||||
import { Installation } from "../installation"
|
||||
import { Flag } from "../flag/flag"
|
||||
import { lazy } from "@/util/lazy"
|
||||
|
||||
// Try to import bundled snapshot (generated at build time)
|
||||
// Falls back to undefined in dev mode when snapshot doesn't exist
|
||||
/* @ts-ignore */
|
||||
const SNAPSHOT = await import("./models-snapshot")
|
||||
.then((m) => m.snapshot as Record<string, unknown>)
|
||||
.catch(() => undefined)
|
||||
|
||||
export namespace ModelsDev {
|
||||
const log = Log.create({ service: "models.dev" })
|
||||
@@ -76,18 +83,24 @@ export namespace ModelsDev {
|
||||
|
||||
export type Provider = z.infer<typeof Provider>
|
||||
|
||||
export async function get() {
|
||||
refresh()
|
||||
function url() {
|
||||
return Flag.OPENCODE_MODELS_URL || "https://models.dev"
|
||||
}
|
||||
|
||||
export const Data = lazy(async () => {
|
||||
const file = Bun.file(filepath)
|
||||
const result = await file.json().catch(() => {})
|
||||
if (result) return result as Record<string, Provider>
|
||||
if (typeof data === "function") {
|
||||
const json = await data()
|
||||
return JSON.parse(json) as Record<string, Provider>
|
||||
}
|
||||
const url = Global.Path.modelsDevUrl
|
||||
const json = await fetch(`${url}/api.json`).then((x) => x.text())
|
||||
return JSON.parse(json) as Record<string, Provider>
|
||||
if (result) return result
|
||||
if (SNAPSHOT) return SNAPSHOT
|
||||
if (Flag.OPENCODE_DISABLE_MODELS_FETCH) return {}
|
||||
const json = await fetch(`${url()}/api.json`).then((x) => x.text())
|
||||
return JSON.parse(json)
|
||||
})
|
||||
|
||||
export async function get() {
|
||||
refresh()
|
||||
const result = await Data()
|
||||
return result as Record<string, Provider>
|
||||
}
|
||||
|
||||
export async function refresh() {
|
||||
@@ -96,8 +109,7 @@ export namespace ModelsDev {
|
||||
log.info("refreshing", {
|
||||
file,
|
||||
})
|
||||
const url = Global.Path.modelsDevUrl
|
||||
const result = await fetch(`${url}/api.json`, {
|
||||
const result = await fetch(`${url()}/api.json`, {
|
||||
headers: {
|
||||
"User-Agent": Installation.USER_AGENT,
|
||||
},
|
||||
@@ -107,8 +119,18 @@ export namespace ModelsDev {
|
||||
error: e,
|
||||
})
|
||||
})
|
||||
if (result && result.ok) await Bun.write(file, await result.text())
|
||||
if (result && result.ok) {
|
||||
await Bun.write(file, await result.text())
|
||||
ModelsDev.Data.reset()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setInterval(() => ModelsDev.refresh(), 60 * 1000 * 60).unref()
|
||||
if (!Flag.OPENCODE_DISABLE_MODELS_FETCH) {
|
||||
setInterval(
|
||||
async () => {
|
||||
await ModelsDev.refresh()
|
||||
},
|
||||
60 * 1000 * 60,
|
||||
).unref()
|
||||
}
|
||||
|
||||
@@ -5,7 +5,6 @@ import path from "path"
|
||||
import fs from "fs/promises"
|
||||
import fsSync from "fs"
|
||||
import { afterAll } from "bun:test"
|
||||
const { Global } = await import("../src/global")
|
||||
|
||||
const dir = path.join(os.tmpdir(), "opencode-test-data-" + process.pid)
|
||||
await fs.mkdir(dir, { recursive: true })
|
||||
@@ -23,18 +22,10 @@ process.env["XDG_CACHE_HOME"] = path.join(dir, "cache")
|
||||
process.env["XDG_CONFIG_HOME"] = path.join(dir, "config")
|
||||
process.env["XDG_STATE_HOME"] = path.join(dir, "state")
|
||||
|
||||
// Pre-fetch models.json so tests don't need the macro fallback
|
||||
// Also write the cache version file to prevent global/index.ts from clearing the cache
|
||||
// Write the cache version file to prevent global/index.ts from clearing the cache
|
||||
const cacheDir = path.join(dir, "cache", "opencode")
|
||||
await fs.mkdir(cacheDir, { recursive: true })
|
||||
await fs.writeFile(path.join(cacheDir, "version"), "14")
|
||||
const url = Global.Path.modelsDevUrl
|
||||
const response = await fetch(`${url}/api.json`)
|
||||
if (response.ok) {
|
||||
await fs.writeFile(path.join(cacheDir, "models.json"), await response.text())
|
||||
}
|
||||
// Disable models.dev refresh to avoid race conditions during tests
|
||||
process.env["OPENCODE_DISABLE_MODELS_FETCH"] = "true"
|
||||
|
||||
// Clear provider env vars to ensure clean test state
|
||||
delete process.env["ANTHROPIC_API_KEY"]
|
||||
|
||||
Reference in New Issue
Block a user