Skip to content

Commit

Permalink
first commit
Browse files Browse the repository at this point in the history
  • Loading branch information
SalomonBrys committed Jul 26, 2013
0 parents commit 1fe71de
Show file tree
Hide file tree
Showing 6 changed files with 185 additions and 0 deletions.
21 changes: 21 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@

.classpath
.project
.cproject
.settings/

*~
.DS_STORE

AndroidManifest.xml
bin/
gen/
libs/
obj/
proguard-project.txt
project.properties
res/

src/com/example/

build/
Binary file added ANRWatchDog.jar
Binary file not shown.
20 changes: 20 additions & 0 deletions LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
The MIT License (MIT)

Copyright (c) 2013 Salomon BRYS

Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
70 changes: 70 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
ANR-WatchDog
============

A simple watchdog that detects Android ANR (Application Not Responding) error and throws a meaningful exception


Why it exists
-------------

There is currently no way for an android application to catch and report ANR error.
If your application is not the play store (either because you are still developing it or because you are distributing it differently),
the only way to investigate an ANR is to pull the file /data/anr/traces.txt and try to navigate your way in this enormous file.

There is an [issue entry](https://code.google.com/p/android/issues/detail?id=35380) in the android bug tracker describing this lack, feel free to star it ;)


What it does
------------

It sets up a watchdog that will detect when the UI thread stops responding. When it does, it raises an exception with the UI thread stack trace.


Can it work with crash reporters like [ACRA](https://github.com/ACRA/acra) ?
----------------------------------------------------------------------------

Yes ! I'm glad you ask : That's the reason why it was developped in the first place !
As this throws an exception, a crash handler can intercept it and handle it the way it needs.


How it works
------------

The watchdog is a simple thread that :

1. Schedule small code to be run on the UI thread as soon as possible.
2. Wait for 5 seconds. (5 seconds is the default, but it can be configured).
3. See if the code has run : if it has, go back to 1
4. If the code has not run, it means that the UI thread has been blocked for at least 5 seconds, raises an exception with the UI thread stack trace


How to use it
-------------

1. [Download the jar](https://github.com/SalomonBrys/ANR-WatchDog/blob/master/ANRWatchDog.jar?raw=true)

2. Put *ANRWatchDog.jar* in the libs/ directory of your project

3. In your application class, add an ANRWatchDog property:

public ANRWatchDog aaw = new ANRWatchDog();

Note that you can configure the watchdog interval (5000 miliseconds by default).
For example, if you want to have a 10 seconds interval:

public ANRWatchDog aaw = new ANRWatchDog(10000);

4. In your application class, in *onCreate*, add:

aaw.start();

5. ***You're done***


Advanced use
------------

* ANRWatchDog is a thread, so you can interrupt it at any time.

* If you are programming with Android's multi process capability (like starting an activity in a new thread), remember that you will need an ANRWatchDog thread per process

20 changes: 20 additions & 0 deletions src/com/github/anrwatchdog/ANRError.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.github.anrwatchdog;

import android.os.Looper;
import android.util.Log;

class ANRError extends Error {
private static final long serialVersionUID = 1L;
public ANRError() {
super("Application Not Responding");
}
@Override
public Throwable fillInStackTrace() {

Log.e("ANRError", "Filling stack trace");

setStackTrace(Looper.getMainLooper().getThread().getStackTrace());

return this;
}
}
54 changes: 54 additions & 0 deletions src/com/github/anrwatchdog/ANRWatchDog.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
package com.github.anrwatchdog;

import android.os.Handler;
import android.os.Looper;
import android.util.Log;

public class ANRWatchDog extends Thread {

private ANRWDSSeter seter = new ANRWDSSeter();

private Handler handler = new Handler(Looper.getMainLooper());

private int tick = 0;

private final int interval;

public ANRWatchDog(int interval) {
super();
this.interval = interval;
}

public ANRWatchDog() {
this(5000);
}

private class ANRWDSSeter implements Runnable {
@Override
public void run() {
tick = (tick + 1) % 10;
// Log.i("ANRWatchDog", "Setting tick: " + (tick));
}
}

@Override
public void run() {
try {
int lastTick = 0;
for (;;) {
lastTick = tick;
handler.post(seter);
Thread.sleep(interval);

if (tick == lastTick) {
Log.e("ANRWatchDog", "ANR DETECTED");
throw new ANRError();
}
}
}
catch (InterruptedException e) {
Log.i("ANRWatchDog", "Interrupted");
}
}

}

0 comments on commit 1fe71de

Please sign in to comment.