Skip to content

feat(execution): cross-platform command execution via ShellPlatform abstraction#7

Merged
genni613 merged 10 commits into
masterfrom
feat/cross-platform-command
Apr 15, 2026
Merged

feat(execution): cross-platform command execution via ShellPlatform abstraction#7
genni613 merged 10 commits into
masterfrom
feat/cross-platform-command

Conversation

@TuYv

@TuYv TuYv commented Apr 15, 2026

Copy link
Copy Markdown
Owner

概要

  • 新增 ShellPlatform sealed class,将所有平台差异封装到单一抽象:buildProcess、extractBaseCommand、hasPathsOutsideWorkspace、toolDefinition、defaultWhitelist
  • Unix 使用 sh -c + run_command 工具,Windows 使用 powershell -NoProfile -Command + run_powershell 工具,AI 收到平台对应的工具定义
  • hasPathsOutsideWorkspace 修复三处安全问题:trailing slash 误判、/dev/null 误拦截、路径前缀边界绕过(/project-evil 冒充 /project)

变更文件

┌──────────────────────────────────────┬────────────────────────────────────────────────┐
│ 文件 │ 变更说明 │
├──────────────────────────────────────┼────────────────────────────────────────────────┤
│ execution/ShellPlatform.kt │ 新增,封装 Unix/Windows 平台差异 │
├──────────────────────────────────────┼────────────────────────────────────────────────┤
│ execution/CommandExecutionService.kt │ 委托给 ShellPlatform.current() │
├──────────────────────────────────────┼────────────────────────────────────────────────┤
│ ChatService.kt │ toolDefinition、toolName、shellHint 走平台抽象 │
├──────────────────────────────────────┼────────────────────────────────────────────────┤
│ settings/PluginSettings.kt │ 默认白名单按平台生成 │
├──────────────────────────────────────┼────────────────────────────────────────────────┤
│ settings/SettingsFormState.kt │ 同上 │
├──────────────────────────────────────┼────────────────────────────────────────────────┤
│ ShellPlatformTest.kt │ 新增,35 个单元测试覆盖两端 │
└──────────────────────────────────────┴────────────────────────────────────────────────┘

测试计划

  • ./gradlew test 本地通过(35 个测试)
  • Unix 路径检测:相对路径、绝对内部路径、绝对外部路径、flag token、trailing slash、/dev/null、路径前缀边界
  • Windows 路径检测:驱动器路径、UNC 路径、前缀边界

Checklist

  • PR 标题遵循 Conventional Commits
  • ./gradlew test 本地通过
  • 涉及 webview:不涉及
  • 无遗留 debug 日志和注释掉的代码

@TuYv TuYv requested a review from genni613 April 15, 2026 07:59
TuYv added 3 commits April 15, 2026 16:16
…OutsideWorkspace

- trimEnd('/') on both basePath and token so exact project paths aren't blocked
- skip tokens starting with /dev/ (e.g. /dev/null in 2>/dev/null redirects)
Replace broad /dev/ prefix skip with an explicit allowlist to prevent
path traversal bypass via /dev/../../etc/passwd patterns
…olName fallback

- Use startsWith(base + separator) to prevent /project-evil bypassing /project check
- Replace hardcoded 'run_command' fallback with ShellPlatform.current().toolName()
@genni613 genni613 merged commit 08fad76 into master Apr 15, 2026
3 checks passed
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.

2 participants