A app de Expo falla con HTTP en Android 9: é cleartext, non a VPN
Unha compilación de Expo que chama unha API HTTP simple falla en Android 9 e posteriores. O túnel é inocente: o indicador cleartext vai na configuración da compilación.
Publicaches unha compilación nova, pasaches á VPN e a mesma pantalla deixou de cargar. En Android 9 e posteriores a explicación máis habitual é máis aburrida: a plataforma rexeita HTTP simple para as apps que apuntan á API 28 ou superior, e a VPN só cambiou o contexto suficiente para deixalo ao descuberto. O erro que ves depende do cliente HTTP, por iso case nunca di cleartext.
Que é en realidade esa falla
Desde Android 9 a plataforma bloquea cleartext de forma predeterminada en canto unha app apunta ao nivel de API 28 ou superior. A plataforma rexeita a petición a un enderezo HTTP simple antes de que saia un só paquete do dispositivo. O erro que vexas depende da biblioteca HTTP: ás veces unha falla de rede xenérica, ás veces un tempo de espera esgotado, ás veces unha mensaxe que nomea cleartext sen rodeos. O que nunca fai é chegar ao teu servidor. Android documenta o valor predeterminado e a alternativa limitada por dominio na súa guía de configuración de seguridade.
Un navegador no mesmo dispositivo aínda pode cargar a páxina, e esa é a pista que case todo o mundo pasa por alto. Os navegadores non están suxeitos á política de seguridade de rede da túa app.
Por que se culpa a VPN
Normalmente cambian tres cousas á vez. Pode que a app resolva outro nome de host tras conectarse a VPN, que o dispositivo sexa novo cunha compilación máis recente, ou que a propia compilación pasase a un nivel de API obxectivo que activa o valor predeterminado. A VPN vese e o SDK obxectivo non, así que a VPN leva o ticket.
Compara os niveis obxectivo das compilacións vella e nova antes de tocar a configuración de rede. Unha app que apunta a 27 ou menos está exenta, e iso explica todos os informes de «a min funcíoname no móbil vello».
Onde acaba realmente o indicador de Expo
Nun proxecto de Expo xestionado, engadir un axuste a app.json non edita un manifesto de Android, porque o manifesto prodúceno o prebuild e as compilacións de desenvolvemento. O plugin de configuración é o que escribe o axuste nesa fase. A ruta admitida é expo-build-properties, configurado na configuración da app coa opción cleartext baixo android.
{
"plugins": [
["expo-build-properties", {
"android": { "usesCleartextTraffic": true }
}]
]
}O fragmento só define a opción do plugin; o manifesto prodúcese despois. Executa un prebuild ou unha compilación nova do cliente de desenvolvemento e, antes de volver probar, revisa o AndroidManifest.xml xerado en busca de android:usesCleartextTraffic, porque unha recarga só de JS conserva o manifesto antigo. Axusta a versión do plugin ao SDK de Expo co que corre o proxecto. As opcións do plugin cambian entre versións, e un fragmento copiado doutro SDK é unha fonte fiable de no-ops silenciosos.
O fluxo bare e a opción máis estreita
Para React Native bare o equivalente é android:usesCleartextTraffic no elemento application, ou unha configuración de seguridade de rede que permita cleartext só para dominios concretos. A forma limitada por dominio é a preferible, porque permite a API interna e deixa todo o demais en HTTPS. Tamén documenta a súa propia lista de excepcións, e esa é a parte que preguntará un revisor.
Ningunha das dúas abordaxes cambia o valor predeterminado da plataforma para nada que non nomeases.
Primeiro demóstrao co rexistro do dispositivo
Antes de editar a configuración, obtén a falla exacta. adb logcat nun dispositivo conectado mostra o rexeitamento de cleartext da plataforma e nomea o compoñente que o provocou. Un socket rexeitado, un nome que non se resolve ou un handshake TLS fallido apuntan a outro sitio por completo, e habilitar cleartext só debilitaría a app para nada.
Despois mantén a produción honesta. Cleartext é aceptable para un punto de laboratorio que non pode ofrecer TLS, e só durante o tempo máis curto que poidas planificar. Se a API pode terminar TLS dentro da rede privada, pon o certificado no almacén de confianza do dispositivo e deixa cleartext desactivado, porque o túnel cifra o camiño ata a súa saída e nada máis aló.
Cando o punto responda por HTTPS, quita o permiso, volve compilar e proba na VPN e en Wi-Fi normal na mesma sesión. A resolución de nomes pode diferir entre eses dous camiños, e só o par che di cal di a verdade.