I am creating an application for device tracking for my company (own company devices)
I created a Background Service using the GooglePlay API to get the updates.
However, when my application is closed, it rarely sends the locations to the server. Rarely does it get update updates.
What should I do? Is there any special permission I can use?
Use WorkManager for this purpose. Even if your app is being killed process scheduled in WorkManager will be executed.
In your case, you can schedule to check location at a fixed interval and send it to server or wherever you want to send.
From official doc:
The WorkManager API makes it easy to specify deferrable, asynchronous
tasks and when they should run. These APIs let you create a task and
hand it off to WorkManager to run immediately or at an appropriate
time. For example, an app might need to download new resources from
the network from time to time. Using these classes, you can set up a
task, choose appropriate circumstances for it to run (like "only while
device is charging and online"), and hand it off to WorkManager to run
when the conditions are met. The task is still guaranteed to run, even
if your app is force-quit or the device is rebooted.
Your task will come under Recurring tasks
Related
In our Android Application - during app start we schedule threads to run every 8 hours for transmitting files. I have been observing inconsistent transmission behavior when the app is terminated after app start (i.e. the user kills the app). I am suspecting that the scheduled threads are somehow cancelled/destroyed/terminated with the app gets terminated. Does anyone know whether this is the case on Android?
Sample Code of how I am deploying scheduled background threads.
scheduledExecutor = new ScheduledThreadPoolExecutor(1, <this param is a class that Creates threads with the default priority set to background.>);
scheduledExecutor.setRejectedExecutionHandler(new ThreadPoolExecutor.DiscardPolicy());
scheduledExecutor.schedule(new Handler(), 28800000, TimeUnit.MILLISECONDS);
during app start we schedule threads to run every 8 hours for transmitting files
That will not work very well.
I have been observing inconsistent transmission behavior when the app is terminated after app start (i.e. the user kills the app)
You will have inconsistent transmission behavior if the app is in the background as well. The only scenario in which what you describe would work is some sort of kiosk mode app or other situation where your app UI is always in the foreground.
I am suspecting that the scheduled threads are somehow cancelled/destroyed/terminated with the app gets terminated
Android will terminate your app's process after a period of time, to free up system RAM for other apps. At that point, your threads and other CPU/RAM structures all go away. This is covered in the documentation, as well as many books and courses on Android app development.
And, for the purposes of transmitting files, your app's ability to use the Internet will be affected by Doze mode, app standby, and manufacturer-specific battery-conservation approaches. Doze mode is covered in the documentation.
The standard recommendation today is to use WorkManager, where you schedule the work with instructions that you need network access when the work is performed.
I've seen lots of APIs for Job Scheduling, if I may mention:
AlarmManager
JobScheduler
JobSchedulerCompat
GCMNetworkManager
And what I'm trying to do is, a user sets a date along with a campaign, he saved it in Firebase, and when that date comes, that created object gets deleted. I've seen something similar with Parse, but as you might know, it's shutting down and I'm storing my data in Firebase anyways.
However, AlarmManager surely doesn't do the task in the cloud (The service doesn't run on the device, but in the cloud.)
JobScheduler is not available for pre-lollipop.
JobSchedulerCompat is deprecated "There's no guarantee this won't explode your device or drain your battery" and I don't think it runs in the cloud anyways.
And I'm not sure about GCMNetworkManager. Does it run in the cloud or is it on the device? Tough example: If every single user who uses my app has his device shut down, will the task still be completed?
Long question short: Does GCMNetworkManager run in the cloud? If not, what alternatives do I have?
Edit: #qbix's answer gave me a hint, but I still cannot understand anything from that link. If anyone answers my question along with an example, he will be awarded the bounty. This includes #qbix.
No, GCMNetworkManager does not run in the cloud. It runs on the device just like the other schedulers you listed.
If I understand your requirements correctly, you should look into the Firebase Server SDK. You would create a server task with limited privileges to access the appropriate sections of your database. It would perform the needed database maintenance for all users on a periodic basis.
Could you pease tell me what is the correct way to do the synchronization jobs in Android (e.g. if I have about 5 jobs)?
Note! By synchronization job I mean a thread which runs in background and sends some data (e.g. analytics) via a Web Service...
For more details please read a more detailed description:
I've got a task to implement some background jobs which will synchronize some data with a restful web service. Some of the jobs should be scheduled periodically with a specific delay. If there is no internet connection then I simply cache the data and later when the connection reappears I try to run the jobs.
Taking into consideration that creating new threads is quite expensive and especially on mobile development, I'm using a cached thread pool (ExecutorService) and every time some actions are requested for processing I'm trying to reuse the threads. I don't use AsyncTask because I've replaced this with this Executor Service (Executors.newCachedTreadPool) and its convenient for me because I don't need to create many AsyncTasks as I reuse the threads from ES... In order to support the scheduled jobs, I use another thread pool(ScheduledExecutorService) and use Callable because I need to see the execution result. I've got a complex logic here... So, when a particular action is done in the app, the 1st thread pool (is like the AsyncTask) will work like an AsyncTask, the advantage is that I don't create new threads but I reus them. This will not block the UI's main thread. It will delegate to the scheduled executor which will do its job.
This solution works. And it sounds good for me as I'm coming from server side, but I'm interested to know how this must be done correctly on Android? Is this too sophisticated for a mobile app?
Merci,
Serge
Use a sync adapter. See http://developer.android.com/training/sync-adapters/index.html. A sync adapter runs in the background, it's managed by the system, and scheduled efficiently so that your sync doesn't waste battery power. Best of all, the system will automatically detect network connectivity and queue up your sync adapter if necessary. If you want, you can use multiple sync adapters.
Notice that although it seems that sync adapters need a content provider and an authenticator, they really don't.
I have a number of backend processes (java applications) which run 24/7. To monitor these backends (i.e. to check if a process is not responding and notify via SMS/EMAIL) I have written another application.
The old backends now log heartbeat at regular time interval and this new applications checks if they are doing it regularly and notifies if necessary.
Now, We have two options
either run it as a scheduled task, which will run after every (let say) 15 min and stop after doing its job or
Run it as another backend process with 15 min sleep time.
The issue we can foresee right now is that what if this monitor application goes into non-responding state? So, my question is Is there any difference between both the cases or both are same? What option would suit my case more?
Please note this is a specific case and is not same as this or this
Environment: Java, hosted on LINUX server
By scheduled task, do you mean triggered by the system scheduler, or as a scheduled thread in the existing backend processes?
To capture unexpected termination or unresponsive states you would be best running a separate process rather than a thread. However, a scheduled thread would give you closer interaction with the owning process with less IPC overhead.
I would implement both. Maintain a record of the local state in each backend process, with a scheduled task in each process triggering a thread to update the current state of that node. This update could be fairly frequent, since it will be less expensive than communicating with a separate process.
Use your separate "monitoring app" process to routinely gather the information about all the backend processes. This should occur less frequently - whether the process is running all the time, or scheduled by a cron job is immaterial since the state is held in each backend process. If one of the backends become unresponsive, this monitoring app will be able to determine the lack of response and perform some meaningful probes to determine what the problem is. It will be this component that will then notify your SMS/Email utility to send a report.
I would go for a backend process as it can maintain state
have a look at the quartz scheduler from terracotta
http://terracotta.org/products/quartz-scheduler
It will be resilient to transient conditions and you only need provide a simple wrap so the monitor app should be robust providing you get the threading stuff right in the quartz.properties file.
You can use nagios core as core and Naptor to monitoring your application. Its easy to setup and embed with your application development.
You can check at this link:
https://github.com/agunghakase/Naptor/tree/ver1.0.0
When should a thread or a service be used?
Should they be used for authentication? For instance, in my app I was considering using a thread or service (I am authenticating via Active Directory.)
Do you have examples of when each would be used?
Update: It seems the Android documentation includes a corresponding clarification now, see http://developer.android.com/reference/android/app/Service.html#WhatIsAService.
Original answer:
In Android, a Service does not provide any concurrent execution ("run in background"). It is actually more of a simple Java object which merely is instantiated (and managed) via the Android system instead of your application via new.
The most important property of a service is therefore not about deferring workload; this can be achieved with simple threads.
What makes a service object special is that it is registered with the Android system as a service. This let's the system know that this object provides some sort of service and should be kept alive as long as possible, or until it is stopped. Normal application threads do not have this special meaning to the Android system and will be terminated much more generously at the discretion of the system.
So, if you need some background activities to go on only while your application/Activity is active, a thread can do what you need.
If you need a component that keeps active will not be purged even when, after a while, the Android system decides to remove your Activities from memory, you should go for the service, or even a "foreground service", which is deemed even more important by the system and even less likely to be terminated to reclaim resources.
Of course, if desired, a Service object can also be made to contain one or more Thread instances which could then live as long as the Service object itself.
Edit:
Oh, plus: A service is, of course, the way to go if you want to provide some service(s) to other applications, which can "bind" to a service only.
A thread should be used in a long running process that would block the UI from updating. If it's more than a second or two you might want to put it into a background thread and notify the user with a dialog or spinner or something. If you lock the UI thread for more than 5 seconds the user will be prompted with a "kill or wait" option by the OS.
A service does not run on separate thread, so it will block the UI, but you can spawn a new thread within a service. A service is used more for something that should happen on an interval or keep running/checking for something when there is no UI shown.
Just look at this nice post Android Thread Constructs(Part 4): Comparisons
.
or Difference between Service, Async Task & Thread?.
Use service if you need something that is either used by other applications or outlives your application activities. The good example of service is file transfer that may take long time and you don't want to force user using your application during this time. Use thread (usually via AsyncTask or similar) in other cases.
For authentication purposes AsyncTask seems like a good choice.
I believe the main difference is about Android system attitude. Service is a part of android infrastructure, so android recognizes service as a working part of application and considers killing service as a last option. Moreover, you can tune up service priority in order to do it as important as foreground activity. As for threads, android does not recognize a thread as important part which must be kept. So usual threads has much more chances to be killed.
For instance If you have an activity which start a working thread and then go background, as android do not recognize thread as a working part, it may think that application do nothing, because no activity or service running and kill the whole app, including the working thread.
As per Android Developer Guide (http://developer.android.com/guide/components/services.html#Basics) :
A service is simply a component that can run in the background even when the user is not interacting with your application. Thus, you should create a service only if that is what you need.
If you need to perform work outside your main thread, but only while the user is interacting with your application, then you should probably instead create a new thread and not a service. For example, if you want to play some music, but only while your activity is running, you might create a thread in onCreate(), start running it in onStart(), then stop it in onStop(). Also consider using AsyncTask or HandlerThread, instead of the traditional Thread class. See the Processes and Threading document for more information about threads.
Remember that if you do use a service, it still runs in your application's main thread by default, so you should still create a new thread within the service if it performs intensive or blocking operations.