Add a custom providerto opencode
opencode can talk to any endpoint that speaks the OpenAI chat format. This page goes through the provider block field by field, using this API as the example, and lists the mistakes that most often leave a model missing from /models.
Where the file goes
opencode.jsonat the root of a project applies to that project..opencode/opencode.jsoninside a project does the same and wins over the file at the root.~/.config/opencode/opencode.jsonapplies to every project, and a project file overrides it.
Both .json and .jsonc are read, so comments are allowed if you name the file opencode.jsonc.
A minimal block
{
"$schema": "https://opencode.ai/config.json",
"provider": {
"uncensored-opencode": {
"npm": "@ai-sdk/openai-compatible",
"name": "Uncensored Opencode",
"options": {
"baseURL": "https://uncensoredopencode.com/v1",
"apiKey": "{env:UNCENSORED_OPENCODE_API_KEY}"
},
"models": {
"glm-5.3-flash-uncensored": {
"name": "GLM 5.3 Flash Uncensored",
"tool_call": true,
"reasoning": true,
"attachment": true,
"limit": { "context": 1048576, "output": 32000 }
}
}
}
},
"model": "uncensored-opencode/glm-5.3-flash-uncensored"
}Field by field
- The key under
provider, hereuncensored-opencode, is the provider id. It is the part before the slash whenever you name a model, as inuncensored-opencode/glm-5.3-flash-uncensored. npmpicks the adapter. Use@ai-sdk/openai-compatiblefor an endpoint that serves/v1/chat/completions.nameis what the provider is called in the/modelslist.options.baseURLis the endpoint up to and including/v1, with no trailing slash and without/chat/completions.options.apiKeyis the key. Write{env:UNCENSORED_OPENCODE_API_KEY}to read it from an environment variable or{file:path}to read it from a file, so the key itself is never in the config.modelsis a map. Each key is the exact model id the endpoint expects, and opencode only offers the models you list.limit.contextandlimit.outputare token limits. If you give a limit, give both.tool_call,reasoningandattachmentsay what the model can do: call tools, think before answering, and take images.
Check it loaded
opencode models uncensored-opencodeThat prints one line per model, in the form uncensored-opencode/glm-5.3-flash-uncensored. If it prints nothing, opencode did not read your block.
Mistakes that hide a model
- The file is valid JSON but in the wrong place. Run opencode from the folder that holds
opencode.json, or use the global file. - The model id is close but not exact. Ids are case sensitive and the endpoint lists the real ones at
https://uncensoredopencode.com/v1/models. baseURLends in/chat/completions. opencode adds that itself, so the request goes to a path that does not exist.- The environment variable is not set in the shell that started opencode. An unset variable becomes an empty key and the endpoint answers 401.
- The top-level
modelnames a model that is not in themodelsmap. limithas a context figure but no output figure.
Every model on this API
The opencode page has the block with all 7 models filled in.
| Model | Build | Context | Tools | Images | Per million tokens |
|---|---|---|---|---|---|
GLM 5.3 Flashglm-5.3-flash-uncensored | Uncensored | 1M tokens | Yes | Yes | $0.30 in / $1.00 out |
Kimi K3.1 Prokimi-k3.1-pro-uncensored | Abliterated | 1M tokens | Yes | Yes | $7.50 in / $37.50 out |
GLM 5.3glm-5.3-uncensored | Uncensored | 1M tokens | Yes | No | $2.00 in / $5.00 out |
DeepSeek V4.1 Flash 1017deepseek-v4.1-flash-1017-uncensored | Abliterated | 1M tokens | Yes | Yes | $1.25 in / $2.50 out |
MiMo V2.6 Flashmimo-v2.6-flash-uncensored | Abliterated | 1M tokens | Yes | Yes | $1.00 in / $2.00 out |
Qwen3.8 27Bqwen3.8-27b-uncensored | Uncensored | 1M tokens | Yes | Yes | $1.50 in / $5.00 out |
GLM 5.3 Flash Cyberglm-5.3-flash-cyber | Security-tuned | 1M tokens | Yes | Yes | On the models page |
Questions
Can I list models the endpoint does not serve?
You can write them, and opencode will show them, but the first request fails with an unknown model error. List only ids the endpoint returns from /v1/models.
Does a custom provider replace the built-in ones?
No. It sits beside them. Every provider you have configured appears in /models.
Do I have to set a limit?
No, but without one opencode assumes 200,000 tokens of context and 32,000 of output for a model it does not know. For a model with a million tokens of context that means compacting five times sooner than necessary.