From 45004436c0c1dd74775e413bcf030981a9cbc4a6 Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Sun, 29 Mar 2026 06:19:55 +0000 Subject: [PATCH] =?UTF-8?q?=F0=9F=9B=A1=EF=B8=8F=20Sentinel:=20refactor=20?= =?UTF-8?q?dockerPrune=20to=20use=20direct=20binary=20execution?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Replaced the shell wrapper (`/bin/bash -c "docker system prune -f 2>&1"`) with direct binary execution using `/usr/bin/env docker`. This mitigates the risk of command injection while securely handling output redirection. Co-authored-by: acebytes <2820910+acebytes@users.noreply.github.com> --- .jules/sentinel.md | 4 ++++ Sources/Cacheout/ViewModels/CacheoutViewModel.swift | 4 ++-- 2 files changed, 6 insertions(+), 2 deletions(-) create mode 100644 .jules/sentinel.md diff --git a/.jules/sentinel.md b/.jules/sentinel.md new file mode 100644 index 0000000..cefdc49 --- /dev/null +++ b/.jules/sentinel.md @@ -0,0 +1,4 @@ +## 2024-05-24 - Avoid Shell Execution for External Commands +**Vulnerability:** Invoking commands like `docker system prune` using a shell wrapper (`/bin/bash -c "..."`) instead of executing the binary directly exposes the application to command injection vulnerabilities, especially if any part of the command were to become dynamic. Using shell wrappers also complicates error handling and securely replicating shell features like redirection. +**Learning:** Shell redirections like `2>&1` in shell commands can be securely replicated natively in Swift's Foundation `Process` without the need for an intermediate shell. This is done by assigning the identical `Pipe()` instance to both `process.standardOutput` and `process.standardError`. Using `URL(fileURLWithPath: "/usr/bin/env")` as the executable URL and passing the tool name as the first argument in `process.arguments` allows executing commands cleanly and directly while still respecting the `PATH` environment variable. +**Prevention:** Always prefer direct binary execution via `Process` in Swift instead of using `/bin/bash -c` or similar shell wrappers. Pass all dynamic inputs explicitly as elements in the `process.arguments` array. If shell-specific features like output redirection are needed, implement them securely using the native `Process` configuration options rather than relying on shell syntax. \ No newline at end of file diff --git a/Sources/Cacheout/ViewModels/CacheoutViewModel.swift b/Sources/Cacheout/ViewModels/CacheoutViewModel.swift index 13a9811..e50a217 100644 --- a/Sources/Cacheout/ViewModels/CacheoutViewModel.swift +++ b/Sources/Cacheout/ViewModels/CacheoutViewModel.swift @@ -231,8 +231,8 @@ class CacheoutViewModel: ObservableObject { let process = Process() let pipe = Pipe() - process.executableURL = URL(fileURLWithPath: "/bin/bash") - process.arguments = ["-c", "docker system prune -f 2>&1"] + process.executableURL = URL(fileURLWithPath: "/usr/bin/env") + process.arguments = ["docker", "system", "prune", "-f"] process.standardOutput = pipe process.standardError = pipe process.environment = [