← Volver al listado de tecnologías
Empaquetado con Buildozer
¿Qué es Buildozer?
Herramienta que automatiza el empaquetado de apps Kivy para Android e iOS.
Instalación
pip install buildozer
# Dependencias Linux (Ubuntu/Debian)
sudo apt-get install -y \
python3-pip \
build-essential \
git \
python3 \
python3-dev \
ffmpeg \
libsdl2-dev \
libsdl2-image-dev \
libsdl2-mixer-dev \
libsdl2-ttf-dev \
libportmidi-dev \
libswscale-dev \
libavformat-dev \
libavcodec-dev \
zlib1g-dev \
libgstreamer1.0 \
gstreamer1.0-plugins-base \
gstreamer1.0-plugins-good \
openjdk-17-jdk \
autoconf \
automake \
libtool \
pkg-config
Iniciar Proyecto
cd mi_proyecto
buildozer init
Esto crea buildozer.spec con la configuración.
Archivo buildozer.spec
Configuración Básica
[app]
# Nombre de la app
title = Mi App
# Nombre del paquete
package.name = miapp
# Dominio del paquete (inverso)
package.domain = org.ejemplo
# Código fuente
source.dir = .
source.include_exts = py,png,jpg,kv,atlas,json
# Versión
version = 1.0.0
# Requisitos
requirements = python3,kivy
# Orientación: portrait, landscape, all
orientation = portrait
# Pantalla completa
fullscreen = 0
Configuración Android
[app]
# Permisos Android
android.permissions = INTERNET,CAMERA,ACCESS_FINE_LOCATION
# API levels
android.minapi = 21
android.api = 33
android.ndk = 25b
# Arquitecturas
android.archs = arm64-v8a, armeabi-v7a
# Modo release o debug
# android.release_artifact = aab # Para Play Store
Iconos y Splash
[app]
# Icono (512x512 recomendado)
icon.filename = %(source.dir)s/assets/icon.png
# Splash screen
presplash.filename = %(source.dir)s/assets/presplash.png
Comandos Buildozer
Compilar APK Debug
buildozer android debug
Compilar y Desplegar
buildozer android debug deploy run
Ver Logs
buildozer android logcat
Limpiar Build
buildozer android clean
APK Release
buildozer android release
AAB para Play Store
# En buildozer.spec:
# android.release_artifact = aab
buildozer android release
Estructura de Proyecto
mi_app/
├── main.py # Punto de entrada (obligatorio)
├── buildozer.spec
├── assets/
│ ├── icon.png # 512x512
│ ├── presplash.png # 512x512
│ ├── images/
│ └── fonts/
├── screens/
│ └── *.py
└── requirements.txt
Requirements Comunes
# Básico
requirements = python3,kivy
# Con KivyMD
requirements = python3,kivy,kivymd
# Con librerías adicionales
requirements = python3,kivy,pillow,requests,pyjnius
# Kivy Garden
requirements = python3,kivy,kivy_garden.mapview
Permisos Android
| Permiso | Uso |
|---|---|
INTERNET | Conexión a red |
CAMERA | Acceso a cámara |
ACCESS_FINE_LOCATION | GPS preciso |
ACCESS_COARSE_LOCATION | GPS aproximado |
WRITE_EXTERNAL_STORAGE | Escribir archivos |
READ_EXTERNAL_STORAGE | Leer archivos |
VIBRATE | Vibración |
RECORD_AUDIO | Micrófono |
android.permissions = INTERNET,CAMERA,WRITE_EXTERNAL_STORAGE
Usar Docker
Evita problemas de dependencias usando Docker:
docker pull kivy/buildozer
docker run --interactive --tty --rm \
--volume "$HOME/.buildozer":/home/user/.buildozer \
--volume "$PWD":/home/user/hostcwd \
kivy/buildozer android debug
GitHub Actions
# .github/workflows/build.yml
name: Build APK
on:
push:
branches: [main]
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Build APK
uses: ArtemSBulgakov/buildozer-action@v1
with:
command: buildozer android debug
- name: Upload APK
uses: actions/upload-artifact@v3
with:
name: apk
path: bin/*.apk
Firmar APK Release
Crear Keystore
keytool -genkey -v \
-keystore mi-keystore.jks \
-keyalg RSA \
-keysize 2048 \
-validity 10000 \
-alias mi-alias
Configurar en buildozer.spec
[app]
android.keystore = mi-keystore.jks
android.keyalias = mi-alias
# No incluir passwords en el spec, usar variables de entorno
Variables de Entorno
export P4A_RELEASE_KEYSTORE_PASSWD=tu_password
export P4A_RELEASE_KEYALIAS_PASSWD=tu_password
buildozer android release
Solución de Problemas
Error: SDK/NDK no encontrado
# Instalar automáticamente
buildozer android debug
# La primera vez descarga SDK/NDK
Error: Java version
# Usar Java 17
sudo update-alternatives --config java
Error: Recipe failed
# Limpiar y reconstruir
buildozer android clean
rm -rf .buildozer
buildozer android debug
Ver más detalles
buildozer -v android debug
Optimización de APK
[app]
# Solo arquitectura necesaria
android.archs = arm64-v8a
# Excluir archivos innecesarios
source.exclude_exts = spec,md,txt
# Excluir patrones
source.exclude_patterns = tests/*,docs/*,*.pyc
iOS con Kivy-iOS
# Solo en macOS
pip install kivy-ios
# Crear proyecto Xcode
toolchain create MiApp ~/mi_proyecto
# Compilar
toolchain build kivy
Recursos
| Recurso | URL |
|---|---|
| Buildozer Docs | https://buildozer.readthedocs.io/ |
| Python-for-Android | https://python-for-android.readthedocs.io/ |
| Kivy iOS | https://github.com/kivy/kivy-ios |
| GitHub Action | https://github.com/ArtemSBulgakov/buildozer-action |
Testing de Configuración
# test_buildozer.py
import unittest
import os
class TestBuildozer(unittest.TestCase):
def test_spec_existe(self):
self.assertTrue(os.path.exists('buildozer.spec'))
def test_main_existe(self):
self.assertTrue(os.path.exists('main.py'))
def test_spec_tiene_campos_requeridos(self):
with open('buildozer.spec', 'r') as f:
contenido = f.read()
campos = ['title', 'package.name', 'package.domain', 'requirements']
for campo in campos:
self.assertIn(campo, contenido, f'Falta {campo}')
def test_requirements_incluye_kivy(self):
with open('buildozer.spec', 'r') as f:
for linea in f:
if linea.startswith('requirements'):
self.assertIn('kivy', linea.lower())
break
if __name__ == '__main__':
unittest.main()
Probar en Dispositivo con ADB
# Instalar APK debug
adb install -r bin/*-debug.apk
# Ver información del APK instalado
adb shell dumpsys package com.ejemplo.miapp | head -50
# Verificar permisos solicitados
adb shell dumpsys package com.ejemplo.miapp | grep permission
# Limpiar datos de la app (útil para testing)
adb shell pm clear com.ejemplo.miapp
# Desinstalar app
adb uninstall com.ejemplo.miapp
# Ver tamaño de la app instalada
adb shell du -h /data/app/*/com.ejemplo.miapp*
Resumen
buildozer initcrea la configuraciónbuildozer android debugcompila APKbuildozer.specdefine metadatos y dependencias- Docker simplifica el entorno de compilación
- GitHub Actions automatiza builds CI/CD
- Firmar con keystore para releases