Document, as a tree-docs tree, the end-to-end procedure to stand up a new web application on the Arcodange platform — a mechanic spread across the factory, tools and app repos with non-trivial ordering dependencies. Covers: Gitea repo creation (org-secret inheritance), Postgres DB + owner role (factory/postgres/iac), platform Vault declaration (gitea_cicd_<app> + policies, tools/hashicorp-vault/iac), the app Helm chart (VSO dynamic secrets via pgbouncer), the app Terraform (app_roles module), the CI workflows (tofu apply + image build, incl. the copy-pasted role pitfall), and ArgoCD registration (factory/argocd/values.yaml). Adds a naming- conventions concept page and an ordered checklist. Wires the legacy doc/adr "setup hello world web app" item and the factory README to the runbook. New docs live under doc/ (singular) per the PR #8 convention. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
5.4 KiB
Factory > Doc > Runbooks > Nouvelle application web > 6. Workflows CI
6. Les workflows CI (.gitea/workflows/)
Status: ✅ Active Upstream: 1. Dépôt Gitea (secrets d'org), 3. Vault plateforme (
gitea_cicd_<app>) Related: 4. Chart Helm · 5. Terraform de l'app · 7. Enregistrement ArgoCD · Conventions de nommage
Summary
Deux workflows Gitea Actions vivent dans le dépôt : vault.yaml applique le Terraform de l'app (iac/) en s'authentifiant à Vault via OIDC, et dockerimage.yaml (optionnel) construit l'image et la pousse au registre Gitea. Le déploiement lui-même n'est pas dans la CI : c'est ArgoCD qui s'en charge (étape 7).
vault.yaml — appliquer le iac/ de l'app
Déclenché sur tout changement de iac/*.tf. Deux jobs : obtenir un JWT depuis Gitea, puis tofu apply.
on:
workflow_dispatch: {}
push: { paths: ['iac/*.tf'] }
pull_request: { paths: ['iac/*.tf'] }
# job 1 : échange OIDC Gitea → JWT (script base64 fourni en secret d'org)
# run: echo -n "${{ secrets.vault_oauth__sh_b64 }}" | base64 -d | bash
# job 2 : lire les secrets de bootstrap puis appliquer
- name: read vault secret
uses: https://gitea.arcodange.lab/arcodange-org/vault-action.git@main
with:
url: https://vault.arcodange.lab
caCertificate: ${{ secrets.HOMELAB_CA_CERT }}
jwtGiteaOIDC: ${{ needs.gitea_vault_auth.outputs.gitea_vault_jwt }}
role: gitea_cicd_<app> # ← le rôle JWT de l'app (étape 3)
method: jwt
path: gitea_jwt
secrets: |
kvv1/google/credentials credentials | GOOGLE_BACKEND_CREDENTIALS ;
kvv1/gitea/tofu_module_reader ssh_private_key | TERRAFORM_SSH_KEY ;
- uses: actions/checkout@v4
- name: terraform apply
uses: dflook/terraform-apply@v1
with: { path: iac, auto_approve: true }
Les deux secrets lus servent au backend (clé GCS GOOGLE_BACKEND_CREDENTIALS) et au clone du module partagé en SSH (TERRAFORM_SSH_KEY, cf. étape 5).
Warning
Piège du
role:copié-collé. Lerole:du stepvault-actionet leroledeiac/providers.tfdoivent tous deux êtregitea_cicd_<app>. L'exempleerpporte encorerole: gitea_cicd_webappdans sonvault.yaml(reliquat de copier-coller) alors que sonproviders.tfutilise biengitea_cicd_erp. Vérifie et aligne sur le nom de ton app, sinon la CI lit/écrit avec la mauvaise identité.
dockerimage.yaml — construire l'image (si image maison)
À n'ajouter que si l'app build sa propre image (pas pour une image publique comme erp/Dolibarr). Déclenché au push sur main, en ignorant README.md et chart/** (changer le chart ne reconstruit pas l'image).
on:
push: { branches: [main], paths-ignore: ['README.md', 'chart/**'] }
jobs:
build-and-push-image:
steps:
- uses: docker/login-action@v3
with:
registry: gitea.arcodange.lab
username: ${{ github.actor }}
password: ${{ secrets.PACKAGES_TOKEN }} # secret d'org (étape 1)
- uses: actions/checkout@v4
- run: |
TAGS="latest ${{ github.ref_name }}"
docker build -t app .
for TAG in $TAGS; do
docker tag app gitea.arcodange.lab/${{ github.repository }}:$TAG
docker push gitea.arcodange.lab/${{ github.repository }}:$TAG
done
L'image atterrit donc en gitea.arcodange.lab/arcodange-org/<app>:latest — exactement ce que image.repository du chart référence (étape 4). Un Dockerfile multi-stage à la racine convient (cf. webapp/Dockerfile).
Vue d'ensemble
%%{init: {'theme': 'base'}}%%
flowchart TB
classDef ci fill:#059669,stroke:#047857,color:#fff
classDef out fill:#7c3aed,stroke:#6d28d9,color:#fff
PUSH["push sur main"]:::ci
PUSH -->|"iac/*.tf modifié"| TF["vault.yaml<br>OIDC → JWT → tofu apply iac/"]:::ci
PUSH -->|"code modifié"| IMG["dockerimage.yaml<br>build + push image"]:::ci
TF --> VR["creds/‹app› + rôle K8s ‹app› + KV"]:::out
IMG --> REG["registre gitea.arcodange.lab/arcodange-org/‹app›"]:::out
Déploiement automatique sur nouvelle image
Pour qu'ArgoCD redéploie quand une nouvelle image est poussée, on n'ajoute rien dans la CI : ce sont les annotations argocd-image-updater posées à l'étape 7 (stratégie digest) qui surveillent le tag latest.
Notes / contraintes
concurrency: cancel-in-progressest activé sur les deux workflows : un nouveau push annule le run précédent sur la même ref.- Le
vault-actionest lui-même un dépôt Gitea (arcodange-org/vault-action) épinglé@main.
Related
- 3. Vault plateforme — d'où vient
gitea_cicd_<app>. - 5. Terraform de l'app — ce que
vault.yamlapplique. - 4. Chart Helm —
image.repository= l'image poussée ici. - 7. Enregistrement ArgoCD — déploie, et porte les annotations d'auto-update.