feat: add DeepSeek provider support#183
Conversation
📝 WalkthroughWalkthroughDeepSeek is added as an OpenAI-compatible provider with setup defaults, model capabilities, gateway routing, smoke-probe support, CLI examples, tests, and onboarding documentation. ChangesDeepSeek provider support
Estimated code review effort: 3 (Moderate) | ~20 minutes Sequence Diagram(s)sequenceDiagram
participant SetupCommand
participant GatewaySetupProfileFactory
participant LlmClientFactory
participant DeepSeekAPI
SetupCommand->>GatewaySetupProfileFactory: configure deepseek profile
GatewaySetupProfileFactory->>LlmClientFactory: create OpenAI-compatible client
LlmClientFactory->>DeepSeekAPI: send authorized chat completion
DeepSeekAPI-->>LlmClientFactory: return model response
Suggested reviewers: 🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
👀 Human Input Needed → Pair Review Briefing |
There was a problem hiding this comment.
Pull request overview
Adds first-class DeepSeek support as a named OpenAI-compatible provider across setup, validation (model doctor + smoke probes), runtime client creation, tests, and user-facing docs so first-run configuration works with DEEPSEEK_API_KEY and sensible defaults.
Changes:
- Introduce
deepseekprovider defaults (endpoint, default model, capabilities) and generate a named DeepSeek model profile during setup. - Route DeepSeek through runtime chat/embedding client creation and provider smoke probing, and surface capabilities in model doctor evaluation.
- Update CLI help + docs and add focused regression tests for setup, model doctor, transport, and smoke probe behavior.
Reviewed changes
Copilot reviewed 13 out of 13 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| src/OpenClaw.Tests/SetupCommandTests.cs | Adds non-interactive setup test ensuring DeepSeek config + env example are generated correctly. |
| src/OpenClaw.Tests/ModelProfileSelectionTests.cs | Validates model doctor derives DeepSeek capabilities from the named provider defaults. |
| src/OpenClaw.Tests/LlmClientFactoryTests.cs | Adds DeepSeek transport + smoke probe tests and extends the test server routing. |
| src/OpenClaw.Gateway/Extensions/LlmClientFactory.cs | Wires deepseek into OpenAI-compatible chat + embedding client creation with a default endpoint. |
| src/OpenClaw.Core/Validation/ProviderSmokeProbe.cs | Adds DeepSeek to OpenAI-style probe path construction. |
| src/OpenClaw.Core/Validation/ModelDoctorEvaluator.cs | Uses DeepSeek named-provider capabilities when guessing provider capability defaults. |
| src/OpenClaw.Core/Setup/GatewaySetupProfileFactory.cs | Generates a DeepSeek-backed model profile (deepseek-default) during setup. |
| src/OpenClaw.Core/Setup/DeepSeekProviderDefaults.cs | New provider defaults + capability profile for DeepSeek. |
| src/OpenClaw.Cli/SetupCommand.cs | Defaults DeepSeek model + API key env reference (env:DEEPSEEK_API_KEY) during setup prompts/args. |
| src/OpenClaw.Cli/Program.cs | Updates CLI usage examples to include DeepSeek. |
| README.md | Documents DeepSeek as a native provider option and adds setup guidance + example command. |
| docs/QUICKSTART.md | Adds DeepSeek-specific quickstart flow and env var usage. |
| docs/GETTING_STARTED.md | Adds DeepSeek setup guidance with DEEPSEEK_API_KEY and named provider usage. |
Comments suppressed due to low confidence (1)
src/OpenClaw.Tests/LlmClientFactoryTests.cs:259
- The test server now accepts both /v1/chat/completions and /chat/completions, but it doesn’t record which route was actually hit. That makes the new DeepSeek smoke-probe test unable to verify that DeepSeek uses the intended canonical /chat/completions path (and could mask regressions). Capture the request path so callers can assert it.
IResult HandleChatCompletions(HttpContext ctx)
{
headers.Clear();
foreach (var header in ctx.Request.Headers)
headers[header.Key] = header.Value.ToString();
| Assert.Equal(SetupCheckStates.Pass, result.Status); | ||
| Assert.Equal("Bearer deepseek-token", server.Headers["Authorization"]); | ||
| } |
| new ModelProfileConfig | ||
| { | ||
| Id = "deepseek-default", | ||
| Provider = DeepSeekProviderDefaults.ProviderId, |
There was a problem hiding this comment.
Using deepseek here still fails config validation whenever plugin-backed providers are disabled, because ConfigValidator.BuiltInLlmProviders was not updated and public setup turns Plugins.Enabled off before validation. That means openclaw setup --profile public --provider deepseek rejects both Llm.Provider and this generated model profile as unsupported.
Severity: medium
🤖 Was this useful? React with 👍 or 👎
| }; | ||
| } | ||
|
|
||
| if (provider == DeepSeekProviderDefaults.ProviderId) |
There was a problem hiding this comment.
This teaches model doctor that an implicit deepseek profile is tool-capable, but the runtime ConfiguredModelProfileRegistry.GuessCapabilities still has no deepseek case. A config that sets OpenClaw:Llm:Provider=deepseek without explicit Models.Profiles will pass doctor with DeepSeek capabilities but runtime registers the default profile as lacking tools and structured outputs.
Severity: medium
🤖 Was this useful? React with 👍 or 👎
| "--workspace", workspace, | ||
| "--provider", "deepseek" | ||
| ], | ||
| new StringReader(string.Empty), |
| var root = CreateTempRoot(); | ||
| try | ||
| { | ||
| var configPath = Path.Combine(root, "config", "openclaw.deepseek.json"); |
| try | ||
| { | ||
| var configPath = Path.Combine(root, "config", "openclaw.deepseek.json"); | ||
| var workspace = Path.Combine(root, "workspace"); |
| Assert.True(profile.GetProperty("capabilities").GetProperty("supportsTools").GetBoolean()); | ||
| Assert.True(profile.GetProperty("capabilities").GetProperty("supportsReasoningEffort").GetBoolean()); | ||
|
|
||
| var envExample = await File.ReadAllTextAsync(Path.Combine(root, "config", "openclaw.deepseek.env.example")); |
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@docs/QUICKSTART.md`:
- Line 221: Update the compound modifier in the DeepSeek setup description to
use “DeepSeek-hosted setup,” preserving the rest of the sentence unchanged.
In `@README.md`:
- Line 85: Update the provider/model setup instruction in the README so entering
a provider key applies only to the hosted DeepSeek provider; describe Ollama and
Embedded separately as local choices without implying they require a key.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro Plus
Run ID: e1b2464a-b1d1-4ded-881b-307e9941dbe5
📒 Files selected for processing (13)
README.mddocs/GETTING_STARTED.mddocs/QUICKSTART.mdsrc/OpenClaw.Cli/Program.cssrc/OpenClaw.Cli/SetupCommand.cssrc/OpenClaw.Core/Setup/DeepSeekProviderDefaults.cssrc/OpenClaw.Core/Setup/GatewaySetupProfileFactory.cssrc/OpenClaw.Core/Validation/ModelDoctorEvaluator.cssrc/OpenClaw.Core/Validation/ProviderSmokeProbe.cssrc/OpenClaw.Gateway/Extensions/LlmClientFactory.cssrc/OpenClaw.Tests/LlmClientFactoryTests.cssrc/OpenClaw.Tests/ModelProfileSelectionTests.cssrc/OpenClaw.Tests/SetupCommandTests.cs
|
|
||
| Plain `openclaw run "hello"` requests work as prompt-only chat with non-tool Ollama profiles when no explicit tool preset is requested. Tool-heavy routes and explicit presets still need a tool-capable model profile or configured fallback. The doctor now warns when an Ollama profile still points at `/v1` or when a local agentic profile is missing a deterministic fallback. | ||
|
|
||
| For a DeepSeek hosted setup, use the named provider. It configures the OpenAI-compatible DeepSeek endpoint automatically and defaults to `deepseek-v4-flash`: |
There was a problem hiding this comment.
📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win
Hyphenate the compound modifier.
Use “DeepSeek-hosted setup” for clearer grammar.
🧰 Tools
🪛 LanguageTool
[grammar] ~221-~221: Use a hyphen to join words.
Context: ... deterministic fallback. For a DeepSeek hosted setup, use the named provider. It...
(QB_NEW_EN_HYPHEN)
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@docs/QUICKSTART.md` at line 221, Update the compound modifier in the DeepSeek
setup description to use “DeepSeek-hosted setup,” preserving the rest of the
sentence unchanged.
Source: Linters/SAST tools
| 2. Launch Companion from the `companion` folder. | ||
| 3. Open the **Setup** tab. | ||
| 4. Choose a provider/model and enter the provider key, choose Ollama for a local model server, or choose Embedded for an OpenClaw-managed local model such as Gemma 4. | ||
| 4. Choose a provider/model and enter the provider key, choose DeepSeek for the hosted OpenAI-compatible DeepSeek API, choose Ollama for a local model server, or choose Embedded for an OpenClaw-managed local model such as Gemma 4. |
There was a problem hiding this comment.
📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win
Clarify the provider-specific key requirement.
This sentence can imply that Ollama and Embedded also require entering a provider key. Separate the hosted DeepSeek instruction from the local-provider choices.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@README.md` at line 85, Update the provider/model setup instruction in the
README so entering a provider key applies only to the hosted DeepSeek provider;
describe Ollama and Embedded separately as local choices without implying they
require a key.
Summary
Closes #182
Validation
SetupCommandTests|FullyQualifiedNameLlmClientFactoryTests|FullyQualifiedName~ModelProfileSelectionTests"Summary by CodeRabbit
New Features
DEEPSEEK_API_KEY, automatic endpoint configuration, and defaultdeepseek-v4-flashmodel selection.deepseek-v4-promodel.Bug Fixes