- wizard.sh: interactive bash wizard that scaffolds new CS projects - lib/: utils, core install, project structure, workflow generation - templates/: Dockerfile, devcontainer.json, agent presets (minimal/standard), system.json, roles, hook rules - README: setup, usage, mobility workflow Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
73 lines
2 KiB
Bash
73 lines
2 KiB
Bash
#!/usr/bin/env bash
|
|
# utils.sh — colors, prompts, helpers
|
|
|
|
RED='\033[0;31m'
|
|
GREEN='\033[0;32m'
|
|
YELLOW='\033[1;33m'
|
|
CYAN='\033[0;36m'
|
|
BOLD='\033[1m'
|
|
RESET='\033[0m'
|
|
|
|
info() { echo -e "${CYAN}${BOLD}[info]${RESET} $*"; }
|
|
success() { echo -e "${GREEN}${BOLD}[ok]${RESET} $*"; }
|
|
warn() { echo -e "${YELLOW}${BOLD}[warn]${RESET} $*"; }
|
|
error() { echo -e "${RED}${BOLD}[error]${RESET} $*" >&2; }
|
|
die() { error "$*"; exit 1; }
|
|
header() { echo -e "\n${BOLD}${CYAN}━━━ $* ━━━${RESET}\n"; }
|
|
|
|
# ask VAR "prompt" "default"
|
|
ask() {
|
|
local var="$1" prompt="$2" default="$3"
|
|
if [[ -n "$default" ]]; then
|
|
echo -ne "${BOLD}${prompt}${RESET} ${CYAN}[${default}]${RESET}: "
|
|
else
|
|
echo -ne "${BOLD}${prompt}${RESET}: "
|
|
fi
|
|
read -r input
|
|
if [[ -z "$input" && -n "$default" ]]; then
|
|
eval "$var=\"$default\""
|
|
else
|
|
eval "$var=\"$input\""
|
|
fi
|
|
}
|
|
|
|
# ask_yn VAR "prompt" "y|n"
|
|
ask_yn() {
|
|
local var="$1" prompt="$2" default="$3"
|
|
local options
|
|
if [[ "$default" == "y" ]]; then options="Y/n"; else options="y/N"; fi
|
|
echo -ne "${BOLD}${prompt}${RESET} ${CYAN}[${options}]${RESET}: "
|
|
read -r input
|
|
input="${input:-$default}"
|
|
if [[ "$input" =~ ^[Yy]$ ]]; then
|
|
eval "$var=y"
|
|
else
|
|
eval "$var=n"
|
|
fi
|
|
}
|
|
|
|
# ask_choice VAR "prompt" option1 option2 ...
|
|
ask_choice() {
|
|
local var="$1" prompt="$2"; shift 2
|
|
local options=("$@")
|
|
echo -e "${BOLD}${prompt}${RESET}"
|
|
for i in "${!options[@]}"; do
|
|
echo -e " ${CYAN}$((i+1))${RESET}) ${options[$i]}"
|
|
done
|
|
echo -ne "Choice ${CYAN}[1]${RESET}: "
|
|
read -r input
|
|
input="${input:-1}"
|
|
if [[ "$input" =~ ^[0-9]+$ ]] && (( input >= 1 && input <= ${#options[@]} )); then
|
|
eval "$var=\"${options[$((input-1))]}\""
|
|
else
|
|
eval "$var=\"${options[0]}\""
|
|
fi
|
|
}
|
|
|
|
require_cmd() {
|
|
command -v "$1" &>/dev/null || die "Required command not found: $1"
|
|
}
|
|
|
|
slugify() {
|
|
echo "$1" | tr '[:upper:]' '[:lower:]' | sed 's/[^a-z0-9]/-/g' | sed 's/-\+/-/g' | sed 's/^-//;s/-$//'
|
|
}
|