diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml deleted file mode 100644 index 4b6e2af..0000000 --- a/.github/workflows/build.yml +++ /dev/null @@ -1,51 +0,0 @@ -name: Build - -on: - push: - branches: - - main - paths: - - docs/** - workflow_dispatch: - -jobs: - build: - name: Build application - runs-on: ubuntu-latest - permissions: - contents: read - packages: write - steps: - - name: Checks-out repository - uses: actions/checkout@v4 - - - name: Set up Docker buildx - uses: docker/setup-buildx-action@v3 - - - name: Set up QEMU (for multi platform build) - uses: docker/setup-qemu-action@v3 - - - name: Login to Container Registry - uses: docker/login-action@v3 - with: - registry: ghcr.io - username: ${{ github.actor }} - password: ${{ secrets.GITHUB_TOKEN }} - logout: true - - - name: Build docker image - uses: docker/build-push-action@v5 - with: - context: . - file: Dockerfile - tags: ghcr.io/${{ github.repository }}:latest - target: prod - platforms: linux/amd64,linux/arm64 - push: true - - - name: Deploy new image - run: | - curl -X POST https://gitops.fabrique-numerique.fr/api/v1/applications/cloud-pi-native-docs/sync \ - -H "Content-Type: application/json" \ - -H "Authorization: Bearer ${{ secrets.ARGOCD_TOKEN }}" \ - -d '${{ vars.ARGOCD_SYNC_PAYLOAD }}' diff --git a/.github/workflows/mirror.yml b/.github/workflows/mirror.yml new file mode 100644 index 0000000..4f04f5a --- /dev/null +++ b/.github/workflows/mirror.yml @@ -0,0 +1,40 @@ +name: Mirror to GitLab + +# Le depot GitLab de la chaine secondaire est un miroir de celui-ci. Chaque +# merge sur main declenche le pipeline GitLab qui va rapatrier le commit ; +# c'est ensuite .gitlab-ci-dso.yml qui construit l'image et ArgoCD qui deploie. +on: + push: + branches: + - main + workflow_dispatch: + +# Deux merges rapproches ne doivent pas lancer deux mirrorings concurrents. +# Celui en cours n'est pas annule : il termine son travail. +concurrency: + group: gitlab-mirror + cancel-in-progress: false + +permissions: + contents: read + +jobs: + trigger: + name: Trigger GitLab mirror pipeline + runs-on: ubuntu-latest + steps: + - name: Trigger mirror pipeline + env: + TRIGGER_URL: ${{ secrets.GITLAB_MIRROR_TRIGGER_URL }} + TRIGGER_TOKEN: ${{ secrets.GITLAB_MIRROR_TRIGGER_TOKEN }} + run: | + : "${TRIGGER_URL:?secret GITLAB_MIRROR_TRIGGER_URL manquant}" + : "${TRIGGER_TOKEN:?secret GITLAB_MIRROR_TRIGGER_TOKEN manquant}" + + curl --fail-with-body -sS \ + --header "PRIVATE-TOKEN: ${TRIGGER_TOKEN}" \ + -X POST \ + -F token="${TRIGGER_TOKEN}" \ + -F ref=main \ + -F "variables[GIT_MIRROR_PROJECT_ID]=31" \ + "${TRIGGER_URL}" diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml deleted file mode 100644 index 4753d69..0000000 --- a/.github/workflows/release.yml +++ /dev/null @@ -1,66 +0,0 @@ -name: Release - -on: - workflow_dispatch: - inputs: - TAG: - description: Console tag used for release (eg. '1.2.3') - required: true - type: string - -jobs: - release: - name: Create new release - runs-on: ubuntu-latest - permissions: - contents: write - steps: - - name: Checks-out repository - uses: actions/checkout@v4 - - - name: Pre release new version - run: | - gh release create v${{ inputs.TAG }} --latest --notes "Cloud Pi Native Documentation - Console v${{ inputs.TAG }}" - - build: - name: Build application - runs-on: ubuntu-latest - needs: - - release - permissions: - contents: read - packages: write - steps: - - name: Checks-out repository - uses: actions/checkout@v4 - - - name: Set up Docker buildx - uses: docker/setup-buildx-action@v3 - - - name: Set up QEMU (for multi platform build) - uses: docker/setup-qemu-action@v3 - - - name: Login to Container Registry - uses: docker/login-action@v3 - with: - registry: ghcr.io - username: ${{ github.actor }} - password: ${{ secrets.GITHUB_TOKEN }} - logout: true - - - name: Build docker image - uses: docker/build-push-action@v5 - with: - context: . - file: Dockerfile - tags: ghcr.io/${{ github.repository }}:latest,ghcr.io/${{ github.repository }}:${{ inputs.TAG }} - target: prod - platforms: linux/amd64,linux/arm64 - push: true - - - name: Deploy new image - run: | - curl -X POST https://gitops.fabrique-numerique.fr/api/v1/applications/cloud-pi-native-docs/sync \ - -H "Content-Type: application/json" \ - -H "Authorization: Bearer ${{ secrets.ARGOCD_TOKEN }}" \ - -d '${{ vars.ARGOCD_SYNC_PAYLOAD }}' diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 4c880ef..913984f 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -16,15 +16,9 @@ on: required: true type: string default: "22" - PNPM_VERSION: - description: Pnpm version used to run build tests - required: true - type: string - default: "10" env: NODE_VERSION: "22" - PNPM_VERSION: "10" jobs: lint: @@ -38,7 +32,6 @@ jobs: uses: pnpm/action-setup@v4 id: pnpm-install with: - version: "${{ inputs.PNPM_VERSION || env.PNPM_VERSION }}" run_install: false - name: Setup Node.js @@ -63,5 +56,8 @@ jobs: - name: Install dependencies run: pnpm install --frozen-lockfile + - name: Lint sources + run: pnpm lint + - name: Test application build run: pnpm run build diff --git a/.gitignore b/.gitignore index 2708831..e4bb37e 100644 --- a/.gitignore +++ b/.gitignore @@ -51,7 +51,9 @@ Temporary Items ### Node ### # Logs -logs +# Ancre a la racine : un "logs" non ancre masquerait tout dossier de ce nom +# n'importe ou dans l'arbre, y compris les pages docs/guide/logs. +/logs *.log npm-debug.log* yarn-debug.log* @@ -221,5 +223,150 @@ $RECYCLE.BIN/ # End of https://www.toptal.com/developers/gitignore/api/node,macos,windows,linux -!docs/guide/logs -!docs/public/img/guide/logs \ No newline at end of file +### Intellij ### +# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio, WebStorm and Rider +# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839 + +# User-specific stuff +.idea/**/workspace.xml +.idea/**/tasks.xml +.idea/**/usage.statistics.xml +.idea/**/dictionaries +.idea/**/shelf + +# AWS User-specific +.idea/**/aws.xml + +# Generated files +.idea/**/contentModel.xml + +# Sensitive or high-churn files +.idea/**/dataSources/ +.idea/**/dataSources.ids +.idea/**/dataSources.local.xml +.idea/**/sqlDataSources.xml +.idea/**/dynamic.xml +.idea/**/uiDesigner.xml +.idea/**/dbnavigator.xml + +# Gradle +.idea/**/gradle.xml +.idea/**/libraries + +# Gradle and Maven with auto-import +# When using Gradle or Maven with auto-import, you should exclude module files, +# since they will be recreated, and may cause churn. Uncomment if using +# auto-import. +# .idea/artifacts +# .idea/compiler.xml +# .idea/jarRepositories.xml +# .idea/modules.xml +# .idea/*.iml +# .idea/modules +# *.iml +# *.ipr + +# CMake +cmake-build-*/ + +# Mongo Explorer plugin +.idea/**/mongoSettings.xml + +# File-based project format +*.iws + +# IntelliJ +out/ + +# mpeltonen/sbt-idea plugin +.idea_modules/ + +# JIRA plugin +atlassian-ide-plugin.xml + +# Cursive Clojure plugin +.idea/replstate.xml + +# SonarLint plugin +.idea/sonarlint/ + +# Crashlytics plugin (for Android Studio and IntelliJ) +com_crashlytics_export_strings.xml +crashlytics.properties +crashlytics-build.properties +fabric.properties + +# Editor-based Rest Client +.idea/httpRequests + +# Android studio 3.1+ serialized cache file +.idea/caches/build_file_checksums.ser + +### Intellij Patch ### +# Comment Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-215987721 + +# *.iml +# modules.xml +# .idea/misc.xml +# *.ipr + +# Sonarlint plugin +# https://plugins.jetbrains.com/plugin/7973-sonarlint +.idea/**/sonarlint/ + +# SonarQube Plugin +# https://plugins.jetbrains.com/plugin/7238-sonarqube-community-plugin +.idea/**/sonarIssues.xml + +# Markdown Navigator plugin +# https://plugins.jetbrains.com/plugin/7896-markdown-navigator-enhanced +.idea/**/markdown-navigator.xml +.idea/**/markdown-navigator-enh.xml +.idea/**/markdown-navigator/ + +# Cache file creation bug +# See https://youtrack.jetbrains.com/issue/JBR-2257 +.idea/$CACHE_FILE$ + +# CodeStream plugin +# https://plugins.jetbrains.com/plugin/12206-codestream +.idea/codestream.xml + +# Azure Toolkit for IntelliJ plugin +# https://plugins.jetbrains.com/plugin/8053-azure-toolkit-for-intellij +.idea/**/azureSettings.xml + +.idea + +### Secrets ### +# Le depot est public : ces motifs evitent qu'un `git add .` malheureux y +# publie des identifiants. Aucun fichier suivi ne correspond a ces motifs. + +# Cles privees et certificats +*.pem +*.key +*.p12 +*.pfx +*.jks +*.keystore +id_rsa +id_ecdsa +id_ed25519 + +# Acces aux clusters et aux registres +kubeconfig +*.kubeconfig +.kube/config +.docker/config.json + +# Fichiers de secrets applicatifs +secrets.yaml +secrets.yml +secrets.json +*.secrets.yaml +*.secrets.yml + +# Identifiants d'outils +.netrc +.npmrc +.pypirc diff --git a/.gitlab-ci-dso.yml b/.gitlab-ci-dso.yml index 7f469ed..061108e 100644 --- a/.gitlab-ci-dso.yml +++ b/.gitlab-ci-dso.yml @@ -9,14 +9,29 @@ default: image: alpine:latest variables: - TAG: "${CI_COMMIT_REF_SLUG}" DOCKERFILE: Dockerfile REGISTRY_URL: "${IMAGE_REPOSITORY}" +# le build et install pnpm sont déjà faits dans le dockerfile, donc pas de stage de test. stages: - read-secret - docker-build +# Le tag de l'image est la version de la console, declaree en appVersion dans +# helm/Chart.yaml. +set-version: + stage: .pre + image: alpine:latest + script: + - | + APP_VERSION=$(sed -n 's/^appVersion:[[:space:]]*\([^[:space:]#]*\).*/\1/p' helm/Chart.yaml | tr -d '"') + test -n "${APP_VERSION}" + echo "TAG=${APP_VERSION}" > version.env + cat version.env + artifacts: + reports: + dotenv: version.env + read_secret: stage: read-secret extends: diff --git a/Dockerfile b/Dockerfile index e2532d2..6e79b39 100644 --- a/Dockerfile +++ b/Dockerfile @@ -2,9 +2,10 @@ FROM docker.io/node:22-slim AS dev WORKDIR /app -RUN npm install --location=global pnpm@10 -COPY --chown=node:root package.json pnpm-lock.yaml ./ -RUN pnpm install +ENV COREPACK_ENABLE_DOWNLOAD_PROMPT=0 +COPY --chown=node:root package.json pnpm-lock.yaml pnpm-workspace.yaml ./ +RUN corepack enable && corepack install +RUN pnpm install --frozen-lockfile COPY --chown=node:root docs ./docs ENTRYPOINT [ "pnpm", "run", "dev" ] @@ -19,7 +20,13 @@ RUN pnpm run build FROM docker.io/bitnamilegacy/nginx:1.27 AS prod USER 0 -COPY --chown=1001:0 --chmod=770 --from=build /app/docs/.vitepress/dist /opt/bitnami/nginx/html/ -COPY --chown=1001:0 --chmod=660 ./nginx.conf /opt/bitnami/nginx/conf/server_blocks/default.conf +# OpenShift ignore le USER de l'image et assigne un UID arbitraire, toujours +# membre du groupe 0 : ce sont les droits de groupe qui comptent, d'ou le +# --chown=1001:0. Sans --chmod, COPY laisse 644 aux fichiers et 755 aux +# repertoires : le groupe 0 lit, les repertoires restent traversables, et les +# fichiers statiques ne portent plus le bit d'execution que --chmod=770 leur +# donnait. +COPY --chown=1001:0 --from=build /app/docs/.vitepress/dist /opt/bitnami/nginx/html/ +COPY --chown=1001:0 --chmod=640 ./nginx.conf /opt/bitnami/nginx/conf/server_blocks/default.conf USER 1001 EXPOSE 8080 diff --git a/docs/agreement/observability.md b/docs/agreement/observability.md index 83ea2d4..a430159 100644 --- a/docs/agreement/observability.md +++ b/docs/agreement/observability.md @@ -1,6 +1,5 @@ # Observabilité - Dans le cadre de l'offre Cloud-Pi Native, l'observabilité est disponible via plusieurs composants: - Prometheus pour les métriques et les dashboards de sécurité - Loki pour les logs @@ -31,7 +30,6 @@ Des dashboards [Grafana](https://grafana.com/grafana/) pour consulter les métri Pour consulter les dashboard de sécurité, [cliquer ici](/guide/dashboardsecurite.md) - ## Dashboard as code À partir de la version 9.4.0 de la console, une fonctionnalité *Dashboard as code* est disponible. @@ -64,7 +62,6 @@ Un objet de type Kubernetes *GrafanaDashboard* est créé pour chaque dashboard > À noter que seule la branche **main** est synchronisée - La video suivante illustre cette fonctionnalité