0

I am trying to use the nearby message api to get message from a eddystone beacon. I have followed the following documentation :

[https://developers.google.com/nearby/messages/overview?hl=en][1]

I am using the SHA1 from the default debug keystore. But I keep getting the following error message

 Nearby.Messages is not enabled for this app: packageName

Device : Nexus 6 (Android version 5.1.1)

Play services version : 8.1.15

rahul.ramanujam
  • 5,608
  • 7
  • 34
  • 56
  • Can you add some information about your device? What version of Google Play Services are you using? – Shailen Tuli Sep 22 '15 at 17:25
  • @ShailenTuli I have updated the post with device and play services version – rahul.ramanujam Sep 22 '15 at 17:28
  • It's hard to know without more context why you're getting the message. Can you build and run the NearbyDevices sample from https://github.com/googlesamples/android-nearby? Follow the instructions in the README for setting up the key in the manifest, etc. Modify the subscription method Nearby.Messages.subscribe(mGoogleApiClient, mMessageListener, PUB_SUB_STRATEGY) to Nearby.Messages.subscribe(mGoogleApiClient, messageListener, Strategy.BLE_ONLY). Let me know if that works. – Shailen Tuli Sep 22 '15 at 17:51
  • I have tried that sample earlier and tried debugging it , I get the same error . Even though I replaced the api key. Is it something to do with the keystore. I use the default debug keystore of android studio. – rahul.ramanujam Sep 22 '15 at 17:54
  • Find the apk generated, and use `keytool -list -printcert -jarfile {something}.apk | grep SHA1` to get the SHA. Then follow the instructions in the README. – Shailen Tuli Sep 22 '15 at 20:52
  • seems its the right SHA1 , I am getting the following error message in onResult() of ResultCallback : Nearby.Messages is not enabled for this app: packageName – rahul.ramanujam Sep 22 '15 at 23:35
  • I just cloned the sample and ran it successfully. Perhaps you can post your log output? – Shailen Tuli Sep 23 '15 at 18:05

2 Answers2

3

You're getting this error because you didn't explicitly ask user for permissions, which you must do in order to use the Nearby API. Here's one way to do this:

// GoogleApiClient connection callback. Initiate permission check here.
@Override
public void onConnected(Bundle connectionHint) {
    Nearby.Messages.getPermissionStatus(mGoogleApiClient).setResultCallback(
            new ErrorCheckingCallback("getPermissionStatus", new Runnable() {
                @Override
                public void run() {
                    publishAndSubscribe();
                }
            })
    );
}


// This is called in response to a button tap in the Nearby permission dialog.
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if (requestCode == REQUEST_RESOLVE_ERROR) {
        mResolvingError = false;
        if (resultCode == RESULT_OK) {
            // Permission granted or error resolved successfully then we proceed
            // with publish or subscribe..
            publishAndSubscribe();
        } else {
            // This may mean that user had rejected to grant nearby permission.
            showToast("Failed to resolve error with code " + resultCode);
        }
    }
}


/**
* A simple ResultCallback that displays a toast when errors occur.
* It also displays the Nearby opt-in dialog when necessary.
*/
private class ErrorCheckingCallback implements ResultCallback<Status> {
   private final String method;
   private final Runnable runOnSuccess;

   private ErrorCheckingCallback(String method) {
       this(method, null);
   }

   private ErrorCheckingCallback(String method, @Nullable Runnable runOnSuccess) {
       this.method = method;
       this.runOnSuccess = runOnSuccess;
   }

   @Override
   public void onResult(@NonNull Status status) {
       if (status.isSuccess()) {
           Log.i(TAG, method + " succeeded.");
           if (runOnSuccess != null) {
               runOnSuccess.run();
           }
       } else {
           // Currently, the only resolvable error is that the device is not opted
           // in to Nearby. Starting the resolution displays an opt-in dialog.
           if (status.hasResolution()) {
               if (!mResolvingError) {
                   try {
                       status.startResolutionForResult(MainActivity.this,
                               REQUEST_RESOLVE_ERROR);
                       mResolvingError = true;
                   } catch (IntentSender.SendIntentException e) {
                       showToastAndLog(Log.ERROR, method + " failed with exception: " + e);
                   }
               } else {
                   // This will be encountered on initial startup because we do
                   // both publish and subscribe together.  So having a toast while
                   // resolving dialog is in progress is confusing, so just log it.
                   Log.i(TAG, method + " failed with status: " + status
                           + " while resolving error.");
               }
           } else {
               showToastAndLog(Log.ERROR, method + " failed with : " + status
                       + " resolving error: " + mResolvingError);
           }
       }
   }
}

You can find a complete example in the documentation.

Also, remember about the guidelines:

  • Don’t surprise the user. Require the user to perform an explicit action (a button tap, going to a section in your app, a special switch, etc) to activate Nearby.

  • On both iOS and Android, calling Nearby for the first time will trigger a permission dialog. Waiting for an explicit user action before invoking Nearby will help the user contextualize the dialog and associate it with your app's proximity-based feature.

EyesClear
  • 28,077
  • 7
  • 32
  • 43
  • minor change, I think it should be "status.startResolutionForResult(MainActivity.this,ConnectionResult.RESOLUTION_REQUIRED);" I couldn't find "REQUEST_RESOLVE_ERROR" – tallen Dec 14 '15 at 15:05
  • @tallen It's just a so-called "request code", a random constant defined by you. It can be any integer. See http://developer.android.com/training/basics/intents/result.html for more info. – EyesClear Dec 16 '15 at 09:07
  • This is, more or less, correct. I found the way they did the callback class (with the runnable) to be needlessly convoluted, or maybe I'm just not that smart, I haven't decided. At run-time you wind up getting called back twice because you are implicitly asking for two permissions(this is the wrong word, opt-in maybe be better). The call to startResolutionForResult pops up an activity that asks for the permissions . These permissions (opt-ins) are not to be confused with the stuff you do in the manifest, it's a GooglePlayServicesAPI thing. – tallen Dec 17 '15 at 03:29
0

You have to explicitly ask user for permission to use Nearby. The Nearby API now provides shortcut for code provided by EyesClear. You just need to call enableAutoManage method on API client builder.

Look for details at: https://developers.google.com/nearby/messages/android/user-consent

Unfortunately this can work only for foreground subscriptions.

Community
  • 1
  • 1
Dietatko
  • 374
  • 1
  • 13