fix(sec): harden CI/CD workflows, validate remote_ref in pre-push hook, and resolve markdownlint warnings
swadhinbiswas committed 2 months ago
2030541
1 parent d23fc60
commit 2030541
7 files changed
+74 -29
Showing 7 changed files+74-29
βΌ.githooks/pre-push
+26-4
| @@ -1,13 +1,35 @@ | ||
1 | 1 | #!/usr/bin/env bash |
2 | 2 | # ============================================================================== |
3 | 3 | # Git Pre-Push Hook |
4 | -# Blocks direct pushes to 'main' β all changes must go through Pull Requests. | |
4 | +# Blocks direct pushes to remote 'main' / 'master' branches. | |
5 | +# All changes must be submitted via Pull Requests. | |
5 | 6 | # ============================================================================== |
6 | 7 | |
7 | -CURRENT_BRANCH=$(git symbolic-ref --short HEAD 2>/dev/null || echo "") | |
8 | +set -e | |
8 | 9 | |
9 | -if [ "$CURRENT_BRANCH" = "main" ] || [ "$CURRENT_BRANCH" = "master" ]; then | |
10 | - printf "\n\033[0;31m[ERROR]\033[0m Direct push to \033[1m%s\033[0m is blocked.\n" "$CURRENT_BRANCH" | |
10 | +BLOCKED=0 | |
11 | + | |
12 | +# Read stdin passed by git push: <local_ref> <local_sha> <remote_ref> <remote_sha> | |
13 | +while read -r local_ref local_sha remote_ref remote_sha; do | |
14 | + if [ "$remote_ref" = "refs/heads/main" ] || [ "$remote_ref" = "refs/heads/master" ]; then | |
15 | + BLOCKED=1 | |
16 | + TARGET_REF="$remote_ref" | |
17 | + break | |
18 | + fi | |
19 | +done | |
20 | + | |
21 | +# Fallback for invocations where stdin might not provide refs | |
22 | +if [ "$BLOCKED" -eq 0 ]; then | |
23 | + CURRENT_BRANCH=$(git symbolic-ref --short HEAD 2>/dev/null || echo "") | |
24 | + if [ "$CURRENT_BRANCH" = "main" ] || [ "$CURRENT_BRANCH" = "master" ]; then | |
25 | + # Check if remote target is default | |
26 | + BLOCKED=1 | |
27 | + TARGET_REF="refs/heads/$CURRENT_BRANCH" | |
28 | + fi | |
29 | +fi | |
30 | + | |
31 | +if [ "$BLOCKED" -eq 1 ]; then | |
32 | + printf "\n\033[0;31m[ERROR]\033[0m Direct push to \033[1m%s\033[0m is blocked.\n" "$TARGET_REF" | |
11 | 33 | printf "Please create a feature branch and submit a Pull Request:\n\n" |
12 | 34 | printf " git checkout -b feature/your-change\n" |
13 | 35 | printf " git push origin feature/your-change\n\n" |
14 | 36 | |
βΌ.github/workflows/ci.yml
+13-7
| @@ -6,6 +6,9 @@ on: | ||
6 | 6 | pull_request: |
7 | 7 | branches: [ main ] |
8 | 8 | |
9 | +permissions: | |
10 | + contents: read | |
11 | + | |
9 | 12 | concurrency: |
10 | 13 | group: ${{ github.workflow }}-${{ github.ref }} |
11 | 14 | cancel-in-progress: true |
| @@ -17,6 +20,8 @@ jobs: | ||
17 | 20 | steps: |
18 | 21 | - name: Checkout Code |
19 | 22 | uses: actions/checkout@v4 |
23 | + with: | |
24 | + persist-credentials: false | |
20 | 25 | |
21 | 26 | - name: Set up Go |
22 | 27 | uses: actions/setup-go@v5 |
| @@ -37,28 +42,25 @@ jobs: | ||
37 | 42 | run: go vet ./... |
38 | 43 | |
39 | 44 | test: |
40 | - name: Test & Coverage (${{ matrix.go-version }}) | |
45 | + name: Test & Coverage | |
41 | 46 | runs-on: ubuntu-latest |
42 | 47 | needs: lint |
43 | - strategy: | |
44 | - fail-fast: false | |
45 | - matrix: | |
46 | - go-version: [ '1.22', '1.23', '1.24' ] | |
47 | 48 | steps: |
48 | 49 | - name: Checkout Code |
49 | 50 | uses: actions/checkout@v4 |
51 | + with: | |
52 | + persist-credentials: false | |
50 | 53 | |
51 | 54 | - name: Set up Go |
52 | 55 | uses: actions/setup-go@v5 |
53 | 56 | with: |
54 | - go-version: ${{ matrix.go-version }} | |
57 | + go-version: '1.24' | |
55 | 58 | cache: true |
56 | 59 | |
57 | 60 | - name: Run Unit Tests with Race Detector |
58 | 61 | run: go test -v -race -coverprofile=coverage.txt -covermode=atomic ./... |
59 | 62 | |
60 | 63 | - name: Upload Coverage Artifact |
61 | - if: matrix.go-version == '1.24' | |
62 | 64 | uses: actions/upload-artifact@v4 |
63 | 65 | with: |
64 | 66 | name: code-coverage |
| @@ -74,6 +76,8 @@ jobs: | ||
74 | 76 | steps: |
75 | 77 | - name: Checkout Code |
76 | 78 | uses: actions/checkout@v4 |
79 | + with: | |
80 | + persist-credentials: false | |
77 | 81 | |
78 | 82 | - name: Set up Go |
79 | 83 | uses: actions/setup-go@v5 |
| @@ -97,6 +101,8 @@ jobs: | ||
97 | 101 | steps: |
98 | 102 | - name: Checkout Code |
99 | 103 | uses: actions/checkout@v4 |
104 | + with: | |
105 | + persist-credentials: false | |
100 | 106 | |
101 | 107 | - name: Set up Go |
102 | 108 | uses: actions/setup-go@v5 |
103 | 109 | |
βΌ.github/workflows/release.yml
+3-1
| @@ -17,6 +17,7 @@ jobs: | ||
17 | 17 | uses: actions/checkout@v4 |
18 | 18 | with: |
19 | 19 | fetch-depth: 0 |
20 | + persist-credentials: false | |
20 | 21 | |
21 | 22 | - name: Set up Go |
22 | 23 | uses: actions/setup-go@v5 |
| @@ -28,9 +29,10 @@ jobs: | ||
28 | 29 | run: go test -v ./... |
29 | 30 | |
30 | 31 | - name: Compile Multi-Architecture Binaries |
32 | + env: | |
33 | + TAG_NAME: ${{ github.ref_name }} | |
31 | 34 | run: | |
32 | 35 | mkdir -p dist |
33 | - TAG_NAME="${{ github.ref_name }}" | |
34 | 36 | |
35 | 37 | # Linux amd64 (x86_64) |
36 | 38 | GOOS=linux GOARCH=amd64 CGO_ENABLED=0 go build -ldflags="-s -w -X main.version=${TAG_NAME}" -o dist/veet-linux-amd64 . |
37 | 39 | |
βΌCONTRIBUTING.md
+2-2
| @@ -8,10 +8,10 @@ Whether you want to add support for a new package manager, improve the TUI desig | ||
8 | 8 | |
9 | 9 | --- |
10 | 10 | |
11 | -## π οΈ Development Setup | |
11 | +## Development Setup | |
12 | 12 | |
13 | 13 | ### Prerequisites |
14 | -- **Go 1.22+** installed ([golang.org](https://go.dev/dl/)) | |
14 | +- **Go 1.24+** installed ([golang.org](https://go.dev/dl/)) | |
15 | 15 | - Linux operating system (or Linux container/WSL) |
16 | 16 | - `git` and `make` (optional) |
17 | 17 | |
18 | 18 | |
βΌMakefile
+3-2
| @@ -18,8 +18,9 @@ fmt: | ||
18 | 18 | lint: |
19 | 19 | $(GO) vet ./... |
20 | 20 | |
21 | -install: | |
22 | - $(GO) install . | |
21 | +install: build | |
22 | + mkdir -p $(HOME)/.local/bin | |
23 | + cp -f $(BINARY_NAME) $(HOME)/.local/bin/$(BINARY_NAME) | |
23 | 24 | |
24 | 25 | clean: |
25 | 26 | rm -f $(BINARY_NAME) coverage.out coverage.html |
26 | 27 | |
βΌREADME.md
+26-12
| @@ -5,9 +5,9 @@ | ||
5 | 5 | <br/> |
6 | 6 | |
7 | 7 | [](https://github.com/swadhinbiswas/veet/actions/workflows/ci.yml) |
8 | -[](https://go.dev) | |
8 | +[](https://go.dev) | |
9 | 9 | [](LICENSE) |
10 | -[](#) | |
10 | +[](#technical-overview) | |
11 | 11 | [](CONTRIBUTING.md) |
12 | 12 | |
13 | 13 | <p align="center"> |
| @@ -56,31 +56,31 @@ Over extended usage, unmanaged leftovers consume significant disk storage. Moder | ||
56 | 56 | <table> |
57 | 57 | <tr> |
58 | 58 | <td width="50%" valign="top"> |
59 | - <h4><img src="assets/icons/sources.svg" width="18" height="18" align="center" /> Multi-Source Parallel Detection</h4> | |
59 | + <h4><img src="assets/icons/sources.svg" alt="" width="18" height="18" align="center" /> Multi-Source Parallel Detection</h4> | |
60 | 60 | <p>Concurrently queries system package managers (<code>pacman</code>/AUR, <code>apt</code>, <code>dnf</code>, <code>zypper</code>), sandboxed formats (<code>Flatpak</code>, <code>Snap</code>), portable bundles (<code>AppImage</code>), and language toolchains (<code>npm -g</code>, <code>pipx</code>, <code>cargo</code>, <code>gem</code>, <code>go install</code>) with zero-cost skipping for absent tools.</p> |
61 | 61 | </td> |
62 | 62 | <td width="50%" valign="top"> |
63 | - <h4><img src="assets/icons/purge.svg" width="18" height="18" align="center" /> Deep Residual Cleanup</h4> | |
63 | + <h4><img src="assets/icons/purge.svg" alt="" width="18" height="18" align="center" /> Deep Residual Cleanup</h4> | |
64 | 64 | <p>Automates residual discovery across user configurations, cached runtime stores, desktop integration entries, icons, and system paths, staging each candidate before disk execution.</p> |
65 | 65 | </td> |
66 | 66 | </tr> |
67 | 67 | <tr> |
68 | 68 | <td width="50%" valign="top"> |
69 | - <h4><img src="assets/icons/orphan.svg" width="18" height="18" align="center" /> Orphaned Dependency Pruning</h4> | |
69 | + <h4><img src="assets/icons/orphan.svg" alt="" width="18" height="18" align="center" /> Orphaned Dependency Pruning</h4> | |
70 | 70 | <p>Live detection of unneeded dependency packages across native package managers (<code>pacman -Qdt</code>, <code>apt autoremove</code>, <code>dnf repoquery --unneeded</code>) ready for safe reclamation.</p> |
71 | 71 | </td> |
72 | 72 | <td width="50%" valign="top"> |
73 | - <h4><img src="assets/icons/journal.svg" width="18" height="18" align="center" /> System Log & Journal Vacuum</h4> | |
73 | + <h4><img src="assets/icons/journal.svg" alt="" width="18" height="18" align="center" /> System Log & Journal Vacuum</h4> | |
74 | 74 | <p>Identifies bloated systemd journal storage (<code>/var/log/journal</code>) and rotated compressed log archives (<code>/var/log/*.gz</code>) with integrated elevated vacuum routines.</p> |
75 | 75 | </td> |
76 | 76 | </tr> |
77 | 77 | <tr> |
78 | 78 | <td width="50%" valign="top"> |
79 | - <h4><img src="assets/icons/terminal.svg" width="18" height="18" align="center" /> Interactive Navigation & Telemetry</h4> | |
79 | + <h4><img src="assets/icons/terminal.svg" alt="" width="18" height="18" align="center" /> Interactive Navigation & Telemetry</h4> | |
80 | 80 | <p>Instant category switching (<kbd>1</kbd>β<kbd>6</kbd>), four-mode list sorting (<kbd>o</kbd>) for rapid disk bloat identification, and in-place staged path inspection (<kbd>p</kbd>).</p> |
81 | 81 | </td> |
82 | 82 | <td width="50%" valign="top"> |
83 | - <h4><img src="assets/icons/security.svg" width="18" height="18" align="center" /> Sudo Batching & Anti-Brick Safety</h4> | |
83 | + <h4><img src="assets/icons/security.svg" alt="" width="18" height="18" align="center" /> Sudo Batching & Anti-Brick Safety</h4> | |
84 | 84 | <p>Core system components (<code>glibc</code>, <code>linux</code>, <code>systemd</code>, active shell) are protected from selection. System paths are batched into a single elevated transaction.</p> |
85 | 85 | </td> |
86 | 86 | </tr> |
| @@ -107,7 +107,7 @@ curl -sSL https://raw.githubusercontent.com/swadhinbiswas/veet/main/install.sh | | ||
107 | 107 | |
108 | 108 | ### Option 2: Go Package Manager |
109 | 109 | |
110 | -Install directly via the standard Go toolchain (requires Go 1.22+): | |
110 | +Install directly via the standard Go toolchain (requires Go 1.24+): | |
111 | 111 | |
112 | 112 | ```bash |
113 | 113 | go install github.com/swadhinbiswas/veet@latest |
| @@ -275,7 +275,7 @@ protected_packages: | ||
275 | 275 | <summary><b>System Architecture & Module Map</b></summary> |
276 | 276 | <br/> |
277 | 277 | |
278 | -``` | |
278 | +```text | |
279 | 279 | veet/ |
280 | 280 | βββ main.go # Cobra CLI entrypoint (scan, clean, tui) |
281 | 281 | βββ internal/ |
| @@ -296,12 +296,26 @@ veet/ | ||
296 | 296 | |
297 | 297 | ## Uninstallation |
298 | 298 | |
299 | -To remove the compiled binary, shell autocompletions, and optionally purge audit logs: | |
300 | - | |
299 | +### From Cloned Source Repository | |
301 | 300 | ```bash |
302 | 301 | ./uninstall.sh |
303 | 302 | ``` |
304 | 303 | |
304 | +### Manual Removal (Binary & Shell Completions) | |
305 | +If installed via `go install` or direct binary download: | |
306 | +```bash | |
307 | +# Remove executable binary | |
308 | +rm -f ~/.local/bin/veet | |
309 | + | |
310 | +# Remove shell autocompletions | |
311 | +rm -f ~/.local/share/bash-completion/completions/veet | |
312 | +rm -f ~/.local/share/zsh/site-functions/_veet | |
313 | +rm -f ~/.config/fish/completions/veet.fish | |
314 | + | |
315 | +# Optionally remove audit logs and configurations | |
316 | +rm -rf ~/.local/share/veet ~/.config/veet | |
317 | +``` | |
318 | + | |
305 | 319 | --- |
306 | 320 | |
307 | 321 | ## Contributing |
308 | 322 | |
βΌinstall.sh
+1-1
| @@ -39,7 +39,7 @@ elif [ -x "/usr/local/go/bin/go" ]; then | ||
39 | 39 | fi |
40 | 40 | |
41 | 41 | if [ -z "$GO_CMD" ]; then |
42 | - printf "${RED}β Error:${NC} Go compiler (Go 1.22+) not found.\n" | |
42 | + printf "${RED}β Error:${NC} Go compiler (Go 1.24+) not found.\n" | |
43 | 43 | printf "Please install Go from ${CYAN}https://go.dev/dl/${NC} and run this installer again.\n\n" |
44 | 44 | exit 1 |
45 | 45 | fi |
46 | 46 | |