#!/usr/bin/env bash set -euo pipefail SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" cd "$SCRIPT_DIR" # --- Colors --- RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' CYAN='\033[0;36m' BOLD='\033[1m' DIM='\033[2m' NC='\033[0m' # --- Config --- KEYSTORE_DIR="keystore" KEYSTORE_FILE="$KEYSTORE_DIR/radio247-release.jks" KEY_ALIAS="radio247" DIST_DIR="dist" GRADLE_BUILD_FILE="app/build.gradle.kts" banner() { echo "" echo -e "${CYAN}╔══════════════════════════════════╗${NC}" echo -e "${CYAN}║${BOLD} Radio 247 Build Tool ${NC}${CYAN}║${NC}" echo -e "${CYAN}╚══════════════════════════════════╝${NC}" echo "" } info() { echo -e "${BLUE}▸${NC} $1"; } success() { echo -e "${GREEN}✓${NC} $1"; } warn() { echo -e "${YELLOW}⚠${NC} $1"; } error() { echo -e "${RED}✗${NC} $1"; } get_version_name() { if [[ ! -f "$GRADLE_BUILD_FILE" ]]; then error "Build file not found: $GRADLE_BUILD_FILE" exit 1 fi local v v=$(grep 'versionName' "$GRADLE_BUILD_FILE" | head -1 | sed 's/.*"\([^"]*\)".*/\1/') if [[ -z "$v" ]]; then error "Could not extract version from $GRADLE_BUILD_FILE" exit 1 fi echo "$v" } preflight_check() { local ok=true if ! command -v java &>/dev/null && [[ -z "${JAVA_HOME:-}" ]]; then error "Java not found. Install JDK 17+ or set JAVA_HOME." ok=false fi if [[ ! -x "./gradlew" ]]; then error "Gradle wrapper not found or not executable." ok=false fi if [[ "$ok" != true ]]; then exit 1 fi } ensure_dist_dir() { mkdir -p "$DIST_DIR" } main_menu() { echo -e "${BOLD}What would you like to do?${NC}" echo "" echo -e " ${BOLD}1)${NC} Build Release APK ${DIM}(signed, shareable)${NC}" echo -e " ${BOLD}2)${NC} Build Debug APK ${DIM}(quick, for testing)${NC}" echo -e " ${BOLD}3)${NC} Manage Keystore ${DIM}(create or check signing key)${NC}" echo -e " ${BOLD}4)${NC} Clean ${DIM}(remove build artifacts)${NC}" echo -e " ${BOLD}5)${NC} Exit" echo "" local choice read -rp "> " choice case $choice in 1) build_release ;; 2) build_debug ;; 3) manage_keystore ;; 4) clean_build ;; 5) echo ""; exit 0 ;; *) warn "Invalid choice. Pick 1-5." ;; esac } read_keystore_password() { local password read -rsp "Keystore password: " password echo >&2 echo "$password" } create_keystore() { echo -e "${BOLD}No keystore found. Let's create one.${NC}" echo "" local cn org password password_confirm read -rp "Your name (for the certificate): " cn [[ -z "$cn" ]] && { error "Name is required."; return 1; } read -rp "Organization (optional, Enter to skip): " org while true; do read -rsp "Password (min 6 chars): " password echo if [[ ${#password} -lt 6 ]]; then warn "Password must be at least 6 characters." continue fi read -rsp "Confirm password: " password_confirm echo if [[ "$password" != "$password_confirm" ]]; then warn "Passwords don't match. Try again." continue fi break done mkdir -p "$KEYSTORE_DIR" local dname="CN=$cn" [[ -n "$org" ]] && dname="$dname, O=$org" info "Creating keystore..." keytool -genkeypair \ -alias "$KEY_ALIAS" \ -keyalg RSA \ -keysize 2048 \ -validity 10000 \ -keystore "$KEYSTORE_FILE" \ -storepass "$password" \ -keypass "$password" \ -dname "$dname" \ 2>/dev/null || true if [[ -f "$KEYSTORE_FILE" ]]; then echo "" success "Keystore created at ${BOLD}$KEYSTORE_FILE${NC}" echo "" warn "IMPORTANT: Back up this file and remember your password." warn "If you lose either, you cannot update the app on devices" warn "that already have this version installed." else error "Keystore creation failed." return 1 fi } manage_keystore() { if [[ -f "$KEYSTORE_FILE" ]]; then success "Keystore exists at ${BOLD}$KEYSTORE_FILE${NC}" echo "" info "Keystore details:" keytool -list -keystore "$KEYSTORE_FILE" -alias "$KEY_ALIAS" \ -storepass "$(read_keystore_password)" 2>/dev/null \ || warn "Could not read keystore (wrong password?)" return fi create_keystore } # Placeholder functions — implemented in subsequent tasks build_release() { warn "Not yet implemented"; } build_debug() { warn "Not yet implemented"; } clean_build() { warn "Not yet implemented"; } # --- Main --- preflight_check banner while true; do main_menu echo "" done