urbanairship / android-library

Urban Airship Android SDK
Other
109 stars 123 forks source link

Crash for Message + In-App-Message on Android 12 with MaterialComponents theme #203

Closed ninovanhooff closed 2 years ago

ninovanhooff commented 2 years ago

Preliminary Info

What Airship dependencies are you using?

core, fcm, automation @ 15.1.0 androidx.appcompat:appcompat:1.3.1 androidx.core:core-splashscreen:1.0.0-alpha01

What are the versions of any relevant development tools you are using?

Android Studio Arctic Fox | 2020.3.1 Patch 3 Build #AI-203.7717.56.2031.7784292, built on October 1, 2021 Runtime version: 11.0.10+0-b96-7281165 x86_64 VM: OpenJDK 64-Bit Server VM by JetBrains s.r.o. macOS 11.6 GC: G1 Young Generation, G1 Old Generation Memory: 4096M Cores: 16 Registry: external.system.auto.import.disabled=true, debugger.valueTooltipAutoShowOnSelection=true, ide.balloon.shadow.size=0 Non-Bundled Plugins: com.dubreuia, com.intellij.marketplace, com.jetbrains.ChooseRuntime, hunspell, mobi.hsz.idea.gitignore, Dart, org.jetbrains.kotlin, zielu.gittoolbox, io.flutter, com.developerphil.adbidea

Report

What unexpected behavior are you seeing?

Crash on Android 12 (100%), reported mostly on Samsung (99%, this could be significant, but realise that about 75% of our userbase has samsung) On Android 12, A crash occurs after a Message + In-app banner was sent. Have not reproduced it myself yet (Google pixel 4a Android 12 did not crash for me). The stacktrace seems to indicate that the Banner part of this reproduction scenario is significant

What is the expected behavior?

No crash

What are the steps to reproduce the unexpected behavior?

Send a pushnotification + in-app-message image

Logging hints at an activity with a non-AppCompat theme Our MainActivity theme definition:

<style name="AppTheme" parent="Theme.MaterialComponents.Light.NoActionBar">

Do you have logging for the issue?

Caused by java.lang.IllegalStateException: You need to use a Theme.AppCompat theme (or descendant) with this activity.
       at androidx.appcompat.app.AppCompatDelegateImpl.createSubDecor(AppCompatDelegateImpl.java:395)
       at androidx.appcompat.app.AppCompatDelegateImpl.ensureSubDecor(AppCompatDelegateImpl.java:4)
       at androidx.appcompat.app.AppCompatDelegateImpl.findViewById(AppCompatDelegateImpl.java)
       at androidx.appcompat.app.AppCompatActivity.findViewById(AppCompatActivity.java:4)
       at com.urbanairship.iam.banner.BannerAdapter.getContainerView(BannerAdapter.java:18)
       at com.urbanairship.iam.banner.BannerAdapter$1.apply(BannerAdapter.java:2)
       at com.urbanairship.iam.banner.BannerAdapter$1.apply(BannerAdapter.java:2)
       at com.urbanairship.app.FilteredActivityListener.onActivityCreated(FilteredActivityListener.java:2)
       at com.urbanairship.app.ForwardingActivityListener.onActivityCreated(ForwardingActivityListener.java:23)
       at com.urbanairship.app.FilteredActivityListener.onActivityCreated(FilteredActivityListener.java:10)
       at com.urbanairship.app.ForwardingActivityListener.onActivityCreated(ForwardingActivityListener.java:23)
       at android.app.Application.dispatchActivityCreated(Application.java:372)
       at android.app.Activity.dispatchActivityCreated(Activity.java:1374)
       at android.app.Activity.onCreate(Activity.java:1651)
       at androidx.core.app.ComponentActivity.onCreate(ComponentActivity.java)
       at androidx.activity.ComponentActivity.onCreate(ComponentActivity.java:10)
       at androidx.fragment.app.FragmentActivity.onCreate(FragmentActivity.java)
       at nl.hema.mobiel.ui.MainActivity.onCreate(MainActivity.java:8)
rlepinski commented 2 years ago

Our SDK does not really care what theme you are using, you are using an app compat activity that needs that theme and it looks like it should be working. Our SDK is just calling findViewById that is triggering the crash because it calls through to the app compat delegate's ensureSubDecor() method.

Are you using any context wrappers or anything of that sort? What are the crash statistics? Number of users, number of crashers per user, device models, etc.. ?

ninovanhooff commented 2 years ago

Answers:

What does impact the theme is that I'm using the Android 12 Splash theme, androidx.core:core-splashscreen:1.0.0-alpha01

This implementation guide mentions the crash I am eperiencing: https://proandroiddev.com/implementing-core-splashscreen-api-e62f0e690f74

I'm implementing the onCreate method as suggested:

override fun onCreate(savedInstanceState: Bundle?) {
        FeatureModuleResourcesValidator.ensureValidAccountMenuResources(this)
        inject(this)

        showReAuthScreenIfNeeded()
        // Enable support for Splash Screen API for
        // proper Android 12+ support
        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.S) installSplashScreen()

        binding = ActivityMainBinding.inflate(layoutInflater)
        setContentView(binding.root)
        [..]
}

So it seems that for andsroid 12, a non-AppCompat theme is used until installSplashScreen is called. We can see in the stack trace is that you are handling the theme during super.onCreate(), which is before installSplashScreen() is called in my code.

You should probably be doing your work after onCreate, not during. I do admit that the system calling dispatchActivityCreated during onCreate is misleading... but still

rlepinski commented 2 years ago

We already have a change internally that will most likely address this we are just trying to reproduce to ensure the change will fix it. Thank you for the info!

ninovanhooff commented 2 years ago

That's good news! As a workaround, would it be enough to not use the in-app-message feature, or should I target users with Android < 12 for any message? @rlepinski

rlepinski commented 2 years ago

Its in-app messages that are sent with a push and banner in-app automations. The other ones should not have this issue.

rlepinski commented 2 years ago

@ninovanhooff Fixed in 16.3.2 - https://github.com/urbanairship/android-library/commit/2a7eb995fa949b67135c37155abc9b8cee88b177

It removes the check on all lifecycle methods and now only does them on the ones we care about. Also added a try/catch to avoid crashing if findViewById throws an exception.