Сбой формы согласия GDPR: WindowManager BadTokenException
Я показываю форму согласия Google на GDPR и замечаю многие из этих отчетов:
Fatal Exception: android.view.WindowManager$BadTokenException
Unable to add window -- token android.os.BinderProxy@38734f2 is not valid; is your activity running?
com.my.project.MainActivity$4.onConsentFormLoaded
В качестве контекста я использую MainActivity.this
:
private void displayConsentForm() {
consentForm = new ConsentForm.Builder(MainActivity.this, GeneralUtils.getAppsPrivacyPolicy())
.withListener(new ConsentFormListener() {
@Override
public void onConsentFormLoaded() {
consentForm.show(); // crashing here for some users
}
@Override
public void onConsentFormOpened() { }
@Override
public void onConsentFormClosed(
ConsentStatus consentStatus, Boolean userPrefersAdFree) {
if(userPrefersAdFree) {
ConsentInformation.getInstance(MainActivity.this)
.setConsentStatus(NON_PERSONALIZED);
} else {
ConsentInformation.getInstance(MainActivity.this)
.setConsentStatus(consentStatus);
}
initAds();
}
@Override
public void onConsentFormError(String errorDescription) {
Log.e("Error",errorDescription);
}
})
.withPersonalizedAdsOption()
.withNonPersonalizedAdsOption()
.withAdFreeOption()
.build();
consentForm.load();
}
Вот дополнительный отчет о сбое Firebase:
Почему это происходит и как это предотвратить? Я не уверен, какую дополнительную проверку поставить перед consentForm.show()
и я не могу воспроизвести проблему. Может быть, этого будет достаточно, если я поставлю эту проверку перед показом формы:
if(!MainActivity.this.isFinishing() && !MainActivity.this.isDestroyed())
?
1 ответ
Самый простой способ обойти это - просто поставить блок try-catch вокруг consentForm.show()
и поймать исключение BadTokenException.
Это не совсем чисто, но, скорее всего, это происходит, когда заканчивается действие (возможно, пользователь закрывает приложение из "Недавних" прямо во время загрузки диалога).
Если бы это был мой проект, я бы сначала попытался добавить это, если у вас есть заявление (хотя вам не нужно MainActivity.this.
часть; ты можешь просто позвонить isFinishing()
а также isDestroyed()
напрямую). Поскольку вы ссылаетесь на Контекст деятельности, об этом следует позаботиться.
Однако, если он все еще падает, вы должны сначала изучить его воспроизведение. Попробуйте добраться до displayConsentForm()
вызывается, а затем закрывает приложение из последних. Поиграйте со временем, и вы, вероятно, воспроизведете аварию. Если нет, то просто добавьте try-catch. Активность не отображается, так как она выдает эту ошибку, поэтому пользователь фактически не находится в приложении.