name: NYX Security Scan on: pull_request: branches: [main, master] jobs: nyx-scan: runs-on: docker-amd64 permissions: issues: write pull-requests: write steps: - name: Checkout PR run: | git clone --depth=1 \ "https://oauth2:${{ github.token }}@bitfreedom.net/code/${{ github.repository }}.git" \ . git fetch --depth=1 origin ${{ github.sha }} git checkout ${{ github.sha }} - name: Clone nyx from Forgejo mirror run: | git clone --depth=1 --branch master \ "https://oauth2:${{ github.token }}@bitfreedom.net/code/apunkt/nyx.git" \ .nyx-src - name: Install Rust run: | curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y --default-toolchain stable echo "$HOME/.cargo/bin" >> $GITHUB_PATH - name: Build nyx from source run: | cd .nyx-src cargo build --release - name: Run NYX scan id: nyx run: | .nyx-src/target/release/nyx scan --format sarif --fail-on HIGH > nyx-results.sarif 2>&1 continue-on-error: true - name: Post findings as PR comment if: always() run: | FINDINGS=$(python3 -c " import json, sys with open('nyx-results.sarif') as f: data = json.load(f) results = data.get('runs', [{}])[0].get('results', []) if not results: body = '✅ NYX scan: no findings above threshold.' else: lines = [f'## 🔴 NYX found {len(results)} issue(s)\n'] for r in results: level = r.get('level', '?') msg = r.get('message', {}).get('text', '?') rule = r.get('ruleId', '?') loc = r.get('locations', [{}])[0].get('physicalLocation', {}) path = loc.get('artifactLocation', {}).get('uri', '?') line = loc.get('region', {}).get('startLine', '?') col = loc.get('region', {}).get('startColumn', '?') lines.append(f'- **{level.upper()}** \`{path}:{line}:{col}\` [{rule}] — {msg}') body = '\n'.join(lines) print(body) ") curl -s -X POST \ -H "Authorization: token ${{ github.token }}" \ -H "Content-Type: application/json" \ "https://bitfreedom.net/code/api/v1/repos/${{ github.repository }}/issues/${{ github.event.pull_request.number }}/comments" \ -d "{\"body\": $(python3 -c 'import json,sys; print(json.dumps(sys.stdin.read()))' <<< "$FINDINGS")}" - name: Fail if HIGH or above findings found if: steps.nyx.outcome == 'failure' run: exit 1