Konvention geaendert: history/ -> docs/history/ (prompts + summary/PROJECT_CONTEXT.md). Harter Cutover im pre-commit Hook (Check 4 + Check 6 erwarten docs/history/). Bestehende Repos werden beim naechsten 'git copilot-update' automatisch per git mv migriert (Fallback mv; bei Konflikt Warnung statt Abbruch). Angepasst: pre-commit Hook, alle 6 Skripte + selftest, beide copilot-instructions.md, settings.json Session-Protokoll, history.prompt.md, README, USER/ADMIN/MAINTAINER (+ ADMIN Migrationsabschnitt). git-templates/history -> git-templates/docs/history (git mv). Validiert: shellcheck clean, fish -n clean, selftest PASS, Migrationstest PASS (sh+fish+both-present).
166 lines
8.3 KiB
Bash
166 lines
8.3 KiB
Bash
#!/usr/bin/env bash
|
||
# deploy.sh – Copilot-Setup auf macOS oder Linux mit bash deployen
|
||
# Usage:
|
||
# bash scripts/deploy.sh # Standard-Deploy (nicht-invasiv)
|
||
# bash scripts/deploy.sh --with-self-update-hook # + post-merge Auto-Deploy im Setup-Repo
|
||
#
|
||
# Hinweis: Setzt KEINEN globalen 'git init'-Alias und KEIN init.templateDir.
|
||
# Standard-'git init'/'git clone' bleiben unberuehrt. Opt-in pro Repo:
|
||
# git init-copilot [pfad] (Alias wird hier angelegt)
|
||
# copilot-bootstrap.sh [pfad] (bestehende Repos ausstatten)
|
||
|
||
set -euo pipefail
|
||
|
||
WITH_SELF_HOOK=0
|
||
for arg in "$@"; do
|
||
case "$arg" in
|
||
--with-self-update-hook) WITH_SELF_HOOK=1 ;;
|
||
*) echo "Unbekanntes Argument: $arg" >&2; exit 2 ;;
|
||
esac
|
||
done
|
||
|
||
REPO_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
|
||
echo "=== Copilot Setup Deploy (bash) ==="
|
||
echo "Source: $REPO_DIR"
|
||
|
||
# VS Code User-Verzeichnis portabel ermitteln (identisch zu copilot-update.sh)
|
||
detect_vscode_user_dir() {
|
||
for d in \
|
||
"$HOME/.vscode-server/data/User" \
|
||
"$HOME/.vscode-server-insiders/data/User" \
|
||
"$HOME/Library/Application Support/Code/User" \
|
||
"$HOME/Library/Application Support/Code - Insiders/User" \
|
||
"$HOME/Library/Application Support/VSCodium/User" \
|
||
"$HOME/Library/Application Support/Cursor/User" \
|
||
"$HOME/.config/Code/User" \
|
||
"$HOME/.config/Code - Insiders/User" \
|
||
"$HOME/.config/VSCodium/User" \
|
||
"$HOME/.config/Cursor/User" \
|
||
"$HOME/.var/app/com.visualstudio.code/config/Code/User" \
|
||
"/mnt/c/Users/${USER:-}/AppData/Roaming/Code/User" \
|
||
"/mnt/c/Users/${USER:-}/AppData/Roaming/Code - Insiders/User"
|
||
do
|
||
if [ -d "$d" ]; then
|
||
printf '%s\n' "$d"
|
||
return 0
|
||
fi
|
||
done
|
||
case "$(uname -s)" in
|
||
Darwin) printf '%s\n' "$HOME/Library/Application Support/Code/User" ;;
|
||
*) printf '%s\n' "$HOME/.config/Code/User" ;;
|
||
esac
|
||
}
|
||
|
||
# ── 1. VS Code User-Verzeichnis ermitteln ─────────────────────────────────────
|
||
VSCODE_USER="$(detect_vscode_user_dir)"
|
||
echo "VS Code User dir: $VSCODE_USER"
|
||
mkdir -p "$VSCODE_USER"
|
||
|
||
# ── 2. User settings.json ─────────────────────────────────────────────────────
|
||
if [[ -f "$VSCODE_USER/settings.json" ]]; then
|
||
echo " ─ settings.json exists – skipping (merge manually if needed)"
|
||
echo " Reference: $REPO_DIR/user-settings/settings.json"
|
||
else
|
||
cp "$REPO_DIR/user-settings/settings.json" "$VSCODE_USER/settings.json"
|
||
echo " ✓ settings.json deployed"
|
||
fi
|
||
|
||
# ── 3. Prompt Files ───────────────────────────────────────────────────────────
|
||
mkdir -p "$VSCODE_USER/prompts"
|
||
for f in "$REPO_DIR/prompts/"*.prompt.md; do
|
||
fname="$(basename "$f")"
|
||
if [[ -f "$VSCODE_USER/prompts/$fname" ]]; then
|
||
echo " ─ prompts/$fname already exists, skipping"
|
||
else
|
||
cp "$f" "$VSCODE_USER/prompts/$fname"
|
||
echo " ✓ prompts/$fname deployed"
|
||
fi
|
||
done
|
||
|
||
# ── 4. Git-Templates ──────────────────────────────────────────────────────────
|
||
GIT_TEMPLATE_DIR="$HOME/.git-templates"
|
||
mkdir -p "$GIT_TEMPLATE_DIR/.github" "$GIT_TEMPLATE_DIR/.vscode" \
|
||
"$GIT_TEMPLATE_DIR/hooks" "$GIT_TEMPLATE_DIR/docs" \
|
||
"$GIT_TEMPLATE_DIR/docs/history/summary"
|
||
cp "$REPO_DIR/git-templates/.github/copilot-instructions.md" "$GIT_TEMPLATE_DIR/.github/"
|
||
cp "$REPO_DIR/git-templates/.vscode/settings.json" "$GIT_TEMPLATE_DIR/.vscode/"
|
||
cp "$REPO_DIR/git-templates/.vscode/extensions.json" "$GIT_TEMPLATE_DIR/.vscode/"
|
||
cp "$REPO_DIR/git-templates/hooks/pre-commit" "$GIT_TEMPLATE_DIR/hooks/"
|
||
chmod +x "$GIT_TEMPLATE_DIR/hooks/pre-commit"
|
||
cp "$REPO_DIR/git-templates/docs/USER.md" "$GIT_TEMPLATE_DIR/docs/"
|
||
cp "$REPO_DIR/git-templates/docs/ADMIN.md" "$GIT_TEMPLATE_DIR/docs/"
|
||
cp "$REPO_DIR/git-templates/docs/MAINTAINER.md" "$GIT_TEMPLATE_DIR/docs/"
|
||
cp "$REPO_DIR/git-templates/docs/history/summary/PROJECT_CONTEXT.md" "$GIT_TEMPLATE_DIR/docs/history/summary/"
|
||
echo " ✓ git-templates deployed → $GIT_TEMPLATE_DIR"
|
||
# init.templateDir wird bewusst NICHT global gesetzt – sonst wuerde jeder
|
||
# 'git init'/'git clone' (auch fremde Repos) automatisch den Quality Gate erben.
|
||
# Frueher gesetzten Wert entfernen, falls er auf unsere Templates zeigt.
|
||
CURRENT_TPL="$(git config --global --get init.templateDir || true)"
|
||
if [[ "$CURRENT_TPL" == "$GIT_TEMPLATE_DIR" ]]; then
|
||
git config --global --unset init.templateDir || true
|
||
echo " ✓ altes globales init.templateDir entfernt (nicht mehr invasiv)"
|
||
else
|
||
echo " ─ init.templateDir nicht global gesetzt (gewollt)"
|
||
fi
|
||
|
||
# ── 5. Bootstrap- & Update-Skripte ───────────────────────────────────────────
|
||
mkdir -p "$HOME/.local/bin"
|
||
cp "$REPO_DIR/scripts/copilot-bootstrap.sh" "$HOME/.local/bin/copilot-bootstrap.sh"
|
||
chmod +x "$HOME/.local/bin/copilot-bootstrap.sh"
|
||
echo " ✓ copilot-bootstrap.sh installed to ~/.local/bin/"
|
||
if [[ -f "$REPO_DIR/scripts/copilot-bootstrap.fish" ]]; then
|
||
cp "$REPO_DIR/scripts/copilot-bootstrap.fish" "$HOME/.local/bin/copilot-bootstrap.fish"
|
||
chmod +x "$HOME/.local/bin/copilot-bootstrap.fish"
|
||
echo " ✓ copilot-bootstrap.fish installed to ~/.local/bin/"
|
||
fi
|
||
cp "$REPO_DIR/scripts/copilot-update.sh" "$HOME/.local/bin/copilot-update.sh"
|
||
chmod +x "$HOME/.local/bin/copilot-update.sh"
|
||
echo " ✓ copilot-update.sh installed to ~/.local/bin/"
|
||
if [[ -f "$REPO_DIR/scripts/copilot-update.fish" ]]; then
|
||
cp "$REPO_DIR/scripts/copilot-update.fish" "$HOME/.local/bin/copilot-update.fish"
|
||
chmod +x "$HOME/.local/bin/copilot-update.fish"
|
||
echo " ✓ copilot-update.fish installed to ~/.local/bin/"
|
||
fi
|
||
|
||
# ── 6. Git-Aliase: init → auto-bootstrap | copilot-update → updater ──────────
|
||
# Verwendet git --exec-path um Rekursion zu vermeiden (kein Alias-Loop).
|
||
# Kein Override des Standard-'git init' mehr. Frueheren invasiven Alias entfernen.
|
||
CURRENT_INIT_ALIAS="$(git config --global --get alias.init || true)"
|
||
if [[ "$CURRENT_INIT_ALIAS" == *copilot-bootstrap* ]]; then
|
||
git config --global --unset alias.init || true
|
||
echo " ✓ alter invasiver 'git init'-Alias entfernt"
|
||
fi
|
||
# Opt-in: explizites 'git init-copilot' macht git init + bootstrap.
|
||
# shellcheck disable=SC2016 # Alias absichtlich literal – git expandiert zur Laufzeit
|
||
git config --global alias.init-copilot '!f() { dir=.; for a in "$@"; do case "$a" in -*) ;; *) dir="$a" ;; esac; done; "$(git --exec-path)/git-init" "$@" && "$HOME/.local/bin/copilot-bootstrap.sh" "$dir"; }; f'
|
||
echo " ✓ git alias 'init-copilot' gesetzt (opt-in: git init + copilot-bootstrap)"
|
||
git config --global alias.copilot-update '!~/.local/bin/copilot-update.sh'
|
||
echo " ✓ git alias 'copilot-update' gesetzt (aktualisiert Templates & Prompts)"
|
||
|
||
# ── 7. post-merge Hook für dieses Setup-Repo ─────────────────────────────────
|
||
# Nur mit --with-self-update-hook: nach jedem 'git pull' auf dem Setup-Repo
|
||
# wird deploy.sh automatisch erneut ausgeführt.
|
||
SELF_HOOKS_DIR="$REPO_DIR/.git/hooks"
|
||
if [[ "$WITH_SELF_HOOK" -eq 1 ]]; then
|
||
if [[ -d "$SELF_HOOKS_DIR" ]]; then
|
||
cat > "$SELF_HOOKS_DIR/post-merge" << 'HOOK'
|
||
#!/usr/bin/env sh
|
||
# post-merge – Auto-Deploy nach git pull auf dem Setup-Repo
|
||
echo ""
|
||
echo " [post-merge] Setup-Repo aktualisiert – deploye Templates neu..."
|
||
SCRIPT_DIR="$(cd "$(dirname "$0")/../../scripts" && pwd)"
|
||
bash "$SCRIPT_DIR/deploy.sh"
|
||
HOOK
|
||
chmod +x "$SELF_HOOKS_DIR/post-merge"
|
||
echo " ✓ post-merge Hook im Setup-Repo installiert (auto-deploy nach git pull)"
|
||
fi
|
||
else
|
||
echo " ─ post-merge Auto-Deploy nicht installiert (opt-in: --with-self-update-hook)"
|
||
fi
|
||
|
||
echo ""
|
||
echo "=== Done ==="
|
||
echo "Next: Activate Settings Sync in VS Code (Cmd+Shift+P → 'Settings Sync: Turn On')"
|
||
echo " Neues Repo mit Copilot-Setup: git init-copilot [pfad]"
|
||
echo " Bestehendes Repo ausstatten: copilot-bootstrap.sh [pfad]"
|
||
echo " Templates aktuell halten: git copilot-update (in jedem Repo)"
|