Oživení FIXED Smart lokátorů

Společnost FIXED zařízla aplikaci Smart a s ní i lokátory Smile. Podívejte se na kompletní návod, jak rozběhnout alternativní open-source backend, opatchovat APK a zachránit hardware před elektroodpadem.

Jakub Žitník
Autor
5 minut

Když výrobce jednostranně ukončí podporu softwaru bez jakékoliv alternativy či uvolnění specifikací, nejde o „nevyhnutelný vývoj“. Jde o ukázkové plánované zastarávání a zbytečné generování elektroodpadu. Přesně to se stalo, když společnost FIXED oficiálně pohřbila aplikaci FIXED Smart a s ní odepsala i oblíbené lokátory FIXED Smile. Bez oficiální náhrady a možnosti dalšího používání se tak z tisíců plně funkčních zařízení staly přes noc bezcenné plastové cihličky.

Z hlediska skutečného vlastnictví hardwaru je neakceptovatelné, aby zařízení postavené na standardním Bluetooth Low Energy (BLE) skončilo v koši jen proto, že výrobce vypnul backend server. Místo smíření se s tímto stavem jsem se rozhodl vzít kontrolu nad zakoupeným hardwarem zpět do vlastních rukou. Pomocí dekompilace původního APK a reverzního inženýrství API se mi povedlo vytvořit alternativní backend pro již zmiňovanou aplikaci FIXED Smart a lokátory oživit.

Jak na to: Oživení lokátorů ve vlastním režimu

Protože celé tajemství „nefunkčnosti“ spočívalo pouze ve vypnutém oficiálním serveru, stačilo tento článek řetězce nahradit. Výsledkem mé analýzy je open-source implementace původního backendu.

Díky tomu nejste nadále závislí na tom, zda se výrobce rozhodne služby provozovat, nebo je zítra znovu vypnout. Veškerá komunikace s aplikací FIXED Smart teď může probíhat výhradně pod vaší kontrolou a na vašem vlastním serveru, Raspberry Pi nebo domácím NASu.

Kompletní zdrojový kód alternativního API je uvolněn pod svobodnou licencí a najdete ho v mém repozitáři na Gitea: gitea.jzitnik.dev/jzitnik/fixed-smile-api

Spuštění vlastního backendu pomocí Dockeru

Nejjednodušší cesta, jak API rozběhnout, je pomocí Dockeru a připraveného kontejneru.

services:
  fixed-api:
    image: gitea.jzitnik.dev/jzitnik/fixed-smile-api:latest
    restart: unless-stopped
    ports:
      - '3000:3000'
    environment:
      - NODE_ENV=production
      - REGISTRATION_DISABLED=false # Změňte na 'true' po registraci vašich zařízení
    volumes:
      - fixed-data:/app/data

volumes:
  fixed-data:

Proměnná REGISTRATION_DISABLED=false umožňuje vytváření nových uživatelských účtů. Jakmile si v aplikaci propojíte své lokátory a účet vytvoříte, doporučuji tuto proměnnou změnit na true a kontejner restartovat, abyste zamezili nechtěné registraci cizích uživatelů na váš server.

Důležité: Bez HTTPS a platného certifikátu vám API nebude fungovat

Aby s vaším novým serverem dokázala mobilní aplikace vůbec navázat spojení, musí být API dostupné přes šifrované HTTPS s plně důvěryhodným SSL certifikátem (např. bezplatný Let’s Encrypt).

Moderní Android z bezpečnostních důvodů striktně blokuje nešifrované HTTP. Nepomůžete si ani se self-signed certifikátem. Bez rootnutého telefonu a manuálního vstřikování certifikátu do systémového úložiště (System Trust Store) telefon takové spojení zahodí.

Nejčistší řešení bez nutnosti rootovat telefon: Postavte před svůj Docker kontejner reverzní proxy (např. Nginx Proxy Manager, Traefik, Caddy nebo Cloudflare Tunnels), která poběží na vaší vlastní doméně či subdoméně a vygeneruje validní, plně důvěryhodný certifikát.

Pathování aplikace aby komunikovala s vaším serverem

Jakmile máte backend úspěšně nasazený a dostupný na své doméně s platným HTTPS, zbývá poslední krok. Musíme „přesvědčit“ oficiální aplikaci FIXED Smart, aby zapomněla na původní, dnes již mrtvé servery výrobce, a začala veškerou komunikaci posílat k vám.

Protože aplikace nenabízí změnu URL adresy serveru v uživatelském nastavení, je nutné zasáhnout přímo do instalačního balíčku. K dekompilaci a úpravě kódu využijeme open-source nástroj APKTool.

1. Získání a dekompilace APK

Nejprve potřebujete instalační soubor aplikace (například ve verzi 1.99.7). Stáhněte si APK z veřejného archivu, jako je APKPure nebo APKMirror.

V terminálu aplikaci dekompilujte příkazem:

apktool d FIXED+Smart_1.99.7_APKPure.apk -o fixed_decoded -f

2. Změna backend URL ve Smali kódu

Přesuňte se do nově vytvořené složky fixed_decoded. Cílem je najít soubor ApiClient.smali, ve kterém je hardcoded adresa původního serveru.

Soubor se obvykle nachází v cestě: fixed_decoded/smali_classes3/io/swagger/client/ApiClient.smali

(Poznámka: V závislosti na konkrétní verzi aplikace nebo APKTool může být soubor v jiné složce, například smali_classes2/io/... nebo smali/io/.....

Otevřete soubor ApiClient.smali v textovém editoru, najděte zhruba řádek 64 a vyhledejte původní definici adresy:

const-string v0, "https://api.buddy-fixed.info/api/v1"

Tento řádek přepište na adresu vašeho vlastního serveru.

Pozor na koncovku: Na konci vaší domény musíte zachovat cestu /api/v1, jinak API nebude správně fungovat.

Výsledek po úpravě by měl vypadat takto:

const-string v0, "https://fixed.moje-domena.cz/api/v1"

Soubor uložte. Další zásahy do kódu nejsou potřeba.

  1. Zpětná kompilace, zarovnání a podpis

Upravené soubory musíte sestavit zpět do .apk balíčku, provést paměťové zarovnání (zipalign) a nakonec soubor podepsat. Moderní Android totiž instalaci nepodepsaného balíčku z bezpečnostních důvodů nedovolí.

Pro přehlednost si nastavením proměnných definujte cesty k souborům a k nástrojům z Android SDK (nástroje zipalign a apksigner najdete v Android SDK ve složce build-tools/):

SRC="fixed_decoded"
OUT="fixed_smart_patched.apk"
BUILD_TOOLS="/cesta/k/android-sdk/build-tools/34.0.0" # Upravte podle své verze SDK

Zpětné sestavení pomocí APKTool:

apktool b "$SRC" -o "$OUT"

Zarovnání archivu (Zipalign): Optimalizuje strukturu archivu pro běh v systému Android. Tento krok je vyžadován před samotným podpisem:

"$BUILD_TOOLS/zipalign" -f -p 4 "$OUT" "${OUT%.apk}_aligned.apk"

Vytvoření podpisového klíče (Keystore): Pokud nemáte vlastní podpisový klíč, vygenerujte si ho tímto příkazem (vytvoří soubor debug.keystore):

KEYSTORE="debug.keystore"

keytool -genkey -v -keystore "$KEYSTORE" -alias debug -keyalg RSA \
  -keysize 2048 -validity 10000 -storepass android -keypass android \
  -dname "CN=Debug,O=Debug,C=US"

Finální podpis balíčku (Apksigner): Upravené a zarovnané APK podepište vygenerovaným klíčem:

"$BUILD_TOOLS/apksigner" sign --ks "$KEYSTORE" \
  --ks-pass pass:android --key-pass pass:android \
  "${OUT%.apk}_aligned.apk"

Výsledný soubor fixed_smart_patched_aligned.apk je připraven. Nyní odinstalujte z telefonu původní oficiální aplikaci a nainstalujte tento upravený balíček.

Aplikace bude komunikovat výhradně s vaším novým serverem a hardware zůstane plně funkční bez ohledu na podporu ze strany výrobce.

Co plánuji do budoucna

Až budu mít více času a větší náladu si hrát s BLE a GATT profily, tak bych chtěl naprogramovat kompletně vlastní aplikaci, která by nepotřebovala externí server, a byla by schopna komunikovat s FIXED Smile lokátory bez externích služeb.

A pokud někdo od FIXED toto čte…

Jako sorry ale dát 50% slevu fakt není dostatečné, když bricknete tisíce zařízení. A úplně zbytečně. Nemluvte o tom že ten backend je hodně deeply integrated, lžete. Celý tag je úplně v pohodě schopen komunikovat lokálně.

Stačilo by jeden update aplikace, který by umožnil fungovat bez serveru, nebylo by to tak těžké. Ale to byste od svých klientů přestali dostávat analytická data a telemetrii…

Ano, to že tu aplikaci podporovat již nechcete je pochopitelné, je to jeden velký legacy junk. To ale neznamená, že je okay jen tak vypnout servery a rozbít funkčnost hardwaru, který si lidi koupili za své peníze.