-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathinstall.sh
More file actions
executable file
·185 lines (163 loc) · 5.84 KB
/
install.sh
File metadata and controls
executable file
·185 lines (163 loc) · 5.84 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
#!/bin/bash
set -e
# Dotfiles installer script
# Usage: curl -sSL fx.github.io/dotfiles/install.sh | sh -s -- [profile]
#
# Environment variables:
# DEBUG=1 - Show detailed error output when git fails
# FORCE_SSH=1 - Fail entirely if SSH doesn't work (no HTTPS fallback)
# Auto-detect profile if not specified
if [ -n "$1" ]; then
PROFILE="$1"
elif [ -n "$DOTFILES_PROFILE" ]; then
PROFILE="$DOTFILES_PROFILE"
elif command -v hyprctl >/dev/null 2>&1; then
# Hyprland is installed - check if laptop (has battery) or desktop
if ls /sys/class/power_supply/BAT* >/dev/null 2>&1; then
PROFILE="laptop"
else
PROFILE="desktop"
fi
else
PROFILE="default"
fi
DOTFILES_REPO="fx/dotfiles"
MISE_INSTALL_URL="https://mise.jdx.dev/install.sh"
# ANSI color codes
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[0;33m'
BLUE='\033[0;34m'
MAGENTA='\033[0;35m'
CYAN='\033[0;36m'
BOLD='\033[1m'
RESET='\033[0m'
# Helper functions for colored output
print_step() { echo -e "${BLUE}${BOLD}→${RESET} ${CYAN}$1${RESET}"; }
print_success() { echo -e "${GREEN}${BOLD}✓${RESET} ${GREEN}$1${RESET}"; }
print_warning() { echo -e "${YELLOW}${BOLD}⚠${RESET} ${YELLOW}$1${RESET}"; }
print_error() { echo -e "${RED}${BOLD}✗${RESET} ${RED}$1${RESET}"; }
print_info() { echo -e "${MAGENTA}${BOLD}ℹ${RESET} ${MAGENTA}$1${RESET}"; }
# Run command with error handling
run_or_fail() {
local msg="$1"
shift
if ! "$@" 2>&1 | tee -a /tmp/install.log; then
print_error "$msg"
echo ""
echo "Error details:"
tail -20 /tmp/install.log
exit 1
fi
}
# Set Git to automatically accept new SSH keys while preserving existing GIT_SSH_COMMAND
export GIT_SSH_COMMAND="${GIT_SSH_COMMAND:-ssh} -o StrictHostKeyChecking=accept-new"
# Purge cached chezmoi directory and state if they exist
if [ -d "$HOME/.local/share/chezmoi" ]; then
print_info "Removing cached chezmoi directory..."
rm -rf "$HOME/.local/share/chezmoi"
fi
if [ -f "$HOME/.config/chezmoi/chezmoistate.boltdb" ]; then
print_info "Removing chezmoi state database..."
rm -f "$HOME/.config/chezmoi/chezmoistate.boltdb"
fi
# Detect if we're running from within the dotfiles repository
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
LOCAL_MODE=false
if [ -f "$SCRIPT_DIR/.chezmoiignore" ] && [ -d "$SCRIPT_DIR/.chezmoiscripts" ]; then
LOCAL_MODE=true
print_success "Using local dotfiles repository at $SCRIPT_DIR"
else
# Test git SSH access by attempting to ls-remote (5 second timeout)
print_step "Checking Git access..."
GIT_SSH_ERROR=$(mktemp)
if timeout 5 git ls-remote "git@github.com:${DOTFILES_REPO}.git" >/dev/null 2>"$GIT_SSH_ERROR"; then
DOTFILES_URL="git@github.com:${DOTFILES_REPO}.git"
print_success "Using SSH for dotfiles repository"
rm -f "$GIT_SSH_ERROR"
else
SSH_EXIT_CODE=$?
if [ "${DEBUG:-0}" = "1" ]; then
print_error "SSH git access failed (exit code: $SSH_EXIT_CODE)"
echo "Error output:"
cat "$GIT_SSH_ERROR"
echo ""
fi
rm -f "$GIT_SSH_ERROR"
if [ "${FORCE_SSH:-0}" = "1" ]; then
print_error "SSH access required (FORCE_SSH=1) but SSH failed"
print_info "Run with DEBUG=1 for more details"
exit 1
fi
DOTFILES_URL="https://github.com/${DOTFILES_REPO}.git"
print_warning "Using HTTPS for dotfiles repository (SSH failed)"
fi
fi
echo ""
echo -e "${BOLD}🚀 Installing dotfiles${RESET}"
echo -e "${BOLD} Profile: ${CYAN}$PROFILE${RESET}"
echo ""
# Check if mise is installed
if command -v mise >/dev/null 2>&1; then
print_success "mise is already installed"
else
print_step "Installing mise..."
run_or_fail "Failed to install mise" sh -c "curl -sSL '$MISE_INSTALL_URL' | sh"
export PATH="$HOME/.local/bin:$PATH"
print_success "mise installed"
fi
# Activate mise
eval "$(mise activate bash)" 2>>/tmp/install.log || run_or_fail "Failed to activate mise" false
# Install chezmoi via mise
print_step "Installing chezmoi..."
run_or_fail "Failed to install chezmoi" mise use -g chezmoi@latest
print_success "chezmoi installed"
# Initialize and apply dotfiles
if [ "$LOCAL_MODE" = true ]; then
# Local dev mode: use --source to apply directly from working tree
print_step "Configuring for local development..."
# Generate chezmoi config with profile settings
CHEZMOI_CONFIG="$HOME/.config/chezmoi/chezmoi.toml"
mkdir -p "$(dirname "$CHEZMOI_CONFIG")"
IS_DESKTOP=false
IS_LAPTOP=false
if [ "$PROFILE" = "desktop" ]; then
IS_DESKTOP=true
elif [ "$PROFILE" = "laptop" ]; then
IS_DESKTOP=true
IS_LAPTOP=true
fi
cat > "$CHEZMOI_CONFIG" << EOF
[data]
profile = "$PROFILE"
include_defaults = true
is_desktop = $IS_DESKTOP
is_laptop = $IS_LAPTOP
[diff]
pager = "less"
EOF
print_success "Configuration ready"
# Apply directly from local source
print_step "Applying dotfiles..."
run_or_fail "Failed to apply dotfiles" mise exec -- chezmoi apply --source="$SCRIPT_DIR" --force
else
# Remote mode: use chezmoi init + apply
print_step "Initializing dotfiles..."
INIT_OUTPUT=$(mktemp)
if mise exec -- chezmoi init --promptString profile="$PROFILE" "$DOTFILES_URL" >"$INIT_OUTPUT" 2>&1; then
grep -v "Cloning into" "$INIT_OUTPUT" | grep -v "^done\.$" || true
rm -f "$INIT_OUTPUT"
else
grep -v "Cloning into" "$INIT_OUTPUT" | grep -v "^done\.$" || true
rm -f "$INIT_OUTPUT"
print_error "Failed to initialize dotfiles"
exit 1
fi
print_success "Dotfiles initialized"
print_step "Applying dotfiles..."
run_or_fail "Failed to apply dotfiles" mise exec -- chezmoi apply --force
fi
print_success "Dotfiles applied"
echo ""
echo -e "${GREEN}${BOLD}✨ Dotfiles installation complete!${RESET}"
echo ""