Created
August 10, 2025 15:36
-
-
Save ShoGinn/2177a045f992cc027f023ec309b5fd3a to your computer and use it in GitHub Desktop.
Update the Blocky app
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
# Blocky Update Helper Script | |
# Updates Blocky to the latest version and restarts the service | |
# Configuration - Modify these variables if needed | |
BLOCKY_DIR="/opt/blocky" | |
SERVICE_NAME="blocky" | |
CONFIG_FILE="config.yml" | |
# Function to detect OS and architecture | |
detect_platform() { | |
local os="" | |
local arch="" | |
# Detect OS | |
case "$(uname -s)" in | |
Linux*) os="Linux" ;; | |
Darwin*) os="Darwin" ;; | |
FreeBSD*) os="Freebsd" ;; | |
NetBSD*) os="Netbsd" ;; | |
OpenBSD*) os="Openbsd" ;; | |
CYGWIN*|MINGW*|MSYS*) os="Windows" ;; | |
*) | |
msg_error "Unsupported operating system: $(uname -s)" | |
exit 1 | |
;; | |
esac | |
# Detect architecture | |
case "$(uname -m)" in | |
x86_64|amd64) arch="x86_64" ;; | |
aarch64|arm64) arch="arm64" ;; | |
armv7l) arch="armv7" ;; | |
armv6l) arch="armv6" ;; | |
*) | |
msg_error "Unsupported architecture: $(uname -m)" | |
msg_error "Supported architectures: x86_64, arm64, armv7, armv6" | |
exit 1 | |
;; | |
esac | |
echo "${os}_${arch}" | |
} | |
# Function to get download URL and file extension | |
get_download_info() { | |
local platform="$1" | |
local release="$2" | |
local file_ext="" | |
# Determine file extension based on OS | |
if [[ "$platform" == Windows_* ]]; then | |
file_ext="zip" | |
else | |
file_ext="tar.gz" | |
fi | |
echo "https://github.com/0xERR0R/blocky/releases/download/v${release}/blocky_v${release}_${platform}.${file_ext}|${file_ext}" | |
} | |
# Colors for output | |
RED='\033[0;31m' | |
GREEN='\033[0;32m' | |
YELLOW='\033[1;33m' | |
BLUE='\033[0;34m' | |
NC='\033[0m' # No Color | |
# Function to print colored messages | |
msg_info() { | |
echo -e "${BLUE}[INFO]${NC} $1" | |
} | |
msg_ok() { | |
echo -e "${GREEN}[OK]${NC} $1" | |
} | |
msg_error() { | |
echo -e "${RED}[ERROR]${NC} $1" | |
} | |
msg_warn() { | |
echo -e "${YELLOW}[WARN]${NC} $1" | |
} | |
# Function to run commands with appropriate privileges | |
run_privileged() { | |
if [[ $EUID -eq 0 ]]; then | |
# Already running as root | |
"$@" | |
else | |
# Use sudo | |
sudo "$@" | |
fi | |
} | |
# Function to check if we can get root privileges | |
check_privileges() { | |
if [[ $EUID -eq 0 ]]; then | |
return 0 | |
fi | |
# Check if sudo is available and user can use it | |
if ! command -v sudo >/dev/null 2>&1; then | |
msg_error "This script requires root privileges and sudo is not available" | |
msg_error "Please run as root: sudo $0" | |
exit 1 | |
fi | |
# Test sudo access without prompting for password if cached | |
if ! sudo -n true 2>/dev/null; then | |
msg_info "This script requires root privileges for system operations" | |
msg_info "You may be prompted for your password..." | |
# Test sudo access with password prompt | |
if ! sudo true; then | |
msg_error "Failed to obtain root privileges" | |
exit 1 | |
fi | |
fi | |
msg_ok "Root privileges confirmed" | |
} | |
# Check for proper privileges early | |
check_privileges | |
# Check if Blocky is installed | |
if [ ! -d "$BLOCKY_DIR" ]; then | |
msg_error "Blocky installation not found in $BLOCKY_DIR" | |
exit 1 | |
fi | |
# Function to create/recreate Blocky service | |
create_blocky_service() { | |
msg_info "Creating/updating Blocky service..." | |
run_privileged tee /etc/systemd/system/${SERVICE_NAME}.service > /dev/null <<EOF | |
[Unit] | |
Description=Blocky | |
After=network.target | |
[Service] | |
User=root | |
WorkingDirectory=$BLOCKY_DIR | |
ExecStart=$BLOCKY_DIR/blocky --config $CONFIG_FILE | |
Restart=on-failure | |
RestartSec=5 | |
[Install] | |
WantedBy=multi-user.target | |
EOF | |
# Reload systemd and enable service | |
run_privileged systemctl daemon-reload | |
run_privileged systemctl enable $SERVICE_NAME | |
msg_ok "Blocky service created/updated" | |
} | |
# Function to validate service file | |
validate_service() { | |
local service_file="/etc/systemd/system/${SERVICE_NAME}.service" | |
if [ ! -f "$service_file" ]; then | |
return 1 | |
fi | |
# Check if service file contains required sections | |
if ! grep -q "\[Unit\]" "$service_file" || \ | |
! grep -q "\[Service\]" "$service_file" || \ | |
! grep -q "\[Install\]" "$service_file" || \ | |
! grep -q "ExecStart=$BLOCKY_DIR/blocky" "$service_file" || \ | |
! grep -q "WorkingDirectory=$BLOCKY_DIR" "$service_file"; then | |
return 1 | |
fi | |
return 0 | |
} | |
# Check and validate Blocky service | |
msg_info "Checking Blocky service..." | |
SERVICE_NEEDS_CREATION=false | |
if ! run_privileged systemctl list-unit-files | grep -q "${SERVICE_NAME}.service"; then | |
msg_warn "Blocky service not found in systemd" | |
SERVICE_NEEDS_CREATION=true | |
elif ! validate_service; then | |
msg_warn "Blocky service file appears to be corrupted or incomplete" | |
SERVICE_NEEDS_CREATION=true | |
else | |
msg_ok "Blocky service found and appears valid" | |
fi | |
# Create/recreate service if needed | |
if [ "$SERVICE_NEEDS_CREATION" = true ]; then | |
create_blocky_service | |
fi | |
msg_info "Starting Blocky update process..." | |
# Detect platform | |
PLATFORM=$(detect_platform) | |
msg_info "Detected platform: $PLATFORM" | |
# Get current version if binary exists | |
CURRENT_VERSION="" | |
if [ -f "$BLOCKY_DIR/blocky" ]; then | |
CURRENT_VERSION=$($BLOCKY_DIR/blocky version 2>/dev/null | grep -oP 'Version: \K[^\s]+' || echo "unknown") | |
msg_info "Current Blocky version: $CURRENT_VERSION" | |
fi | |
# Get latest release version | |
msg_info "Checking for latest Blocky release..." | |
RELEASE=$(curl -fsSL https://api.github.com/repos/0xERR0R/blocky/releases/latest | grep "tag_name" | awk '{print substr($2, 3, length($2)-4) }') | |
if [ -z "$RELEASE" ]; then | |
msg_error "Failed to fetch latest release version" | |
exit 1 | |
fi | |
msg_info "Latest Blocky version: $RELEASE" | |
# Normalize versions for comparison (remove 'v' prefix if present) | |
CURRENT_VERSION_CLEAN="${CURRENT_VERSION#v}" | |
RELEASE_CLEAN="${RELEASE#v}" | |
# Compare versions (skip if current version is unknown) | |
if [ "$CURRENT_VERSION_CLEAN" != "unknown" ] && [ "$CURRENT_VERSION_CLEAN" = "$RELEASE_CLEAN" ]; then | |
msg_ok "Blocky is already up to date (v$RELEASE_CLEAN)" | |
exit 0 | |
fi | |
# Stop Blocky service if it's running | |
msg_info "Stopping Blocky service..." | |
if run_privileged systemctl is-active --quiet $SERVICE_NAME; then | |
if ! run_privileged systemctl stop $SERVICE_NAME; then | |
msg_error "Failed to stop Blocky service" | |
exit 1 | |
fi | |
msg_ok "Blocky service stopped" | |
else | |
msg_ok "Blocky service was not running" | |
fi | |
# Backup current binary (if exists) | |
if [ -f "$BLOCKY_DIR/blocky" ]; then | |
msg_info "Backing up current Blocky binary..." | |
# Use sudo for cp if we don't have write access to the directory | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR" ]; then | |
cp $BLOCKY_DIR/blocky $BLOCKY_DIR/blocky.backup | |
else | |
run_privileged cp $BLOCKY_DIR/blocky $BLOCKY_DIR/blocky.backup | |
fi | |
msg_ok "Current binary backed up as blocky.backup" | |
fi | |
# Download and install new version | |
DOWNLOAD_INFO=$(get_download_info "$PLATFORM" "$RELEASE") | |
DOWNLOAD_URL=$(echo "$DOWNLOAD_INFO" | cut -d'|' -f1) | |
FILE_EXT=$(echo "$DOWNLOAD_INFO" | cut -d'|' -f2) | |
msg_info "Downloading Blocky v${RELEASE} for ${PLATFORM}..." | |
TEMP_DIR=$(mktemp -d) | |
DOWNLOAD_FILE="$TEMP_DIR/blocky.$FILE_EXT" | |
if ! curl -fsSL "$DOWNLOAD_URL" -o "$DOWNLOAD_FILE"; then | |
msg_error "Failed to download Blocky v${RELEASE} for ${PLATFORM}" | |
msg_error "Download URL: $DOWNLOAD_URL" | |
# Restore backup if download fails | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR" ]; then | |
mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
else | |
run_privileged mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
fi | |
msg_warn "Restored backup binary" | |
fi | |
run_privileged systemctl start $SERVICE_NAME | |
rm -rf "$TEMP_DIR" | |
exit 1 | |
fi | |
msg_info "Extracting Blocky v${RELEASE}..." | |
if [[ "$FILE_EXT" == "tar.gz" ]]; then | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR" ]; then | |
if ! tar -xzf "$DOWNLOAD_FILE" -C $BLOCKY_DIR/; then | |
msg_error "Failed to extract Blocky" | |
# Restore backup if extraction fails | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
msg_warn "Restored backup binary" | |
fi | |
run_privileged systemctl start $SERVICE_NAME | |
rm -rf "$TEMP_DIR" | |
exit 1 | |
fi | |
else | |
if ! run_privileged tar -xzf "$DOWNLOAD_FILE" -C $BLOCKY_DIR/; then | |
msg_error "Failed to extract Blocky" | |
# Restore backup if extraction fails | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
run_privileged mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
msg_warn "Restored backup binary" | |
fi | |
run_privileged systemctl start $SERVICE_NAME | |
rm -rf "$TEMP_DIR" | |
exit 1 | |
fi | |
fi | |
elif [[ "$FILE_EXT" == "zip" ]]; then | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR" ]; then | |
if ! unzip -q "$DOWNLOAD_FILE" -d $BLOCKY_DIR/; then | |
msg_error "Failed to extract Blocky" | |
msg_error "Note: unzip command is required for Windows builds" | |
# Restore backup if extraction fails | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
msg_warn "Restored backup binary" | |
fi | |
run_privileged systemctl start $SERVICE_NAME | |
rm -rf "$TEMP_DIR" | |
exit 1 | |
fi | |
else | |
if ! run_privileged unzip -q "$DOWNLOAD_FILE" -d $BLOCKY_DIR/; then | |
msg_error "Failed to extract Blocky" | |
msg_error "Note: unzip command is required for Windows builds" | |
# Restore backup if extraction fails | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
run_privileged mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
msg_warn "Restored backup binary" | |
fi | |
run_privileged systemctl start $SERVICE_NAME | |
rm -rf "$TEMP_DIR" | |
exit 1 | |
fi | |
fi | |
fi | |
# Clean up temp directory | |
rm -rf "$TEMP_DIR" | |
# Make sure the binary is executable (not needed for Windows, but doesn't hurt) | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR/blocky" ]; then | |
chmod +x $BLOCKY_DIR/blocky | |
else | |
run_privileged chmod +x $BLOCKY_DIR/blocky | |
fi | |
# Verify the installation | |
msg_info "Verifying installation..." | |
NEW_VERSION=$($BLOCKY_DIR/blocky version 2>/dev/null | grep -oP 'Version: \K[^\s]+' || echo "unknown") | |
NEW_VERSION_CLEAN="${NEW_VERSION#v}" | |
RELEASE_CLEAN="${RELEASE#v}" | |
if [ "$NEW_VERSION_CLEAN" = "$RELEASE_CLEAN" ]; then | |
msg_ok "Successfully installed Blocky $NEW_VERSION" | |
# Remove backup if verification successful | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR" ]; then | |
rm $BLOCKY_DIR/blocky.backup | |
else | |
run_privileged rm $BLOCKY_DIR/blocky.backup | |
fi | |
fi | |
else | |
msg_error "Version verification failed. Expected: $RELEASE_CLEAN, Got: $NEW_VERSION_CLEAN" | |
# Restore backup if verification fails | |
if [ -f "$BLOCKY_DIR/blocky.backup" ]; then | |
if [[ $EUID -eq 0 ]] || [ -w "$BLOCKY_DIR" ]; then | |
mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
else | |
run_privileged mv $BLOCKY_DIR/blocky.backup $BLOCKY_DIR/blocky | |
fi | |
msg_warn "Restored backup binary" | |
fi | |
fi | |
# Start Blocky service | |
msg_info "Starting Blocky service..." | |
# Ensure service is enabled | |
if ! run_privileged systemctl is-enabled --quiet $SERVICE_NAME; then | |
msg_info "Enabling Blocky service..." | |
run_privileged systemctl enable $SERVICE_NAME | |
fi | |
if ! run_privileged systemctl start $SERVICE_NAME; then | |
msg_error "Failed to start Blocky service" | |
msg_error "Check service status with: systemctl status $SERVICE_NAME" | |
exit 1 | |
fi | |
# Wait a moment and check service status | |
sleep 2 | |
if run_privileged systemctl is-active --quiet $SERVICE_NAME; then | |
msg_ok "Blocky service started successfully" | |
msg_ok "Update completed! Blocky is now running version $NEW_VERSION" | |
else | |
msg_error "Blocky service failed to start properly" | |
msg_error "Check service status with: systemctl status $SERVICE_NAME" | |
msg_error "Check logs with: journalctl -u $SERVICE_NAME -f" | |
exit 1 | |
fi | |
# Optional: Show service status | |
echo | |
msg_info "Service Status:" | |
run_privileged systemctl status $SERVICE_NAME --no-pager -l |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment