Skip to content

Instantly share code, notes, and snippets.

@arshad115
Created June 10, 2015 09:50
Show Gist options
  • Save arshad115/158c7d079337e0120727 to your computer and use it in GitHub Desktop.
Save arshad115/158c7d079337e0120727 to your computer and use it in GitHub Desktop.
Android L - fixing Service Intent must be explicit, with multiple results/packages
/***
* Android L (lollipop, API 21) introduced a new problem when trying to invoke implicit intent,
* "java.lang.IllegalArgumentException: Service Intent must be explicit"
*
* The function given here works for a single application package with the same intent filter.
* https://gist.github.com/SeanZoR/068f19545e51e4627749
*
* I had a scenario in which there was a free version and a paid version of the same app installed, this function returns null in that case.
* So I decided to fix it and here is the working solution which matches the application package and then returns the correct intent.
*
* @param context
* @param implicitIntent - The original implicit intent
* @return Explicit Intent created from the implicit original intent
*/
public static Intent createExplicitFromImplicitIntent(Context context, Intent implicitIntent) {
// Retrieve all services that can match the given intent
PackageManager pm = context.getPackageManager();
List<ResolveInfo> resolveInfo = pm.queryIntentServices(implicitIntent, 0);
if (resolveInfo == null) {
return null;
}
if ( resolveInfo.size() != 1) {
//more than one found
for (ResolveInfo item : resolveInfo) {
String packageName = item.serviceInfo.packageName;
String className = item.serviceInfo.name;
if (packageName.equals(context.getApplicationContext().getPackageName())) {
ComponentName component = new ComponentName(packageName, className);
// Create a new intent. Use the old one for extras and such reuse
Intent explicitIntent = new Intent(implicitIntent);
// Set the component to be explicit
explicitIntent.setComponent(component);
return explicitIntent;
}
}
}
// Get component info and create ComponentName
ResolveInfo serviceInfo = resolveInfo.get(0);
String packageName = serviceInfo.serviceInfo.packageName;
String className = serviceInfo.serviceInfo.name;
ComponentName component = new ComponentName(packageName, className);
// Create a new intent. Use the old one for extras and such reuse
Intent explicitIntent = new Intent(implicitIntent);
// Set the component to be explicit
explicitIntent.setComponent(component);
return explicitIntent;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment