Skip to content

fix(doctor): probe VLM Function-Calling support in check_vlm (#3066)#3088

Open
chethanuk wants to merge 3 commits into
volcengine:mainfrom
chethanuk:fix/issue-3066-doctor-vlm-function-calling-check
Open

fix(doctor): probe VLM Function-Calling support in check_vlm (#3066)#3088
chethanuk wants to merge 3 commits into
volcengine:mainfrom
chethanuk:fix/issue-3066-doctor-vlm-function-calling-check

Conversation

@chethanuk

Copy link
Copy Markdown
Contributor

Description

openviking-server doctor's VLM check (check_vlm()) previously only validated that config fields were present (provider, model, api_key) — it made no API call, so it could not detect whether the configured model actually supports Function Calling (tool use). A model without Function Calling therefore passed doctor all-green, then failed only at real tool-call time with 400 code 20037 "Function call is not supported for this model.".

This PR folds a live Function-Calling probe into check_vlm(), mirroring how check_embedding() already probes the embedder. User-facing effect: doctor now emits a WARN (with a Fix: line) when the configured VLM lacks Function Calling, surfacing the gap before it breaks the bot adapter (--with-bot) and session working-memory/extraction — both of which require tool calls. It is a WARN rather than a hard failure because pure parse/retrieval deployments never use tools, so a Function-Calling-less model is valid for them; exit code stays 0 on warnings.

Related Issue

Fixes #3066

Type of Change

  • Bug fix (non-breaking change that fixes an issue)
  • New feature (non-breaking change that adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Documentation update
  • Refactoring (no functional changes)
  • Performance improvement
  • Test update

Changes Made

  • New _probe_vlm_function_calling(vlm_config) in openviking_cli/doctor.py: sends one trivial tool-call request (a 1-property function tool + "ping") through the same VLMConfig.get_completion_async(..., tools=..., tool_choice="auto") path the bot adapter uses, bounded by asyncio.wait_for(timeout=10.0) — the exact mechanism _probe_embedding_provider uses. Returns tri-state CheckStatus.
  • check_vlm() wiring: the final real-provider return True, ... now calls the probe and returns its tuple. The codex-oauth and ollama-via-litellm early-return paths are left untouched (codex auth is already verified live; ollama Function-Calling support varies by local model).
  • WARN, not fail: a detected missing capability (_fc_unsupported_warn) and any transient/unverifiable outcome (timeout, connection error) both return warn with an actionable Fix: line — never a hard fail — so retrieval/parse-only deployments are not blocked. A transient outage is reported as "probe could not complete" and is never mislabeled as a Function-Calling verdict.
  • litellm registry short-circuit: on the non-ollama litellm backend path only, a best-effort litellm.supports_function_calling(model) lookup returns the WARN without spending a live request when it gives an explicit False; True, unknown-model, or any exception falls through to the live probe. No new dependency — litellm is already a VLM backend here.
  • Tests (tests/cli/test_doctor.py): added table-driven probe coverage — probe pass, the faithful 20037 repro, phrase-only Function-Calling detection, timeout/other-error WARN, fold-into-check_vlm, config-fail skips the probe, run_doctor WARN formatting + exit 0, codex/ollama paths unchanged, litellm registry prefilter, and a transient-error-not-mislabeled assertion. Existing TestCheckVlm/TestRunDoctor pass tests now stub the probe, mirroring the embedding-probe stubbing.

Testing

  • I have added tests that prove my fix is effective or that my feature works

  • New and existing unit tests pass locally with my changes

  • I have tested this on the following platforms:

    • Linux
    • macOS
    • Windows
  • .venv/bin/python -m pytest tests/cli/test_doctor.py70 passed

  • ruff check → clean

  • mypy0 net-new errors (repo has ~1000 pre-existing, non-blocking)

Checklist

  • My code follows the project's coding style
  • I have performed a self-review of my code
  • I have commented my code, particularly in hard-to-understand areas
  • My changes generate no new warnings

Additional Notes

Probe decision flow (real-provider api_key path):

flowchart TD
    A[check_vlm reaches real-provider api_key path] --> B{provider == litellm?}
    B -- yes --> C{supports_function_calling == False?}
    C -- yes --> W[WARN: no Function Calling]
    C -- "True / unknown / error" --> P[live probe]
    B -- no --> P
    P --> D{tool-call request outcome}
    D -- success --> OK[pass: function-calling ok]
    D -- "20037 / 'function call' + 'not supported'" --> W
    D -- "timeout / other error" --> T[WARN: probe could not complete]
Loading

chethanuk added 3 commits July 8, 2026 21:14
…ine#3066)

check_vlm now folds in a live tool-call probe (_probe_vlm_function_calling)
that verifies the configured model supports Function Calling, reported as a
WARN (not a hard fail) since parse/retrieval deployments never use tools. On
the non-ollama litellm path, a best-effort litellm registry lookup
short-circuits the live request when it returns an explicit False.

Refs volcengine#3066
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Backlog

Development

Successfully merging this pull request may close these issues.

[Bug]: openviking-server doctor VLM 检查未验证 Function Calling 支持,导致 Agent 运行时才报错

1 participant