javascriptibm-cloudmqttiotwatson-iot

Cannot connect to IBM Watson IoT Platform using Eclipse PAHO MQTT Library for JavaScript


It seems that IBM recently stopped to accept non TLS connections to the MQTT borker for security reasons.

I'm fond of a little application which reads accelerometer sensor data from the smartphone using JavaScript and sends it to the message broker via MQTT.

This application is broken. Therefore I'm trying to fix it in this fork.

As already mentioned, non TLS connections are rejected, that's why I've enabled TLS:

        window.client.connect({
            onSuccess: onConnectSuccess,
            onFailure: onConnectFailure,
            userName: "use-token-auth",
            password: window.password,
            useSSL: true
});

It still doesn't connect. On the IBM Watson IoT Platform I'm seeing this error in the log, nothing else:

Closed connection from 213.55.176.207. The operation is not authorized.

Now I've created a little test index.html file. If I'm connecting as a device, it still doesn't work, but if I'm connecting as an application it works, as can be seen here. But I've created the devices in the platform. And if I'm using an old instance of Watson IoT Platform it works but with newer ones not.

What am I doing wrong?


Solution

  • in your code for the application you have this:

    window.client = new Paho.MQTT.Client("bmzc5i.messaging.internetofthings.ibmcloud.com", 8883, 'a:myOrgId:'+Math.random().toString(16).substr(2, 8));

    which is fine, when an application connects the format of the id is a:orgId:uniqueIdentifierForTheApplication

    uniqueIdentifierForTheApplication can be any string (within the allowed character set), and does not need to be pre-registered, so generating a random number here works in 99% of cases.

    window.client = new Paho.MQTT.Client("bmzc5i.messaging.internetofthings.ibmcloud.com", 8883, 'd:bmzc5i:'+Math.random().toString(16).substr(2, 8));

    when a device connects the id is in the format d:orgId:typeId:deviceId. To connect a device it must first be registered, so an id of d:orgId:randomNumber will not work.

    If you register a device with id myDevice of a device type with id myType, and set it's auth token to myToken then you would form the connection as below:

    window.client = new Paho.MQTT.Client("bmzc5i.messaging.internetofthings.ibmcloud.com", 8883, 'd:bmzc5i:myType:myDevice'); window.client.connect({ onSuccess: onConnectSuccess, onFailure: onConnectFailure, userName: "use-token-auth", password: "myToken", useSSL: true

    Also, you should note the difference in the topic space when connecting as a device and as an application.

    When you connect as an application you have org-wide scope. So to publish/subscribe an event on behalf of a device you would use a topic such as:

    publish to iot-2/type/myType/id/myDevice/evt/statusEvent/fmt/json

    When you connect as a device you have device-scope only (this is a security mechanism to limit the damage a compromised device can do). So for a device the same thing is achieved with a publish to:

    iot-2/evt/statusEvent/fmt/json

    The Platform uses the identity of the device making the publish to determine which device that belongs to, whereas with an application the application decides which device to assign the event to.