Skip to content

feat(model): Kimi K3 (1M context) + fix vision-blinding provider config - #143

Merged
cnjack merged 4 commits into
mainfrom
feat/kimi-k3-vision-fixes
Jul 16, 2026
Merged

feat(model): Kimi K3 (1M context) + fix vision-blinding provider config#143
cnjack merged 4 commits into
mainfrom
feat/kimi-k3-vision-fixes

Conversation

@cnjack

@cnjack cnjack commented Jul 16, 2026

Copy link
Copy Markdown
Owner

What

1. Add Kimi K3 to the Kimi For Coding provider (internal/model/registry.go)

  • k3: 1,048,576-token context, image input, tool calls, reasoning on by default — per the official third-party-agents doc.
  • Thinking depth offers only max: the docs state K3 accepts only max today (low/high are "planned"), so ReasoningOptions declares exactly that instead of the standard four levels.
  • K3 takes the provider's Recommended star from kimi-for-coding; the latter stays default-enabled for the Andante tier that cannot call k3 (Moderato+ required).
  • Output limit is unstated in the docs; carries the family's 32768 default pending live confirmation.

2. Fix the provider settings form silently blinding vision models (web/, internal/web/providers.go)

Root cause of "model says it sees no image while the UI shows thumbnails": the provider add/edit form defaulted its vision/thinking switches to false and always submitted them, so saving a provider — even without touching the switches — wrote "vision": false into config, which makes toOpenAIMessage strip every image part.

  • The vision control is removed from the provider form entirely. Image support is per-model metadata (registry modalities / custom-model attachment). Because the update API uses replacement semantics, one save of an affected provider now auto-clears the stale override; hand-edited config values remain honored as an escape hatch.
  • The thinking (enable_thinking kwarg) control survives only for custom providers, as tri-state Default/On/Off where Default omits the field.
  • Provider updates now hot-rebuild the agents of live engines on that provider (rebuildEnginesForProvider, mirroring the MCP-reload path) — previously connection changes needed a restart or model switch to take effect.
  • The chat input's imageSupport is recomputed on every model/provider-list change; it used to be set only at page load, so switching text-only ↔ vision models left the attach button in the wrong state until a reload.

Verification

  • Live endpoint (real key): k3 answers an image question through the OpenAI-compatible path using the exact multipart payload jcode sends; reasoning_effort=max round-trips.
  • Mock endpoint capture: with vision:false the user turn arrives text-only (bug reproduced); after clearing via the new UI — no restart — the same turn arrives as [text, image_url] and no chat_template_kwargs is sent.
  • Browser walkthrough on a dev instance: attach button enables/disables live when switching models; K3 shows the Recommended badge, 1M context, and a Default/max-only effort picker; saving the provider once removes stale vision/thinking keys from config.
  • go test ./internal/model ./internal/web green; pnpm typecheck clean.

Reviewer notes

  • registry_generated.go is intentionally untouched (concurrent regeneration in flight on main); the static kimi-for-coding provider does not exist in models.dev output, so there is no id collision.
  • Backend API still accepts vision for backward compatibility; only the frontend stopped sending it.

🤖 Generated with Claude Code

Summary by CodeRabbit

  • New Features

    • Added support for the official k3 Kimi for Coding model.
    • Provider updates now take effect immediately for active sessions.
    • Image support status now updates automatically when providers, models, or metadata change.
    • Added Default, On, and Off options for thinking on custom providers.
  • Improvements

    • Image support is now determined by model metadata rather than a provider-level override.
    • Removed the provider-level vision override from provider configuration.

cnjack and others added 2 commits July 17, 2026 01:28
Adds the k3 model documented for the coding plan's third-party-agent
setup: 1,048,576-token context (4x the kimi-for-coding window), image
input, and deep reasoning on by default. Per the official docs only
"max" is currently accepted for thinking depth (low/high are documented
as planned but not yet live), so ReasoningOptions offers "max" alone.

k3 takes over the provider's Recommended star from kimi-for-coding as
the flagship; kimi-for-coding stays DefaultEnabled for the lower
Andante tier that cannot call k3 (k3 needs Moderato or above). Output
limit is unstated in the docs, so it carries the family's 32768 default
pending live confirmation.

Verified against the live endpoint with a real key: k3 answers image
questions through the OpenAI-compatible path with the exact multipart
format jcode sends, and reasoning_effort=max round-trips.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The provider add/edit form defaulted its vision/thinking switches to
false and always submitted them, so saving any provider (even without
touching the switches) wrote "vision": false into config. That override
makes chatmodel collapse multimodal messages to text-only — the UI
shows attached image thumbnails while the model receives none of them.
Reproduced end to end against a logging mock endpoint: with the stored
override the user turn arrives text-only; without it the same turn
arrives as [text, image_url].

Fixes, verified in the browser against a live dev instance:

- Remove the vision control from the provider form entirely. Image
  support is per-model metadata (registry modalities / custom-model
  attachment), not a provider connection setting. The update API uses
  replacement semantics, so simply not sending the field means one save
  of an affected provider clears the stale override from config.
  Hand-edited config values are still honored as an escape hatch.
- Keep the thinking (enable_thinking kwarg) control for custom
  providers only, as a tri-state Default/On/Off that omits the field on
  Default instead of forcing an explicit false. Registry providers
  derive everything from models.dev metadata.
- Rebuild the agents of live engines running on a provider after its
  config is updated (rebuildEnginesForProvider), so connection-level
  changes — api_key, base_url, headers, vision, thinking, effort —
  take effect on the next turn instead of after a restart or model
  switch. Mirrors the MCP-reload rebuild path.
- Recompute the chat input's imageSupport whenever the selected model
  or the provider list changes. It was only set from /health at page
  load and from loadModels, so switching from a text-only model to a
  vision model in the picker left the attach button disabled (and the
  reverse allowed attaching to models that cannot see images) until a
  reload.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Jul 16, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@cnjack, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 50 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: f41d22f0-8fd6-4f5b-86b9-bfe4c640ef20

📥 Commits

Reviewing files that changed from the base of the PR and between 715f5f7 and efa4e6a.

📒 Files selected for processing (10)
  • internal/model/registry.go
  • internal/web/engine.go
  • internal/web/providers.go
  • web/src/app/store.ts
  • web/src/components/SettingsDialog.tsx
  • web/src/i18n/locales/en.ts
  • web/src/i18n/locales/ja.ts
  • web/src/i18n/locales/ko.ts
  • web/src/i18n/locales/zh-Hans.ts
  • web/src/i18n/locales/zh-Hant.ts
📝 Walkthrough

Walkthrough

The change adds the k3 Kimi model, rebuilds live agents after provider updates, derives image support from model metadata, and replaces provider-level vision and boolean thinking settings with model metadata and tri-state custom-provider thinking overrides.

Changes

Provider synchronization

Layer / File(s) Summary
Kimi model metadata
internal/model/registry.go
Adds the k3 model definition and updates recommendation metadata for kimi-for-coding.
Live provider agent rebuilding
internal/web/providers.go
Rebuilds agents for matching live engines after provider configuration updates, retaining existing agents when rebuilding fails.
Provider settings and image capability state
web/src/components/SettingsDialog.tsx, web/src/lib/api.ts, web/src/app/store.ts
Adds tri-state custom-provider thinking controls, removes vision overrides from provider payloads, and derives image support from selected model metadata.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Sequence Diagram(s)

sequenceDiagram
  participant SettingsDialog
  participant ProviderAPI
  participant handleUpdateProvider
  participant LiveEngine
  participant Agent
  SettingsDialog->>ProviderAPI: save provider settings
  ProviderAPI->>handleUpdateProvider: update provider
  handleUpdateProvider->>LiveEngine: rebuild matching engines
  LiveEngine->>Agent: create replacement agent
  Agent-->>LiveEngine: updated agent
Loading

Possibly related PRs

  • cnjack/jcode#46: Updates related model recommendation and default-enabled handling.
  • cnjack/jcode#131: Also applies provider updates to running server behavior.
  • cnjack/jcode#142: Introduces the static registry changes extended here for Kimi models.
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly matches the main changes: adding Kimi K3 and fixing provider vision/config handling.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/kimi-k3-vision-fixes

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
web/src/app/store.ts (1)

474-506: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Clear stale image support when loaded metadata has no matching model.

After providers are loaded, setProvider can produce a missing provider/model pair and retain the previous model’s capability indefinitely. Preserve the /health fallback only while providers is empty; otherwise default unmatched selections to false.

Proposed fix
 function syncImageSupport(s: ModelState) {
   const cur = s.providers
     .find((p) => p.id === s.providerName)
     ?.models.find((m) => m.id === s.modelName)
-  if (cur) s.imageSupport = !!cur.image_support
+  if (cur) {
+    s.imageSupport = !!cur.image_support
+  } else if (s.providers.length > 0) {
+    s.imageSupport = false
+  }
 }
🤖 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 `@web/src/app/store.ts` around lines 474 - 506, Update syncImageSupport in the
model slice so unmatched provider/model selections set imageSupport to false
once providers metadata is loaded; retain the existing /health fallback only
when s.providers is empty. Ensure setProvider, setModel, and setProviders
continue using this helper.
🤖 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 `@internal/web/providers.go`:
- Line 660: Update Server.rebuildEnginesForProvider to accept context.Context as
its first parameter, then propagate that context through the agent-creation
calls within the rebuild flow. Update every caller to pass its active context so
cancellation and shutdown can interrupt the synchronous rebuild operation.
- Around line 683-692: Update the agent refresh flow around eng.modelSnapshot,
eng.createAgent, and eng.setAgent to recheck the captured provider and model
while holding emu after rebuilding. Install the new agent only when the
provider/model snapshot still matches; otherwise skip the stale refresh.

In `@web/src/components/SettingsDialog.tsx`:
- Around line 1222-1224: Update the tri-state option labels in SettingsDialog to
use the existing react-i18next translation function t(...) instead of hardcoded
“Default”, “On”, and “Off” text. Add or reuse appropriate translation keys while
preserving the option values and surrounding provider-settings behavior.

---

Outside diff comments:
In `@web/src/app/store.ts`:
- Around line 474-506: Update syncImageSupport in the model slice so unmatched
provider/model selections set imageSupport to false once providers metadata is
loaded; retain the existing /health fallback only when s.providers is empty.
Ensure setProvider, setModel, and setProviders continue using this helper.
🪄 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

Run ID: e14f7763-df03-4a00-96b7-60f9e541aa6c

📥 Commits

Reviewing files that changed from the base of the PR and between 1c5f3d7 and 715f5f7.

📒 Files selected for processing (5)
  • internal/model/registry.go
  • internal/web/providers.go
  • web/src/app/store.ts
  • web/src/components/SettingsDialog.tsx
  • web/src/lib/api.ts

Comment thread internal/web/providers.go
Comment thread internal/web/providers.go Outdated
Comment thread web/src/components/SettingsDialog.tsx Outdated
…llback

- Guard the provider-update agent rebuild against a concurrent model
  switch: setAgentIfModel installs the rebuilt agent only if the engine
  is still on the same provider/model, checked under emu, so a switch
  landing mid-rebuild is never clobbered with a stale agent.
- Localize the custom-provider thinking select (Default/On/Off) via new
  common.default/on/off keys in all five locales.
- syncImageSupport: once the provider list is loaded, an unmatched
  provider/model pair resets imageSupport to false instead of carrying
  the previous model's capability forward; the /health seed only
  survives while providers are still empty.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@cnjack
cnjack merged commit 7822b25 into main Jul 16, 2026
3 checks passed
@cnjack
cnjack deleted the feat/kimi-k3-vision-fixes branch July 16, 2026 17:42
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant