I am working on app which needs to executes a web-service at app install and only once.
Currently i used Shared Preferences for this, But if user clear app data then it lost Shared Preferences value and my code detracts that app is newly created and my code executes web-service further.
So i need solution which broadcast event of my own app install.
I also create broadcast for that but broadcasts only when other app install.
This code i used...
For Check Status
private void checkAppStatus() {
boolean isOpen = AppMethod.getBooleanPreference(MainActivity.this, AppConstant.PREF_IS_OPEN);
if (!isOpen) {
executeWS();
}
}
Broadcast
public class AppInfoReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
Log.e("My App", "Install");
}
}
Manifest
<receiver android:name=".receiver.AppInfoReceiver">
<intent-filter>
<action android:name="android.intent.action.PACKAGE_INSTALL" />
<action android:name="android.intent.action.PACKAGE_ADDED" />
<action android:name="android.intent.action.PACKAGE_REMOVED" />
<data android:scheme="package" />
</intent-filter>
</receiver>
If you have a server, you can save status in your server and get the status before execute task
You have following options:
You can create a file in hidden directory on external memory with
needed information.
You can create and use your web service for those needs.
Your code doesn't work because your application not installed at that time when broadcast created and because in android your application can receive broadcasts only if it was launched at least one time by user.
As I understood, first option doesn't fit your needs too, cause there is some probability that external memory would be erased or replaced. Android devices doesn't provide any kind of memory that 100% would be persistent in time, and if you really need information about installation of your application you should run your server that receives android device id and sends back to your application information about rather it is first installation or re installation. However I suppose that you should assume clearing app data as application reinstall and run your web service one more time. Simplest solution: just pass to your service android device id and do your things if it is new id or not if it is already done.
Related
I uninstalled an android mobile app and immediately got SMS that says "sorry to see you go". How did they track that I uninstalled the app?
We can implement a BroadcastReceiver in our application for listening the action "android.intent.action.QUERY_PACKAGE_RESTART" and match our package name inside onReceive() method. If the broadcast was received for selection of our desired application package, then we'll initiate a background thread that will keep monitoring the foreground running activities using the ActivityManager.
Once we find the foreground activity to be "com.android.packageinstaller.UninstallerActivity", it'll be confirm that user wants to uninstall our application. At this point we'll perform the desired tasks (either display a dialogue, or start another activity overlapping the uninstallation window, etc..) that are to be performed before uninstallation. After performing our task, we'll allow the user to continue with confirming the uninstallation process.
When the user clicks on the Uninstall button under Manage Apps settings, we'll perform our pre-uninstallation tasks and then promt the user to the Confirmation window where user can either confirm to uninstall or can Cancel the operation.
Edit you used to be able to do it this way, the permission required is now deprecated
When uninstalling an app, it fires a Broadcast for "QUERY_PACKAGE_RESTART".
So you would need to have Permissions and to build a Broadcast Receiver
<uses-permission android:name="android.permission.GET_TASKS"/>
And then the manifest.xml
<receiver android:name=".UninstallBroadcastReceiver">
<intent-filter android:priority="0">
<action android:name="android.intent.action.QUERY_PACKAGE_RESTART" />
<data android:scheme="package" />
</intent-filter>
</receiver>
UninstallBroadcastReceiver
public class UninstallBroadcastReceiver extends BroadcastReceiver{
#Override
public void onReceive(Context context, Intent intent) {
String[] packageNames = intent.getStringArrayExtra("android.intent.extra.PACKAGES");
if(packageNames!=null){
for(String packageName: packageNames){
if(packageName!=null && packageName.equals("YOUR_APPLICATION_PACKAGE_NAME")){
//Do Something ?
}
}
}
}
}
Still not sure how you would need to track if the user cancels the action, but fire a network call informing your app is about to be uninstalled.
I'm aware of the fact that the app is uninstalled and re-installed during the course of an app update from the play store.
I have a very crucial service which needs to be running ALWAYS in the background. And this service gets killed during the update process. Is there any way to restart this service without having the user to go manually to the app (without going to the activity)?
I've implemented the following code. But somehow this doesn't work either. (Probably because the app gets uninstalled anyway)
public class AppUpdateReceiver extends BroadcastReceiver{
#Override
public void onReceive(Context context, Intent intent)
{
if ("android.intent.action.PACKAGE_REPLACED".equals(intent.getAction()))
// Start service here
}
}
MANIFEST:
<receiver android:name="com.company.services.AppUpdateReceiver">
<intent-filter>
<action android:name="android.intent.action.PACKAGE_REPLACED"/>
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</receiver>
Other info : minSDK = 14, Target SDK = 20
I'm aware of the fact that the app is uninstalled and re-installed during the course of an app update from the play store
No, it is not. Your process is terminated, though.
I have a very crucial service which needs to be running ALWAYS in the background
A user can stop your service whenever the user wants to, above and beyond the OS terminating your process whenever the OS feels that it is appropriate.
But somehow this doesn't work either
Try to use ACTION_MY_PACKAGE_REPLACED instead and see if that helps.
I have two apps that I have complete control over. Both are signed with the same cert and both use the exact same intent filter. One sends the broadcast from a fragment, the other is suppose to receive it and do something. This however is not working:
Strings.FILTER_INIT_REGISTER = "com.app.FILTER_INIT_REGISTER"
Intent intent = new Intent(Strings.FILTER_INIT_REGISTER);
getActivity().sendBroadcast(intent);
I have registered the receiver in the Manifest app tag for the app containing the ReportingReceiver class:
<receiver
android:name=".receivers.ReportingReceiver"
android:exported="true"
>
<intent-filter>
<action android:name="com.app.FILTER_INIT_REGISTER" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</receiver>
Curious why the ReportingReceiver class is not getting the intent call?
If your application only has a service and receivers then this won't work in Android 3.1 and later. The reason is that the system will not send broadcast Intents to application that are in the STOPPED STATE. An application is in the STOPPED STATE when it is first installed. It is removed from the STOPPED STATE when the user manually starts the application for the first time. It is returned to the STOPPED STATE if the user forces the application to stop using the application manager tool.
Since your application has no Activities, there is no way for the user to "start" it. Therefore it will never come out of the stopped state.
See http://developer.android.com/about/versions/android-3.1.html#launchcontrols
As Android Addict says in his comment to David Wasser's answer ... there is a way around this behaviour.
Just add the following flag to the calling Intent. This will ensure that you also reach broadcast receivers from "stopped" applications.
http://developer.android.com/reference/android/content/Intent.html#FLAG_INCLUDE_STOPPED_PACKAGES
You can read more about this Android 3.1 change here
http://developer.android.com/about/versions/android-3.1.html#launchcontrols
and here
http://code.google.com/p/android/issues/detail?id=18225
I have implemented an app that is basically a custom app store for updating and launching a family of related apps. It also needs to update itself, which works, but the app is killed without warning during the install process. I want to automatically restart the app in this case so that the user can continue to use it immediately after an update.
So I made a separate application including only a single Broadcast Receiver that listens for package events for the first app's package name and starts a new activity. That receiver is never called:
<application android:icon="#drawable/ic_launcher"
android:label="#string/app_name">
<receiver android:name=".AppUpdateReceiver">
<intent-filter>
<action android:name="android.intent.action.PACKAGE_REPLACED"/>
<action android:name="android.intent.action.PACKAGE_ADDED"/>
<action android:name="android.intent.action.PACKAGE_INSTALL"/>
<data android:scheme="package" />
</intent-filter>
</receiver>
In searching for similar implementations I have seen directly contradictory information on whether an application with only a receiver will ever execute, and whether a receiver will be called if its app is not already running. I've even come across example code of an application containing only a receiver, with a manifest very similar to my own. So what do I need in this application to ensure that the receiver is called whenever another package is installed?
If there is a better solution, I'd be happy to hear it.
Depending on the version of Android, you might need to start an application component in order for the BroadcastReceiver to be registered. By this I mean there will need to be a launcher Activity which must be started manually by the user.
From Honeycomb (I think) onwards it isn't possible to have application components 'active' unless the app has been manually started in some way. The reasoning behind this is the potential for insecure code executing without the end-users' knowledge.
I suspect this is what you're experiencing. To test it, add a simple "Hello World" Activity to the app that has the BroadcastReceiver in it. Launch the Activity and then check to see if the BroadcastReceiver then gets called after your other package is updated.
OK, so not entirely sure this is possible...
But trying to write an application so that I can run some code before any of the following activities are performed.
1) APK is downloaded from web and market launches installer
2) Install button is pressed on android market
Is it possible to intercept and prompt on these events, or has Google locked that stuff down quite tightly?
This isn't an answer per se, but I can't find any commenting tool here. Sorry.
I'm having this issue as well. I would like to be able to detect new application installs. I know it is possible - for example, the app Apps to SD posts a notification when you install a new app that when clicked opens a dialog to move that new app to the sd card.
So far, all I've been able to figure is like this:
manifest.xml:
...
<receiver android:name=".IntentReceiver">
<intent-filter>
<action android:name="android.intent.action.PACKAGE_ADDED" />
<action android:name="android.intent.action.PACKAGE_REMOVED" />
<data android:scheme="package" />
</intent-filter>
</receiver>
...
IntentReciever.java:
public class IntentReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
context.startService(new Intent(context, YourService.class));
}
}
YourService is then created and calls onCreate() then onStartCommand(). However, I haven't been able to debug this or successfully display any notifications from the service class, so I'm not entirely sure this works. I have gotten this to work for other Receivers like android.intent.action.BOOT_COMPLETED.
Using a BroadcastReceiver you can filter the android.intent.action.PACKAGE_ADDED intent. However this will only be after the two actions you describe, not before. And it will not stop or interrupt the installation.
AFAIK there is no way to do anything before or to interrupt the Market. And then we're even talking about another app than the one that's being installed ofcourse.