Connect through Wifi to IBM MQTT cloud https://quickstart.internetofthings.ibmcloud.com

Dependencies:   MQTT NetworkSocketAPI X_NUCLEO_IDW01M1v2 X_NUCLEO_IKS01A1 mbed NDefLib X_NUCLEO_NFC01A1

Fork of IDW01M1_Cloud_IBM by ST Expansion SW Team

To start the demo the following expansion boards are required

X_NUCLEO_IDW01M1v2, X_NUCLEO_IKS01A1, X_NUCLEO_NFC01A1

After having mounted the board stack on the Nucleo board the below steps should be followed:

  • Program in the application source code you local WiFi SSID and password and flash the binary. Make sure the Wifi network has visible SSID.
  • Reset the Nucleo board and after few seconds the Nucleo green led will be on (it means the Nucleo is connected to the local Wifi and to the IBM cloud server)
  • Read the NFC tag with an Android device and the browser will be automatically opened and directed to the specific brocker IBM demo page where the environmental values are displayed in form of a x-y graph. The values are updated every few seconds. On the Hyperterminal is possible to see the values sent to the IBM cloud server and the board mac address to be entered on the IBM quickstart web page if a manual connection is needed (eg. to connect from a PC browser).
Committer:
mapellil
Date:
Wed Oct 19 09:36:51 2016 +0000
Revision:
21:78fac4c1b0fa
Parent:
20:517b559ce91d
Child:
22:d278e4bb5ded
fixed "publish" string syntax, changed type name to iotsample-mbed-Nucleo

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mridup 10:c7b62ce013ad 1 /* SpwfInterface NetworkSocketAPI Example Program
mridup 10:c7b62ce013ad 2 * Copyright (c) 2015 ARM Limited
mridup 10:c7b62ce013ad 3 *
mridup 10:c7b62ce013ad 4 * Licensed under the Apache License, Version 2.0 (the "License");
mridup 10:c7b62ce013ad 5 * you may not use this file except in compliance with the License.
mridup 10:c7b62ce013ad 6 * You may obtain a copy of the License at
mridup 10:c7b62ce013ad 7 *
mridup 10:c7b62ce013ad 8 * http://www.apache.org/licenses/LICENSE-2.0
mridup 10:c7b62ce013ad 9 *
mridup 10:c7b62ce013ad 10 * Unless required by applicable law or agreed to in writing, software
mridup 10:c7b62ce013ad 11 * distributed under the License is distributed on an "AS IS" BASIS,
mridup 10:c7b62ce013ad 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
mridup 10:c7b62ce013ad 13 * See the License for the specific language governing permissions and
mridup 10:c7b62ce013ad 14 * limitations under the License.
mridup 10:c7b62ce013ad 15 */
mridup 10:c7b62ce013ad 16
mridup 0:cbf8bc43bc9e 17 #include "mbed.h"
mapellil 14:641560b57584 18 #include "SpwfInterface.h"
mridup 4:1ed7f173eec5 19 #include "TCPSocket.h"
fabiombed 13:0b31131bf711 20 #include "MQTTClient.h"
mapellil 14:641560b57584 21 #include "MQTTWiFi.h"
mapellil 14:641560b57584 22 #include <ctype.h>
mapellil 14:641560b57584 23 #include "x_nucleo_iks01a1.h"
fabiombed 13:0b31131bf711 24
mridup 0:cbf8bc43bc9e 25 //------------------------------------
mridup 0:cbf8bc43bc9e 26 // Hyperterminal configuration
mridup 0:cbf8bc43bc9e 27 // 9600 bauds, 8-bit data, no parity
mridup 0:cbf8bc43bc9e 28 //------------------------------------
mridup 8:6df01cb43137 29 Serial pc(SERIAL_TX, SERIAL_RX);
mridup 3:dfb8c6c8c31b 30 DigitalOut myled(LED1);
mapellil 14:641560b57584 31 SpwfSAInterface spwf(D8, D2, false);
mapellil 14:641560b57584 32 bool quickstartMode = true;
mapellil 17:83d0cd810ed3 33
mapellil 17:83d0cd810ed3 34 #define ORG_QUICKSTART // comment to connect to play.internetofthings.ibmcloud.com
mapellil 14:641560b57584 35
mapellil 14:641560b57584 36 #define MQTT_MAX_PACKET_SIZE 250
mapellil 14:641560b57584 37 #define MQTT_MAX_PAYLOAD_SIZE 300
mapellil 17:83d0cd810ed3 38
mapellil 14:641560b57584 39 // Configuration values needed to connect to IBM IoT Cloud
mapellil 17:83d0cd810ed3 40 #ifdef ORG_QUICKSTART
mapellil 17:83d0cd810ed3 41 #define ORG "quickstart" // connect to quickstart.internetofthings.ibmcloud.com/ For a registered connection, replace with your org
mapellil 17:83d0cd810ed3 42 #define ID ""
mapellil 17:83d0cd810ed3 43 #define AUTH_TOKEN ""
mapellil 21:78fac4c1b0fa 44 #define DEFAULT_TYPE_NAME "iotsample-mbed-Nucleo"
mapellil 17:83d0cd810ed3 45 #else
mapellil 17:83d0cd810ed3 46 #define ORG "play" // connect to play.internetofthings.ibmcloud.com/ For a registered connection, replace with your org
mapellil 17:83d0cd810ed3 47 #define ID "testnucleo2" // For a registered connection, replace with your id
mapellil 17:83d0cd810ed3 48 #define AUTH_TOKEN "centrallab"// For a registered connection, replace with your auth-token
mapellil 17:83d0cd810ed3 49 #define DEFAULT_TYPE_NAME "sensor"
mapellil 17:83d0cd810ed3 50 #endif
mapellil 17:83d0cd810ed3 51
mapellil 14:641560b57584 52 #define TYPE DEFAULT_TYPE_NAME // For a registered connection, replace with your type
mapellil 14:641560b57584 53 #define MQTT_PORT 1883
mapellil 14:641560b57584 54 #define MQTT_TLS_PORT 8883
mapellil 14:641560b57584 55 #define IBM_IOT_PORT MQTT_PORT
mapellil 16:233b89a6b72f 56 // WiFi network credential
mapellil 21:78fac4c1b0fa 57 #define SSID "crespan" // Network must be visible otherwise it can't connect
mapellil 21:78fac4c1b0fa 58 #define PASSW "Elfrontal1"
nikapov 20:517b559ce91d 59 #warning "Wifi SSID & password empty"
mapellil 14:641560b57584 60
mapellil 14:641560b57584 61 char id[30] = ID; // mac without colons
mapellil 14:641560b57584 62 char org[12] = ORG;
mapellil 14:641560b57584 63 int connack_rc = 0; // MQTT connack return code
mapellil 14:641560b57584 64 const char* ip_addr = "";
mapellil 14:641560b57584 65 char* host_addr = "";
mapellil 14:641560b57584 66 char type[30] = TYPE;
mapellil 14:641560b57584 67 char auth_token[30] = AUTH_TOKEN; // Auth_token is only used in non-quickstart mode
mapellil 14:641560b57584 68 bool netConnecting = false;
mapellil 14:641560b57584 69 //int connectTimeout = 1000;
mapellil 14:641560b57584 70 int connectTimeout = 10;
mapellil 14:641560b57584 71 bool mqttConnecting = false;
mapellil 14:641560b57584 72 bool netConnected = false;
mapellil 14:641560b57584 73 bool connected = false;
mapellil 14:641560b57584 74 int retryAttempt = 0;
mapellil 14:641560b57584 75
mapellil 14:641560b57584 76 PressureSensor *pressure_sensor;
mapellil 14:641560b57584 77 HumiditySensor *humidity_sensor;
mapellil 14:641560b57584 78 TempSensor *temp_sensor1;
mapellil 14:641560b57584 79
mapellil 14:641560b57584 80
mapellil 14:641560b57584 81 int connect(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack)
mapellil 14:641560b57584 82 {
mapellil 14:641560b57584 83 const char* iot_ibm = ".messaging.internetofthings.ibmcloud.com";
mapellil 14:641560b57584 84
mapellil 14:641560b57584 85 char hostname[strlen(org) + strlen(iot_ibm) + 1];
mapellil 14:641560b57584 86 sprintf(hostname, "%s%s", org, iot_ibm);
mapellil 14:641560b57584 87 SpwfSAInterface& WiFi = ipstack->getWiFi();
mapellil 14:641560b57584 88 ip_addr = WiFi.get_ip_address();
mapellil 14:641560b57584 89 printf ("ID: %s\n\r",id);
mapellil 14:641560b57584 90 // Construct clientId - d:org:type:id
mapellil 14:641560b57584 91 char clientId[strlen(org) + strlen(type) + strlen(id) + 5];
mapellil 14:641560b57584 92 sprintf(clientId, "d:%s:%s:%s", org, type, id);
mapellil 14:641560b57584 93 // Network debug statements
mapellil 14:641560b57584 94 LOG("=====================================\n\r");
mapellil 14:641560b57584 95 LOG("Connecting WiFi.\n\r");
mapellil 14:641560b57584 96 LOG("IP ADDRESS: %s\n\r", WiFi.get_ip_address());
mapellil 14:641560b57584 97 LOG("MAC ADDRESS: %s\n\r", WiFi.get_mac_address());
mapellil 14:641560b57584 98 LOG("Server Hostname: %s\n\r", hostname);
mapellil 17:83d0cd810ed3 99 // for(int i = 0; clientId[i]; i++){
mapellil 17:83d0cd810ed3 100 // clientId[i] = tolower(clientId[i]);
mapellil 17:83d0cd810ed3 101 // }
mapellil 14:641560b57584 102 LOG("Client ID: %s\n\r", clientId);
mapellil 14:641560b57584 103 LOG("=====================================\n\r");
mapellil 14:641560b57584 104
mapellil 14:641560b57584 105 netConnecting = true;
mapellil 14:641560b57584 106 ipstack->open(&ipstack->getWiFi());
mapellil 14:641560b57584 107 int rc = ipstack->connect(hostname, IBM_IOT_PORT, connectTimeout);
mapellil 14:641560b57584 108 if (rc != 0)
mapellil 14:641560b57584 109 {
mapellil 14:641560b57584 110 WARN("IP Stack connect returned: %d\n", rc);
mapellil 14:641560b57584 111 return rc;
mapellil 14:641560b57584 112 }
mapellil 14:641560b57584 113 netConnected = true;
mapellil 14:641560b57584 114 netConnecting = false;
mapellil 14:641560b57584 115
mapellil 14:641560b57584 116 // MQTT Connect
mapellil 14:641560b57584 117 mqttConnecting = true;
mapellil 14:641560b57584 118 MQTTPacket_connectData data = MQTTPacket_connectData_initializer;
mapellil 17:83d0cd810ed3 119 data.MQTTVersion = 4;
mapellil 17:83d0cd810ed3 120 data.struct_version=0;
mapellil 14:641560b57584 121 data.clientID.cstring = clientId;
mapellil 14:641560b57584 122
mapellil 14:641560b57584 123 if (!quickstartMode)
mapellil 14:641560b57584 124 {
mapellil 14:641560b57584 125 data.username.cstring = "use-token-auth";
mapellil 14:641560b57584 126 data.password.cstring = auth_token;
mapellil 14:641560b57584 127 }
mapellil 14:641560b57584 128 if ((rc = client->connect(data)) == 0)
mapellil 14:641560b57584 129 {
mapellil 14:641560b57584 130 connected = true;
mapellil 14:641560b57584 131 printf ("--->Connected\n\r");
mapellil 14:641560b57584 132 }
mapellil 14:641560b57584 133 else {
mapellil 14:641560b57584 134 WARN("MQTT connect returned %d\n", rc);
mapellil 14:641560b57584 135 }
mapellil 14:641560b57584 136 if (rc >= 0)
mapellil 14:641560b57584 137 connack_rc = rc;
mapellil 14:641560b57584 138 mqttConnecting = false;
mapellil 14:641560b57584 139 return rc;
mapellil 14:641560b57584 140 }
mapellil 14:641560b57584 141
mapellil 14:641560b57584 142 int getConnTimeout(int attemptNumber)
mapellil 14:641560b57584 143 { // First 10 attempts try within 3 seconds, next 10 attempts retry after every 1 minute
mapellil 14:641560b57584 144 // after 20 attempts, retry every 10 minutes
mapellil 14:641560b57584 145 return (attemptNumber < 10) ? 3 : (attemptNumber < 20) ? 60 : 600;
mapellil 14:641560b57584 146 }
mapellil 14:641560b57584 147
mapellil 14:641560b57584 148 void attemptConnect(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack)
mapellil 14:641560b57584 149 {
mapellil 14:641560b57584 150 connected = false;
mapellil 14:641560b57584 151
mapellil 14:641560b57584 152 while (connect(client, ipstack) != MQTT_CONNECTION_ACCEPTED)
mapellil 14:641560b57584 153 {
mapellil 14:641560b57584 154 if (connack_rc == MQTT_NOT_AUTHORIZED || connack_rc == MQTT_BAD_USERNAME_OR_PASSWORD) {
mapellil 14:641560b57584 155 printf ("File: %s, Line: %d\n\r",__FILE__,__LINE__);
mapellil 14:641560b57584 156 return; // don't reattempt to connect if credentials are wrong
mapellil 14:641560b57584 157 }
mapellil 14:641560b57584 158 int timeout = getConnTimeout(++retryAttempt);
mapellil 14:641560b57584 159 WARN("Retry attempt number %d waiting %d\n", retryAttempt, timeout);
mapellil 14:641560b57584 160
mapellil 14:641560b57584 161 // if ipstack and client were on the heap we could deconstruct and goto a label where they are constructed
mapellil 14:641560b57584 162 // or maybe just add the proper members to do this disconnect and call attemptConnect(...)
mapellil 14:641560b57584 163
mapellil 14:641560b57584 164 // this works - reset the system when the retry count gets to a threshold
mapellil 14:641560b57584 165 if (retryAttempt == 5)
mapellil 14:641560b57584 166 NVIC_SystemReset();
mapellil 14:641560b57584 167 else
mapellil 14:641560b57584 168 wait(timeout);
mapellil 14:641560b57584 169 }
mapellil 14:641560b57584 170 }
mapellil 14:641560b57584 171
mapellil 14:641560b57584 172 int publish(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack)
mapellil 14:641560b57584 173 {
mapellil 14:641560b57584 174 MQTT::Message message;
mapellil 14:641560b57584 175 char* pubTopic = "iot-2/evt/status/fmt/json";
mapellil 14:641560b57584 176
mapellil 14:641560b57584 177 char buf[MQTT_MAX_PAYLOAD_SIZE];
mapellil 14:641560b57584 178 float temp, press, hum;
mapellil 14:641560b57584 179 temp_sensor1->GetTemperature(&temp);
mapellil 14:641560b57584 180 pressure_sensor->GetPressure(&press);
mapellil 14:641560b57584 181 humidity_sensor->GetHumidity(&hum);
mapellil 14:641560b57584 182 sprintf(buf,
mapellil 21:78fac4c1b0fa 183 "{\"d\":{\"ST\":\"Nucleo-IoT-mbed\",\"Temp\":%0.4f,\"Pressure\":%0.4f,\"Humidity\":%0.4f}}",
mapellil 14:641560b57584 184 temp, press, hum);
mapellil 14:641560b57584 185 message.qos = MQTT::QOS0;
mapellil 14:641560b57584 186 message.retained = false;
mapellil 14:641560b57584 187 message.dup = false;
mapellil 14:641560b57584 188 message.payload = (void*)buf;
mapellil 14:641560b57584 189 message.payloadlen = strlen(buf);
mapellil 14:641560b57584 190
mapellil 14:641560b57584 191 LOG("Publishing %s\n", buf);
mapellil 14:641560b57584 192 return client->publish(pubTopic, message);
mapellil 14:641560b57584 193 }
mridup 4:1ed7f173eec5 194
fabiombed 13:0b31131bf711 195 int main()
fabiombed 13:0b31131bf711 196 {
mapellil 16:233b89a6b72f 197 const char * ssid = SSID; // Network must be visible otherwise it can't connect
mapellil 16:233b89a6b72f 198 const char * seckey = PASSW;
mapellil 14:641560b57584 199
mapellil 14:641560b57584 200 // Timer tyeld;
mapellil 14:641560b57584 201
mapellil 14:641560b57584 202 DevI2C *i2c = new DevI2C(I2C_SDA, I2C_SCL);
mapellil 14:641560b57584 203 i2c->frequency(400000);
mapellil 14:641560b57584 204
mapellil 14:641560b57584 205 X_NUCLEO_IKS01A1 *mems_expansion_board = X_NUCLEO_IKS01A1::Instance(i2c);
mapellil 14:641560b57584 206
mapellil 14:641560b57584 207 pressure_sensor = mems_expansion_board->pt_sensor;
mapellil 14:641560b57584 208 temp_sensor1 = mems_expansion_board->ht_sensor;
mapellil 14:641560b57584 209 humidity_sensor = mems_expansion_board->ht_sensor;
mridup 4:1ed7f173eec5 210
mridup 6:0d838d564181 211 pc.printf("\r\nX-NUCLEO-IDW01M1 mbed Application\r\n");
mapellil 14:641560b57584 212 pc.printf("\r\nconnecting to AP\r\n");
fabiombed 13:0b31131bf711 213
mapellil 17:83d0cd810ed3 214 quickstartMode=false;
mapellil 16:233b89a6b72f 215 if (strcmp(org, "quickstart") == 0){quickstartMode = true;}
mapellil 16:233b89a6b72f 216 MQTTWiFi ipstack(spwf, ssid, seckey, NSAPI_SECURITY_WPA2);
mapellil 16:233b89a6b72f 217 MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE> client(ipstack);
mapellil 16:233b89a6b72f 218 if (quickstartMode){
mapellil 14:641560b57584 219 char mac[50];
mapellil 17:83d0cd810ed3 220 char *digit=NULL;
mapellil 17:83d0cd810ed3 221 sprintf (id,"%s", "");
mapellil 14:641560b57584 222 sprintf (mac,"%s",ipstack.getWiFi().get_mac_address());
mapellil 14:641560b57584 223 strcpy (mac, ipstack.getWiFi().get_mac_address());
mapellil 14:641560b57584 224 digit = strtok (mac,":");
mapellil 14:641560b57584 225 while (digit != NULL)
mapellil 14:641560b57584 226 {
mapellil 14:641560b57584 227 strcat (id, digit);
mapellil 14:641560b57584 228 digit = strtok (NULL, ":");
mapellil 17:83d0cd810ed3 229 }
mapellil 16:233b89a6b72f 230 }
mapellil 16:233b89a6b72f 231 attemptConnect(&client, &ipstack);
mapellil 16:233b89a6b72f 232 if (connack_rc == MQTT_NOT_AUTHORIZED || connack_rc == MQTT_BAD_USERNAME_OR_PASSWORD)
mapellil 16:233b89a6b72f 233 {
mapellil 16:233b89a6b72f 234 while (true)
mapellil 16:233b89a6b72f 235 wait(1.0); // Permanent failures - don't retry
mapellil 16:233b89a6b72f 236 }
mapellil 16:233b89a6b72f 237 int count = 0;
mapellil 16:233b89a6b72f 238 // tyeld.start();
mapellil 14:641560b57584 239 while (true)
mridup 8:6df01cb43137 240 {
mapellil 14:641560b57584 241 if (++count == /*100*/2)
mapellil 14:641560b57584 242 { // Publish a message every second
mapellil 14:641560b57584 243 if (publish(&client, &ipstack) != 0)
mapellil 14:641560b57584 244 attemptConnect(&client, &ipstack); // if we have lost the connection
mapellil 14:641560b57584 245 count = 0;
mapellil 14:641560b57584 246 }
mapellil 14:641560b57584 247 // int start = tyeld.read_ms();
mapellil 14:641560b57584 248 client.yield(/*10*/1); // allow the MQTT client to receive messages
mapellil 14:641560b57584 249 // printf ("tyeld: %d\n\r",tyeld.read_ms()-start);
mridup 3:dfb8c6c8c31b 250 }
mridup 4:1ed7f173eec5 251 }