# Gullrune - Build & Run Commands # Cross-platform build automation for Flet app .PHONY: help run install test clean build_win build_android build_aab install_android deploy_android serve_apk build_ios build_linux build_all # ── Toolchain paths (auto-detected by flet, override here if needed) ────────── JAVA_HOME ?= $(HOME)/java/17.0.13+11 ANDROID_HOME ?= $(HOME)/Android/sdk # ── Versionierung ────────────────────────────────────────────────────────────── # Überschreibbar: make build_aab BUILD_VERSION=1.1.0 BUILD_NUMBER=2 BUILD_VERSION ?= 1.0.0 BUILD_NUMBER ?= 1 # Default target help: @echo "Gullrune - Build Commands" @echo "=========================" @echo "" @echo "Available targets:" @echo " make run - Run the app in development mode" @echo " make install - Install all dependencies" @echo " make test - Run security tests" @echo " make clean - Clean build artifacts" @echo "" @echo "Build targets:" @echo " make build_win - Build Windows desktop app" @echo " make build_android - Build Android APK" @echo " make install_android - Install APK auf verbundenem Android-Gerät (USB)" @echo " make deploy_android - Build + Install in einem Schritt" @echo " make serve_apk - APK per lokalem HTTP-Server im WLAN bereitstellen" @echo " make build_ios - Build iOS IPA (macOS only)" @echo " make build_linux - Build Linux app" @echo " make build_all - Build for all platforms" @echo "" @echo "Migration targets:" @echo " make migrate - Run Alembic migrations" @echo " make migrate_create - Create new migration" # Run the app in development mode run: @echo "Starting Gullrune..." uv run python main.py # Install dependencies install: @echo "Installing dependencies..." pip install -r requirements.txt @echo "Done! All dependencies installed." # Run tests test: @echo "Running security tests..." pytest tests/ -v @echo "Tests completed." # Run tests with coverage test_coverage: @echo "Running tests with coverage..." pytest tests/ --cov=src --cov-report=html @echo "Coverage report generated in htmlcov/" # Clean build artifacts clean: @echo "Cleaning build artifacts..." rm -rf build/ rm -rf dist/ rm -rf *.egg-info find . -type d -name __pycache__ -exec rm -rf {} + 2>/dev/null || true find . -type f -name "*.pyc" -delete 2>/dev/null || true @echo "Clean complete." # Build Windows desktop app build_win: @echo "Building Windows desktop application..." @echo "This will create a standalone .exe in build/windows/" flet build windows --verbose @echo "Windows build complete! Check build/windows/" # Build Android APK # ───────────────────────────────────────────────────────────────────────────── # Voraussetzungen (werden beim ersten Build automatisch installiert falls nötig): # - JDK 17 → $(HOME)/java/17.0.13+11 (auto-install by flet) # - Android SDK 36 + Build-Tools 28.0.3 (auto-install by flet) # # Bekannte Fallstricke: # - flet[all] in pyproject.toml zieht watchdog rein → kein Android-Wheel. # Lösung: [project].dependencies nutzt nur "flet==...", flet[all] liegt # unter [project.optional-dependencies].dev # - Dart SDK-Cache nach Flutter-Update leeren: # rm -rf $(HOME)/flutter/3.41.4/bin/cache # # Ausgabe: build/apk/gullrune.apk # ───────────────────────────────────────────────────────────────────────────── build_android: @echo "Building Gullrune Android APK..." @echo "Erster Build: 10-20 Minuten (Gradle + SDK-Download)" @echo "Folge-Builds: ~3-5 Minuten (Cache)" uv run python3 scripts/gen_version.py --version $(BUILD_VERSION) --build $(BUILD_NUMBER) JAVA_HOME="$(JAVA_HOME)" ANDROID_HOME="$(ANDROID_HOME)" \ uv run flet build apk \ --project gullrune \ --product "Gullrune" \ --org com.keldamar \ --bundle-id com.keldamar.gullrune \ --build-version $(BUILD_VERSION) \ --build-number $(BUILD_NUMBER) \ --splash-color "#1A2A38" \ --splash-dark-color "#1A2A38" \ --android-adaptive-icon-background "#2A6F9E" \ --compile-app \ --compile-packages \ --exclude tests .git .venv user_data @echo "" @echo "APK fertig:" @find build/apk -name "*.apk" -type f @echo "" @sha256sum build/apk/gullrune.apk | tee build/apk/gullrune.apk.sha256 @echo "" @echo "Auf Gerät installieren: adb install build/apk/gullrune.apk" @echo "WLAN-Download starten: make serve_apk" # Build Android App Bundle (AAB) — für den Google Play Store # ───────────────────────────────────────────────────────────────────────────── # AAB ist das von Google empfohlene Format für den Play Store. # Google Play optimiert die Auslieferung pro Gerät automatisch. # # Vor dem Upload: AAB mit Upload-Keystore signieren (siehe Signing-Anleitung). # Ausgabe: build/aab/gullrune.aab # ───────────────────────────────────────────────────────────────────────────── build_aab: @echo "Building Gullrune Android App Bundle (AAB) für Play Store..." uv run python3 scripts/gen_version.py --version $(BUILD_VERSION) --build $(BUILD_NUMBER) JAVA_HOME="$(JAVA_HOME)" ANDROID_HOME="$(ANDROID_HOME)" \ uv run flet build aab \ --project gullrune \ --product "Gullrune" \ --org com.keldamar \ --bundle-id com.keldamar.gullrune \ --build-version $(BUILD_VERSION) \ --build-number $(BUILD_NUMBER) \ --splash-color "#1A2A38" \ --splash-dark-color "#1A2A38" \ --android-adaptive-icon-background "#2A6F9E" \ --compile-app \ --compile-packages \ --exclude tests .git .venv user_data @echo "" @echo "AAB fertig:" @find build/aab -name "*.aab" -type f @echo "" @sha256sum build/aab/gullrune.aab | tee build/aab/gullrune.aab.sha256 @echo "" @echo "Nächste Schritte:" @echo " 1. AAB mit Upload-Keystore signieren (falls noch nicht via flet signing konfiguriert)" @echo " 2. In Play Console hochladen: Test and release → Internal testing → Upload" # Install Android APK auf verbundenem Gerät # ───────────────────────────────────────────────────────────────────────────── # Voraussetzungen: # - Android-Gerät per USB verbunden, USB-Debugging aktiviert # - APK muss bereits gebaut sein (make build_android) # # Mehrere Geräte: DEVICE= make install_android # Serials anzeigen mit: adb devices # ───────────────────────────────────────────────────────────────────────────── APK := build/apk/gullrune.apk ADB := $(ANDROID_HOME)/platform-tools/adb install_android: @echo "Suche verbundene Android-Geräte..." @$(ADB) devices | grep -v "List of" | grep "device$$" > /dev/null || \ (echo "FEHLER: Kein Gerät gefunden. USB-Kabel und USB-Debugging prüfen." && exit 1) @test -f "$(APK)" || \ (echo "FEHLER: $(APK) nicht gefunden. Zuerst 'make build_android' ausführen." && exit 1) @echo "Installiere $(APK)..." $(if $(DEVICE), \ $(ADB) -s $(DEVICE) install -r "$(APK)", \ $(ADB) install -r "$(APK)" \ ) @echo "" @echo "Installation abgeschlossen. App auf Gerät starten:" $(if $(DEVICE), \ $(ADB) -s $(DEVICE) shell am start -n com.keldamar.gullrune/.MainActivity, \ $(ADB) shell am start -n com.keldamar.gullrune/.MainActivity \ ) # Shortcut: Build + Install in einem Schritt deploy_android: build_android install_android # APK per lokalem HTTP-Server im WLAN bereitstellen # ───────────────────────────────────────────────────────────────────────────── # Das Handy muss im selben WLAN wie dieser Rechner sein. # Ablauf: # 1. QR-Code im Terminal scannen # 2. Im Android-Browser die angezeigte URL öffnen # 3. APK herunterladen und "Installieren" tippen # 4. Einmalig: Einstellungen → Sicherheit → Browser als Installationsquelle erlauben # # Port überschreiben: PORT=9090 make serve_apk # ───────────────────────────────────────────────────────────────────────────── PORT ?= 8888 serve_apk: @test -f "$(APK)" || \ (echo "FEHLER: $(APK) nicht gefunden. Zuerst 'make build_android' ausführen." && exit 1) uv run python3 scripts/serve_apk.py --dir build/apk --port $(PORT) serve_apk_debug: @test -f "$(APK)" || \ (echo "FEHLER: $(APK) nicht gefunden. Zuerst 'make build_android' ausführen." && exit 1) uv run python3 scripts/serve_apk.py --dir build/apk --port $(PORT) --debug # Build iOS IPA (macOS only) build_ios: @echo "Building iOS IPA..." @echo "Requirements: macOS with Xcode installed" @echo "This may take 10-20 minutes on first build..." flet build ipa --verbose @echo "iOS IPA build complete! Check build/ipa/" # Build Linux desktop app # ───────────────────────────────────────────────────────────────────────────── # Voraussetzung: lld (LLVM-Linker) muss installiert sein. # Falls nicht vorhanden: # sudo apt install lld # # Das Target prüft dies automatisch und gibt einen klaren Hinweis. # # Ausgabe: build/linux/gullrune (ausführbare Datei + shared libs) # ───────────────────────────────────────────────────────────────────────────── build_linux: @which ld.lld > /dev/null 2>&1 || \ (echo "" && \ echo "FEHLER: ld.lld (LLVM-Linker) nicht gefunden." && \ echo "Bitte installieren mit:" && \ echo " sudo apt install lld" && \ echo "" && exit 1) @echo "Building Gullrune Linux app..." uv run flet build linux \ --project gullrune \ --product "Gullrune" \ --build-version 1.0.0 \ --build-number 1 \ --compile-app \ --compile-packages \ --exclude tests .git .venv user_data @echo "" @echo "Linux build fertig:" @find build/linux -maxdepth 2 -name "gullrune" -type f @echo "" @echo "Starten: ./build/linux/gullrune" # Build for all platforms (use with caution) build_all: build_win build_linux @echo "All platform builds complete!" @echo "Note: Android and iOS builds skipped (use build_android/build_ios separately)" # Database migration targets migrate: @echo "Running database migrations..." alembic upgrade head @echo "Migrations complete." migrate_create: @echo "Creating new migration..." @read -p "Migration message: " message; \ alembic revision --autogenerate -m "$$message" @echo "Migration created in alembic/versions/" migrate_downgrade: @echo "Rolling back last migration..." alembic downgrade -1 @echo "Rollback complete." # Relay server # ───────────────────────────────────────────────────────────────────────────── # Startet den Gullrune Relay-Server lokal (für Entwicklung / Test). # Für Produktion: systemd-Service oder Docker auf einem VPS. # # Beispiel Docker: # docker run -d -p 8765:8765 \ # -v $(PWD)/server:/app \ # python:3.12-slim \ # sh -c "pip install websockets && python /app/relay.py" # ───────────────────────────────────────────────────────────────────────────── RELAY_PORT ?= 8765 relay: @echo "Starting Gullrune relay server on ws://0.0.0.0:$(RELAY_PORT) ..." uv run python server/relay.py --port $(RELAY_PORT) # Development helpers dev: install run format: @echo "Formatting code with black..." black src/ tests/ main.py @echo "Code formatted." lint: @echo "Linting code..." pylint src/ main.py || true @echo "Lint complete." # Package for distribution package_win: build_win @echo "Creating Windows installer..." @echo "TODO: Add NSIS or InnoSetup script" package_android: build_android @echo "Android APK ready for distribution at:" @find build/apk -name "*.apk" -type f # Security check security_check: @echo "Running security checks..." @echo "Checking for .env in git..." @git check-ignore .env && echo "✓ .env is ignored" || echo "✗ WARNING: .env not ignored!" @echo "Checking database encryption..." @grep -q "DB_ENCRYPTION_KEY" .env && echo "✓ Encryption key exists" || echo "✗ WARNING: No encryption key!" @echo "Security check complete."