fix(ci_base_image) — le contexte de build doit être SUR la machine, pas sur le contrôleur
Le playbook 03_cicd est mort sur les deux hôtes :
"/Users/…/roles/ci_base_image/files/" is not an existing directory
`docker_image_build` s'exécute SUR LA CIBLE : son `path:` est un chemin de la
cible. Je passais `{{ role_path }}/files/`, un chemin du CONTRÔLEUR.
Le motif venait du rôle `playwright`, qui l'emploie LÉGITIMEMENT parce qu'il
construit en local. Recopié pour un build distant, il ne pouvait pas marcher —
et aucune relecture ne l'aurait montré, seule l'exécution le dit.
⚠ L'échec est arrivé AVANT les tâches qui déploient le runner : les deux
runners sont restés `Up 6 days`, rien n'a été cassé. Le seul effet fut un jeton
d'API Gitea créé par le rôle gitea_token, son comportement normal.
Le contexte est désormais déposé sur la machine (`/tmp/ci-base-image`), et la
RECONSTRUCTION DEVIENT CONDITIONNELLE : `never` en régime normal — le playbook
ne rebâtit pas 3,3 Go à chaque passage — mais `always` dès que le Dockerfile a
CHANGÉ sur la machine. Ajouter une bibliothèque devient donc effectif sans avoir
à penser à un drapeau.
Co-Authored-By: Claude Opus 5 (1M context) <[email protected]>
This commit is contained in:
@@ -48,5 +48,15 @@ ci_base_image_node_major: 20
|
|||||||
# images de runner elles-mêmes.
|
# images de runner elles-mêmes.
|
||||||
ci_base_image_pin: true
|
ci_base_image_pin: true
|
||||||
|
|
||||||
# Reconstruire même si l'image existe déjà (utile après un changement de version).
|
# Où le contexte de build est déposé SUR LA MACHINE CIBLE. `docker_image_build`
|
||||||
|
# s'exécute sur la cible : son `path:` est un chemin de la cible, jamais du
|
||||||
|
# contrôleur. (Première version : `{{ role_path }}/files/` → le playbook mourait
|
||||||
|
# sur « is not an existing directory », sur les deux hôtes.)
|
||||||
|
ci_base_image_contexte: /tmp/ci-base-image
|
||||||
|
|
||||||
|
# Reconstruire même si l'image existe déjà. ⚠ Inutile pour un simple changement
|
||||||
|
# du Dockerfile : le rôle le détecte et reconstruit tout seul (voir tasks/).
|
||||||
|
# Ce drapeau sert aux cas que le Dockerfile ne montre pas — une montée de
|
||||||
|
# `bun.lock` côté kadans, par exemple, qui change les VERSIONS attendues sans
|
||||||
|
# changer le fichier.
|
||||||
ci_base_image_force_rebuild: false
|
ci_base_image_force_rebuild: false
|
||||||
|
|||||||
@@ -6,12 +6,45 @@
|
|||||||
# atterrit sur une machine sans l'image échouerait AVANT sa première étape —
|
# atterrit sur une machine sans l'image échouerait AVANT sa première étape —
|
||||||
# `runs-on`/`container:` est résolu par le runner, pas par le workflow.
|
# `runs-on`/`container:` est résolu par le runner, pas par le workflow.
|
||||||
|
|
||||||
|
# ══════════════════════════════════════════════════════════════════════════
|
||||||
|
# ⚠ LE CONTEXTE DE BUILD DOIT ÊTRE SUR LA MACHINE, PAS SUR LE CONTRÔLEUR.
|
||||||
|
#
|
||||||
|
# `docker_image_build` s'exécute SUR LA CIBLE : son `path:` est un chemin de la
|
||||||
|
# cible. La première version passait `{{ role_path }}/files/` — un chemin du
|
||||||
|
# CONTRÔLEUR — et le playbook mourait sur les deux hôtes :
|
||||||
|
#
|
||||||
|
# "/Users/…/roles/ci_base_image/files/" is not an existing directory
|
||||||
|
#
|
||||||
|
# Le motif venait du rôle `playwright`, qui l'utilise LÉGITIMEMENT parce qu'il
|
||||||
|
# construit en local ; recopié tel quel pour un build distant, il ne peut pas
|
||||||
|
# marcher. On copie donc le contexte d'abord.
|
||||||
|
# ══════════════════════════════════════════════════════════════════════════
|
||||||
|
- name: Créer le répertoire de contexte de build sur la machine
|
||||||
|
ansible.builtin.file:
|
||||||
|
path: '{{ ci_base_image_contexte }}'
|
||||||
|
state: directory
|
||||||
|
mode: '0755'
|
||||||
|
|
||||||
|
- name: Déposer le Dockerfile sur la machine
|
||||||
|
ansible.builtin.copy:
|
||||||
|
src: Dockerfile
|
||||||
|
dest: '{{ ci_base_image_contexte }}/Dockerfile'
|
||||||
|
mode: '0644'
|
||||||
|
register: ci_base_image_dockerfile
|
||||||
|
|
||||||
- name: Construire {{ ci_base_image_name }}:{{ ci_base_image_tag }}
|
- name: Construire {{ ci_base_image_name }}:{{ ci_base_image_tag }}
|
||||||
community.docker.docker_image_build:
|
community.docker.docker_image_build:
|
||||||
name: '{{ ci_base_image_name }}'
|
name: '{{ ci_base_image_name }}'
|
||||||
tag: '{{ ci_base_image_tag }}'
|
tag: '{{ ci_base_image_tag }}'
|
||||||
path: '{{ role_path }}/files/'
|
path: '{{ ci_base_image_contexte }}'
|
||||||
rebuild: '{{ "always" if ci_base_image_force_rebuild else "never" }}'
|
# RECONSTRUCTION CONDITIONNELLE : `never` en régime normal (le playbook ne
|
||||||
|
# rebâtit pas 3,3 Go à chaque passage), mais `always` dès que le Dockerfile
|
||||||
|
# a CHANGÉ sur la machine — c'est ce qui rend l'ajout d'une bibliothèque
|
||||||
|
# effectif sans avoir à penser à un drapeau.
|
||||||
|
rebuild: >-
|
||||||
|
{{ "always"
|
||||||
|
if (ci_base_image_force_rebuild or ci_base_image_dockerfile is changed)
|
||||||
|
else "never" }}
|
||||||
args:
|
args:
|
||||||
CI_BASE_FROM: '{{ ci_base_image_from }}'
|
CI_BASE_FROM: '{{ ci_base_image_from }}'
|
||||||
NODE_MAJOR: '{{ ci_base_image_node_major }}'
|
NODE_MAJOR: '{{ ci_base_image_node_major }}'
|
||||||
|
|||||||
Reference in New Issue
Block a user