T09 · Insecure Skill Coding Practices
- Location
utils/gitManager.js:84- Finding
Repository-Wide Git Staging Can Upload Unrelated Sensitive Files
- Content
View full analysis
{ try { const addResult = gitRun(["add", "."], dir); if (!addResult.success) throw new Error(`git add failed: ${addResult.stderr}`); const statusResult = gitRun(["status", "--porcelain"], dir); if (!statusResult.stdout.trim()) { logger.info("No changes to commit."); return false; } const commitResult = gitRun(["commit", "-m", message], dir); if (!commitResult.success) throw new Error(`git commit failed: ${commitResult.stderr}`); logger.success(`Committed changes: ${message}`); return true; } catch (err) { logger.error(`Git commit failed: ${err.message}`); return false; } }, ``` The resulting commit can then be pushed: ```js push: (dir) => { try { logger.info("Pushing changes to remote..."); const currentBranch = gitManager._getCurrentBranch(dir); logger.info(`Detected branch: ${currentBranch}`); const result = gitRun(["push", "origin", currentBranch], dir); if (!result.success) throw new Error(result.stderr); logger.success(`Pushed to GitHub (${currentBranch})!`); return true; } catch (err) { logger.warn(`Git push failed (check network/auth): ${err.message}`); return false; } }, ``` ### Technical Analysis The synchronization feature is described as committing and pushing generated inventory manifests. However, `git add .` stages every unignored change under the current Git working tree rather than only the generated JSON and Markdown manifests. The `.gitignore` created by initialization covers only a limited set of patterns: ```js const ignoreList = [ ".openclaw/credentials", "*.key", "secrets.*", "node_modules", ".DS_Store", "*.bak" ].join("\n" ...[truncated 1750 chars]- Remediation
View remediation
