Skip to content

firebase-auth calls ContextCompat.registerReceiver(Context, BroadcastReceiver, IntentFilter, int) but declares no androidx.core dependency #8505

Description

@nbransby

[REQUIRED] Step 2: Describe your environment

  • Android Studio version: n/a — Gradle build, AGP 8.12.0 / Gradle 8.14.3
  • Firebase Component: Auth
  • Component version: 23.2.1 (via firebase-bom 33.15.0); also verified against 24.2.0

[REQUIRED] Step 3: Describe the problem

firebase-auth calls ContextCompat.registerReceiver(Context, BroadcastReceiver, IntentFilter, int) when it sets up the SMS retriever for phone auth. That overload was added in androidx.core 1.9.0.

firebase-auth does not declare a dependency on androidx.core at any version. Its POM declares:

androidx.browser:browser:1.4.0
androidx.collection:collection:1.0.0
androidx.credentials:credentials:1.2.0-rc01
androidx.credentials:credentials-play-services-auth:1.2.0-rc01
androidx.fragment:fragment:1.1.0
androidx.localbroadcastmanager:localbroadcastmanager:1.0.0

androidx.fragment:1.1.0 is far too old to pull in a suitable androidx.core, so nothing in the declared graph guarantees the method exists. The highest androidx.core reachable from firebase-auth alone is 1.2.0, via play-services-base:18.0.1 / play-services-basement:18.4.0.

The result is that any consumer whose dependency graph does not otherwise contain androidx.core >= 1.9.0 gets a hard crash on the first phone auth call.

This is masked for most apps, because appcompat, activity, Compose and core-ktx all bring androidx.core 1.13–1.19 and conflict resolution picks those. It is not masked for consumers with a lean graph — in our case an instrumented-test APK for a library that wraps the Firebase SDKs, which depends on firebase-auth and androidx.test but not on any UI artifact.

Steps to reproduce:

  1. Create an Android module that depends on com.google.firebase:firebase-auth without appcompat, activity, Compose, or core-ktx.
  2. Confirm the resolved version is old — ./gradlew :module:dependencyInsight --configuration debugRuntimeClasspath --dependency androidx.core:core reports androidx.core:core:1.2.0, selection reason By conflict resolution: between versions 1.2.0, 1.1.0 and 1.0.0.
  3. Call PhoneAuthProvider.verifyPhoneNumber(...).
  4. It crashes as soon as the SMS retriever is registered.

Verified that androidx.core:core:1.9.0 contains the overload and 1.2.0 does not, by decompiling both:

$ javap -classpath <core-1.9.0> androidx.core.content.ContextCompat | grep registerReceiver
  public static android.content.Intent registerReceiver(android.content.Context, android.content.BroadcastReceiver, android.content.IntentFilter, int);
  public static android.content.Intent registerReceiver(android.content.Context, android.content.BroadcastReceiver, android.content.IntentFilter, java.lang.String, android.os.Handler, int);

$ javap -classpath <core-1.2.0> androidx.core.content.ContextCompat | grep registerReceiver
  (no such overload)

Relevant Code:

java.lang.NoSuchMethodError: No static method registerReceiver(Landroid/content/Context;Landroid/content/BroadcastReceiver;Landroid/content/IntentFilter;I)Landroid/content/Intent;
in class Landroidx/core/content/ContextCompat; or its super classes
(declaration of 'androidx.core.content.ContextCompat' appears in /data/app/~~-GawQ-mLA-xVH6tujzcrdw==/dev.gitlive.firebase.auth.test-YTNifziXwZqfmlaaSKp6KQ==/base.apk)
	at com.google.android.gms.internal.firebase-auth-api.zzafu.zza(com.google.firebase:firebase-auth@@23.2.1:115)
	at com.google.android.gms.internal.firebase-auth-api.zzaef.zza(com.google.firebase:firebase-auth@@23.2.1:148)
	at com.google.android.gms.internal.firebase-auth-api.zzaee.zza(com.google.firebase:firebase-auth@@23.2.1:9)
	at com.google.android.gms.internal.firebase-auth-api.zzafj.run(com.google.firebase:firebase-auth@@23.2.1:3)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1137)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:637)
	at com.google.firebase.concurrent.CustomThreadFactory.lambda$newThread$0$com-google-firebase-concurrent-CustomThreadFactory(CustomThreadFactory.java:47)
	at com.google.firebase.concurrent.CustomThreadFactory$$ExternalSyntheticLambda0.run(D8$$SyntheticClass:0)
	at java.lang.Thread.run(Thread.java:1012)

Suggested fix

Have firebase-auth declare the minimum androidx.core its code actually requires, either as a dependency or as a constraint:

api("androidx.core:core:1.9.0")

1.9.0 is the exact floor for the overload in use. Declaring it would let Gradle's conflict resolution do the right thing for lean consumers, while apps that already bring a newer androidx.core are unaffected.

We have worked around it locally by pinning androidx.core on the affected test source set, so this is not blocking us — filing because the underdeclaration looks unintentional and still applies in 24.2.0.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions