Skip to content

fix(skill-scan): recover missing tool-call args during discovery - #648

Open
li872 wants to merge 1 commit into
Tencent:mainfrom
li872:cursor/fix-skill-scan-tool-args-a83f
Open

fix(skill-scan): recover missing tool-call args during discovery#648
li872 wants to merge 1 commit into
Tencent:mainfrom
li872:cursor/fix-skill-scan-tool-args-a83f

Conversation

@li872

@li872 li872 commented Sep 12, 2026

Copy link
Copy Markdown

Summary

Skill-scan info collection (AIG three-stage mode) often finished with an empty report after models such as qwen3-7 / glm5-2 / qwen3.7-plus emitted tool calls that the parser only partially understood. The dispatcher then called tool_func(**{}), which raised TypeError: missing 1 required positional argument: 'thought' / 'command' / 'path'. The agent treated the tools as broken, skipped the real project tree, and finished with 0 findings.

Root cause (parser + dispatcher, not the filesystem):

  1. Parser (skill_scan/utils/parse.py) only extracted parameter tags inside function tags. Qwen/GLM-style JSON bodies, child tags, inline attributes, leftover free text, and tool_call wrappers produced a tool name with an empty args dict.
  2. Dispatcher (skill_scan/tools/dispatcher.py) forwarded those kwargs unchanged. Missing required Python parameters became a raw TypeError. Legacy execute_shell (from mcp-scan prompts / model memory) is not a skill-scan tool, so listing attempts never recovered to dir_tree/ls.
  3. Stage 1 did not inject the on-disk repo tree (stage 2 already did), so a failed discovery tool sequence had no fallback file listing.

Fix (minimal, recoverable):

  • Resilient parsing of the issue-shaped payloads plus common Qwen/GLM wrappers.
  • call_compat normalizes aliases (path to file_path, cmd to command, list_dir to ls), defaults dir_tree/ls path to the uploaded project folder, remaps listing execute_shell calls onto dir_tree, and otherwise returns a retryable error that names the missing argument and shows the correct function/parameter format.
  • Info Collection now injects the real directory tree as a safety net.

No shell execution was added. Arbitrary execute_shell commands are rejected with a clear “use dir_tree/ls/read_file/grep” error.

Type of change

  • Bug fix
  • New feature
  • Fingerprint rule (data/fingerprints/)
  • Vulnerability rule (data/vuln/)
  • MCP security plugin (data/mcp/)
  • Jailbreak evaluation dataset (data/eval/)
  • Documentation
  • Other (please describe)

How was this tested?

Run:

cd skill-scan
python3 -m pytest pytests/test_tool_call_resilience.py -v
python3 -m pytest pytests/ -v

Result: 47 passed.

Regression tests feed the #629 shapes (missing thought, missing command, dir_tree with no path / child-tag path / Qwen tool_call JSON) and assert the scanner recovers a real SKILL.md tree or returns a retryable error — never a TypeError / empty discovery.

Tests

  • skill-scan/pytests/test_tool_call_resilience.py (24 new cases)
  • Full skill-scan/pytests/ suite: 47 passed

Demo

Passing regression run:

https://raw.githubusercontent.com/li872/AI-Infra-Guard/cursor/fix-skill-scan-tool-args-a83f/docs/pr-629-demo/pytest-issue-629.log

Related issue

Fixes #629

Checklist

  • go build ./... succeeds locally (Go sources unchanged)
  • I followed the existing file/rule format conventions for this contribution type
  • I have not introduced hardcoded secrets or credentials

Malformed LLM tool calls (missing thought/command/path, legacy
execute_shell, Qwen/GLM wrappers) no longer abort skill-scan info
collection with an empty report.

Fixes Tencent#629
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.

更新版本后,多次出现列目录失败导致skill扫描失败问题,上机后查看目录正常

1 participant