Expose standalone tool healing utilities#5583
Conversation
|
Warning You have reached your daily quota limit. Please wait up to 24 hours and I will start processing your requests again! |
59e03f6 to
f95db43
Compare
|
Supersedes #5571. The branch has been rebased onto current |
08e1efc to
11288f4
Compare
11288f4 to
6d4e358
Compare
6d4e358 to
c5c7d87
Compare
|
Pushed a follow-up commit on top of your branch addressing the review:
One thing worth calling out in the description: I ran the new module against the previous inline parser in Local run (Python 3.14, no torch / transformers / structlog): all 11 tests pass. |
|
Thanks! |
798f5ef to
bc38756
Compare
|
Reworked and squashed the branch to a single commit. Dropping the new top-level The new home is What this commit does:
Final diff: 3 files, +485 / -136. PR is single-commit and mergeable. |
Move the inline tool-call XML parser and stripper out of studio/backend/core/inference/llama_cpp.py into a new studio/backend/core/tool_healing.py so external inference servers (llama-server wrappers, llama-swap, custom shims) can reuse the same logic without importing the inference orchestrator, structlog, httpx, or anything from torch / transformers / unsloth. Closes unslothai#5502. What this PR does: - New file studio/backend/core/tool_healing.py contains the regex constants (_TOOL_CLOSED_PATS, _TOOL_ALL_PATS, _TC_JSON_START_RE, _TC_FUNC_START_RE, _TC_END_TAG_RE, _TC_FUNC_CLOSE_RE, _TC_PARAM_START_RE, _TC_PARAM_CLOSE_RE), parse_tool_calls_from_text, and strip_tool_call_markup. The regexes and function bodies are byte-for-byte the same as the previous inline implementation in llama_cpp.py; only the @staticmethod decorator and the closure-only `if not auto_heal_tool_calls: return text` short-circuit are dropped (the latter stays in the caller as a fast path when healing is off). - studio/backend/core/inference/llama_cpp.py now imports the regexes and helpers from .tool_healing. LlamaCppBackend._parse_tool_calls_from_text becomes a one-line delegate; the _strip_tool_markup closure keeps the auto_heal_tool_calls fast path and delegates the work. - Helper module imports cleanly without torch, transformers, structlog, httpx, or numpy. studio.backend.core itself is already stdlib-only at import time (lazy __getattr__), so `from studio.backend.core.tool_healing import parse_tool_calls_from_text, strip_tool_call_markup` is the lightweight import path issue unslothai#5502 asked for. No behaviour change for existing Studio paths. parse_tool_calls_from_text and strip_tool_call_markup produce the same OpenAI-shape output the old inline code produced for every input. Co-authored-by: Daniel Han <danielhanchen@gmail.com>
c43537f to
1e75cfb
Compare
|
Thanks a lot! I removed |
…nslothai#5583) Move the inline tool-call XML parser and stripper out of studio/backend/core/inference/llama_cpp.py into a new studio/backend/core/tool_healing.py so external inference servers (llama-server wrappers, llama-swap, custom shims) can reuse the same logic without importing the inference orchestrator, structlog, httpx, or anything from torch / transformers / unsloth. Closes unslothai#5502. What this PR does: - New file studio/backend/core/tool_healing.py contains the regex constants (_TOOL_CLOSED_PATS, _TOOL_ALL_PATS, _TC_JSON_START_RE, _TC_FUNC_START_RE, _TC_END_TAG_RE, _TC_FUNC_CLOSE_RE, _TC_PARAM_START_RE, _TC_PARAM_CLOSE_RE), parse_tool_calls_from_text, and strip_tool_call_markup. The regexes and function bodies are byte-for-byte the same as the previous inline implementation in llama_cpp.py; only the @staticmethod decorator and the closure-only `if not auto_heal_tool_calls: return text` short-circuit are dropped (the latter stays in the caller as a fast path when healing is off). - studio/backend/core/inference/llama_cpp.py now imports the regexes and helpers from .tool_healing. LlamaCppBackend._parse_tool_calls_from_text becomes a one-line delegate; the _strip_tool_markup closure keeps the auto_heal_tool_calls fast path and delegates the work. - Helper module imports cleanly without torch, transformers, structlog, httpx, or numpy. studio.backend.core itself is already stdlib-only at import time (lazy __getattr__), so `from studio.backend.core.tool_healing import parse_tool_calls_from_text, strip_tool_call_markup` is the lightweight import path issue unslothai#5502 asked for. No behaviour change for existing Studio paths. parse_tool_calls_from_text and strip_tool_call_markup produce the same OpenAI-shape output the old inline code produced for every input. Co-authored-by: Daniel Han <danielhanchen@gmail.com>
What changed
unsloth_core.tool_healingmodule for parsing and stripping model-emitted tool-call markup without importing the training stack.unsloth.core.tool_healingfor existing Unsloth import paths.studio/backendremains importable when launched as a standalone tree without the repo root onPYTHONPATH.DEFAULT_MODELS_GGUF[0](unsloth/Qwen3.6-27B-MTP-GGUF).Why
External inference servers can reuse tool healing without importing torch, transformers, or the full Unsloth training runtime.
Closes #5502
Tests
python -m pytest tests/python/test_tool_healing_public_api.py -qpython - <<'PY' ... assert EXPECTED_DEFAULT == DEFAULT_MODELS_GGUF[0] ... PYpython -m py_compile unsloth_core/tool_healing.py unsloth_core/__init__.py unsloth/core/tool_healing.py unsloth/core/__init__.py studio/backend/core/tool_healing.py studio/backend/core/inference/llama_cpp.py tests/python/test_tool_healing_public_api.py tests/studio/playwright_chat_ui.py