← Proyectos

Awaken Wake-on-LAN Controller

App Android para encender mis equipos desde casa y apagarlos desde donde esté. Wake-on-LAN para despertarlos, SSH para apagarlos y ping ICMP para saber si están en línea.

Stack
Android · Java · Kotlin · SQLCipher · SSH
Estado
Terminado
Año
2026
ymid@ubuntu:~$ uptime up 0 min, 1 user ymid@ubuntu:~$ ▍ shutting down… router · 192.168.1.1 ubuntu · 192.168.1.12 ethernet awaken MAGIC PACKET → UDP :9 FF FF FF FF FF FF + ••:••:••:••:••:4F ×16 SSH :22 · ymid@ubuntu sudo shutdown -h now ICMP ECHO reply · 20 ms 00:55 Devices HOME Ubuntu ••:••:••:••:••:4F OfflineOnline · 20 ms Turn… Shut… Magic packet sent AWAKEN · now Ubuntu is online Confirm it’s you Shut down Ubuntu Touch the fingerprint sensor
  1. 01 Despertar Magic packet · UDP 9
  2. 02 Detectar Ping ICMP
  3. 03 Apagar Biometría · SSH

Una habitación de noche. El PC está apagado.

Encender es fácil, apagar no

Awaken empezó porque quería encender el PC de mi casa desde el teléfono. Wake-on-LAN lo resuelve con un solo paquete UDP, pero solo sirve para despertar un equipo: no existe un magic packet para apagarlo. Para cerrar el ciclo necesitaba otro canal, uno que pudiera entrar a la máquina y ejecutar un comando.

La respuesta fue SSH. Awaken inicia sesión en el equipo con contraseña o clave privada y ejecuta el comando de apagado que configuras para cada uno, por ejemplo sudo shutdown -h now. Por ahora el apagado funciona en equipos Linux.

Encender en casa, apagar desde cualquier lugar

Lo que más me costó fue la diferencia entre estar en casa y estar fuera. En la red local todo es directo: el magic packet va por broadcast y el SSH va a la IP local del PC. Desde internet, el router bloquea ese tráfico, y abrir el puerto de SSH al mundo no era una opción.

Para apagar desde fuera abrí un solo puerto en el router, el de una VPN WireGuard que corre en el mismo PC, y el firewall del equipo deja entrar solo lo necesario. El teléfono se conecta a la VPN y Awaken habla con el PC como si estuviera en casa. SSH nunca queda expuesto a internet: solo se llega a él desde la red local o por el túnel.

Encender desde fuera es otro problema: con el PC apagado, la VPN tampoco existe, así que el magic packet necesitaría otro camino abierto hacia la red. Investigué hasta ahí y decidí no seguir. Encender solo desde la red local es más seguro y cubre el uso real: lo que sí necesito es poder apagar el PC si salgo de afán y se me olvida.

Saber en qué red estás

Uno de los fallos que más tardé en resolver fue que la app reconociera en qué red Wi-Fi estaba el teléfono. Android no lo pone fácil: leer el nombre de la red o escanear las que hay alrededor depende de permisos, sobre todo el de ubicación, y sin ellos el sistema simplemente no te dice nada. Lo necesitaba para las redes de confianza: en el Wi-Fi de casa, apagar un equipo no pide huella; en cualquier otra red, sí.

Credenciales que no se pueden filtrar

Para apagar por SSH, Awaken guarda el usuario y la contraseña o clave privada de cada equipo. Con eso se entra a una máquina. Mi primera versión no las protegía como debía: lo detecté en una revisión con ayuda de IA y pasé la base de datos local a SQLCipher, que la cifra en disco. La clave de esa base de datos se genera al azar en el primer arranque y queda guardada con el Android Keystore, nunca en el código.

Además, la primera vez que Awaken se conecta a un equipo guarda la huella de su clave SSH. Si en una conexión posterior la huella cambia, se niega a conectar en vez de enviar la contraseña a un equipo que podría no ser el tuyo. Y cualquier acción destructiva, como apagar, pide huella o PIN.

Lo demás

  • Monitoreo en segundo plano con ping ICMP real, sin root, sobre un socket ICMP no privilegiado: avisa cuando un equipo se enciende o se apaga, aunque la app esté cerrada.
  • Accesos sin abrir la app: tiles de ajustes rápidos, widget, atajos y Device Controls.
  • Comandos de voz con Google Assistant, mediante deep links wakeonlan://.
  • El monitoreo se puede desactivar a distancia con Firebase Remote Config si gastara demasiada batería, sin publicar una actualización.
  • Exportar e importar la lista de equipos en JSON.

En un dispositivo real

La misma secuencia, grabada en el teléfono.