Files
dotfiles/setup.sh
1jamesthompson1 6a99575c9f Add tool config system to setup.sh
- Add .dotfiles-tools config file with tool definitions
- setup.sh now parses config and installs by priority
- Add --with-optional/-w flag to auto-install optional tools
- Includes: bash, kitty, vim, git, curl (required), rust, opencode, dua (optional)
2026-03-23 10:05:38 +13:00

124 lines
3.5 KiB
Bash

set -euo pipefail
TOOLS_FILE="$HOME/.dotfiles-tools"
# CLI: parse flags
PROMPT_DELETE=1
INSTALL_OPTIONAL=0
while [[ $# -gt 0 ]]; do
case "$1" in
--no-prompt|-n)
PROMPT_DELETE=0
shift
;;
--prompt|-p)
PROMPT_DELETE=1
shift
;;
--with-optional|-w)
INSTALL_OPTIONAL=1
shift
;;
*) break
esac
done
echo ">>> Bootstrapping new Debian-like machine..."
# Parse tools from config file
parse_tools() {
local priority="$1"
while IFS='|' read -r name check_cmd install_cmd prio; do
[[ "$name" =~ ^#.*$ ]] && continue
[[ -z "$name" ]] && continue
[[ "$prio" == "$priority" ]] && echo "$name|$check_cmd|$install_cmd"
done < "$TOOLS_FILE"
}
# Install required tools
echo ">>> Installing required tools..."
sudo apt update
while IFS='|' read -r name check_cmd install_cmd prio; do
[[ "$prio" != "required" ]] && continue
if ! command -v "$name" &> /dev/null && [[ "$prio" == "required" ]]; then
echo ">>> Installing $name..."
eval "$install_cmd"
fi
done < "$TOOLS_FILE"
# Ask about optional tools
if [[ "$INSTALL_OPTIONAL" == "1" ]] || [[ "$PROMPT_DELETE" == "1" ]]; then
echo ""
echo ">>> Optional tools available:"
while IFS='|' read -r name check_cmd install_cmd prio; do
[[ "$prio" != "optional" ]] && continue
if ! command -v "$name" &> /dev/null; then
echo " - $name"
fi
done < "$TOOLS_FILE"
echo ""
if [[ "$PROMPT_DELETE" == "1" ]] && [[ -t 1 ]]; then
read -r -p "Install optional tools? (y/N): " resp
case "$resp" in
[Yy]* ) INSTALL_OPTIONAL=1 ;;
* ) INSTALL_OPTIONAL=0 ;;
esac
fi
fi
if [[ "$INSTALL_OPTIONAL" == "1" ]]; then
echo ">>> Installing optional tools..."
while IFS='|' read -r name check_cmd install_cmd prio; do
[[ "$prio" != "optional" ]] && continue
if ! command -v "$name" &> /dev/null; then
echo ">>> Installing $name..."
eval "$install_cmd"
fi
done < "$TOOLS_FILE"
fi
# Clone dotfiles
if [ ! -d "$HOME/.dotfiles" ]; then
echo ">>> Cloning dotfiles repo..."
git clone --bare https://gitea.sjhl.nz/james/dotfiles $HOME/.dotfiles
else
echo ">>> Dotfiles repo already exists."
fi
dotfiles() {
/usr/bin/git --git-dir="$HOME/.dotfiles/" --work-tree="$HOME" "$@"
}
echo ">>> Checking out dotfiles..."
if ! dotfiles checkout; then
echo ">>> Conflicts detected! Handling conflicting dotfiles..."
mkdir -p "$HOME/.dotfiles-backup"
conflicts=$(dotfiles checkout 2>&1 | grep -E "\s+\." | awk '{print $1}')
if [ -n "$conflicts" ]; then
if [ "$PROMPT_DELETE" = "0" ]; then
while IFS= read -r f; do
[ -z "$f" ] && continue
mv "$f" "$HOME/.dotfiles-backup/$f"
done <<< "$conflicts"
else
while IFS= read -r f; do
[ -z "$f" ] && continue
if [ -t 1 ]; then
read -r -p "Move '$f' to backup? (y/N): " resp
case "$resp" in
[Yy]* ) mv "$f" "$HOME/.dotfiles-backup/$f" ;;
* ) echo "Skipping '$f'." ;;
esac
else
echo "Non-interactive environment detected; skipping '$f'."
fi
done <<< "$conflicts"
fi
fi
dotfiles checkout
fi
dotfiles config --local status.showUntrackedFiles no
echo ">>> Done! Bash, kitty, vim, and dotfiles are ready."