An mbed wrapper around the helium-client to communicate with the Helium Atom

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers Helium.h Source File

Helium.h

00001 /*
00002  * Copyright 2017, Helium Systems, Inc.
00003  * All Rights Reserved. See LICENSE.txt for license information
00004  */
00005 
00006 #ifndef HELIUM_H
00007 #define HELIUM_H
00008 
00009 #include "BufferedSerial.h"
00010 #include "helium-client/helium-client.h"
00011 #include "mbed.h"
00012 
00013 /**
00014  * \class Helium
00015  *
00016  * \brief Enables communication with the Helium Atom
00017  *
00018  * This class offers the basic ability to communicate with the Helium
00019  * Atom module.
00020  */
00021 class Helium
00022 {
00023   public:
00024     /** Create a Helium instance on a hardware serial port.
00025      *
00026      * @param serial The hardware serial port to use
00027      */
00028     Helium(PinName tx, PinName rx);
00029 
00030     /** Set communication speed with the Helium Atom.
00031      *
00032      * This sets communication speed with the Helium Atom to the given
00033      * value.
00034      *
00035      * @param baud The baud rate to use.
00036      */
00037     int baud(enum helium_baud baud);
00038 
00039     /** Get information on the Helium atom
00040      *
00041      * Gets basic information about the Helium Atom such as it's MAC
00042      * address and the current network time, if connected.
00043      *
00044      * @param info The information structure to fill out
00045      */
00046     int info(struct helium_info * info);
00047 
00048     /** Connect the Helium Atom to the network.
00049      *
00050      * This tries to connect the Helium Atom to a nearby Element and
00051      * the Helium Network. Connections can be quick or slow. A quick
00052      * connection attempt to re-connect to the network using revious
00053      * _connection_ state which was retrieved using %sleep. If the
00054      * quick connect was not requested or if it fails a normal, slower
00055      * connection attempt is made.
00056      *
00057      * Connect is an asynchronous operation. The given are a
00058      * convenience to attempt a number of retries before returning the
00059      * current connection state.
00060      *
00061      * @param connection A previously retrieved connection structure
00062      *        that reflects sleep state.
00063      *
00064      * @param retries The number of retries to attempt to connect.
00065      *
00066      * @return helium_connect_status
00067      */
00068     int connect(struct connection * connection = NULL,
00069                 uint32_t            retries    = HELIUM_POLL_RETRIES_5S);
00070 
00071     /** Check if the Atom is connected to the network
00072      *
00073      * Checks whether the Atom is connected to the network.
00074      *
00075      * @returns true if connected, false if not connected
00076      */
00077     bool connected();
00078 
00079     /** Disconnects the Atom from the network and puts it in sleep mode.
00080      *
00081      * This disconnects the Helium Atom from the network and puts it
00082      * in sleep mode. If a connection structure is given, it is filled
00083      * with sleep state which can be used in a sub-sequent connect
00084      * call to quick connect to the network.
00085      *
00086      * @param connection Sleep connection buffer to fill in.
00087      */
00088     int sleep(struct connection * connection = NULL);
00089 
00090     /** Checks if the Atom needs resetting.
00091      *
00092      * Checks if the Atom needs a reset. This is set over the air by
00093      * the Helium network when the Helium Atom has a firmware update
00094      * ready to apply.
00095      *
00096      * @returns true if the Atom needs to be reset, false otherwise.
00097      */
00098     bool needs_reset();
00099 
00100     /** Resets the Atom.
00101      *
00102      * This resets the Atom. Use this method when `needs_reset`
00103      * returns true to apply any pending firmware updates to the Atom.
00104      */
00105     int reset();
00106 
00107 
00108   private:
00109     struct helium_ctx _ctx;
00110     BufferedSerial    serial;
00111 
00112     friend class Channel;
00113     friend class Config;
00114 };
00115 
00116 /**
00117  * \class Channel
00118  *
00119  * \brief A Channel to an IoT platform.
00120  *
00121  * Channels represent a delivery mechanism from the device to a number
00122  * of supported back-end IoT platforms.
00123  *
00124  * To use a channel, make sure you have it set up in your Helium
00125  * Dashboard and then call Channel#begin with the channel name as you
00126  * configured it on the Helium Dashboard. This will automatically
00127  * ensure that the device is securely authenticated and registered
00128  * with the channel.
00129  *
00130  */
00131 class Channel
00132 {
00133   public:
00134     /** Construct a channel.
00135      *
00136      * @param helium The Helium Atom to communicate with
00137      */
00138     Channel(Helium * helium);
00139 
00140     /** Begin communicating over a channel
00141      *
00142      * Always call this method before calling Channel#send. Beginning
00143      * communication will ensure that the device is authenticated and
00144      * registered with the channel with the given name as configured
00145      * in the Helium Dashboard.
00146      *
00147      * The `result` value will be 0 if the channel was created
00148      * successfully and non-`0` otherwise.
00149      *
00150      * @param name The name of the channel to authenticate with.
00151      * @param result An out parameter for the result of the request.
00152      */
00153     int begin(const char * name, int8_t * result);
00154 
00155     /** Send data to this channel.
00156      *
00157      * Send data to a given channel. The given data is sent to the
00158      * configured channel and the result as returned by the channel is
00159      * put in the `result` output variable. The result value is `0`
00160      * for success and non-`0` if an error occurred.
00161      *
00162      * @note The maximum number of bytes that can be transmitted is
00163      * limited to HELIUM_MAX_DATA_SIZE (about 100 bytes).
00164      *
00165      * @param data The data bytes to send
00166      * @param len The number of bytes in data to send
00167      * @param result An out parameter for the result returned by the channel
00168      */
00169     int send(void const * data, size_t len, int8_t * result);
00170 
00171     /** Asynchronous begin method.
00172      *
00173      * The Channel#begin(const char *) method is a synchronous version
00174      * of this method. Sending a request to a channel returns a
00175      * `token` which can be used in a subsequent call to #poll() to
00176      * check for results from the remote channel.
00177      *
00178      * @param name The name of the channel to authenticate with.
00179      * @param token The output parameter for the pending result token.
00180      */
00181     int begin(const char * name, uint16_t * token);
00182 
00183     /** Asynchornous send method.
00184      *
00185      * This is the asynchronous version of the #send(void const *data,
00186      * size_t int8_t *) method.
00187      *
00188      * @param data The data bytes to send
00189      * @param len The number of bytes in data to send
00190      * @param token The output parameter for the pending result token
00191      */
00192     int send(void const * data, size_t len, uint16_t * token);
00193 
00194     /** Poll for a result token.
00195      *
00196      * This polls the Helium Atom for the given number of retries for
00197      * the result of a given `token`. Use HELIUM_POLL_RETRIES_5S for
00198      * the recommended number of retries.
00199      *
00200      * If succcessful the result will be helium_status_OK and the
00201      * result value will be set to the result of the original request
00202      * that the token represents.
00203      *
00204      * @param token The token to check for
00205      * @param result[out] The result of the given request token
00206      * @param retries The number of times to retry
00207      */
00208     int poll_result(uint16_t token,
00209                     int8_t * result,
00210                     uint32_t retries = HELIUM_POLL_RETRIES_5S);
00211 
00212     /** Poll for data on a channel.
00213      *
00214      * This polls the Helium Atom for the given number of retries for
00215      * any data on the channel.
00216      *
00217      * If successful the result will be helium_status_OK and the given
00218      * `data` buffer will be filled with the received data. The `used`
00219      * out parameter will be set to the number of bytes read. Note
00220      * that the maximum number of bytes that can be sent is set by
00221      * HELIUM_MAX_DATA_SIZE.
00222      *
00223      * @param[out] data The data buffer to fill with received data
00224      * @param len The available length of the data buffer
00225      * @param[out] used On success the number of bytes used up in data
00226      * @param retries The number of times to retry
00227      */
00228     int poll_data(void *   data,
00229                   size_t   len,
00230                   size_t * used,
00231                   uint32_t retries = HELIUM_POLL_RETRIES_5S);
00232 
00233     /** The Helium Atom this channel uses to communicate. */
00234     Helium * helium;
00235 
00236   private:
00237     int8_t   _channel_id;
00238 
00239     friend class Config;
00240 };
00241 
00242 
00243 enum config_poll_get_status
00244 {
00245     config_status_POLL_FOUND      = 0,
00246     config_status_POLL_FOUND_NULL = -1,
00247     config_status_POLL_ERR_TYPE   = -2,
00248 };
00249 
00250 
00251 /**
00252  * \class Config
00253  *
00254  * \brief A Channel Configuration
00255  *
00256  * Channels can have configuration data for the Helium Atom
00257  * available. Depending on the IoT platform the configuration data is
00258  * a representation of device configuration. Other terms used are
00259  * device "twins" or "shadows".
00260  *
00261  * To use a channel configuration construct it with a channel that
00262  * supports configuration and use the get methods to retrieve
00263  * configuration values from the IoT platform's device
00264  * representation. Use the set methods to set values in the IoT
00265  * platform's representation of the device.
00266  *
00267  * Note that most IoT platforms represent sets and gets in different
00268  * namespaces. The get methods represent the IoT platform's desired or
00269  * expected namespace of the device, while the set methods are
00270  * reflected in the actual, or current namespace of the device.
00271  *
00272  */
00273 class Config
00274 {
00275   public:
00276     /** Construct a Configuration
00277      *
00278      * @param channel The channel to get/set configuration with
00279      */
00280     Config(Channel * channel);
00281 
00282     /** Get an integer configuration value
00283      *
00284      * @param key The configuration key to get
00285      * @param[out] value The target for the received value
00286      * @param default_value The default value in case of errors
00287      * @param retries The number of times to retry (optional)
00288      * @returns 0 on success. If the result is > 0 the result code is
00289      *     one of the helium_status_ error codes. If the result is < 0
00290      *     it is one of the config_poll_get_status error codes
00291      */
00292     int get(const char * key,
00293             int32_t *    value,
00294             int32_t      default_value,
00295             uint32_t     retries = HELIUM_POLL_RETRIES_5S)
00296     {
00297         return _get(key,
00298                     helium_config_i32,
00299                     value,
00300                     sizeof(*value),
00301                     &default_value,
00302                     sizeof(default_value),
00303                     retries);
00304     }
00305 
00306     /** Get a float configuration value
00307      *
00308      * @param key The configuration key to get
00309      * @param[out] value The target for the received value
00310      * @param default_value The default value in case of errors
00311      * @param retries The number of times to retry (optional)
00312      * @returns 0 on success. If the result is > 0 the result code is
00313      *     one of the helium_status_ error codes. If the result is < 0
00314      *     it is one of the config_poll_get_status error codes
00315      */
00316     int get(const char * key,
00317             float *      value,
00318             float        default_value,
00319             uint32_t     retries = HELIUM_POLL_RETRIES_5S)
00320     {
00321         return _get(key,
00322                     helium_config_f32,
00323                     value,
00324                     sizeof(*value),
00325                     &default_value,
00326                     sizeof(default_value),
00327                     retries);
00328     }
00329 
00330 
00331     /** Get a boolean configuration value
00332      *
00333      * @param key The configuration key to get
00334      * @param[out] value The target for the received value
00335      * @param default_value The default value in case of errors
00336      * @param retries The number of times to retry (optional)
00337      * @returns 0 on success. If the result is > 0 the result code is
00338      *     one of the helium_status_ error codes. If the result is < 0
00339      *     it is one of the config_poll_get_status error codes
00340      */
00341     int get(const char * key,
00342             bool *       value,
00343             bool         default_value,
00344             uint32_t     retries = HELIUM_POLL_RETRIES_5S)
00345     {
00346         return _get(key,
00347                     helium_config_bool,
00348                     value,
00349                     sizeof(*value),
00350                     &default_value,
00351                     sizeof(default_value),
00352                     retries);
00353     }
00354 
00355     /** Get a string configuration value
00356      *
00357      * @param key The configuration key to get
00358      * @param[out] value The target buffer for the received string
00359      * @param value_len The length of the available buffer space
00360      * @param default_value The default value to use if not found
00361      * @param default_value_len The length of the default_value buffer.
00362      *     Note: Ensure to include the trailing NULL in this length
00363      *     parameter
00364      * @param retries The number of times to retry (optional)
00365      * @returns 0 on success. If the result is > 0 the result code is
00366      *     one of the helium_status_ error codes. If the result is < 0
00367      *     it is one of the config_poll_get_status error codes
00368      */
00369     int get(const char * key,
00370             char *       value,
00371             size_t       value_len,
00372             char *       default_value,
00373             size_t       default_value_len,
00374             uint32_t     retries = HELIUM_POLL_RETRIES_5S)
00375     {
00376         return _get(key,
00377                     helium_config_str,
00378                     value,
00379                     value_len,
00380                     default_value,
00381                     default_value_len,
00382                     retries);
00383     }
00384 
00385     /** Send a request for a configuration value.
00386      *
00387      * Getting a configuration value requires sending a request with
00388      * the configuration key and then using the resulting token in a
00389      * #poll_get_result() call to wait for a response.
00390      *
00391      * @param key The configuration key to get
00392      * @param[out] token The token representing the response.
00393      * @returns 0 on success. One of the helium_status_ error
00394      *     codes otherwise.
00395      */
00396     int get(const char * key, uint16_t * token);
00397 
00398     /** Poll the response of a configuration request.
00399      *
00400      * Polls the given token and validates any response against the
00401      * given configuration key and expected type. If these match the
00402      * value is copied into the given value buffer.
00403      *
00404      * Note: The short form methods for getting config values hide
00405      * most of the complexity required to make a configuration get
00406      * work.
00407      *
00408      * @param token The token returned from a previous #get() request
00409      * @param config_key The configuration key to check for
00410      * @param config_type The configuration type to check for
00411      * @param[out] value The destination buffer to copy the result into
00412      * @param value_len The size of the given destination buffer
00413      * @param default_value The default value to use if not found
00414      * @param default_value_len The length of the default_value buffer.
00415      * @param retries The number of times to retry (optional)
00416      * @param[out] result The channel response code.
00417      *     0 for no errors, non-0 otherwise
00418      * @returns 0 on success. If the result is > 0 the result code is
00419      *     one of the helium_status_ error codes. If the result is < 0
00420      *     it is one of the config_poll_get_status error codes
00421      */
00422     int poll_get_result(uint16_t                token,
00423                         const char *            config_key,
00424                         enum helium_config_type config_type,
00425                         void *                  value,
00426                         size_t                  value_len,
00427                         void *                  default_value,
00428                         size_t                  default_value_len,
00429                         int8_t *                result,
00430                         uint32_t retries = HELIUM_POLL_RETRIES_5S);
00431 
00432     /** Set a float configuration value
00433      *
00434      * @param key The configuration key to set
00435      * @param value The value to set
00436      * @param retries The number of times to retry (optional)
00437      * @returns 0 on success. One of the helium_status_ error
00438      *     codes otherwise.
00439      */
00440     int set(const char * key, float value, uint32_t retries = HELIUM_POLL_RETRIES_5S)
00441     {
00442         return _set(key, helium_config_f32, &value, retries);
00443     }
00444 
00445     /** Set an integer configuration value
00446      *
00447      * @param key The configuration key to set
00448      * @param value The value to set
00449      * @param retries The number of times to retry (optional)
00450      * @returns 0 on success. One of the helium_status_ error
00451      *     codes otherwise.
00452      */
00453     int set(const char * key,
00454             int32_t      value,
00455             uint32_t     retries = HELIUM_POLL_RETRIES_5S)
00456     {
00457         return _set(key, helium_config_i32, &value, retries);
00458     }
00459 
00460     /** Set a boolean configuration value
00461      *
00462      * @param key The configuration key to set
00463      * @param value The value to set
00464      * @param retries The number of times to retry (optional)
00465      * @returns 0 on success. One of the helium_status_ error
00466      *     codes otherwise.
00467      */
00468     int set(const char * key, bool value, uint32_t retries = HELIUM_POLL_RETRIES_5S)
00469     {
00470         return _set(key, helium_config_bool, &value, retries);
00471     }
00472 
00473     /** Set a string configuration value
00474      *
00475      * @param key The configuration key to set
00476      * @param value The value to set
00477      * @param retries The number of times to retry (optional)
00478      * @returns 0 on success. One of the helium_status_ error
00479      *     codes otherwise.
00480      */
00481     int set(const char * key,
00482             const char * value,
00483             uint32_t     retries = HELIUM_POLL_RETRIES_5S)
00484     {
00485         return _set(key, helium_config_str, &value, retries);
00486     }
00487 
00488     /** Set a null configuration value
00489      *
00490      * @param key The configuration key to set
00491      * @param retries The number of times to retry (optional)
00492      * @returns 0 on success. One of the helium_status_ error
00493      *     codes otherwise.
00494      */
00495     int set_null(const char * key, uint32_t retries = HELIUM_POLL_RETRIES_5S)
00496     {
00497         return _set(key, helium_config_null, NULL, retries);
00498     }
00499 
00500     /** Send a request for setting a configuration value.
00501      *
00502      * Setting a configuration value requires sending a request with
00503      * the configuration key, the value type and the value and then
00504      * using the resulting token in a #poll_set_result() call to wait
00505      * for a response.
00506      *
00507      * @param key The configuration key to set
00508      * @param value_type The type of the configuration value to set
00509      * @param value A pointer to the value that needs to be st
00510      * @param[out] token The token representing the response.
00511      * @returns 0 on success. One of the helium_status_ error
00512      *     codes otherwise.
00513      */
00514     int set(const char *       key,
00515             helium_config_type value_type,
00516             void *             value,
00517             uint16_t *         token);
00518 
00519     /** Poll the response of a configuration set request.
00520      *
00521      * Polls the given token and returns the result code of the set
00522      * request.
00523      *
00524      * Note: The short form methods for getting config values hide
00525      * most of the complexity required to make a configuration get
00526      * work.
00527      *
00528      * @param token The token returned from a previous #set() request
00529      * @param[out] result A pointer to storage for the response code
00530      * @param retries The number of times to retry (optional)
00531      * @returns A helium_status result code for the actual
00532      *     communication part. If the result is helium_status_OK, the
00533      *     result code can be used to check if the set was
00534      *     successful. The result code will be 0 on success, and
00535      *     non-zero otherwise.
00536      */
00537     int poll_set_result(uint16_t token,
00538                         int8_t * result,
00539                         uint32_t retries = HELIUM_POLL_RETRIES_5S);
00540 
00541     /** Check whether configuration values are stale.
00542      *
00543      * Checks whether there has been a system indication that
00544      * configuration attributes may have gone stale.
00545      *
00546      * When this returns true you should assume that any configuration
00547      * values you have previously retrieved are no longer valid.
00548      *
00549      * @returns true if previous configuration values are stale, false
00550      *     if not
00551      */
00552     bool is_stale();
00553 
00554 
00555   private:
00556     int       _get(const char *            config_key,
00557                    enum helium_config_type config_type,
00558                    void *                  value,
00559                    size_t                  value_len,
00560                    void *                  default_value,
00561                    size_t                  default_value_len,
00562                    uint32_t                retries);
00563     int       _set(const char *            config_key,
00564                    enum helium_config_type value_type,
00565                    void *                  value,
00566                    uint32_t                retries);
00567     Channel * _channel;
00568 };
00569 
00570 
00571 #endif // HELIUM_H