| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164 |
- #!/bin/bash
- # compile.sh - Compile installer sources into a single distributable script
- # This script is run during the build process to create the final installer
- set -e
- SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
- OUTPUT_FILE="${1:-install-usm.sh}"
- VERSION="${2:-0.1.0}"
- USM_SOURCE_DIR="${3:-$SCRIPT_DIR/../src}"
- # Temporary directory for building
- WORK_DIR=$(mktemp -d)
- trap "rm -rf $WORK_DIR" EXIT
- echo "Compiling USM installer..."
- echo " Version: $VERSION"
- echo " Output: $OUTPUT_FILE"
- echo " USM Source: $USM_SOURCE_DIR"
- # Step 1: Clone external repositories
- echo "Cloning external repositories..."
- SOURCES_DIR="$WORK_DIR/sources"
- mkdir -p "$SOURCES_DIR"
- # Clone Invercargill
- if [[ ! -d "$SOURCES_DIR/Invercargill" ]]; then
- echo " Cloning Invercargill..."
- git clone --depth 1 https://fabrica.unitatem.net/Tilo15/Invercargill.git "$SOURCES_DIR/Invercargill" 2>/dev/null || {
- echo "Warning: Could not clone Invercargill, will try without --depth 1"
- git clone https://fabrica.unitatem.net/Tilo15/Invercargill.git "$SOURCES_DIR/Invercargill" 2>/dev/null || {
- echo "Error: Could not clone Invercargill repository"
- exit 1
- }
- }
- fi
- # Clone Invercargill-Json
- if [[ ! -d "$SOURCES_DIR/Invercargill-Json" ]]; then
- echo " Cloning Invercargill-Json..."
- git clone --depth 1 https://git.sr.ht/~tilo15/Invercargill-Json "$SOURCES_DIR/Invercargill-Json" 2>/dev/null || {
- echo "Warning: Could not clone Invercargill-Json, will try without --depth 1"
- git clone https://git.sr.ht/~tilo15/Invercargill-Json "$SOURCES_DIR/Invercargill-Json" 2>/dev/null || {
- echo "Error: Could not clone Invercargill-Json repository"
- exit 1
- }
- }
- fi
- # Copy USM source (USM's meson.build is in src/, not project root)
- echo "Copying USM source..."
- mkdir -p "$SOURCES_DIR/usm"
- # USM_SOURCE_DIR points to the src/ directory which contains meson.build
- # Copy the entire src directory contents to usm/
- cp -r "$USM_SOURCE_DIR"/* "$SOURCES_DIR/usm/" 2>/dev/null || true
- # Copy additional root level files for reference
- cp "$USM_SOURCE_DIR/../MANIFEST.usm" "$SOURCES_DIR/usm/" 2>/dev/null || true
- cp "$USM_SOURCE_DIR/../usm.config" "$SOURCES_DIR/usm/" 2>/dev/null || true
- # Step 2: Create the combined script header
- echo "Building combined script..."
- HEADER_FILE="$WORK_DIR/header.sh"
- cat > "$HEADER_FILE" << SCRIPT_HEADER
- #!/bin/bash
- # USM Installer - self-contained installation script
- # This script was automatically generated. Do not edit.
- # Version: $VERSION
- # Generated: $(date -u +"%Y-%m-%d %H:%M:%S UTC")
- set -e
- SCRIPT_HEADER
- # Step 3: Auto-detect package manager implementations
- PM_IMPLEMENTATIONS=()
- for pm_file in "$SCRIPT_DIR"/pm_*.sh; do
- if [[ -f "$pm_file" ]]; then
- # Extract PM name from filename (pm_apt.sh -> apt)
- pm_name=$(basename "$pm_file" .sh | sed 's/^pm_//')
- # Skip pm_base.sh - it's the interface, not an implementation
- if [[ "$pm_name" != "base" ]]; then
- PM_IMPLEMENTATIONS+=("$pm_name")
- fi
- fi
- done
- echo " Detected package managers: ${PM_IMPLEMENTATIONS[*]}"
- # Step 4: Combine all shell scripts
- COMBINED_FILE="$WORK_DIR/combined.sh"
- # Build the PM implementations array initialization
- PM_ARRAY_FILE="$WORK_DIR/pm_array.sh"
- cat > "$PM_ARRAY_FILE" << PM_ARRAY
- # Auto-detected package manager implementations
- PM_IMPLEMENTATIONS=(${PM_IMPLEMENTATIONS[*]})
- PM_ARRAY
- # Function to process a script file
- process_script() {
- local file="$1"
- local section="$2"
-
- echo "# === $section ==="
- cat "$file"
- }
- # Combine scripts in order
- {
- process_script "$SCRIPT_DIR/utils.sh" "Utils"
- echo ""
- process_script "$SCRIPT_DIR/ui.sh" "UI"
- echo ""
- # Include PM implementations first
- for pm_name in "${PM_IMPLEMENTATIONS[@]}"; do
- process_script "$SCRIPT_DIR/pm_${pm_name}.sh" "Package Manager ${pm_name}"
- echo ""
- done
- # Include PM array initialization
- cat "$PM_ARRAY_FILE"
- echo ""
- # Include pm_base which uses the array
- process_script "$SCRIPT_DIR/pm_base.sh" "Package Manager Base"
- echo ""
- process_script "$SCRIPT_DIR/build_config.sh" "Build Config"
- echo ""
- process_script "$SCRIPT_DIR/main.sh" "Main"
- echo ""
- # Add the main call at the very end
- echo "# Run main function"
- echo 'main "$@"'
- } > "$COMBINED_FILE"
- # Replace version placeholder in combined file
- sed -i "s/@VERSION@/$VERSION/g" "$COMBINED_FILE"
- # Step 5: Create the payload
- echo "Creating compressed payload..."
- PAYLOAD_FILE="$WORK_DIR/payload.tar.xz"
- # Use highest compression for smaller file size
- tar -C "$SOURCES_DIR" -cf - . | xz -9 -T0 > "$PAYLOAD_FILE"
- # Step 6: Assemble final installer
- echo "Assembling final installer..."
- {
- cat "$HEADER_FILE"
- cat "$COMBINED_FILE"
- echo ""
- echo "__PAYLOAD_START__"
- cat "$PAYLOAD_FILE"
- } > "$OUTPUT_FILE"
- # Make executable
- chmod +x "$OUTPUT_FILE"
- # Calculate output size
- OUTPUT_SIZE=$(du -h "$OUTPUT_FILE" | cut -f1)
- echo ""
- echo "✓ Installer created successfully!"
- echo " Output: $OUTPUT_FILE"
- echo " Size: $OUTPUT_SIZE"
|