Translated ['src/mobile-pentesting/android-app-pentesting/react-native-a

This commit is contained in:
Translator 2025-08-21 04:19:44 +00:00
parent 15ba4068a8
commit 4c301f26c8

View File

@ -1,7 +1,7 @@
{{#include ../../banners/hacktricks-training.md}}
# Análise de Aplicações React Native
{{#include ../../banners/hacktricks-training.md}}
Para confirmar se a aplicação foi construída no framework React Native, siga estes passos:
1. Renomeie o arquivo APK com uma extensão zip e extraia-o para uma nova pasta usando o comando `cp com.example.apk example-apk.zip` e `unzip -qq example-apk.zip -d ReactNative`.
@ -10,6 +10,20 @@ Para confirmar se a aplicação foi construída no framework React Native, siga
3. Use o comando `find . -print | grep -i ".bundle$"` para procurar o arquivo JavaScript.
Nota: Se você receber um Android App Bundle (.aab) em vez de um APK, gere um APK universal primeiro e depois extraia o bundle:
```bash
# Get bundletool.jar and generate a universal APK set
java -jar bundletool.jar build-apks \
--bundle=app-release.aab \
--output=app.apks \
--mode=universal \
--overwrite
# Extract the APK and then unzip it to find assets/index.android.bundle
unzip -p app.apks universal.apk > universal.apk
unzip -qq universal.apk -d ReactNative
ls ReactNative/assets/
```
## Código Javascript
Se ao verificar o conteúdo do `index.android.bundle` você encontrar o código JavaScript da aplicação (mesmo que minificado), você pode **analisá-lo para encontrar informações sensíveis e vulnerabilidades**.
@ -32,7 +46,7 @@ Para analisar ainda mais o código JavaScript, você pode fazer o upload do arqu
Se você encontrar um arquivo chamado `index.android.bundle.map`, poderá analisar o código-fonte em um formato não minificado. Os arquivos de mapa contêm mapeamento de origem, que permite mapear identificadores minificados.
Para procurar credenciais e endpoints sensíveis, siga estas etapas:
Para procurar credenciais sensíveis e endpoints, siga estas etapas:
1. Identifique palavras-chave sensíveis para analisar o código JavaScript. Aplicações React Native costumam usar serviços de terceiros como Firebase, endpoints de serviço AWS S3, chaves privadas, etc.
@ -40,42 +54,142 @@ Para procurar credenciais e endpoints sensíveis, siga estas etapas:
3. Foi uma sorte que credenciais sensíveis codificadas foram encontradas no código JavaScript durante o processo de reconhecimento.
### Caça rápida a segredos/endpoints em pacotes
Esses greps simples frequentemente revelam indicadores interessantes mesmo em JS minificado:
```bash
# Common backends and crash reporters
strings -n 6 index.android.bundle | grep -Ei "(api\.|graphql|/v1/|/v2/|socket|wss://|sentry\.io|bugsnag|appcenter|codepush|firebaseio\.com|amplify|aws)"
# Firebase / Google keys (heuristics)
strings -n 6 index.android.bundle | grep -Ei "(AIza[0-9A-Za-z_-]{35}|AIzaSy[0-9A-Za-z_-]{33})"
# AWS access key id heuristic
strings -n 6 index.android.bundle | grep -E "AKIA[0-9A-Z]{16}"
# Expo/CodePush deployment keys
strings -n 6 index.android.bundle | grep -Ei "(CodePush|codepush:\\/\\/|DeploymentKey)"
# Sentry DSN
strings -n 6 index.android.bundle | grep -Ei "(Sentry\.init|dsn\s*:)"
```
Se você suspeitar de frameworks de atualização Over-The-Air, também procure por:
- Chaves de implantação do Microsoft App Center / CodePush
- Configuração de Atualizações do Expo EAS (`expo-updates`, `expo\.io`, certificados de assinatura)
### Mudar o código JS e reconstruir
Neste caso, mudar o código é fácil. Você só precisa renomear o aplicativo para usar a extensão `.zip` e extraí-lo. Então você pode **modificar o código JS dentro deste pacote e reconstruir o aplicativo**. Isso deve ser suficiente para permitir que você **injete código** no aplicativo para fins de teste.
## Hermes bytecode
## Código de bytes Hermes
Se o pacote contiver **Hermes bytecode**, você **não poderá acessar o código Javascript** do aplicativo (nem mesmo a versão minificada).
Se o pacote contiver **código de bytes Hermes**, você **não poderá acessar o código Javascript** do aplicativo (nem mesmo a versão minificada).
Você pode verificar se o pacote contém Hermes bytecode executando o seguinte comando:
Você pode verificar se o pacote contém código de bytes Hermes executando o seguinte comando:
```bash
file index.android.bundle
index.android.bundle: Hermes JavaScript bytecode, version 96
```
No entanto, você pode usar as ferramentas **[hbctool](https://github.com/bongtrop/hbctool)**, **[hermes-dec](https://github.com/P1sec/hermes-dec)** ou **[hermes_rs](https://github.com/Pilfer/hermes_rs)** para **desmontar o bytecode** e também para **decompilá-lo para algum código JS pseudo**. Para fazer isso, por exemplo, esses comandos:
No entanto, você pode usar as ferramentas **[hbctool](https://github.com/bongtrop/hbctool)**, forks atualizados do hbctool que suportam versões mais novas de bytecode, **[hasmer](https://github.com/lucasbaizer2/hasmer)**, **[hermes_rs](https://github.com/Pilfer/hermes_rs)** (biblioteca/APIs Rust), ou **[hermes-dec](https://github.com/P1sec/hermes-dec)** para **desmontar o bytecode** e também para **decompilá-lo em algum código pseudo JS**. Por exemplo:
```bash
# Disassemble and re-assemble with hbctool (works only for supported HBC versions)
hbctool disasm ./index.android.bundle ./hasm_out
# ...edit ./hasm_out/**/*.hasm (e.g., change comparisons, constants, feature flags)...
hbctool asm ./hasm_out ./index.android.bundle
# Using hasmer (focus on disassembly; assembler/decompiler are WIP)
hasmer disasm ./index.android.bundle -o hasm_out
# Using hermes-dec to produce pseudo-JS
hbc-disassembler ./index.android.bundle /tmp/my_output_file.hasm
hbc-decompiler ./index.android.bundle /tmp/my_output_file.js
hbc-decompiler ./index.android.bundle /tmp/my_output_file.js
```
### Mudar código e reconstruir
Dica: O projeto open-source Hermes também fornece ferramentas de desenvolvedor como `hbcdump` em lançamentos específicos do Hermes. Se você compilar a versão correspondente do Hermes usada para produzir o pacote, `hbcdump` pode despejar funções, tabelas de strings e bytecode para uma análise mais profunda.
Idealmente, você deve ser capaz de modificar o código desmontado (mudando uma comparação, ou um valor ou qualquer coisa que você precise modificar) e então **reconstruir o bytecode** e depois reconstruir o aplicativo.
### Mudar código e recompilar (Hermes)
A ferramenta **[hbctool](https://github.com/bongtrop/hbctool)** suporta a desmontagem do pacote e a reconstrução após as alterações serem realizadas, no entanto, ela **suporta apenas versões antigas** do bytecode Hermes.
Idealmente, você deve ser capaz de modificar o código desmontado (mudando uma comparação, ou um valor ou qualquer coisa que você precise modificar) e então **recompilar o bytecode** e recompilar o aplicativo.
A ferramenta **[hermes-dec](https://github.com/P1sec/hermes-dec)** não suporta a reconstrução do bytecode.
- O **[hbctool](https://github.com/bongtrop/hbctool)** original suporta desmontar o pacote e reconstruí-lo após as alterações, mas historicamente suportou apenas versões mais antigas de bytecode. Forks mantidos pela comunidade estendem o suporte a versões mais novas do Hermes (incluindo meados dos anos 8096) e muitas vezes são a opção mais prática para corrigir aplicativos RN modernos.
- A ferramenta **[hermes-dec](https://github.com/P1sec/hermes-dec)** não suporta a recompilação do bytecode (apenas descompilador/desmontador), mas é muito útil para navegar na lógica e despejar strings.
- A ferramenta **[hasmer](https://github.com/lucasbaizer2/hasmer)** visa suportar tanto a desmontagem quanto a montagem para várias versões do Hermes; a montagem ainda está se desenvolvendo, mas vale a pena tentar em bytecode recente.
A ferramenta **[hermes_rs](https://github.com/Pilfer/hermes_rs)** suporta a reconstrução do bytecode, mas na verdade é uma biblioteca e não uma ferramenta CLI.
Um fluxo de trabalho mínimo com montadores semelhantes ao hbctool:
```bash
# 1) Disassemble to HASM directories
hbctool disasm assets/index.android.bundle ./hasm
# 2) Edit a guard or feature flag (example: force boolean true)
# In the relevant .hasm, replace a LoadConstUInt8 0 with 1
# or change a conditional jump target to bypass a check.
# 3) Reassemble into a new bundle
hbctool asm ./hasm assets/index.android.bundle
# 4) Repack the APK and resign
zip -r ../patched.apk *
# Align/sign as usual (see Android signing section in HackTricks)
```
Note que o formato de bytecode do Hermes é versionado e o montador deve corresponder exatamente ao formato em disco. Se você receber erros de formato, mude para um fork/alternativa atualizado ou reconstrua as ferramentas Hermes correspondentes.
## Análise Dinâmica
Você pode tentar analisar dinamicamente o aplicativo usando o Frida para habilitar o modo de desenvolvedor do aplicativo React e usar **`react-native-debugger`** para se conectar a ele. No entanto, para isso, você aparentemente precisa do código-fonte do aplicativo. Você pode encontrar mais informações sobre isso em [https://newsroom.bedefended.com/hooking-react-native-applications-with-frida/](https://newsroom.bedefended.com/hooking-react-native-applications-with-frida/).
Você pode tentar analisar dinamicamente o aplicativo usando Frida para habilitar o modo de desenvolvedor do aplicativo React e usar **`react-native-debugger`** para se conectar a ele. No entanto, para isso, você aparentemente precisa do código-fonte do aplicativo. Você pode encontrar mais informações sobre isso em [https://newsroom.bedefended.com/hooking-react-native-applications-with-frida/](https://newsroom.bedefended.com/hooking-react-native-applications-with-frida/).
### Habilitando o Suporte ao Desenvolvedor em release com Frida (advertências)
Alguns aplicativos acidentalmente enviam classes que tornam o Suporte ao Desenvolvedor alternável. Se presente, você pode tentar forçar `getUseDeveloperSupport()` a retornar true:
```javascript
// frida -U -f com.target.app -l enable-dev.js
Java.perform(function(){
try {
var Host = Java.use('com.facebook.react.ReactNativeHost');
Host.getUseDeveloperSupport.implementation = function(){
return true; // force dev support
};
console.log('[+] Patched ReactNativeHost.getUseDeveloperSupport');
} catch (e) {
console.log('[-] Could not patch: ' + e);
}
});
```
Atenção: Em builds de release corretamente construídos, `DevSupportManagerImpl` e classes relacionadas apenas para depuração são removidas e mudar esta flag pode fazer o app travar ou não ter efeito. Quando isso funciona, você pode tipicamente expor o menu de desenvolvedor e anexar depuradores/inspetores.
### Interceptação de rede em apps RN
React Native Android geralmente depende do OkHttp por baixo dos panos (via o módulo nativo `Networking`). Para interceptar/observar tráfego em um dispositivo não enraizado durante testes dinâmicos:
- Use proxy do sistema + confie no CA do usuário ou use outras técnicas genéricas de bypass de TLS do Android.
- Dica específica do RN: se o app incluir Flipper na release por engano (ferramentas de depuração), o plugin de Rede do Flipper pode expor requisições/respostas.
Para técnicas genéricas de interceptação e bypass de pinning do Android, consulte:
{{#ref}}
make-apk-accept-ca-certificate.md
{{#endref}}
{{#ref}}
frida-tutorial/objection-tutorial.md
{{#endref}}
## Problemas recentes em bibliotecas populares do RN (o que procurar)
Ao auditar módulos de terceiros visíveis no bundle JS ou libs nativas, verifique por vulnerabilidades conhecidas e verifique versões em `package.json`/`yarn.lock`.
- react-native-mmkv (Android): versões anteriores a 2.11.0 registravam a chave de criptografia opcional nos logs do Android. Se ADB/logcat estiver disponível, segredos poderiam ser recuperados. Assegure-se de usar >= 2.11.0. Indicadores: uso de `react-native-mmkv`, declarações de log mencionando a inicialização do MMKV com criptografia. CVE-2024-21668.
- react-native-document-picker: versões < 9.1.1 eram vulneráveis a travessia de caminho no Android (seleção de arquivo), corrigido na 9.1.1. Valide entradas e versão da biblioteca.
Verificações rápidas:
```bash
grep -R "react-native-mmkv" -n {index.android.bundle,*.map} 2>/dev/null || true
grep -R "react-native-document-picker" -n {index.android.bundle,*.map} 2>/dev/null || true
# If you also have the node_modules (rare on release): grep -R in package.json / yarn.lock
```
## Referências
- [https://medium.com/bugbountywriteup/lets-know-how-i-have-explored-the-buried-secrets-in-react-native-application-6236728198f7](https://medium.com/bugbountywriteup/lets-know-how-i-have-explored-the-buried-secrets-in-react-native-application-6236728198f7)
- [https://www.assetnote.io/resources/research/expanding-the-attack-surface-react-native-android-applications](https://www.assetnote.io/resources/research/expanding-the-attack-surface-react-native-android-applications)
- [https://payatu.com/wp-content/uploads/2023/02/Mastering-React-Native-Application-Pentesting-A-Practical-Guide-2.pdf](https://payatu.com/wp-content/uploads/2023/02/Mastering-React-Native-Application-Pentesting-A-Practical-Guide-2.pdf)
- CVE-2024-21668: react-native-mmkv registra a chave de criptografia dos logs no Android, corrigido na v2.11.0 (NVD): https://nvd.nist.gov/vuln/detail/CVE-2024-21668
- hbctool (e forks) para montar/desmontar Hermes: https://github.com/bongtrop/hbctool
{{#include ../../banners/hacktricks-training.md}}