OnMessageReceived在WearableListenerService中未被调用

15

我正在使用Eclipse IDE开发Android Wear应用程序。我为Wear应用程序和移动应用程序使用相同的包名称,并根据Google文档手动打包可穿戴应用程序。一切正常,通过USB调试安装在Android Wear模拟器上。

我的问题是,当我使用以下代码向可穿戴设备发送消息时:

List<Node> nodeList=getNodes();
for(Node node : nodeList) {
    Log.v(" ", "telling " + node.getId() );

    PendingResult<MessageApi.SendMessageResult> result = Wearable.MessageApi.sendMessage(
        mGoogleApiClient,
        node.getId(),
        START_ACTIVITY_PATH,
        null
    );

    result.setResultCallback(new ResultCallback<MessageApi.SendMessageResult>() {
        @Override
        public void onResult(MessageApi.SendMessageResult sendMessageResult) {
            Log.v(" ", "Phone: " + sendMessageResult.getStatus().getStatusMessage());
        }
    });
}

在 WearableListenerService 中,当设备建立对等连接时,OnPeerConnected 方法会运行,但是 OnMessageReceived 从未被调用。这是我的 WearableListenerService 代码:

public class DataLayerListenerService extends WearableListenerService {

    private static final String TAG = "DataLayerSample";
    private static final String START_ACTIVITY_PATH = "/start/MainActivity";
    private static final String DATA_ITEM_RECEIVED_PATH = "/data-item-received";
    private static final String LOG_TAG = "log";
    @Override
    public void onPeerConnected(Node peer) {
        super.onPeerConnected(peer);

        String id = peer.getId();
        String name = peer.getDisplayName();

        Log.d(LOG_TAG, "Connected peer name & ID: " + name + "|" + id);
    }
    @Override
    public void onDataChanged(DataEventBuffer dataEvents) {
        System.out.println("Recevive message3");
    }

    @Override
    public void onMessageReceived(MessageEvent messageEvent) {
        System.out.println("service watch message1");
        if (messageEvent.getPath().equals(START_ACTIVITY_PATH)) {
            System.out.println("service watch message2");
            Intent startIntent = new Intent(this, MainActivity.class);
            startIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
            startActivity(startIntent);
        }
    }
}

同时在Logcat中,总是出现一个警告信息:

应用不匹配记录的应用密钥:AppKey [com.myapp,c3f31717fa35401056c20a2798907f1232efa75e]!= AppKey [com.myapp,f36e726eefc7e528db26a1c25f6fbf2f93dacd70]

如果两个应用程序的应用密钥应该相同,那么我如何为两个应用程序创建相同的应用密钥。

非常感谢任何帮助,谢谢。


com.myphoneappcom.wearableapp是什么? - Maciej Ciemięga
@Maciej。这是一个错误。现在我已经更正了我的帖子。第一个“com.myapp”语句是用于手机应用程序的包名,第二个语句是用于手表应用程序。无论如何,感谢您的回复。 - Lakhan Sharma
没问题。请看下面我的回答 :) - Maciej Ciemięga
3个回答

12

您收到的错误信息是:

应用程序与记录的应用程序密钥不匹配: AppKey[com.myapp,c3f31717fa35401056c20a2798907f1232efa75e] != AppKey[com.myapp,f36e726eefc7e528db26a1c25f6fbf2f93dacd70]

这表示您的应用程序使用了不同的密钥进行签名。
手机和可穿戴设备应用程序的包名称相同,这很好,但它们还需要共享相同的签名。这就是消息无法传递的原因 - 基于包名称和签名,可穿戴应用程序被识别为“同一应用程序的一部分”。

请确保您使用相同的密钥对两个应用程序进行签名。如果您正在测试自动安装功能,请确保从手表模拟器中卸载可穿戴应用程序的调试版本。


谢谢@Maciej。现在我可以看到问题了。可穿戴应用已经签名,但是Android应用程序是直接通过USB调试安装在手机上的。如果我没错的话,那么我该怎么做才能让它签名呢?或者根据您的意见,如果卸载调试版本可以解决这个问题,那么我该如何操作呢?请指导一下... - Lakhan Sharma
你说你的可穿戴应用已经签名了 - 你是如何签名的?你需要对手机应用进行签名,以便让它们彼此通信。仅仅卸载是无法解决问题的:) - 你需要用签名版本替换它(这意味着:卸载未签名版本 + 安装新的签名版本)。请注意,在测试和开发过程中,您可以使用两个未签名的应用程序。只有在进行一些最终测试(在发布到商店之前)时,您才可以在签名应用上测试最终结果。另外,请告诉我更多关于您的安装的详细信息,为什么一个应用已经签名而另一个没有? - Maciej Ciemięga
我使用签名密钥库证书将可穿戴应用程序打包到移动应用程序中。现在,我正在使用USB调试在我的手机上进行测试。当我使用USB进行测试时,没有选项可以对我的手机应用程序进行签名,即我没有创建其apk文件并直接安装在手机上。因此,我认为我的手机应用程序是未签名的,这对我来说是一个令人困惑的情况。 - Lakhan Sharma
1
如果您想测试已签名的手机apk,您需要打包手机apk并使用您的密钥库对其进行签名。在此步骤之后,您将需要使用adb命令安装此apk:adb -d install path/to/your/phone_signed.apk-d表示此命令将被定向到通过adb连接的任何设备(而不是模拟器实例-如果您在PC上启动了Android Wear模拟器)。如果您不熟悉adb,可以采用“简单方法”,只需从计算机复制已签名的apk到手机存储器中,并使用手机上的某个文件浏览器进行安装。您需要先卸载未签名版本。 - Maciej Ciemięga
谢谢你,Maciej。终于你的解决方案对我有用了。非常感谢你宝贵的时间。 - Lakhan Sharma

11

我遇到了同样的错误,原因是“wear”模块的包名与应用程序不一致。

BAD:
[module: app] es.voghdev.myapp
[module: wear] es.voghdev.myapp.wear

GOOD:
[module: app] es.voghdev.myapp
[module: wear] es.voghdev.myapp

让我浪费了很多时间!! >:-(


2
使用AsynTask发送消息,以避免阻塞UI线程。此外,您需要调用await方法。为了使应用程序具有相同的密钥,您需要使用Gradle构建变体。
public class SendMessageTask extends AsyncTask<Void, Void, Void> {

    @Override
    protected Void doInBackground(Void... voids) {
        NodeApi.GetConnectedNodesResult nodes =
                Wearable.NodeApi.getConnectedNodes(apiClient).await();
        for (Node node : nodes.getNodes()) {
            Wearable.MessageApi
                    .sendMessage(apiClient, node.getId(), "/start/MainActivity", null)
                    .await();
        }

        return null;
    }

    @Override
    protected void onPostExecute(Void aVoid) {
        super.onPostExecute(aVoid);
        Toast.makeText(MainActivity.this, "Message Sent", Toast.LENGTH_SHORT).show();
    }
}

1
不必使用AsyncTask,因为MessageApi已经具备了异步支持。只需用setResultCallback()替换.await()调用并传递回调函数即可在调用完成时进行回调。使用AsyncTask只会创建一个不必要的额外线程。 - Martin

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接