1.. _mqtt_sn_socket_interface: 2 3MQTT-SN 4####### 5 6.. contents:: 7 :local: 8 :depth: 2 9 10Overview 11******** 12 13MQTT-SN is a variant of the well-known MQTT protocol - see :ref:`mqtt_socket_interface`. 14 15In contrast to MQTT, MQTT-SN does not require a TCP transport, but is designed to be used 16over any message-based transport. Originally, it was mainly created with ZigBee in mind, 17but others like Bluetooth, UDP or even a UART can be used just as well. 18 19Zephyr provides an MQTT-SN client library built on top of BSD sockets API. The 20library can be enabled with :kconfig:option:`CONFIG_MQTT_SN_LIB` Kconfig option 21and is configurable at a per-client basis, with support for MQTT-SN version 221.2. The Zephyr MQTT-SN implementation can be used with any message-based transport, 23but support for UDP is already built-in. 24 25MQTT-SN clients require an MQTT-SN gateway to connect to. These gateways translate between 26MQTT-SN and MQTT. The Eclipse Paho project offers an implementation of a MQTT-SN gateway, but 27others are available too. 28https://www.eclipse.org/paho/index.php?page=components/mqtt-sn-transparent-gateway/index.php 29 30The MQTT-SN spec v1.2 can be found here: 31https://www.oasis-open.org/committees/download.php/66091/MQTT-SN_spec_v1.2.pdf 32 33Sample usage 34************ 35 36To create an MQTT-SN client, a client context structure and buffers need to be 37defined: 38 39.. code-block:: c 40 41 /* Buffers for MQTT client. */ 42 static uint8_t rx_buffer[256]; 43 static uint8_t tx_buffer[256]; 44 45 /* MQTT-SN client context */ 46 static struct mqtt_sn_client client; 47 48Multiple MQTT-SN client instances can be created in the application and managed 49independently. Additionally, a structure for the transport is needed as well. 50The library already comes with an example implementation for UDP. 51 52.. code-block:: c 53 54 /* MQTT Broker address information. */ 55 static struct mqtt_sn_transport tp; 56 57The MQTT-SN library will inform clients about certain events using a callback. 58 59.. code-block:: c 60 61 static void evt_cb(struct mqtt_sn_client *client, 62 const struct mqtt_sn_evt *evt) 63 { 64 switch(evt->type) { 65 { 66 /* Handle events here. */ 67 } 68 } 69 70For a list of possible events, see :ref:`mqtt_sn_api_reference`. 71 72The client context structure needs to be initialized and set up before it can be 73used. An example configuration for UDP transport is shown below: 74 75.. code-block:: c 76 77 struct mqtt_sn_data client_id = MQTT_SN_DATA_STRING_LITERAL("ZEPHYR"); 78 struct sockaddr_in gateway = {0}; 79 80 uint8_t tx_buf[256]; 81 uint8_t rx_buf[256]; 82 83 mqtt_sn_transport_udp_init(&tp, (struct sockaddr*)&gateway, sizeof((gateway))); 84 85 mqtt_sn_client_init(&client, &client_id, &tp.tp, evt_cb, tx_buf, sizeof(tx_buf), rx_buf, sizeof(rx_buf)); 86 87After the configuration is set up, the network address for the gateway to 88connect to must be defined. The MQTT-SN protocol offers functionality to 89discover gateways through an advertisement or a search mechanism. A user 90should do at least one of the following steps to define a Gateway for the library: 91 92* Call the :c:func:`mqtt_sn_add_gw` function to manually define a Gateway address. 93* Wait for an :c:enumerator:`MQTT_SN_EVT_ADVERTISE`. 94* Call the :c:func:`mqtt_sn_search` function and wait for an :c:enumerator:`MQTT_SN_EVT_GWINFO` callback. 95 Make sure to call the :c:func:`mqtt_sn_input` function periodically to process incoming messages. 96 97Example :c:func:`mqtt_sn_search` function call: 98 99.. code-block:: c 100 101 err = mqtt_sn_search(&mqtt_client, 1); 102 k_sleep(K_SECONDS(10)); 103 err = mqtt_sn_input(&mqtt_client); 104 __ASSERT(err == 0, "mqtt_sn_search() failed %d", err); 105 106After the Gateway address has been defined or found, the MQTT-SN client can 107connect to the gateway. Call the :c:func:`mqtt_sn_connect` function, which will send a 108``CONNECT`` MQTT-SN message. The application should periodically call the :c:func:`mqtt_sn_input` 109function to process the response received. The application does not have to call 110:c:func:`mqtt_sn_input` if it knows that no data has been received (e.g. when using Bluetooth). 111Note that :c:func:`mqtt_sn_input` is a non-blocking function, if the transport struct contains a 112:c:func:`poll` compatible function pointer. 113If the connection was successful, :c:enumerator:`MQTT_SN_EVT_CONNECTED` will be notified to the 114application through the callback function. 115 116.. code-block:: c 117 118 err = mqtt_sn_connect(&client, false, true); 119 __ASSERT(err == 0, "mqtt_sn_connect() failed %d", err); 120 121 while (1) { 122 mqtt_sn_input(&client); 123 if (connected) { 124 mqtt_sn_publish(&client, MQTT_SN_QOS_0, &topic_p, false, &pubdata); 125 } 126 k_sleep(K_MSEC(500)); 127 } 128 129In the above code snippet, the gateway is connected to before publishing messages. 130If the connection fails at the MQTT level or a timeout occurs, the connection will be aborted and 131an error returned. 132 133After the connection is established, an application needs to call :c:func:`mqtt_input` 134function periodically to process incoming data. Connection upkeep, on the other hand, 135is done automatically using a k_work item. 136If a MQTT message is received, an MQTT callback function will be called and an 137appropriate event notified. 138 139The connection can be closed by calling the :c:func:`mqtt_sn_disconnect` function. This 140has no effect on the transport, however. If you want to close the transport (e.g. 141the socket), call :c:func:`mqtt_sn_client_deinit`, which will deinit the transport as well. 142 143Zephyr provides sample code utilizing the MQTT-SN client API. See 144:zephyr:code-sample:`mqtt-sn-publisher` for more information. 145 146Deviations from the standard 147**************************** 148 149Certain parts of the protocol are not yet supported in the library. 150 151* Pre-defined topic IDs 152* QoS -1 - it's most useful with predefined topics 153* Setting the will topic and message after the initial connect 154* Forwarder Encapsulation 155 156.. _mqtt_sn_api_reference: 157 158API Reference 159************* 160 161.. doxygengroup:: mqtt_sn_socket 162