ANR Exception handling - android

I have an application, where we are providing the Remote UI(which contains all the buttons to control the Media server).
The problem is when we click any of the button, we are executing the corresponding action, which is very long UPNP network operation.
so when we press the buttons continuously , finally the device comes up with ANR Exception and force close the application. I made some research on this ANR Exception and finally found that, we can use Thread or AsyncTask to solve this problem.
But in my application since we are providing so many buttons, when user presses buttons continuously , it may inturn lead to lot of threads created in the application.
Please give me your suggestions on this.
How to overcome this problem?
Thanks

One of the many advantages of using AsyncTask is that it manages the threading (and thread pooling) for you. So if you use AsyncTask, you shouldn't have the problem of creating too many threads.
In addition, if you're concerned with creating too many AsyncTasks, consider putting the tasks in a member variable (such as a Queue or ArrayList) and keeping track of their state. If one is still processing it might not be necessary to start another. Or you can remove tasks whose results are no longer needed.

Just keeping track of the button click in member variable and using One AsyncTask you can perform this long running operation in queue wise.
If possible just avoid multi-threads for these operations.

Related

Is there any point in using Asynctasks for api calls that require a response to proceed?

I feel that the answer to this question is too obvious, but part of me still wants to ask it anyway.
I am creating an Android app that makes several HTTP POST/GET requests using APIs when the app is launched for the first time by the user. All these requests are made by launching Asynctasks within the activity.
For example, there is an activity where athe user has to select an item from a list retrieved from the API. After he selects one, a progress bar is displayed to the user while the app sends the selection to the API to retrieve another list, and in the next activity, the user selects items from this list. Clearly, the user can't go this second list until a response has been received from the server after the app sends it the first list's selection.
In such a case, is there any point in using an Asynctask to send the selection of the first list, since the user is prevented from doing anything (by being shown a progress bar) until a response is received and the next activity is started. Wouldn't it make the code less complex if I just made the API call on the main thread?
I hope this wasn't too confusing.
Thanks
I got your doubt completely. Good question. The root cause of the doubt because you are thinking you don't need to interact with the app till the process completes. But you actually want to. Event the progress bar will freeze if you could do something like it.
Ok, let's just assume you don't even have a ProgressBar. However, handling the different UI components such as Spinners, EditTexts is not the only duty of the main thread. It should define different callbacks in the activity lifecycle. Doing big tasks in main thread will also freeze callbacks like onPause(), onStop() etc. That is why the 'NetworkOnMainThreadException' is being thew.
Basically you cannot call the api on main thread as it will block the UI. Also now Android does not allow it to happen and throws 'NetworkOnMainThread Exception'. Its fine to use Asynctask for any task that takes few seconds and you get the callback in it , which in your case is required before you proceed to next screen.
Best way to do it is by using Networking libraries:
Refer this
https://developer.android.com/training/volley/simple.html
First of all you cannot do netwok call on main thread, it will raise NetworkOnMainThreadException , You can still by pass this exception by adding the couple of following lines in your activity
StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();
StrictMode.setThreadPolicy(policy);
but it is always recommended to perform network operation in background,
else it may cause your app to stop responding, and can result in the OS killing your app for being badly behaved , go through this article once link
Any operation that takes more than a few seconds to perform should be added in a separate thread. All network operations should be performed on AsyncTask or do have a look at RxJava and RxAndroid. To be specific to your operation, any UI Operations during a network call can be performed in onPostExecute. If you're working with thread class then use a Handler.
As others mentioned, if main thread is used for network operation, it would make your app unresponsive.
User may want to start a different flow in your app by starting an activity from menu or action bar whatever is available in your app to start other flow.

How to insert large amount of data in sqlite database in Android

I have a lot of data that is stored in a CSV file (about 20,100 rows), which I need to insert into a sqlite database.
This insert is taking very long to complete. What is the fastest way to insert this data?
As you have suggested, number of rows are huge I will recommend not to use AsyncTask, as its not tied to your Activity lifecycle i.e if you activity which started it dies, it doesnt mean AsyncTask dies as well, so if you try initiate a AsyncTask and somehow if your activity dies e.g screen rotation or back key pressed, upon restarting another AsyncTask will get spawned rather then it getting linked to already executing AsyncTask. hence duplicating same operations.
So, all in all I would recommend following approach
(A)
Create a IntentService, it's handleIntent() api already executes in a worker thread so you don't have to worry about any thing, and once all messaged in its queue are finished it automatically dies, so no worry at all about leaking any resources.
write your logic for inserting rows in bulk, use content resolver bulkInsert() api for same. I will recommend inserting in 100 roes per batch, you can implement rollback and error checks to make sure insert goes normally.
Once all insert is finish, you can post back to your UI using Handler and Messengers.
with all this you will achieve two major challenge
Not to hang up your UI, escaping any possible ANR
Even if back key is pressed, ensured that db operation goes on smoothly as it was taken up in background task.
Using AsyncTask<>, insert 20,100 rows inserts in database. Using this asynctask whole work run in background. For more information follow this link
The best solution would be using services and executor because as OP described, process can take a lot time. Thanks that You will be able to close app or move it to background with no worried Your long process is destroyed.
Using AsyncTask is not a good idea because it was designed for short operations as it is described on http://developer.android.com/reference/android/os/AsyncTask.html You must also be careful with using it. Changing orientation screen cause recreating view and also task of asynctask.
AsyncTasks should ideally be used for short operations (a few seconds
at the most.) If you need to keep threads running for long periods of
time, it is highly recommended you use the various APIs provided by
the java.util.concurrent package such as Executor, ThreadPoolExecutor
and FutureTask.

android app touch unrensponsiveness

I have developed an application that is used very intensively for hours, makes a lot of web services calls, uses a lot of async tasks and does a lot of operations on an sqlite database. The problem is that absolutely randomly the display dims, as if it goes in power saving mode (this is happened also when the battery was charged) and the UI does not respond at all (the log written for buttons click are not written). If I click the home button the phone works correctly and every app works fine. If I go back to my app the display dims again. I really don't have any idea about the cause of this behavior, I really hope some of you can help me because my boss wants an explanation because the customer wants an answer.
EDIT: I've noticed that when the problem occurs, it's just after unlocking the screen, so it should have something to do with app resuming, but I don't really have any idea of what is causing this behavior.
It seems that some operations may be blocking the main UI thread and the app goes to not responding state. Check if any such intensive operations are done in UI thread.
As jaibatrik says, this might be caused by doing too much work in the UI thread rather than in background threads, AsyncTasks etc. One way this may be achieved which is less obvious is if all the work is correctly done in a background thread (of some type) but a UI thread operation is waiting for the outcome of a background thread operation.
you could prevent display dim like this.
ll.setKeepScreenOn(true);
you should handle onresume(), onpause() & co.
maybe you create memoryleaks within your backgroundtasks or services.

Handling program flow for an application

I am currently trying to write a simple application very similar to this:
http://lab.andre-michelle.com/tonematrix
My main problem is that I do not know how to handle the general program flow. Traditionally, I would use a loop inside the main function that handled the drawing and updated the state and everything. The way the android framework works is a bit confusing since the access points into the program are the various onSomething() functions. This is quite confusing for a beginner.
How do I keep track of time and how do I know how when to move to the next square column?
Do I HAVE to use threads? Is there a single thread solution, similar to the single loop approach?
You can use timers, they do already run in their own threads.
You can also use handlers for timed execution.
In case of the sample program u linked to, you would add something with onTouch and have a timer running in the background to periodically play the tune.
The activity lifecycle should be seen as the lifeline of your program not so much of the code in it.
How to keep track of time ?
System.currentTimeMillis();

Android: Single service with multiple threads

I am building an application which performs 3 tasks concurrently.->
Listening to new devices.
A proxy to interact with the device in real-time.
A set of business Logic to be run on the data provided by the device proxies.
And of couse a Main UI (thread)
I want task 1,2 and 3 to run even when the application is in the background.
What should be done?
Using 3 services, one for each.. (apparently not practical).
Can a single service support all the tasks.( one service with multiple threads sort of design)?
Please help.
Basically, What i intend to ask is that is a model available to perform all 3 tasks even if the application is in the background? If service is the answer, how can it be implemented in an efficient way without putting too much load on the system i.e. using 3 services?
I would go for three threads started in your action or (Surface)View depending on what sort of updates you'll have on screen.
When doing threads though you really need to keep synchronization in mind so your application won't blow up from accessing the same variables and getting unexpected results.
Using Multiple Threads to perform your tasks concurrently.
The following link gives a good idea about Multiple threads: http://edwards.sdsu.edu/labsite/index.php/josh/124-multiple-background-threads-in-android
Make sure your service runs in the foreground; this will make it work.

Categories

Resources