- Expand .env.example with full runtime, cache, Docker, and AI keys - Add deployment secrets to .gitignore (docker-compose/.env, docker/.registry.env) - Remove VIMEO_ACCESS_TOKEN from compose files; add OAuth redirect URIs - Load registry credentials from .registry.env in deploy-img.sh - Fail fast if protected registry lacks auth during pre-checks - Pass DOCKER_USERNAME/PASSWORD explicitly to WSL in deploy-img.ps1 - Remove inline collapse buttons from themes-nav.component.html
This commit is contained in:
@@ -0,0 +1,14 @@
|
||||
# Identifiants du registre Docker distant — NE PAS VERSIONNER.
|
||||
# Copiez ce fichier en `.registry.env` (ignoré par git) et remplissez les valeurs.
|
||||
# cp .registry.env.example .registry.env
|
||||
#
|
||||
# Priorité de lecture dans deploy-img.sh :
|
||||
# 1. variables d'environnement DOCKER_USERNAME / DOCKER_PASSWORD
|
||||
# 2. ce fichier
|
||||
#
|
||||
# Sous Windows, deploy-img.ps1 exécute le script dans WSL : WSL n'hérite pas des
|
||||
# variables de Windows, ce fichier est donc la voie la plus fiable. Le .ps1
|
||||
# exporte aussi les variables Windows qu'il trouve, en repli.
|
||||
|
||||
DOCKER_USERNAME=votre_utilisateur
|
||||
DOCKER_PASSWORD=votre_mot_de_passe
|
||||
@@ -29,7 +29,19 @@ try {
|
||||
wsl -d Debian -- chmod +x "$wslScriptDir/deploy-img.sh"
|
||||
|
||||
Write-Verbose "[Étape 4] Construction de la commande Bash à exécuter."
|
||||
# WSL n'hérite PAS des variables d'environnement de Windows : on les
|
||||
# exporte explicitement dans la commande bash. Sans cela, un DOCKER_USERNAME
|
||||
# défini dans PowerShell n'arriverait jamais dans deploy-img.sh et le push
|
||||
# échouerait en "push access denied".
|
||||
$innerCmd = "cd '$wslScriptDir' && ./deploy-img.sh"
|
||||
foreach ($var in @('DOCKER_USERNAME', 'DOCKER_PASSWORD')) {
|
||||
$value = [Environment]::GetEnvironmentVariable($var)
|
||||
if ($value) {
|
||||
# Échappement des caractères spéciaux bash (simple quotes)
|
||||
$escaped = $value -replace "'", "'\''"
|
||||
$innerCmd = "export $var='$escaped'; " + $innerCmd
|
||||
}
|
||||
}
|
||||
|
||||
Write-Verbose "[Étape 5] Exécution du script deploy-img.sh dans WSL Debian."
|
||||
wsl -d Debian bash -lc $innerCmd
|
||||
|
||||
+57
-11
@@ -2,7 +2,7 @@
|
||||
# Script: deploy-img.sh
|
||||
# Description: Pousse l'image Docker locale vers un registre HTTP (insecure), gère le versioning semver et la rétention
|
||||
# Date: 2025-04-18
|
||||
# Mise à jour: 2025-09-19 - Vérification stricte du daemon (insecure-registries), compatibilité Windows/Linux
|
||||
# Mise à jour: 2026-09-28 - Lecture des identifiants depuis .registry.env, échec rapide si le registre est protégé
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
@@ -29,6 +29,16 @@ JQ_BIN="${JQ_BIN:-jq}" # possibilité de surcharger via env
|
||||
# Headers pour obtenir le digest (manifest v2)
|
||||
ACCEPT_MANIFEST='application/vnd.docker.distribution.manifest.v2+json'
|
||||
|
||||
# Auth du registre. Ordre de priorité :
|
||||
# 1. variables déjà exports (DOCKER_USERNAME / DOCKER_PASSWORD)
|
||||
# 2. fichier .registry.env à côté du script (non versionné, cf. .gitignore)
|
||||
# Le fichier permet à deploy-img.ps1 (qui exécute ce script dans WSL) de trouver
|
||||
# les identifiants : WSL n'hérite pas des variables d'environnement de Windows.
|
||||
# (Ce bloc est exécuté plus bas, après la définition de info/warn/error.)
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
REGISTRY_ENV_FILE="${REGISTRY_ENV_FILE:-${SCRIPT_DIR}/.registry.env}"
|
||||
AUTH_ARGS=()
|
||||
|
||||
#####################################
|
||||
# UTILITAIRES #
|
||||
#####################################
|
||||
@@ -55,6 +65,23 @@ require_cmd() {
|
||||
command -v "$1" >/dev/null 2>&1 || { error "Commande requise manquante: $1"; exit 1; }
|
||||
}
|
||||
|
||||
# Chargement des identifiants (voir commentaire en section CONFIG)
|
||||
if [[ -f "${REGISTRY_ENV_FILE}" ]]; then
|
||||
info "Lecture des identifiants depuis ${REGISTRY_ENV_FILE}"
|
||||
set -a
|
||||
# shellcheck disable=SC1090
|
||||
source "${REGISTRY_ENV_FILE}"
|
||||
set +a
|
||||
fi
|
||||
|
||||
if [[ -n "${DOCKER_USERNAME:-}" && -n "${DOCKER_PASSWORD:-}" ]]; then
|
||||
AUTH_ARGS=(-u "${DOCKER_USERNAME}:${DOCKER_PASSWORD}")
|
||||
else
|
||||
warn "Aucun identifiant registre (DOCKER_USERNAME / DOCKER_PASSWORD)."
|
||||
warn "Créez ${REGISTRY_ENV_FILE} avec :"
|
||||
printf '%s\n' " DOCKER_USERNAME=votre_utilisateur" " DOCKER_PASSWORD=votre_mot_de_passe"
|
||||
fi
|
||||
|
||||
#####################################
|
||||
# PRÉ-VÉRIFICATIONS #
|
||||
#####################################
|
||||
@@ -96,20 +123,39 @@ if ! docker info 2>/dev/null \
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Ping HTTP direct du registre (API v2)
|
||||
# Ping HTTP direct du registre (API v2).
|
||||
# Un registre protégé répond 401 : cela prouve qu'il EST joignable, donc on
|
||||
# accepte 200 comme 401 (et seulement eux). `-f` seul faisait échouer le script
|
||||
# sur un registre authentifié.
|
||||
info "Vérification HTTP directe du registre (http://${REGISTRY}/v2/)…"
|
||||
if ! ${CURL} "http://${REGISTRY}/v2/" >/dev/null 2>&1; then
|
||||
error "Impossible de joindre http://${REGISTRY}/v2/. Le registre écoute-t-il bien en HTTP sur :${REGISTRY_PORT} ?"
|
||||
HTTP_CODE="$(curl -s -o /dev/null -w '%{http_code}' ${AUTH_ARGS[@]+"${AUTH_ARGS[@]}"} \
|
||||
--connect-timeout 10 -m 20 "http://${REGISTRY}/v2/" 2>/dev/null || echo "000")"
|
||||
if [[ "${HTTP_CODE}" != "200" && "${HTTP_CODE}" != "401" ]]; then
|
||||
error "Impossible de joindre http://${REGISTRY}/v2/ (code HTTP: ${HTTP_CODE})."
|
||||
error "Le registre écoute-t-il bien en HTTP sur :${REGISTRY_PORT} ?"
|
||||
exit 1
|
||||
fi
|
||||
# Un 401 sur un registre protégé SANS identifiants est bloquant : continuer
|
||||
# produirait un push qui échoue en fin de course ("push access denied") après
|
||||
# avoir déjà tagué l'image. On s'arrête ici avec un message actionnable.
|
||||
if [[ "${HTTP_CODE}" == "401" && ${#AUTH_ARGS[@]} -eq 0 ]]; then
|
||||
error "Le registre ${REGISTRY} exige une authentification et aucun identifiant n'est fourni."
|
||||
error "Créez ${REGISTRY_ENV_FILE} :"
|
||||
printf '%s\n' " DOCKER_USERNAME=votre_utilisateur" " DOCKER_PASSWORD=votre_mot_de_passe"
|
||||
exit 1
|
||||
fi
|
||||
[[ "${HTTP_CODE}" == "401" ]] && info "Registre protégé (401) : authentification avec ${DOCKER_USERNAME}."
|
||||
|
||||
# Auth facultative via env (DOCKER_USERNAME / DOCKER_PASSWORD)
|
||||
if [[ -n "${DOCKER_USERNAME:-}" && -n "${DOCKER_PASSWORD:-}" ]]; then
|
||||
# Auth auprès du daemon (utile pour le push)
|
||||
if [[ ${#AUTH_ARGS[@]} -gt 0 ]]; then
|
||||
info "Authentification au registre (docker login)…"
|
||||
# NB: docker login respecte le mode HTTP si daemon configuré en insecure-registries
|
||||
echo "${DOCKER_PASSWORD}" | docker login "${REGISTRY}" --username "${DOCKER_USERNAME}" --password-stdin >/dev/null
|
||||
if ! echo "${DOCKER_PASSWORD}" | docker login "${REGISTRY}" --username "${DOCKER_USERNAME}" --password-stdin >/dev/null 2>&1; then
|
||||
error "docker login a échoué sur ${REGISTRY}. Vérifiez DOCKER_USERNAME / DOCKER_PASSWORD."
|
||||
exit 1
|
||||
fi
|
||||
else
|
||||
info "Aucun identifiant Docker fourni (DOCKER_USERNAME/DOCKER_PASSWORD). Tentative sans authentification."
|
||||
info "Aucun identifiant : le registre est ouvert, push sans authentification."
|
||||
fi
|
||||
|
||||
mkdir -p "${TEMP_DIR}"
|
||||
@@ -121,7 +167,7 @@ get_all_tags() {
|
||||
# Renvoie la liste des tags (un par ligne) ou rien si vide/erreur
|
||||
# Utilise jq si dispo, sinon un parseur simple.
|
||||
local tags_json
|
||||
if ! tags_json="$(${CURL} "http://${REGISTRY}/v2/${IMAGE_NAME}/tags/list" 2>/dev/null)"; then
|
||||
if ! tags_json="$(${CURL} ${AUTH_ARGS[@]+"${AUTH_ARGS[@]}"} "http://${REGISTRY}/v2/${IMAGE_NAME}/tags/list" 2>/dev/null)"; then
|
||||
return 0
|
||||
fi
|
||||
|
||||
@@ -190,7 +236,7 @@ delete_by_tag() {
|
||||
local tag="$1"
|
||||
local digest
|
||||
# On demande le digest via HEAD + Accept manifest v2
|
||||
digest="$(curl -fsSI -H "Accept: ${ACCEPT_MANIFEST}" "http://${REGISTRY}/v2/${IMAGE_NAME}/manifests/${tag}" \
|
||||
digest="$(curl -fsSI ${AUTH_ARGS[@]+"${AUTH_ARGS[@]}"} -H "Accept: ${ACCEPT_MANIFEST}" "http://${REGISTRY}/v2/${IMAGE_NAME}/manifests/${tag}" \
|
||||
| tr -d '\r' \
|
||||
| awk -F': ' 'tolower($1)=="docker-content-digest"{print $2}' \
|
||||
| tail -n1)"
|
||||
@@ -201,7 +247,7 @@ delete_by_tag() {
|
||||
|
||||
info "Suppression manifest ${tag} (digest: ${digest})…"
|
||||
# La delete API ne renvoie rien en cas de succès (204)
|
||||
if ! curl -fsS -X DELETE "http://${REGISTRY}/v2/${IMAGE_NAME}/manifests/${digest}" >/dev/null; then
|
||||
if ! curl -fsS ${AUTH_ARGS[@]+"${AUTH_ARGS[@]}"} -X DELETE "http://${REGISTRY}/v2/${IMAGE_NAME}/manifests/${digest}" >/dev/null; then
|
||||
warn "Échec suppression manifest pour ${tag} (digest: ${digest})."
|
||||
fi
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user