name: Qualité & Sécurité # Analyse statique (MegaLinter, config racine .mega-linter.yml) + CVE des # dépendances (Trivy). Workflow SÉPARÉ de ci.yml : un rouge qualité ne bloque # pas la chaîne tests → release pendant la phase de rodage. Une fois la base # assainie, on pourra l'ajouter aux checks requis de la branch protection. on: push: # beta inclus : c'est la branche de dev, le feedback qualité doit y vivre # (ci.yml/e2e.yml, eux, restent volontairement sur main + PR). branches: [main, beta] pull_request: branches: [main] jobs: megalinter: name: MegaLinter (PMD · Ruff · Bandit · gitleaks · hadolint) runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 with: # Historique complet : requis par gitleaks (scan de l'historique) # et par le mode "fichiers modifiés seulement" en PR. fetch-depth: 0 # Flavor "cupcake" : image allégée couvrant les langages courants # (Java/Python/TS inclus). Si un linter activé manquait à la flavor, # MegaLinter échoue en l'indiquant → remplacer par oxsecurity/megalinter@v9 # (image complète, plus lourde). - name: MegaLinter uses: oxsecurity/megalinter/flavors/cupcake@v9 env: # main → scan complet du dépôt ; beta et PR → seulement les fichiers # modifiés par rapport à main (rapide, feedback ciblé). VALIDATE_ALL_CODEBASE: ${{ github.ref == 'refs/heads/main' }} # v3 obligatoire : l'API artifacts v4 (@actions/artifact 2.x) n'est pas # supportée par Gitea (GHESNotSupportedError constaté avec v4). - name: Publier les rapports if: always() uses: actions/upload-artifact@v3 with: name: megalinter-reports path: megalinter-reports/ web-lint: name: Web (ESLint · angular-eslint + sonarjs) runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - uses: actions/setup-node@v4 with: node-version: '20' cache: npm cache-dependency-path: web/package-lock.json - name: npm ci working-directory: web run: npm ci --no-audit --no-fund # Lint via la toolchain du projet (et non via MegaLinter : ESLint a # besoin des plugins de web/node_modules et du contexte Angular). # Config + règles : web/eslint.config.js (sonarjs = règles "à la Sonar"). - name: ng lint working-directory: web run: npm run lint trivy: name: Trivy (CVE dépendances Maven / pip / npm) runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 # Pour résoudre pom.xml (versions héritées du parent Spring Boot), Trivy # télécharge les BOMs depuis Maven Central — qui finit par rate-limiter # l'IP du runner (429). Parade officielle : peupler ~/.m2 AVANT le scan, # Trivy lit le cache local en priorité. Le cache setup-java (clé pom.xml) # rend l'étape quasi gratuite d'un run à l'autre. - uses: actions/setup-java@v4 with: distribution: temurin java-version: '17' cache: maven - name: Précharger le cache Maven (~/.m2) working-directory: core run: | chmod +x ./mvnw ./mvnw -B -q dependency:go-offline - name: Installer Trivy run: curl -sfL https://raw.githubusercontent.com/aquasecurity/trivy/main/contrib/install.sh | sh -s -- -b /usr/local/bin # Scanne les manifestes du dépôt (pom.xml, requirements*.txt, # package-lock.json) contre les bases CVE. --ignore-unfixed : on ne # bloque que sur les vulnérabilités qui ONT un correctif publié. # --offline-scan : AUCUNE requête vers Maven Central pendant la # résolution — Trivy allait y chercher les POMs parents même avec le # cache rempli, et l'IP du runner finissait rate-limitée (429, 30 min). # Tout est déjà dans ~/.m2 grâce au dependency:go-offline ci-dessus ; # contrepartie : une dépendance absente du cache serait ignorée en # silence (impossible ici, go-offline échouerait d'abord). - name: Scan des dépendances (HIGH/CRITICAL bloquants) run: | trivy fs . \ --scanners vuln \ --severity HIGH,CRITICAL \ --ignore-unfixed \ --offline-scan \ --skip-dirs node_modules \ --skip-dirs docusaurus \ --exit-code 1