[question]: I am not able to ask for notification permission on app start
How can we help?
Description:
I have an Android Jetpack Compose App with indeed has a login page -> because of that I need to wait for a user to login and than retrieve the credentials together with the appID
Therefore here is my code
class MainActivity : ComponentActivity() {
private val Context.dataStore by preferencesDataStore(name = "settings")
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val environmentManager = EnvironmentManager()
val dataStorageRepository = DataStorageRepository(dataStore)
val context = applicationContext
// Should be removed when releasing
OneSignal.Debug.logLevel = LogLevel.VERBOSE
OneSignal.initWithContext(context)
CoroutineScope(Dispatchers.IO).launch {
OneSignal.Notifications.requestPermission(true)
}
setContent {
....
}
}
}
The problem is that as soon as I start the app I get in the logcat those errors
FATAL EXCEPTION: DefaultDispatcher-worker-3
Process: com.ts.org, PID: 32008
java.lang.Exception: Must call 'initWithContext' before use
at com.onesignal.internal.OneSignalImp.getNotifications(OneSignalImp.kt:99)
at com.onesignal.OneSignal.getNotifications(OneSignal.kt:62)
at com.ts.org.app.host.MainActivity$onCreate$1.invokeSuspend(MainActivity.kt:53)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:108)
at kotlinx.coroutines.internal.LimitedDispatcher$Worker.run(LimitedDispatcher.kt:115)
at kotlinx.coroutines.scheduling.TaskImpl.run(Tasks.kt:103)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:584)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.executeTask(CoroutineScheduler.kt:793)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.runWorker(CoroutineScheduler.kt:697)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:684)
Suppressed: kotlinx.coroutines.internal.DiagnosticCoroutineContextException: [StandaloneCoroutine{Cancelling}@bb53738, Dispatchers.IO]
```
Furthermore, when a user is logged in - in another class I do this
```kt
fun subscribe(creds: ...., appID: String) {
OneSignal.Debug.logLevel = LogLevel.VERBOSE
OneSignal.initWithContext(context, appID)
CoroutineScope(Dispatchers.IO).launch {
val accepted = OneSignal.Notifications.requestPermission(true)
if (accepted) {
Log.i(TAG, "User accepted notifications")
OneSignal.login(creds.userID)
}
}
}
In the other class I never get the popup dialog for accepting the permissions for push notifications.
Version: 5.1.18
Question: What is wrong how can I proceed?
Code of Conduct
- [X] I agree to follow this project's Code of Conduct
@Kalo2412 to avoid the java.lang.Exception: Must call 'initWithContext' before use error and to prevent other initialization issues you should call OneSignal.initWithContext in your Application.onCreate instead of your Activity.onCreate.
Note that OneSignal.Notifications.requestPermission() only prompts on Android 13 and newer devices, as notifications are enabled by default on older devices. It's possible for all versions of Android to turn off notifications so calling OneSignal.Notifications.requestPermission(true) will take them to the settings if they turned it off.
I have now moved the logic in the MyApplication
** class MyApplication : Application() { override fun onCreate() { super.onCreate()
// Initialize OneSignal
OneSignal.Debug.logLevel = LogLevel.VERBOSE
OneSignal.initWithContext(this)
CoroutineScope(Dispatchers.IO).launch {
OneSignal.Notifications.requestPermission(true)
}
}
} **
I still get this error: FATAL EXCEPTION: DefaultDispatcher-worker-1 Process: com.ts.org, PID: 17941 java.lang.Exception: Must call 'initWithContext' before use at com.onesignal.internal.OneSignalImp.getNotifications(OneSignalImp.kt:99) at com.onesignal.OneSignal.getNotifications(OneSignal.kt:62) at com.ts.org.app.host.MyApplication$onCreate$1.invokeSuspend(MainApplication.kt:21) at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33) at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:108) at kotlinx.coroutines.internal.LimitedDispatcher$Worker.run(LimitedDispatcher.kt:115) at kotlinx.coroutines.scheduling.TaskImpl.run(Tasks.kt:103) at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:584) at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.executeTask(CoroutineScheduler.kt:793) at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.runWorker(CoroutineScheduler.kt:697) at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:684) Suppressed: kotlinx.coroutines.internal.DiagnosticCoroutineContextException: [StandaloneCoroutine{Cancelling}@c16b1d9, Dispatchers.IO]
Device is on Android 14
@jkasten2 What is the difference between this two methods
@kotlin.jvm.JvmStatic public final fun initWithContext(context: android.content.Context): kotlin.Boolean { /* compiled code */ }
@kotlin.jvm.JvmStatic public final fun initWithContext(context: android.content.Context, appId: kotlin.String): kotlin.Unit { /* compiled code */ }
Why should some one call initWithContext without to pass the appID if so can we pass the appid later in the application in some service class
Furthermore I do not find any docs page for the android sdk for the link provided in the README I receive page not found https://documentation.onesignal.com/docs/android-native-sdk
Any progress here?
Hello @Kalo2412, it looks like you are calling initWithContext with an empty app ID. The error "must call initWithContext before use" is expected when you try to access OneSignal without supplying a valid app ID.