2014-04-10 12 views
10

Jest to ogólne pytanie, który powstał z określonego scenariusza, ale chciałbym, aby uzyskać ogólne odpowiedź jak radzić sobie z następującej sytuacji:Jak zapobiec zawieszaniu się aplikacji na Androida z powodu wyjątku w wątku tła?

Tło:

Mam app, który jest za pomocą biblioteki innej firmy (SDK dostawcy sieci reklamowej - konkretnie - AdMob SDK, na podstawie Google Play Services). Funkcjonalność tej biblioteki nie jest krytyczna dla aplikacji. Biblioteka tworzy jeden lub więcej wątków procesu roboczego. Czasami (bardzo rzadko) występuje nieobsługiwany wyjątek w jednym z tych wątków tła, powodując awarię aplikacji. Chciałbym zignorować wszystkie wyjątki, spowodowane przez tę bibliotekę, niezależnie od ich przyczyny: w najgorszym przypadku użytkownik aplikacji nie zobaczy reklamy - jest znacznie lepsza niż awarie aplikacji.

Ponieważ sama biblioteka tworzy wątki tła - nie mogę po prostu zawinąć ich za pomocą polecenia try/catch.

Pytanie

Czy istnieje jakiś sposób, aby złapać wszystkie nie obsługiwane tła (bez wyjątków) główne nitki i po prostu zabić wątku w takim przypadku, i aby zapobiec awarii aplikacji?

Podobne pytania

Widziałem wiele różnych pytań, ale niektóre z nich są zbyt szczegółowe (i nie obejmuje moim przypadku), inni odnoszą się do sytuacji, gdy deweloper ma kontrolę nad tworzeniem wątku i jest w stanie opakować cały wątek metodą try/catch. Jeśli nadal brakowało mi odpowiedniego pytania, obejmującego tę sprawę, z pewnością doceniam link:

+2

Czy próbowałeś instalacji obsługi do wątku roboczego i starają się nie zabić proces? Nie wiem, czy to możliwe, ponieważ możesz nie mieć dostępu do wątku roboczego, który ulega awarii. Wiem, że flurry udaje się zainstalować program obsługi dla całego procesu i przesłać raport o błędzie zanim aplikacja ulegnie awarii. Być może jest to możliwe dzięki tej trasie. –

+0

@over_optimistic Dzięki! Próbowałem używać Thread.setDefaultUncaughtExceptionHandler i działa jak urok :)! Proszę napisać to jako odpowiedź, więc mogę to zaakceptować. –

+1

http://stackoverflow.com/questions/2764394/ideal-way-to-set-global-uncaught-exception-handler-in-android/ – fadden

Odpowiedz

12

Wszystko, co musisz zrobić, to rozszerzyć wszystkie działania o BaseActivity. Aplikacja nigdy awarii w dowolnym momencie

Kod sniplet dla BaseActivity:

public class BaseActivity extends Activity{ 
    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() { 
      public void uncaughtException(Thread paramThread, Throwable paramThrowable) { 
       Log.e("Error"+Thread.currentThread().getStackTrace()[2],paramThrowable.getLocalizedMessage()); 
      } 
     }); 
    } 
} 
+0

Myślę, że lepiej jest umieścić ten kod do niestandardowej klasy aplikacji, ponieważ jest przeznaczony do uruchomienia tylko raz w ciągu życia aplikacji –

+1

po dodaniu go do mojej aplikacji, Ilekroć moja aplikacja się zawiesza, pojawia się na czarnym ekranie. Proszę, pomóż mi z tym –

2

Jak wspomniano powyżej, Thread.setDefaultUncaughtExceptionHandler jest właściwy sposób, aby sobie z tym poradzić. Utwórz klasę:

private class MyThreadUncaughtExceptionHandler implements Thread.UncaughtExceptionHandler { 

    @Override 
    public void uncaughtException(Thread thread, Throwable ex) { 
     Log.e(TAG, "Received exception '" + ex.getMessage() + "' from thread " + thread.getName(), ex); 
    } 
} 

Następnie zadzwonić setDefaultUncaughtExceptionHandler od głównego wątku:

Thread t = Thread.currentThread(); 
t.setDefaultUncaughtExceptionHandler(new MyThreadUncaughtExceptionHandler()); 
Powiązane problemy