tawasuyu/llimphi
Sovereign retained-mode GPU UI framework in Rust (wgpu+vello+taffy+parley), Elm loop, 40+ widgets.
feat: llimphi standalone — framework UI soberano extraído del monorepo
1#!/usr/bin/env bash
2# ============================================================================
3# build-android.sh — empaca un crate Llimphi-Android como APK firmado.
4#
5# Uso:
6# ./build-android.sh <crate-dir> [arch] [profile]
7#
8# crate-dir : path al Cargo.toml del crate Android (cdylib + android_main)
9# arch : arm64 | x64 (default arm64)
10# profile : release | debug (default release)
11#
12# Requisitos:
13# - rustup target add aarch64-linux-android x86_64-linux-android
14# - cargo install xbuild (binario `x`)
15# - cargo install cargo-ndk (opcional, sólo si querés build sin APK)
16# - NDK r27+ en $ANDROID_NDK_HOME
17# - Android SDK en $ANDROID_HOME (cmdline-tools + build-tools)
18# - PEM dev en $LLIMPHI_PEM (se crea automáticamente la primera vez)
19#
20# Resultado:
21# target/x/<profile>/android/<crate>.apk — APK firmado v2, instalable con
22# `adb install -r <apk>`.
23# ============================================================================
24set -euo pipefail
25
26CRATE_DIR="${1:?se requiere crate-dir como primer argumento}"
27ARCH="${2:-arm64}"
28PROFILE="${3:-release}"
29
30# --- toolchain -------------------------------------------------------------
31: "${ANDROID_NDK_HOME:=/home/sergio/android-ndk-r27c}"
32: "${ANDROID_NDK_ROOT:=$ANDROID_NDK_HOME}"
33: "${ANDROID_HOME:=/opt/android-sdk}"
34: "${LLIMPHI_PEM:=$HOME/.local/share/llimphi-android/debug.pem}"
35export ANDROID_NDK_HOME ANDROID_NDK_ROOT ANDROID_HOME
36
37X_BIN="${X_BIN:-$HOME/.cargo/bin/x}"
38test -x "$X_BIN" || { echo "❌ xbuild (cargo install xbuild)"; exit 1; }
39test -d "$ANDROID_NDK_HOME" || { echo "❌ NDK no encontrado en $ANDROID_NDK_HOME"; exit 1; }
40test -d "$ANDROID_HOME" || { echo "❌ SDK no encontrado en $ANDROID_HOME"; exit 1; }
41
42# --- PEM de firma dev (RSA 2048 + cert auto-firmado) -----------------------
43if [ ! -f "$LLIMPHI_PEM" ]; then
44 echo "→ generando PEM de firma dev en $LLIMPHI_PEM"
45 mkdir -p "$(dirname "$LLIMPHI_PEM")"
46 openssl req -x509 -newkey rsa:2048 \
47 -keyout "${LLIMPHI_PEM}.key" \
48 -out "${LLIMPHI_PEM}.cert" \
49 -days 36500 -nodes \
50 -subj "/CN=llimphi-dev/O=gioser/C=AR" 2>/dev/null
51 cat "${LLIMPHI_PEM}.key" "${LLIMPHI_PEM}.cert" > "$LLIMPHI_PEM"
52fi
53
54# --- flags -----------------------------------------------------------------
55PROFILE_FLAG="--release"
56[ "$PROFILE" = "debug" ] && PROFILE_FLAG="--debug"
57
58# --- build ----------------------------------------------------------------
59cd "$CRATE_DIR"
60CRATE_NAME=$(grep '^name *=' Cargo.toml | head -1 | sed -E 's/.*"([^"]+)".*/\1/')
61echo "→ building $CRATE_NAME · $ARCH · $PROFILE"
62
63"$X_BIN" build \
64 --platform android \
65 --arch "$ARCH" \
66 --format apk \
67 $PROFILE_FLAG \
68 --pem "$LLIMPHI_PEM"
69
70# --- locate + verify -------------------------------------------------------
71APK=$(find ../../../../target/x/$PROFILE/android -name "${CRATE_NAME}.apk" 2>/dev/null | head -1)
72[ -z "$APK" ] && APK=$(find . -name "${CRATE_NAME}.apk" 2>/dev/null | head -1)
73[ -z "$APK" ] && { echo "❌ APK no encontrado"; exit 1; }
74APK=$(readlink -f "$APK")
75SIZE=$(du -h "$APK" | cut -f1)
76
77APKSIGNER="$ANDROID_HOME/build-tools/37.0.0/apksigner"
78if [ -x "$APKSIGNER" ]; then
79 if "$APKSIGNER" verify --min-sdk-version 24 "$APK" 2>/dev/null; then
80 echo "✓ firma verificada (APK Signature Scheme v2)"
81 else
82 echo "⚠ firma no verifica"
83 fi
84fi
85
86echo "✓ $APK ($SIZE)"
87echo
88echo "Instalar en device:"
89echo " adb install -r $APK"