To quote Roman Elizarov, the Kotlin libraries team lead who works on Coroutines, on this topic:
There is hardly ever reason to use GlobalScope in an application that
is based on Kotlin coroutines.
If, as you say, you want the "job to complete no matter what" keep in mind that everything has a scope. Whether it's a fragment, activity or application, everything comes to an end, eventually. So the better solution is to use structured concurrency and launch your database job from the scope associated with its work.
It sounds like that's the activity in your case. However, if your UI cannot prevent the user from leaving the activity before work is done, and it is critical that the job always completes, then you probably need more than just coroutines. Consider scheduling your long-running work with WorkManager, instead.
Either way, try to avoid GlobalScope since it is not the right solution.
WorkManagerfor the jobs that are not directly connected with your activity/fragment.