Skip to content
Open
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions packages/opencode/src/auth/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ export namespace Auth {
.object({
type: z.literal("api"),
key: z.string(),
customBaseUrl: z.string().optional(),
})
.meta({ ref: "ApiAuth" })

Expand Down
18 changes: 18 additions & 0 deletions packages/opencode/src/cli/cmd/auth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -253,6 +253,23 @@ export const AuthLoginCommand = cmd({
prompts.log.info("You can create an api key at https://vercel.link/ai-gateway-token")
}

let customBaseUrl: string | undefined
if (provider === "cloudflare-workers-ai") {

if(!providers[provider].api) {
UI.error("Cloudflare API URL not found")
return
}

const accountIdInput = await prompts.text({
message: "Enter your Cloudflare Account ID",
validate: (x) => (x && x.length > 0 ? undefined : "Required"),
})
if (prompts.isCancel(accountIdInput)) throw new UI.CancelledError()

customBaseUrl = providers[provider].api?.replace("{CLOUDFLARE_ACCOUNT_ID}", accountIdInput)
}

const key = await prompts.password({
message: "Enter your API key",
validate: (x) => (x && x.length > 0 ? undefined : "Required"),
Expand All @@ -261,6 +278,7 @@ export const AuthLoginCommand = cmd({
await Auth.set(provider, {
type: "api",
key,
...(customBaseUrl && { customBaseUrl }),
})

prompts.outro("Done")
Expand Down
25 changes: 21 additions & 4 deletions packages/opencode/src/provider/provider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ export namespace Provider {

type CustomLoader = (
provider: ModelsDev.Provider,
api?: string,
auth?: Auth.Info,
) => Promise<{
autoload: boolean
getModel?: (sdk: any, modelID: string) => Promise<any>
Expand Down Expand Up @@ -143,6 +143,18 @@ export namespace Provider {
},
}
},
"cloudflare-workers-ai": async (_provider, auth) => {
if (!auth || auth.type !== "api" || !auth.customBaseUrl) {
return { autoload: false, options: {} }
}

return {
autoload: true,
options: {
baseURL: auth.customBaseUrl,
},
}
},
}

const state = Instance.state(async () => {
Expand Down Expand Up @@ -256,18 +268,23 @@ export namespace Provider {
)
}

// load apikeys
// load apikeys and customBaseUrl
for (const [providerID, provider] of Object.entries(await Auth.all())) {
if (disabled.has(providerID)) continue
if (provider.type === "api") {
mergeProvider(providerID, { apiKey: provider.key }, "api")
const options: Record<string, any> = { apiKey: provider.key }
if (provider.customBaseUrl) {
options["baseURL"] = provider.customBaseUrl
}
mergeProvider(providerID, options, "api")
}
}

// load custom
for (const [providerID, fn] of Object.entries(CUSTOM_LOADERS)) {
if (disabled.has(providerID)) continue
const result = await fn(database[providerID])
const auth = await Auth.get(providerID)
const result = await fn(database[providerID], auth)
if (result && (result.autoload || providers[providerID])) {
mergeProvider(providerID, result.options ?? {}, "custom", result.getModel)
}
Expand Down
Loading