ANR în Android: ce este, cauze și metode de remediere

Autor: IT Sectr Publicat: 2026-07-28 Timp de citire: 9 min

ANR (Application Not Responding) — este o notificare de sistem Android care apare atunci când aplicația nu răspunde la intrare timp de 5 secunde. Spre deosebire de glitch-uri (erori logice fără blocarea UI) și lag-uri (încetinire fără oprire completă), ANR este o defecțiune critică înregistrată de sistemul de operare: Android afișează dialogul „Aplicația nu răspunde” cu opțiunea de a închide sau aștepta. Conform Android Vitals Documentation, aplicațiile cu o rată ANR peste 0,5% au un rating scăzut în Google Play și pot fi ascunse din recomandări. Diagnosticul include analiza /data/anr/traces.txt, utilizarea StrictMode și profilarea thread-ului principal.

Principalele puncte

  • ANR — notificare de sistem Android la blocarea thread-ului principal pentru mai mult de 5 secunde, ducând la dialogul „Aplicația nu răspunde”
  • Cauze principale — blocarea thread-ului principal (BroadcastReceiver, Service), deadlock între thread-uri, operație lungă în ContentProvider
  • Diagnostic — analiza /data/anr/traces.txt, Android Studio Profiler, Firebase Performance Monitoring
  • Remediere — mutarea sarcinilor în WorkManager, utilizarea Kotlin Coroutines cu Dispatchers.IO, StrictMode pentru detectare timpurie
  • Prevenție — limitarea timpului BroadcastReceiver la 10 secunde, Service la 20 secunde, ContentProvider la 15 secunde

Ce este ANR în Android

ANR (Application Not Responding) — este un mecanism de protecție a utilizatorului în Android care se activează atunci când aplicația încetează să răspundă la intrări. Sistemul urmărește timpul de procesare a evenimentelor: dacă BroadcastReceiver nu finalizează onReceive în 10 secunde, Service nu revine din onCreate în 20 de secunde, iar ContentProvider nu răspunde în 15 secunde — Android generează ANR.

Cum arată ANR pentru utilizator

Când apare ANR, Android afișează un dialog de sistem deasupra tuturor ferestrelor: „Aplicația nu răspunde. Doriți să o închideți sau să așteptați?”. Utilizatorul poate închide aplicația sau poate aștepta recuperarea acesteia. Dacă ANR se repetă frecvent, utilizatorul șterge aplicația. Google Play ia în considerare rata ANR — procentul sesiunilor cu ANR — în algoritmii de clasare.

Diferența dintre ANR și înghețările pe iOS

Pe iOS nu există un echivalent al ANR cu dialog de sistem. În schimb, Apple folosește Watchdog, care termină procesul aplicației cu codul 0x8badf00d. Utilizatorul nu vede niciun dialog — aplicația se închide pur și simplu pe ecranul principal. Acest lucru face ca ANR pe Android să fie mai vizibil pentru utilizator, dar oferă sistemului mai multe informații pentru diagnostic.

Cauze principale ale ANR

ANR apare atunci când sistemul urmărește timeout-ul pentru unul dintre cele patru tipuri de componente. Fiecare componentă are propria limită de timp.

Blocarea în BroadcastReceiver

BroadcastReceiver se execută în thread-ul principal. Dacă onReceive lansează o cerere de rețea sincronă, o operație lungă de scriere în baza de date sau așteaptă o blocare — după 10 secunde apare ANR. Soluție: utilizați goAsync() și WorkManager pentru procesarea în fundal. Scenariu tipic — primirea unei notificări Push de la FCM și salvarea sincronă în Room.

Operație lungă în Service

Service.onCreate și Service.onStartCommand au o limită de 20 de secunde. Dacă serviciul lansează o inițializare grea (încărcarea bibliotecilor, citirea configurației din rețea) în thread-ul principal — ANR este inevitabil. Utilizați IntentService (învechit) sau WorkManager pentru execuția garantată în thread-ul de fundal.

ContentProvider cu inițializare lungă

ContentProvider.onCreate se execută înainte de apelul Application.onCreate și are o limită de 15 secunde. Dacă providerul execută migrarea bazei de date, încărcarea dicționarelor sau inițializarea SDK din rețea — acest lucru provoacă ANR la pornirea aplicației. Soluție: inițializare lazy, mutarea operațiilor grele în WorkManager.

  • BroadcastReceiver — 10 secunde pentru onReceive; utilizați goAsync() pentru procesarea în fundal
  • Service — 20 secunde pentru onCreate/onStartCommand; utilizați WorkManager sau CoroutineWorker
  • ContentProvider — 15 secunde pentru onCreate; mutați inițializarea în Application.onCreate cu pornire întârziată
  • Thread UI — 5 secunde fără procesarea evenimentelor; orice blocare mai lungă de 5 secunde provoacă ANR

Cum să diagnosticați ANR

Android oferă mai multe instrumente pentru analiza ANR: de la jurnale de sistem până la biblioteci specializate.

Analiza traces.txt

La fiecare ANR, Android salvează fișierul /data/anr/traces.txt cu dump-ul stivelor tuturor thread-urilor aplicației. Găsiți thread-ul „main” — ultima metodă din stivă indică cauza. Modele tipice: Thread.sleep(), InputStream.read(), BinderProxy.transact(). Pentru extragerea fișierului de pe dispozitiv, utilizați adb cu drepturi de superutilizator.

Firebase Crashlytics cu rapoarte ANR

Firebase Crashlytics colectează automat ANR-urile și le afișează în dashboard împreună cu trasarea. Pentru Android 11+, rapoartele ANR vin cu stiva completă a thread-ului principal. Integrarea necesită adăugarea dependenței și inițializarea FirebaseApp în Application.onCreate.

Android Studio Profiler cu trasarea thread-urilor

CPU Profiler din Android Studio vă permite să înregistrați trasarea funcționării aplicației și să vedeți ce metode ocupă timp CPU. Activați „Record with method traces” și reproduceți scenariul care provoacă ANR. Pe axa temporală va fi vizibil ce metode se executau în thread-ul principal în momentul înghețării.

Exemplu de integrare Firebase Crashlytics pentru colectarea ANR pe Android:

kotlin
class App : Application() {
    override fun onCreate() {
        super.onCreate()
        FirebaseApp.initializeApp(this)
        FirebaseCrashlytics.getInstance()
            .setCrashlyticsCollectionEnabled(true)
        StrictMode.setThreadPolicy(StrictMode.ThreadPolicy.Builder()
            .detectAll()
            .penaltyLog()
            .build())
    }
}

Metode de remediere a ANR

Remedierea ANR înseamnă în primul rând mutarea tuturor operațiilor lungi din thread-ul principal în cele de fundal. Să analizăm tehnicile specifice pentru fiecare tip de componentă.

Utilizarea WorkManager pentru sarcini de fundal

WorkManager — soluția recomandată de Google pentru munca în fundal. Garantează execuția sarcinii în thread-ul de fundal ținând cont de starea dispozitivului. Spre deosebire de Service, WorkManager nu blochează thread-ul principal și este rezistent la repornirea aplicației. Pentru BroadcastReceiver, utilizați goAsync() și transmiteți rezultatul PendingResult către WorkManager.

Kotlin Coroutines cu dispatcheri corecți

Lansați toate cererile de rețea, lucrul cu baza de date și operațiile cu fișiere cu Dispatchers.IO. Thread-ul principal ar trebui să actualizeze doar UI. Utilizați viewModelScope pentru anularea automată a corutinelor la distrugerea Activity. Evitați runBlocking() în orice context — aceasta este o blocare sincronă a thread-ului curent.

Inițializarea lazy a ContentProvider

Dacă ContentProvider execută o inițializare lungă, utilizați mecanismul de încărcare întârziată: creați un provider care returnează datele imediat, iar inițializarea grea lansați-o prin WorkManager cu întârziere. Aceasta previne ANR la pornirea aplicației, când sistemul este cel mai sensibil la întârzieri.

Exemplu de utilizare corectă a BroadcastReceiver cu goAsync în Android:

kotlin
class FcmReceiver : BroadcastReceiver() {
    override fun onReceive(context: Context?, intent: Intent?) {
        val pendingResult = goAsync()
        WorkManager.getInstance(context!!)
            .enqueue(OneTimeWorkRequest.from(NotificationWorker::class.java))
        pendingResult.finish()
    }
}

Prevenirea ANR în dezvoltare

Cea mai bună modalitate de a lupta cu ANR este prevenirea apariției lor în faza de dezvoltare prin instrumente și soluții arhitecturale.

StrictMode pentru detectarea blocărilor thread-ului principal

StrictMode cu politicile detectNetwork() și detectDiskReads()/detectDiskWrites() activate detectează potențialele ANR în faza de dezvoltare. În compilarea Debug, setați penaltyDeath — orice încălcare va duce la o cădere imediată, iar dezvoltatorul va vedea problema înainte de commit.

Firebase Performance Monitoring pentru metrici de producție

Firebase Performance urmărește timpul de execuție al operațiilor cheie și arată care scenarii depășesc pragul ANR. Configurați trasări personalizate pentru fiecare ecran și cerere de rețea. Dacă timpul de execuție depășește 3 secunde — acesta este un ANR potențial care necesită optimizare.

Testarea cu întârzieri de rețea și disc

Simulați condiții lente: limitați viteza rețelei prin Network Link Conditioner pe iOS sau Android Emulator. Încetiniți citirea de pe disc prin emularea memoriei lente. ANR apare adesea tocmai în astfel de condiții, pe dispozitivele rapide ale dezvoltatorului nefiind vizibile.

  • BroadcastReceiver — utilizați întotdeauna goAsync() pentru procesarea mai lungă de 1 secundă
  • Service — înlocuiți cu WorkManager sau CoroutineWorker cu dispatcher de fundal
  • ContentProvider — evitați rețeaua și baza de date în onCreate, utilizați lazy-init cu WorkManager
  • Thread UI — StrictMode cu penaltyDeath în Debug, Firebase Performance pentru monitorizare în producție

Întrebări frecvente

De ce apare ANR pe Android, dar nu pe iOS?

Android urmărește explicit timpul de procesare a evenimentelor pe thread-ul principal și afișează dialogul ANR. iOS folosește Watchdog, care închide forțat aplicația după înghețare de peste 10–20 de secunde. ANR este o caracteristică a arhitecturii Android, unde mai multe componente (BroadcastReceiver, Service) au timeout-uri stricte.

Cum găsesc traces.txt pe un dispozitiv fără root?

Pe Android 11+ puteți obține dump-ul ANR prin adb shell dumpsys dropbox --print data_app_anr. Pe Android 10 și mai jos, fără root, nu există acces la /data/anr/traces.txt. Utilizați Firebase Crashlytics — colectează automat rapoartele ANR pentru Android 11+.

Ce rată ANR este considerată acceptabilă?

Google Play recomandă o rată ANR sub 0,5% — adică nu mai mult de 5 ANR la 1000 de sesiuni. O aplicație cu o rată peste 1% primește un avertisment în Google Play Console și poate fi ascunsă din recomandări. În mod ideal, rata ANR ar trebui să fie sub 0,1%.

Poate o corutină să provoace ANR?

Corutina în sine nu blochează thread-ul. Dar dacă în interiorul corutinei se execută runBlocking pe thread-ul principal sau corutina este lansată cu Dispatchers.Main și execută o operație CPU lungă — aceasta va provoca ANR. Utilizați Dispatchers.IO pentru intrare-ieșire și Dispatchers.Default pentru calcule.

Cum testez ANR în emulator?

Utilizați Android Emulator cu profilul „Slow Network” sau scrieți un test care apelează Thread.sleep(6000) pe thread-ul principal. Lansați aplicația prin Debug și după 5 secunde veți vedea dialogul ANR. Verificați că în logcat a apărut o înregistrare ANR cu trasare.

Concluzii

  • ANR — notificare de sistem Android la blocarea thread-ului principal pentru mai mult de 5 secunde sau depășirea timeout-urilor componentelor
  • Timeout-uri: BroadcastReceiver — 10 s, Service — 20 s, ContentProvider — 15 s, UI — 5 s
  • Diagnostic — /data/anr/traces.txt, Firebase Crashlytics, CPU Profiler în Android Studio
  • Remediere — WorkManager, goAsync(), Kotlin Coroutines cu Dispatchers.IO, inițializare lazy ContentProvider
  • Prevenție — StrictMode cu penaltyDeath, Firebase Performance Monitoring, testare cu întârzieri de rețea
  • Google Play recomandă rata ANR < 0,5%; la rata > 1% aplicația intră sub restricții de vizibilitate
  • Recomandare: configurați Firebase Crashlytics și Performance pentru colectarea ANR în producție și setați alerte la depășirea pragului de 0,3%

Vom dezvolta o aplicație mobilă la cheie

IT Sectr creează aplicații iOS și Android pentru startup-uri și afaceri din 2017. Vă vom consilia și vă vom propune cea mai bună soluție.

Discutați proiectul

Citiți și