Giter VIP home page Giter VIP logo

ki-labs / gps-permission-checks-livedata Goto Github PK

View Code? Open in Web Editor NEW
40.0 5.0 12.0 219 KB

Sample project to demonstrate how GPS and Runtime Location Permission checks can be done on UI and Background Service using LiveData

Home Page: https://medium.com/ki-labs-engineering/monitoring-gps-and-location-permission-checks-using-livedata-part-1-278907344b77

License: MIT License

Kotlin 100.00%
android livedata service location-services

gps-permission-checks-livedata's Introduction

Monitoring GPS and Location Permission checks using LiveData

Background:

In Android apps, users need to allow specific permissions so that app can use that particular resource. All location tracking apps need “GPS to be enabled” and want users to allow “Location Permission” so that app can start receiving location coordinates. For our usecase, it was critically needed to ensure both of these requirements are fulfilled. If not, user should be alerted and informed on UI level during or after Onboarding and also when Location Tracking is started/running in background.

This is a sample app to demonstrate the usecase.

Motivation to publish my solution:

There are already native android ways to implement both of these checks but we tried to do it using LiveData which is a newly introduced API from Android to handle asynchronous operations using Subscribe/Publish mechanism. We faced our fair share of challenges and there was limited help available as not many have tried for this usecase. Solutions which are challenging are the best candidate to be shared with public because it means many others out there will face the same problems and it could save their time. At the end of the day, it’s basically giving back to the community.

What is this project about:

  1. UI (app is active): Checking for both elements, displaying state and showing dialogs for user to react accordingly

    Medium Article: Read Here

  2. Background (app is not active): Check for both elements as part of Service whenever it is started by System and inform user via notification so that user can enable them for us. Otherwise, location tracking won’t succeed at all.

    Medium Article: Read Here

How sample app looks like or behaves


                                     



                                     

gps-permission-checks-livedata's People

Contributors

wahibhaq avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar

gps-permission-checks-livedata's Issues

Does permission listener LiveData actually work?

I consider myself a beginner regarding Kotlin, so hopefully it is just me that is doing something wrong, but I have been struggling for several days to try to get this LiveData to actually work, but without success.

In the end, I built this app and just added some extra logging in the listener class to see when it actually reacts to permission changes:

class PermissionStatusListener(private val context: Context,
                               private val permissionToListen: String) : LiveData<PermissionStatus>() {

    private val TAG = "* Permission listener "
    override fun onActive() = handlePermissionCheck()

    private fun handlePermissionCheck() {
        val isPermissionGranted = ActivityCompat.checkSelfPermission(context,
                permissionToListen) == PackageManager.PERMISSION_GRANTED

        Log.d(TAG, " permission status ${isPermissionGranted}")
        if (isPermissionGranted)
            postValue(PermissionStatus.Granted())
        else
            postValue(PermissionStatus.Denied())
    }
}

sealed class PermissionStatus {
    data class Granted(
            val message: Int = R.string.permission_status_granted
    ) : PermissionStatus()
    data class Denied(
            val message: Int = R.string.permission_status_denied
    ) : PermissionStatus()
    data class Blocked(
            val message: Int = R.string.permission_status_blocked
    ) : PermissionStatus()
}

When the app starts, it shows the correct status of the permission:

2019-12-21 21:55:04.668 11799-11799/com.wahibhaq.locationservicelivedata D/* Permission listener:  permission status false

But when the permission is granted, there is no update of the LiveData, only the normal permission handling callbacks:

2019-12-21 22:20:47.899 11799-11799/com.wahibhaq.locationservicelivedata D/Permissions: No rationale.
2019-12-21 22:20:47.939 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: setView = DecorView@b80bcc5[PermissionsActivity] TM=true MM=false
2019-12-21 22:20:47.956 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: dispatchAttachedToWindow
2019-12-21 22:20:47.969 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: Relayout returned: old=[0,63][1080,2094] new=[540,1078][540,1078] result=0x7 surface={valid=true 532950945792} changed=true
2019-12-21 22:20:47.976 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: MSG_RESIZED: frame=Rect(540, 1078 - 540, 1078) ci=Rect(0, 0 - 0, 0) vi=Rect(0, 0 - 0, 0) or=1
2019-12-21 22:20:51.313 11799-11799/com.wahibhaq.locationservicelivedata D/Permissions: Just allowed.
2019-12-21 22:20:51.363 11799-11799/com.wahibhaq.locationservicelivedata I/MainActivity$permissionHandler: Activity: 2131427403
2019-12-21 22:20:51.381 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: MSG_WINDOW_FOCUS_CHANGED 0 1
2019-12-21 22:20:51.381 11799-11799/com.wahibhaq.locationservicelivedata D/InputMethodManager: prepareNavigationBarInfo() DecorView@b80bcc5[PermissionsActivity]
2019-12-21 22:20:51.413 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: MSG_WINDOW_FOCUS_CHANGED 0 0
2019-12-21 22:20:51.428 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: setWindowStopped(true) old=false
2019-12-21 22:20:51.433 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: dispatchDetachedFromWindow
2019-12-21 22:20:51.434 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: Surface release. android.view.ViewRootImpl.doDie:7979 android.view.ViewRootImpl.die:7947 android.view.WindowManagerGlobal.removeViewLocked:497 android.view.WindowManagerGlobal.removeView:435 android.view.WindowManagerImpl.removeViewImmediate:124 android.app.ActivityThread.handleDestroyActivity:4753 android.app.servertransaction.DestroyActivityItem.execute:39 android.app.servertransaction.TransactionExecutor.executeLifecycleState:145 
2019-12-21 22:20:51.644 11799-11799/com.wahibhaq.locationservicelivedata D/ViewRootImpl@ac9ab27[PermissionsActivity]: Surface release. android.view.ViewRootImpl$ViewRootHandler.handleMessage:4825 android.os.Handler.dispatchMessage:106 

To me it seems that the LiveData is only updated when the observing activity is resumed, and not directly when the permission is granted.

Am I missing something obvious, or does the Android framework not allow this listener to see the changed permission and update the LiveData immediately?

Update

Hello!

The application does not work pointing to the api 29 and changing the libraries to androidx. Could you update the code please?

Greetings,
Patrick

Introduce everything with Dagger2

  • separate permissions 3rd party lib and keep livedata for only service. Keep mainactivity observe simple on just GPS for now.
  • show both dialogs on app foreground. Keep the link click for now.
  • TBD PermissionStatusListener to be separated to that can be injected directly...test if it will even work
    • Try keeping Permission lib for just UI so makes sense to keep livedata only for service
  • MainViewModel shouldn't inject Context
  • Also decide for once how UI should react

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.