Karumi / Dexter

Android library that simplifies the process of requesting permissions at runtime.
http://karumi.com
Apache License 2.0
5.23k stars 671 forks source link

NullPointerException on Activity.finish #221

Closed tritueviet closed 4 years ago

tritueviet commented 5 years ago

Caused by java.lang.NullPointerException Attempt to invoke virtual method 'void android.app.Activity.finish()' on a null object reference com.karumi.dexter.DexterInstance.onPermissionsChecked (Unknown Source:27) com.karumi.dexter.DexterInstance.updatePermissionsAsDenied (Unknown Source:36) com.karumi.dexter.DexterInstance.onPermissionRequestDenied (Unknown Source) com.karumi.dexter.Dexter.onPermissionsRequested (Unknown Source:11) com.karumi.dexter.DexterActivity.onRequestPermissionsResult (Unknown Source:46) android.app.Activity.dispatchRequestPermissionsResult (Activity.java:7825) com.android.internal.os.ZygoteInit.main (ZygoteInit.java:836)

nick252 commented 5 years ago

Same crash at com.karumi.dexter.DexterInstance.onPermissionsChecked(Unknown Source) at com.karumi.dexter.DexterInstance.updatePermissionsAsDenied(Unknown Source) at com.karumi.dexter.DexterInstance.onPermissionRequestDenied(Unknown Source) at com.karumi.dexter.Dexter.onPermissionsRequested(Unknown Source) at com.karumi.dexter.DexterActivity.onRequestPermissionsResult(Unknown Source) at android.app.Activity.dispatchRequestPermissionsResult(Activity.java:6564)

HTC, Android 6

mhopmann commented 4 years ago

I had the same behavior when calling Dexter check from OnResume (from a Fragment, but it is probably the same from an Activity). When I call it from onViewCreated, it's ok.

pedrovgs commented 4 years ago

@mhopmann can you please tell us the version of the library you are using?

mhopmann commented 4 years ago

I'm using 6.0

alexeyvasilyev commented 4 years ago

Same crash on 6.0.

2019-10-14 17:46:20.475 19473-19473/? E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.mypackage, PID: 19473
    java.lang.RuntimeException: Failure delivering result ResultInfo{who=@android:requestPermissions:, request=42, result=-1, data=Intent { act=android.content.pm.action.REQUEST_PERMISSIONS (has extras) }} to activity {com.mypackage/com.karumi.dexter.DexterActivity}: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.app.Activity.finish()' on a null object reference
        at android.app.ActivityThread.deliverResults(ActivityThread.java:4845)
        at android.app.ActivityThread.handleSendResult(ActivityThread.java:4886)
        at android.app.servertransaction.ActivityResultItem.execute(ActivityResultItem.java:51)
        at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
        at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2016)
        at android.os.Handler.dispatchMessage(Handler.java:107)
        at android.os.Looper.loop(Looper.java:214)
        at android.app.ActivityThread.main(ActivityThread.java:7356)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)
     Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.app.Activity.finish()' on a null object reference
        at com.karumi.dexter.DexterInstance.onPermissionsChecked(Unknown Source:27)
        at com.karumi.dexter.DexterInstance.updatePermissionsAsGranted(Unknown Source:26)
        at com.karumi.dexter.DexterInstance.onPermissionRequestGranted(Unknown Source:0)
        at com.karumi.dexter.Dexter.onPermissionsRequested(Unknown Source:4)
        at com.karumi.dexter.DexterActivity.onRequestPermissionsResult(Unknown Source:51)
        at android.app.Activity.dispatchRequestPermissionsResult(Activity.java:8264)
        at android.app.Activity.dispatchActivityResult(Activity.java:8114)
        at android.app.ActivityThread.deliverResults(ActivityThread.java:4838)
        at android.app.ActivityThread.handleSendResult(ActivityThread.java:4886) 
        at android.app.servertransaction.ActivityResultItem.execute(ActivityResultItem.java:51) 
        at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135) 
        at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95) 
        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2016) 
        at android.os.Handler.dispatchMessage(Handler.java:107) 
        at android.os.Looper.loop(Looper.java:214) 
        at android.app.ActivityThread.main(ActivityThread.java:7356) 
        at java.lang.reflect.Method.invoke(Native Method) 
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492) 
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930) 
pedrovgs commented 4 years ago

Hey @alexeyvasilyev @mhopmann I'm trying to reproduce the error you mentioned but there is no way. If I request any permission from the onResume method what I get is a stack overflow because Dexter opens an invisible activity and once the dialog is closed the onResume method is executed and this ends up in an infinite loop. I'm wondering if you could upload somewhere a repository reproducing the error so we can find what's going on and fix the error. Thank you in advance 😃

alexeyvasilyev commented 4 years ago

This is my code. Issue started to happen when user denied permission request second time. Issue happens randomly in 30-50% cases. Easily reproducible on my Pixel XL2 running Android 10. Cannot reproduce the issue on Dexter sample app.

    private void makeSnapshot(int cameraId) {
        if (DEBUG)
            Log.v(TAG, "makeSnapshot(cameraId=" + cameraId + ")");

        Dexter
            .withActivity(this)
            .withPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE)
            .withListener(new PermissionListener() {
                @Override
                public void onPermissionGranted(PermissionGrantedResponse response) {
                    if (DEBUG)
                        Log.v(TAG, "onPermissionGranted()");
                    makeSnapshotImpl(cameraId);
                }

                @Override
                public void onPermissionDenied(PermissionDeniedResponse response) {
                    if (DEBUG)
                        Log.v(TAG, "onPermissionDenied() permanently=" + response.isPermanentlyDenied());
                    if (response.isPermanentlyDenied()) {
                        // Already shown permission request several times. Force to show app settings.
                        PermissionUtils.showOpenSettingsDialog(LiveViewActivity.this, R.string.perm_needed_storage);
                    }
                }

                @Override
                public void onPermissionRationaleShouldBeShown(PermissionRequest request, PermissionToken token) {
                    if (DEBUG)
                        Log.v(TAG, "onPermissionRationaleShouldBeShown()");
                    PermissionUtils.showRationaleDialog(LiveViewActivity.this, token, R.string.perm_needed_storage);
                }
            })
            .check();
    }

    public static void showRationaleDialog(final @NonNull Context context, final PermissionToken token, @StringRes int messageId) {
        new AlertDialog.Builder(context)
                .setMessage(messageId)
                .setPositiveButton(R.string.dialog_button_ok, (dialog, which) -> {
                    dialog.dismiss();
                    token.continuePermissionRequest();
                })
                .setOnDismissListener(dialog -> token.cancelPermissionRequest())
                .show();
    }

AndroidManifest.xml

        <activity
            android:name="LiveViewActivity"
            android:configChanges="keyboardHidden|orientation|screenSize|smallestScreenSize|screenLayout"
            android:launchMode="singleTop"
            android:exported="true"
            android:supportsPictureInPicture="true"
            android:resizeableActivity="true"
            tools:ignore="UnusedAttribute">
pedrovgs commented 4 years ago

@alexeyvasilyev with the code you provided we can't reproduce the bug because there are a lot of implementation details we don't have and could affect the implementation. Could you try to create an empty android project with the code reproducing the error? I'd love to be able to use your code but it's not possible right now because there is a lot of code missing. With this copy/pasted code the error could be related to other code not present in the snippet you pasted and we will never figure that out.

I'd also need to know if you invoke dexter from any onResume method.

pedrovgs commented 4 years ago

I'm going to send a PR with a tentative fix and once it's merged and release we will close the issue. We are not able to reproduce this error and our uses either so this will be a tentative fix. Please after releasing our new version update your app and let us know if you can still reproduce the error. Please, if the PR I've sent doesn't fix the error, please reopen this issue.

pedrovgs commented 4 years ago

I can confirm Dexter 6.0.1 fixed this issue. If someone else would check it out, that'd be awesome.