From 231392d0c6e51185e81886bed787b17a3fc2105b Mon Sep 17 00:00:00 2001 From: Euripedes Rocha Filho Date: Tue, 15 Dec 2020 13:10:10 +0000 Subject: [PATCH 01/10] experimental/mqtt_cxx: Adds a C++ Mqtt client wrapper - Base class with separated event handlers for each Mqtt client event. - Topic matcher added to support data events. - Filter class to allow only mqtt valid topic filters. - Initial code for unit test on the host. --- .../components/esp_mqtt_cxx/CMakeLists.txt | 25 ++ .../components/esp_mqtt_cxx/component.mk | 5 + .../components/esp_mqtt_cxx/esp_mqtt_cxx.cpp | 299 ++++++++++++++++++ .../esp_mqtt_cxx/include/esp_mqtt.hpp | 229 ++++++++++++++ .../include/esp_mqtt_client_config.hpp | 221 +++++++++++++ .../esp_mqtt_cxx/ssl/CMakeLists.txt | 14 + .../experimental/esp_mqtt_cxx/ssl/Makefile | 12 + .../esp_mqtt_cxx/ssl/main/CMakeLists.txt | 4 + .../esp_mqtt_cxx/ssl/main/Kconfig.projbuild | 9 + .../esp_mqtt_cxx/ssl/main/component.mk | 1 + .../ssl/main/mqtt_eclipse_org.pem | 27 ++ .../ssl/main/mqtt_eclipseprojects_io.pem | 30 ++ .../ssl/main/mqtt_ssl_example.cpp | 85 +++++ .../esp_mqtt_cxx/ssl/sdkconfig.defaults | 3 + .../esp_mqtt_cxx/tcp/CMakeLists.txt | 12 + .../experimental/esp_mqtt_cxx/tcp/Makefile | 12 + .../esp_mqtt_cxx/tcp/main/CMakeLists.txt | 3 + .../esp_mqtt_cxx/tcp/main/Kconfig.projbuild | 9 + .../esp_mqtt_cxx/tcp/main/component.mk | 0 .../tcp/main/mqtt_tcp_example.cpp | 81 +++++ .../esp_mqtt_cxx/tcp/sdkconfig.defaults | 3 + 21 files changed, 1084 insertions(+) create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipse_org.pem create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipseprojects_io.pem create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/sdkconfig.defaults create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/main/component.mk create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt new file mode 100644 index 000000000..5dd0329d0 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt @@ -0,0 +1,25 @@ +idf_build_get_property(target IDF_TARGET) + +idf_component_register(SRCS "esp_mqtt_cxx.cpp" + INCLUDE_DIRS "include" + ) + +target_compile_options(${COMPONENT_LIB} PRIVATE "-std=gnu++17") + +if(TEST_BUILD) + message(STATUS "Test build") + idf_component_get_property(mqtt_dir mqtt COMPONENT_DIR) + idf_component_get_property(experimental_cpp_component_dir experimental_cpp_component COMPONENT_DIR) + idf_component_get_property(esp_common_dir esp_common COMPONENT_DIR) + idf_component_get_property(esp_event_dir esp_event COMPONENT_DIR) + target_include_directories(${COMPONENT_LIB} PUBLIC ${mqtt_dir}/esp-mqtt/include + ${esp_event_dir}/include + ${experimental_cpp_component_dir}/include + ${esp_common_dir}/include) + +else() + idf_component_get_property(mqtt_lib mqtt COMPONENT_LIB) + idf_component_get_property(log_lib log COMPONENT_LIB) + idf_component_get_property(experimental_cpp_component_lib experimental_cpp_component COMPONENT_LIB) + target_link_libraries(${COMPONENT_LIB} PUBLIC ${log_lib} ${mqtt_lib} ${experimental_cpp_component_lib}) +endif() diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk new file mode 100644 index 000000000..9e4987ab4 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk @@ -0,0 +1,5 @@ +COMPONENT_ADD_INCLUDEDIRS := include + +COMPONENT_SRCDIRS := ./ + +CXXFLAGS += -std=gnu++17 diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp new file mode 100644 index 000000000..b5f705b18 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp @@ -0,0 +1,299 @@ +// Copyright 2021 Espressif Systems (Shanghai) CO LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include +#include + +#include "mqtt_client.h" +#include "esp_log.h" + +#include "esp_mqtt.hpp" +#include "esp_mqtt_client_config.hpp" + +namespace { + +// Helper for static assert. +template +constexpr bool always_false = false; + +template struct overloaded : Ts... { + using Ts::operator()...; +}; +template overloaded(Ts...) -> overloaded; + +using namespace idf::mqtt; + +/* + * This function is responsible for fill in the configurations for the broker related data + * of mqtt_client_config_t + */ +void config_broker(esp_mqtt_client_config_t &mqtt_client_cfg, BrokerConfiguration const &broker) +{ + std::visit(overloaded{ + [&mqtt_client_cfg](Host const & host) + { + mqtt_client_cfg.host = host.address.c_str(); + mqtt_client_cfg.path = host.path.c_str(); + mqtt_client_cfg.transport = host.transport; + }, + [&mqtt_client_cfg](URI const & uri) + { + mqtt_client_cfg.uri = uri.address.c_str(); + }, + []([[maybe_unused ]]auto & unknown) + { + static_assert(always_false, "Missing type handler for variant handler"); + } + }, + broker.address.address); + + std::visit(overloaded{ + []([[maybe_unused]]Insecure const & insecure) {}, + [&mqtt_client_cfg](GlobalCAStore const & use_global_store) + { + mqtt_client_cfg.use_global_ca_store = true; + }, + [&mqtt_client_cfg](CryptographicInformation const & certificates) + { + std::visit(overloaded{ + [&mqtt_client_cfg](PEM const & pem) + { + mqtt_client_cfg.cert_pem = pem.data; + }, [&mqtt_client_cfg](DER const & der) + { + mqtt_client_cfg.cert_pem = der.data; + mqtt_client_cfg.cert_len = der.len; + }}, certificates); + }, + []([[maybe_unused]] PSK const & psk) {}, + []([[maybe_unused]] auto & unknown) + { + static_assert(always_false, "Missing type handler for variant handler"); + } + }, + broker.security); + mqtt_client_cfg.port = broker.address.port; +} + +/* + * This function is responsible for fill in the configurations for the client credentials related data + * of mqtt_client_config_t + */ +void config_client_credentials(esp_mqtt_client_config_t &mqtt_client_cfg, ClientCredentials const &credentials) +{ + mqtt_client_cfg.client_id = credentials.client_id.has_value() ? credentials.client_id.value().c_str() : nullptr ; + mqtt_client_cfg.username = credentials.username.has_value() ? credentials.username.value().c_str() : nullptr ; + std::visit(overloaded{ + [&mqtt_client_cfg](Password const & password) + { + mqtt_client_cfg.password = password.data.c_str(); + }, + [](ClientCertificate const & certificate) {}, + [](SecureElement const & enable_secure_element) {}, + []([[maybe_unused ]]auto & unknown) + { + static_assert(always_false, "Missing type handler for variant handler"); + } + }, credentials.authentication); +} + +esp_mqtt_client_config_t make_config(BrokerConfiguration const &broker, ClientCredentials const &credentials, Configuration const &config) +{ + esp_mqtt_client_config_t mqtt_client_cfg{}; + config_broker(mqtt_client_cfg, broker); + config_client_credentials(mqtt_client_cfg, credentials); + return mqtt_client_cfg; +} +} + +namespace idf::mqtt { + +Client::Client(BrokerConfiguration const &broker, ClientCredentials const &credentials, Configuration const &config): Client(make_config(broker, credentials, config)) {} + +Client::Client(esp_mqtt_client_config_t const &config) : handler(esp_mqtt_client_init(&config)) +{ + if (handler == nullptr) { + throw MQTTException(ESP_FAIL); + }; + CHECK_THROW_SPECIFIC(esp_mqtt_client_register_event(handler.get(), MQTT_EVENT_ANY, mqtt_event_handler, this), mqtt::MQTTException); + CHECK_THROW_SPECIFIC(esp_mqtt_client_start(handler.get()), mqtt::MQTTException); +} + + +void Client::mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, void *event_data) noexcept +{ + ESP_LOGD(TAG, "Event dispatched from event loop base=%s, event_id=%d", base, event_id); + auto *event = static_cast(event_data); + auto &client = *static_cast(handler_args); + switch (event->event_id) { + case MQTT_EVENT_CONNECTED: + ESP_LOGI(TAG, "MQTT_EVENT_CONNECTED"); + client.on_connected(event); + break; + case MQTT_EVENT_DISCONNECTED: + ESP_LOGI(TAG, "MQTT_EVENT_DISCONNECTED"); + client.on_disconnected(event); + break; + + case MQTT_EVENT_SUBSCRIBED: + ESP_LOGI(TAG, "MQTT_EVENT_SUBSCRIBED, msg_id=%d", event->msg_id); + client.on_subscribed(event); + break; + case MQTT_EVENT_UNSUBSCRIBED: + ESP_LOGI(TAG, "MQTT_EVENT_UNSUBSCRIBED, msg_id=%d", event->msg_id); + client.on_unsubscribed(event); + break; + case MQTT_EVENT_PUBLISHED: + ESP_LOGI(TAG, "MQTT_EVENT_PUBLISHED, msg_id=%d", event->msg_id); + client.on_published(event); + break; + case MQTT_EVENT_DATA: + ESP_LOGI(TAG, "MQTT_EVENT_DATA"); + client.on_data(event); + break; + case MQTT_EVENT_ERROR: + ESP_LOGI(TAG, "MQTT_EVENT_ERROR"); + client.on_error(event); + break; + case MQTT_EVENT_BEFORE_CONNECT: + ESP_LOGI(TAG, "MQTT_EVENT_BEFORE_CONNECT"); + client.on_before_connect(event); + break; + default: + ESP_LOGI(TAG, "Other event id:%d", event->event_id); + break; + } +} + +void Client::on_error(esp_mqtt_event_handle_t const event) +{ + auto log_error_if_nonzero = [](const char *message, int error_code) { + if (error_code != 0) { + ESP_LOGE(TAG, "Last error %s: 0x%x", message, error_code); + } + }; + if (event->error_handle->error_type == MQTT_ERROR_TYPE_TCP_TRANSPORT) { + log_error_if_nonzero("reported from esp-tls", event->error_handle->esp_tls_last_esp_err); + log_error_if_nonzero("reported from tls stack", event->error_handle->esp_tls_stack_err); + log_error_if_nonzero("captured as transport's socket errno", event->error_handle->esp_transport_sock_errno); + ESP_LOGI(TAG, "Last errno string (%s)", strerror(event->error_handle->esp_transport_sock_errno)); + } +} +void Client::on_disconnected(esp_mqtt_event_handle_t const event) +{ +} +void Client::on_subscribed(esp_mqtt_event_handle_t const event) +{ + printf("Subscribed to %.*s\r\n", event->topic_len, event->topic); +} +void Client::on_unsubscribed(esp_mqtt_event_handle_t const event) +{ +} +void Client::on_published(esp_mqtt_event_handle_t const event) +{ +} +void Client::on_before_connect(esp_mqtt_event_handle_t const event) +{ +} +void Client::on_connected(esp_mqtt_event_handle_t const event) +{ +} +void Client::on_data(esp_mqtt_event_handle_t const event) +{ +} + +std::optional Client::subscribe(std::string const &topic, QoS qos) +{ + auto res = esp_mqtt_client_subscribe(handler.get(), topic.c_str(), + static_cast(qos)); + if (res < 0) { + return std::nullopt; + } + return MessageID{res}; +} + +bool is_valid(std::string::const_iterator first, std::string::const_iterator last) +{ + if (first == last) { + return false; + } + auto number = std::find(first, last, '#'); + if (number != last) { + if (std::next(number) != last) { + return false; + } + if (*std::prev(number) != '/' && number != first) { + return false; + } + } + + auto plus = std::find(first, last, '+'); + if (plus != last) { + if (*(std::prev(plus)) != '/' && plus != first) { + return false; + } + if (std::next(plus) != last && *(std::next(plus)) != '/') { + return false; + } + } + return true; +} + +Filter::Filter(std::string user_filter) : filter(std::move(user_filter)) +{ + if (!is_valid(filter.begin(), filter.end())) { + throw std::domain_error("Forbidden Filter string"); + } +} + +[[nodiscard]] bool Filter::match(std::string::const_iterator topic_begin, std::string::const_iterator topic_end) const noexcept +{ + auto filter_begin = filter.begin(); + auto filter_end = filter.end(); + for (auto mismatch = std::mismatch(filter_begin, filter_end, topic_begin); + mismatch.first != filter.end() and mismatch.second != topic_end; + mismatch = std::mismatch(filter_begin, filter_end, topic_begin)) { + if (*mismatch.first != '#' and * mismatch.first != '+') { + return false; + } + if (*mismatch.first == '#') { + return true; + } + if (*mismatch.first == '+') { + filter_begin = advance(mismatch.first, filter_end); + topic_begin = advance(mismatch.second, topic_end); + if (filter_begin == filter_end and topic_begin != topic_end) { + return false; + } + } + } + return true; +} +const std::string &Filter::get() +{ + return filter; +} + +[[nodiscard]] bool Filter::match(char const *const first, int size) const noexcept +{ + auto it = static_cast(first); + return match(it, it + size); +} +std::string::const_iterator Filter::advance(std::string::const_iterator first, std::string::const_iterator last) const +{ + constexpr auto separator = '/'; + return std::find(first, last, separator); +} + +} diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp new file mode 100644 index 000000000..9d071f247 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp @@ -0,0 +1,229 @@ +// Copyright 2021 Espressif Systems (Shanghai) CO LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +#pragma once + +#include +#ifndef __cpp_exceptions +#error MQTT class can only be used when __cpp_exceptions is enabled. Enable CONFIG_COMPILER_CXX_EXCEPTIONS in Kconfig +#endif + +#include +#include +#include +#include +#include +#include "esp_exception.hpp" +#include "esp_mqtt_client_config.hpp" +#include "mqtt_client.h" + +namespace idf::mqtt { + +constexpr auto *TAG = "mqtt_client_cpp"; + +struct MQTTException : ESPException { + using ESPException::ESPException; +}; + +/** + * @brief QoS for publish and subscribe + * + * Sets the QoS as: + * AtMostOnce : Best effort delivery of messages. Message loss can occur. + * AtLeastOnce : Guaranteed delivery of messages. Duplicates can occur. + * ExactlyOnce : Guaranteed delivery of messages exactly once. + * + */ +enum class QoS { AtMostOnce = 0, AtLeastOnce = 1, ExactlyOnce = 2 }; + +/** + * @brief Sets if a message must be retained. + * + * Retained messages are delivered to future subscribers that match the topic name. + * + */ +enum class Retain : bool { NotRetained = false, Retained = true }; + + +/** + * @brief Message class template to publish. + * + */ +template struct Message { + T data; /*!< Data for publish. Should be a contiguous type*/ + QoS qos = QoS::AtLeastOnce; /*!< QoS for the message*/ + Retain retain = Retain::NotRetained; /*!< Retention mark for the message.*/ +}; + +/** + * @brief Message type that holds std::string for data + * + */ +using StringMessage = Message; + +[[nodiscard]] bool filter_is_valid(std::string::const_iterator first, std::string::const_iterator last); + +/** + * @brief Filter for mqtt topic subscription. + * @throws std::domain_error if the filter is invalid. + * + * Topic filter. + * + */ +class Filter { +public: + + explicit Filter(std::string user_filter); + + + /** + * @brief Get the filter string used. + * + */ + const std::string &get(); + + /** + * @brief Checks the filter string against a topic name. + * + * @param first Iterator to the beginning of the sequence. + * @param last Iterator to the end of the sequence. + * + * @return true if the topic name match the filter + */ + [[nodiscard]] bool match(std::string::const_iterator first, + std::string::const_iterator last) const noexcept; + + /** + * @brief Checks the filter string against a topic name. + * + * @param topic topic name + * + * @return true if the topic name match the filter + */ + [[nodiscard]] bool match(const std::string &topic) const noexcept; + + /** + * @brief Checks the filter string against a topic name. + * + * @param first Char array with topic name. + * @param last Size of given topic name. + * + * @return true if the topic name match the filter + */ + [[nodiscard]] bool match(const char *const begin, int size) const noexcept; + + +private: + + /** + * @brief Advance the topic to the next level. + * + * An mqtt topic ends with a /. This function is used to iterate in topic levels. + * + * @return Iterator to the start of the topic. + */ + [[nodiscard]] std::string::const_iterator advance(std::string::const_iterator begin, std::string::const_iterator end) const; + std::string filter; +}; + +/** + * @brief Message identifier to track delivery. + * + */ +enum class MessageID : int {}; + +/** + * @brief Base class for MQTT client + * + * Should be inherited to provide event handlers. + */ +class Client { +public: + + Client(const BrokerConfiguration &broker,const ClientCredentials &credentials,const Configuration &config); + + Client(const esp_mqtt_client_config_t &config); + + /** + * @brief Subscribe to topic + * + * @param filter + * @param qos QoS subscription, defaulted as QoS::AtLeastOnce + * + * @return Optional MessageID. In case of failure std::nullopt is returned. + */ + std::optional subscribe(const std::string &filter, QoS qos = QoS::AtLeastOnce); + + /** + * @brief publish message to topic + * + * @tparam Container Type for data container. Must be a contiguous memory. + * @param topic Topic name + * @param message Message struct containing data, qos and retain configuration. + * + * @return Optional MessageID. In case of failure std::nullopt is returned. + */ + template std::optional publish(const std::string &topic, const Message& message) + { + return publish(topic, std::begin(message.data), std::end(message.data), message.qos, message.retain); + } + + /** + * @brief publish message to topic + * + * @tparam InputIt Input data iterator type. + * @param topic Topic name + * @param first, last Iterator pair of data to publish + * @param message Message struct containing data, qos and retain configuration. + * + * @return Optional MessageID. In case of failure std::nullopt is returned. + */ + template + std::optional publish(const std::string &topic, InputIt first, InputIt last, QoS qos = QoS::AtLeastOnce, Retain retain = Retain::NotRetained) + { + auto size = std::distance(first, last); + auto res = esp_mqtt_client_publish(handler.get(), topic.c_str(), &(*first), size, static_cast(qos), + static_cast(retain)); + if (res < 0) { + return std::nullopt; + } + return MessageID{res}; + } + + virtual ~Client() = default; + +protected: + struct MqttClientDeleter { + void operator()(esp_mqtt_client *client_handler) + { + esp_mqtt_client_destroy(client_handler); + } + }; + + using ClientHandler = std::unique_ptr; + ClientHandler handler; + +private: + static void mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, + void *event_data) noexcept; + void init(const esp_mqtt_client_config_t &config); + virtual void on_error(const esp_mqtt_event_handle_t event); + virtual void on_disconnected(const esp_mqtt_event_handle_t event); + virtual void on_subscribed(const esp_mqtt_event_handle_t event); + virtual void on_unsubscribed(const esp_mqtt_event_handle_t event); + virtual void on_published(const esp_mqtt_event_handle_t event); + virtual void on_before_connect(const esp_mqtt_event_handle_t event); + virtual void on_connected(const esp_mqtt_event_handle_t event) = 0; + virtual void on_data(const esp_mqtt_event_handle_t event) = 0; +}; +} // namespace idf::mqtt diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp new file mode 100644 index 000000000..0fbba636f --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp @@ -0,0 +1,221 @@ +// Copyright 2021 Espressif Systems (Shanghai) CO LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +#pragma once + +#include +#include +#include +#include +#include + +#include "mqtt_client.h" + +namespace idf::mqtt { + + + +/** + * @brief Broker addresss + * + * Use this to set the broker without parsing the URI string. + * + */ +struct Host { + std::string address; /*!< Host name*/ + std::string path; /*!< Route path of the broker in host*/ + esp_mqtt_transport_t transport; /*!< Transport scheme to use. */ +}; + +/** + * @brief Broker addresss URI + * + * Use this to set the broker address using the URI. + * + */ +struct URI { + std::string address; /*!< Broker adddress URI*/ +}; + + +/** + * @brief Broker addresss. + * + */ +struct BrokerAddress { + std::variant address; /*!< Address, defined by URI or Host struct */ + uint32_t port = 0; /*!< Port used, defaults to 0 to select common port for the scheme used */ +}; + +/** + * @brief PEM formated data + * + * Store certificates, keys and cryptographic data. + * + */ +struct PEM { + const char *data; +}; + +/** + * @brief DER formated data + * + * Store certificates, keys and cryptographic data. + * + */ +struct DER { + const char *data; + size_t len; +}; + +/** + * @brief Holds cryptography related information + * + * Hold PEM or DER formated cryptographic data. + * + */ +using CryptographicInformation = std::variant; + + +/** + * @brief Do not verify broker certificate. + * + * To be used when doing MQTT over TLS connection but not verify broker's certificates. + * + */ +struct Insecure {}; + +/** + * @brief Use global CA store + * + * To be used when client should use the Global CA Store to get trusted certificates for the broker. + * + */ +struct GlobalCAStore {}; + +/** + * @brief Use a pre shared key for broker authentication. + * + * To be used when client should use a PSK to authenticate the broker. + * + */ +struct PSK { + const struct psk_key_hint *hint_key;/* Pointer to PSK struct defined in esp_tls.h to enable PSK authentication */ +}; + + +/** + * @brief Authentication method for Broker + * + * Selects the method for authentication based on the type it holds. + * + */ +using BrokerAuthentication = std::variant; + +/** + * @brief Password related data. + * + */ +struct Password { + std::string data; +}; + +/** + * @brief Data to authenticate client with certificates. + * + */ +struct ClientCertificate { + CryptographicInformation certificate; /*!< Certificate in PEM or DER format.*/ + CryptographicInformation key; /*!< Key data in PEM or DER format.*/ + std::optional key_password = std::nullopt; /*!< Optional password for key */ +}; + +/** + * @brief Used to select usage of Secure Element + * + * Enables the usage of the secure element present in ESP32-WROOM-32SE. + * + */ +struct SecureElement {}; + + +/** + * @brief Used to select usage of Digital Signature Peripheral. + * + * Enables the usage of the Digital Signature hardware accelerator. + * + */ +struct DigitalSignatureData { + void *ds_data; /* carrier of handle for digital signature parameters */ +}; + +using AuthenticationFactor = std::variant; + +struct BrokerConfiguration { + BrokerAddress address; + BrokerAuthentication security; +}; + +struct ClientCredentials { + std::optional username; // MQTT username + AuthenticationFactor authentication; + std::vector alpn_protos; /*!< List of supported application protocols to be used for ALPN */ + /* default is ``ESP32_%CHIPID%`` where %CHIPID% are last 3 bytes of MAC address in hex format */ + std::optional client_id = std::nullopt; +}; + +struct Event { + mqtt_event_callback_t event_handle; /*!< handle for MQTT events as a callback in legacy mode */ + esp_event_loop_handle_t event_loop_handle; /*!< handle for MQTT event loop library */ +}; + +struct LastWill { + const char *lwt_topic; /*!< LWT (Last Will and Testament) message topic (NULL by default) */ + const char *lwt_msg; /*!< LWT message (NULL by default) */ + int lwt_qos; /*!< LWT message qos */ + int lwt_retain; /*!< LWT retained message flag */ + int lwt_msg_len; /*!< LWT message length */ +}; + +struct Session { + LastWill last_will; + int disable_clean_session; /*!< mqtt clean session, default clean_session is true */ + int keepalive; /*!< mqtt keepalive, default is 120 seconds */ + bool disable_keepalive; /*!< Set disable_keepalive=true to turn off keep-alive mechanism, false by default (keepalive is active by default). Note: setting the config value `keepalive` to `0` doesn't disable keepalive feature, but uses a default keepalive period */ + esp_mqtt_protocol_ver_t protocol_ver; /*!< MQTT protocol version used for connection, defaults to value from menuconfig*/ +}; + +struct Task { + int task_prio; /*!< MQTT task priority, default is 5, can be changed in ``make menuconfig`` */ + int task_stack; /*!< MQTT task stack size, default is 6144 bytes, can be changed in ``make menuconfig`` */ +}; + +struct Connection { + esp_mqtt_transport_t transport; /*!< overrides URI transport */ + int reconnect_timeout_ms; /*!< Reconnect to the broker after this value in miliseconds if auto reconnect is not disabled (defaults to 10s) */ + int network_timeout_ms; /*!< Abort network operation if it is not completed after this value, in milliseconds (defaults to 10s) */ + int refresh_connection_after_ms; /*!< Refresh connection after this value (in milliseconds) */ + bool disable_auto_reconnect; /*!< this mqtt client will reconnect to server (when errors/disconnect). Set disable_auto_reconnect=true to disable */ +}; + +struct Configuration { + Event event; + Task task; + Session session; + Connection connection; + void *user_context; /*!< pass user context to this option, then can receive that context in ``event->user_context`` */ + int buffer_size; /*!< size of MQTT send/receive buffer, default is 1024 (only receive buffer size if ``out_buffer_size`` defined) */ + int out_buffer_size; /*!< size of MQTT output buffer. If not defined, both output and input buffers have the same size defined as ``buffer_size`` */ +}; + +} // idf::mqtt diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt new file mode 100644 index 000000000..a5f94f087 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt @@ -0,0 +1,14 @@ +# The following four lines of boilerplate have to be in your project's CMakeLists +# in this exact order for cmake to work correctly +cmake_minimum_required(VERSION 3.5) + +# (Not part of the boilerplate) +# This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. +set(EXTRA_COMPONENT_DIRS $ENV{IDF_PATH}/examples/common_components/protocol_examples_common + $ENV{IDF_PATH}/examples/cxx/experimental/experimental_cpp_component + $ENV{IDF_PATH}/examples/cxx/experimental/esp_mqtt_cxx/components) + +include($ENV{IDF_PATH}/tools/cmake/project.cmake) +project(mqtt_ssl_cxx) + +target_add_binary_data(mqtt_ssl_cxx.elf "main/mqtt_eclipseprojects_io.pem" TEXT) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile b/examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile new file mode 100644 index 000000000..392ad4a33 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile @@ -0,0 +1,12 @@ +# +# This is a project Makefile. It is assumed the directory this Makefile resides in is a +# project subdirectory. +# +PROJECT_NAME := mqtt_tcp_cxx + +EXTRA_COMPONENT_DIRS := $(IDF_PATH)/examples/common_components/protocol_examples_common +EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/esp_mqtt_cxx/components +EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/experimental_cpp_component + +CXXFLAGS += -std=gnu++17 +include $(IDF_PATH)/make/project.mk diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt new file mode 100644 index 000000000..9871f4c78 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt @@ -0,0 +1,4 @@ +idf_component_register(SRCS "mqtt_ssl_example.cpp" + INCLUDE_DIRS ".") + +target_compile_options(${COMPONENT_LIB} PRIVATE "-std=gnu++17") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild new file mode 100644 index 000000000..6d8dc0a35 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild @@ -0,0 +1,9 @@ +menu "Example Configuration" + + config BROKER_URI + string "Broker URL" + default "mqtts://mqtt.eclipse.org:8883" + help + URL of the broker to connect to + +endmenu diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk new file mode 100644 index 000000000..c0c0f87e6 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk @@ -0,0 +1 @@ +COMPONENT_EMBED_TXTFILES := mqtt_eclipseprojects_io.pem diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipse_org.pem b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipse_org.pem new file mode 100644 index 000000000..0002462ce --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipse_org.pem @@ -0,0 +1,27 @@ +-----BEGIN CERTIFICATE----- +MIIEkjCCA3qgAwIBAgIQCgFBQgAAAVOFc2oLheynCDANBgkqhkiG9w0BAQsFADA/ +MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT +DkRTVCBSb290IENBIFgzMB4XDTE2MDMxNzE2NDA0NloXDTIxMDMxNzE2NDA0Nlow +SjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUxldCdzIEVuY3J5cHQxIzAhBgNVBAMT +GkxldCdzIEVuY3J5cHQgQXV0aG9yaXR5IFgzMIIBIjANBgkqhkiG9w0BAQEFAAOC +AQ8AMIIBCgKCAQEAnNMM8FrlLke3cl03g7NoYzDq1zUmGSXhvb418XCSL7e4S0EF +q6meNQhY7LEqxGiHC6PjdeTm86dicbp5gWAf15Gan/PQeGdxyGkOlZHP/uaZ6WA8 +SMx+yk13EiSdRxta67nsHjcAHJyse6cF6s5K671B5TaYucv9bTyWaN8jKkKQDIZ0 +Z8h/pZq4UmEUEz9l6YKHy9v6Dlb2honzhT+Xhq+w3Brvaw2VFn3EK6BlspkENnWA +a6xK8xuQSXgvopZPKiAlKQTGdMDQMc2PMTiVFrqoM7hD8bEfwzB/onkxEz0tNvjj +/PIzark5McWvxI0NHWQWM6r6hCm21AvA2H3DkwIDAQABo4IBfTCCAXkwEgYDVR0T +AQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8EBAMCAYYwfwYIKwYBBQUHAQEEczBxMDIG +CCsGAQUFBzABhiZodHRwOi8vaXNyZy50cnVzdGlkLm9jc3AuaWRlbnRydXN0LmNv +bTA7BggrBgEFBQcwAoYvaHR0cDovL2FwcHMuaWRlbnRydXN0LmNvbS9yb290cy9k +c3Ryb290Y2F4My5wN2MwHwYDVR0jBBgwFoAUxKexpHsscfrb4UuQdf/EFWCFiRAw +VAYDVR0gBE0wSzAIBgZngQwBAgEwPwYLKwYBBAGC3xMBAQEwMDAuBggrBgEFBQcC +ARYiaHR0cDovL2Nwcy5yb290LXgxLmxldHNlbmNyeXB0Lm9yZzA8BgNVHR8ENTAz +MDGgL6AthitodHRwOi8vY3JsLmlkZW50cnVzdC5jb20vRFNUUk9PVENBWDNDUkwu +Y3JsMB0GA1UdDgQWBBSoSmpjBH3duubRObemRWXv86jsoTANBgkqhkiG9w0BAQsF +AAOCAQEA3TPXEfNjWDjdGBX7CVW+dla5cEilaUcne8IkCJLxWh9KEik3JHRRHGJo +uM2VcGfl96S8TihRzZvoroed6ti6WqEBmtzw3Wodatg+VyOeph4EYpr/1wXKtx8/ +wApIvJSwtmVi4MFU5aMqrSDE6ea73Mj2tcMyo5jMd6jmeWUHK8so/joWUoHOUgwu +X4Po1QYz+3dszkDqMp4fklxBwXRsW10KXzPMTZ+sOPAveyxindmjkW8lGy+QsRlG +PfZ+G6Z6h7mjem0Y+iWlkYcV4PIWL1iwBi8saCbGS5jN2p8M+X+Q7UNKEkROb3N6 +KOqkqm57TH2H3eDJAkSnh6/DNFu0Qg== +-----END CERTIFICATE----- diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipseprojects_io.pem b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipseprojects_io.pem new file mode 100644 index 000000000..43b222a60 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipseprojects_io.pem @@ -0,0 +1,30 @@ +-----BEGIN CERTIFICATE----- +MIIFFjCCAv6gAwIBAgIRAJErCErPDBinU/bWLiWnX1owDQYJKoZIhvcNAQELBQAw +TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh +cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMjAwOTA0MDAwMDAw +WhcNMjUwOTE1MTYwMDAwWjAyMQswCQYDVQQGEwJVUzEWMBQGA1UEChMNTGV0J3Mg +RW5jcnlwdDELMAkGA1UEAxMCUjMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK +AoIBAQC7AhUozPaglNMPEuyNVZLD+ILxmaZ6QoinXSaqtSu5xUyxr45r+XXIo9cP +R5QUVTVXjJ6oojkZ9YI8QqlObvU7wy7bjcCwXPNZOOftz2nwWgsbvsCUJCWH+jdx +sxPnHKzhm+/b5DtFUkWWqcFTzjTIUu61ru2P3mBw4qVUq7ZtDpelQDRrK9O8Zutm +NHz6a4uPVymZ+DAXXbpyb/uBxa3Shlg9F8fnCbvxK/eG3MHacV3URuPMrSXBiLxg +Z3Vms/EY96Jc5lP/Ooi2R6X/ExjqmAl3P51T+c8B5fWmcBcUr2Ok/5mzk53cU6cG +/kiFHaFpriV1uxPMUgP17VGhi9sVAgMBAAGjggEIMIIBBDAOBgNVHQ8BAf8EBAMC +AYYwHQYDVR0lBBYwFAYIKwYBBQUHAwIGCCsGAQUFBwMBMBIGA1UdEwEB/wQIMAYB +Af8CAQAwHQYDVR0OBBYEFBQusxe3WFbLrlAJQOYfr52LFMLGMB8GA1UdIwQYMBaA +FHm0WeZ7tuXkAXOACIjIGlj26ZtuMDIGCCsGAQUFBwEBBCYwJDAiBggrBgEFBQcw +AoYWaHR0cDovL3gxLmkubGVuY3Iub3JnLzAnBgNVHR8EIDAeMBygGqAYhhZodHRw +Oi8veDEuYy5sZW5jci5vcmcvMCIGA1UdIAQbMBkwCAYGZ4EMAQIBMA0GCysGAQQB +gt8TAQEBMA0GCSqGSIb3DQEBCwUAA4ICAQCFyk5HPqP3hUSFvNVneLKYY611TR6W +PTNlclQtgaDqw+34IL9fzLdwALduO/ZelN7kIJ+m74uyA+eitRY8kc607TkC53wl +ikfmZW4/RvTZ8M6UK+5UzhK8jCdLuMGYL6KvzXGRSgi3yLgjewQtCPkIVz6D2QQz +CkcheAmCJ8MqyJu5zlzyZMjAvnnAT45tRAxekrsu94sQ4egdRCnbWSDtY7kh+BIm +lJNXoB1lBMEKIq4QDUOXoRgffuDghje1WrG9ML+Hbisq/yFOGwXD9RiX8F6sw6W4 +avAuvDszue5L3sz85K+EC4Y/wFVDNvZo4TYXao6Z0f+lQKc0t8DQYzk1OXVu8rp2 +yJMC6alLbBfODALZvYH7n7do1AZls4I9d1P4jnkDrQoxB3UqQ9hVl3LEKQ73xF1O +yK5GhDDX8oVfGKF5u+decIsH4YaTw7mP3GFxJSqv3+0lUFJoi5Lc5da149p90Ids +hCExroL1+7mryIkXPeFM5TgO9r0rvZaBFOvV2z0gp35Z0+L4WPlbuEjN/lxPFin+ +HlUjr8gRsI3qfJOQFy/9rKIJR0Y/8Omwt/8oTWgy1mdeHmmjk7j1nYsvC9JSQ6Zv +MldlTTKB3zhThV1+XWYp6rjd5JW1zbVWEkLNxE7GJThEUG3szgBVGP7pSWTUTsqX +nLRbwHOoq7hHwg== +-----END CERTIFICATE----- diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp new file mode 100644 index 000000000..8493d52d0 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp @@ -0,0 +1,85 @@ +/* C++ MQTT (over TCP) Example + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. +*/ + +#include +#include +#include "esp_mqtt_client_config.hpp" +#include "nvs_flash.h" +#include "protocol_examples_common.h" + + +#include "esp_log.h" +#include "esp_mqtt.hpp" + +namespace { +constexpr auto *TAG = "MQTT_EXAMPLE"; + +extern const char mqtt_eclipse_org_pem_start[] asm("_binary_mqtt_eclipseprojects_io_pem_start"); +extern const char mqtt_eclipse_org_pem_end[] asm("_binary_mqtt_eclipseprojects_io_pem_end"); + +class MyClient final : public idf::mqtt::Client { +public: + using idf::mqtt::Client::Client; +private: + void on_connected(esp_mqtt_event_handle_t const event) override + { + using idf::mqtt::QoS; + subscribe(messages.get()); + subscribe(sent_load.get(), QoS::AtMostOnce); + } + void on_data(esp_mqtt_event_handle_t const event) override + { + if (messages.match(event->topic, event->topic_len)) { + ESP_LOGI(TAG, "Received in the messages topic"); + } + } + idf::mqtt::Filter messages{std::string{"$SYS/broker/messages/received"}}; + idf::mqtt::Filter sent_load{std::string{"$SYS/broker/load/+/sent"}}; +}; +} + +namespace mqtt = idf::mqtt; + +extern "C" void app_main(void) +{ + ESP_LOGI(TAG, "[APP] Startup.."); + ESP_LOGI(TAG, "[APP] Free memory: %d bytes", esp_get_free_heap_size()); + ESP_LOGI(TAG, "[APP] IDF version: %s", esp_get_idf_version()); + + esp_log_level_set("*", ESP_LOG_INFO); + esp_log_level_set("MQTT_CLIENT", ESP_LOG_VERBOSE); + esp_log_level_set("MQTT_EXAMPLE", ESP_LOG_VERBOSE); + esp_log_level_set("TRANSPORT_TCP", ESP_LOG_VERBOSE); + esp_log_level_set("TRANSPORT_SSL", ESP_LOG_VERBOSE); + esp_log_level_set("TRANSPORT", ESP_LOG_VERBOSE); + esp_log_level_set("OUTBOX", ESP_LOG_VERBOSE); + + ESP_ERROR_CHECK(nvs_flash_init()); + ESP_ERROR_CHECK(esp_netif_init()); + ESP_ERROR_CHECK(esp_event_loop_create_default()); + + /* This helper function configures Wi-Fi or Ethernet, as selected in menuconfig. + * Read "Establishing Wi-Fi or Ethernet Connection" section in + * examples/protocols/README.md for more information about this function. + */ + ESP_ERROR_CHECK(example_connect()); + + mqtt::BrokerConfiguration broker{ + .address = {mqtt::URI{std::string{CONFIG_BROKER_URI}}}, + .security = mqtt::CryptographicInformation{mqtt::PEM{mqtt_eclipse_org_pem_start}} + }; + idf::mqtt::ClientCredentials credentials{}; + idf::mqtt::Configuration config{}; + + MyClient client{broker, credentials, config}; + while (true) { + constexpr TickType_t xDelay = 500 / portTICK_PERIOD_MS; + vTaskDelay( xDelay ); + } +} diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/sdkconfig.defaults b/examples/cxx/experimental/esp_mqtt_cxx/ssl/sdkconfig.defaults new file mode 100644 index 000000000..a365ac658 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/sdkconfig.defaults @@ -0,0 +1,3 @@ +# Enable C++ exceptions and set emergency pool size for exception objects +CONFIG_COMPILER_CXX_EXCEPTIONS=y +CONFIG_COMPILER_CXX_EXCEPTIONS_EMG_POOL_SIZE=1024 diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt new file mode 100644 index 000000000..29bdec289 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt @@ -0,0 +1,12 @@ +# The following four lines of boilerplate have to be in your project's CMakeLists +# in this exact order for cmake to work correctly +cmake_minimum_required(VERSION 3.5) + +# (Not part of the boilerplate) +# This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. +set(EXTRA_COMPONENT_DIRS $ENV{IDF_PATH}/examples/common_components/protocol_examples_common + $ENV{IDF_PATH}/examples/cxx/experimental/experimental_cpp_component + $ENV{IDF_PATH}/examples/cxx/experimental/esp_mqtt_cxx/components) + +include($ENV{IDF_PATH}/tools/cmake/project.cmake) +project(mqtt_tcp_cxx) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile b/examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile new file mode 100644 index 000000000..392ad4a33 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile @@ -0,0 +1,12 @@ +# +# This is a project Makefile. It is assumed the directory this Makefile resides in is a +# project subdirectory. +# +PROJECT_NAME := mqtt_tcp_cxx + +EXTRA_COMPONENT_DIRS := $(IDF_PATH)/examples/common_components/protocol_examples_common +EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/esp_mqtt_cxx/components +EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/experimental_cpp_component + +CXXFLAGS += -std=gnu++17 +include $(IDF_PATH)/make/project.mk diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt new file mode 100644 index 000000000..07fa3e75c --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt @@ -0,0 +1,3 @@ +idf_component_register(SRCS "mqtt_tcp_example.cpp" + INCLUDE_DIRS ".") +target_compile_options(${COMPONENT_LIB} PRIVATE "-std=gnu++17") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild new file mode 100644 index 000000000..34c04a02c --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild @@ -0,0 +1,9 @@ +menu "Example Configuration" + + config BROKER_URL + string "Broker URL" + default "mqtt://mqtt.eclipse.org" + help + URL of the broker to connect to + +endmenu diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/component.mk b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/component.mk new file mode 100644 index 000000000..e69de29bb diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp new file mode 100644 index 000000000..edfb53550 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp @@ -0,0 +1,81 @@ +/* C++ MQTT (over TCP) Example + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. +*/ + +#include "nvs_flash.h" +#include "protocol_examples_common.h" + +#include "esp_log.h" +#include "esp_mqtt.hpp" +#include "esp_mqtt_client_config.hpp" + +namespace mqtt = idf::mqtt; + +namespace { +constexpr auto *TAG = "MQTT_EXAMPLE"; + +class MyClient final : public mqtt::Client { +public: + using mqtt::Client::Client; + +private: + void on_connected(esp_mqtt_event_handle_t const event) override + { + using mqtt::QoS; + subscribe(messages.get()); + subscribe(sent_load.get(), QoS::AtMostOnce); + } + void on_data(esp_mqtt_event_handle_t const event) override + { + if (messages.match(event->topic, event->topic_len)) { + ESP_LOGI(TAG, "Received in the messages topic"); + } + } + mqtt::Filter messages{"$SYS/broker/messages/received"}; + mqtt::Filter sent_load{"$SYS/broker/load/+/sent"}; +}; +} + +extern "C" void app_main(void) +{ + ESP_LOGI(TAG, "[APP] Startup.."); + ESP_LOGI(TAG, "[APP] Free memory: %d bytes", esp_get_free_heap_size()); + ESP_LOGI(TAG, "[APP] IDF version: %s", esp_get_idf_version()); + + esp_log_level_set("*", ESP_LOG_INFO); + esp_log_level_set("MQTT_CLIENT", ESP_LOG_VERBOSE); + esp_log_level_set("MQTT_EXAMPLE", ESP_LOG_VERBOSE); + esp_log_level_set("TRANSPORT_TCP", ESP_LOG_VERBOSE); + esp_log_level_set("TRANSPORT_SSL", ESP_LOG_VERBOSE); + esp_log_level_set("TRANSPORT", ESP_LOG_VERBOSE); + esp_log_level_set("OUTBOX", ESP_LOG_VERBOSE); + + ESP_ERROR_CHECK(nvs_flash_init()); + ESP_ERROR_CHECK(esp_netif_init()); + ESP_ERROR_CHECK(esp_event_loop_create_default()); + + /* This helper function configures Wi-Fi or Ethernet, as selected in menuconfig. + * Read "Establishing Wi-Fi or Ethernet Connection" section in + * examples/protocols/README.md for more information about this function. + */ + ESP_ERROR_CHECK(example_connect()); + + mqtt::BrokerConfiguration broker{ + .address = {mqtt::URI{std::string{CONFIG_BROKER_URL}}}, + .security = mqtt::Insecure{} + }; + mqtt::ClientCredentials credentials{}; + mqtt::Configuration config{}; + + MyClient client{broker, credentials, config}; + + while (true) { + constexpr TickType_t xDelay = 500 / portTICK_PERIOD_MS; + vTaskDelay(xDelay); + } +} diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults b/examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults new file mode 100644 index 000000000..a365ac658 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults @@ -0,0 +1,3 @@ +# Enable C++ exceptions and set emergency pool size for exception objects +CONFIG_COMPILER_CXX_EXCEPTIONS=y +CONFIG_COMPILER_CXX_EXCEPTIONS_EMG_POOL_SIZE=1024 From 4f013e3522f4ebb199030684c05d6c21861c511c Mon Sep 17 00:00:00 2001 From: Roland Dobai Date: Fri, 5 Nov 2021 15:38:25 +0100 Subject: [PATCH 02/10] Build & config: Remove leftover files from the unsupported "make" build system --- .../components/esp_mqtt_cxx/component.mk | 5 ----- examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile | 12 ------------ .../experimental/esp_mqtt_cxx/ssl/main/component.mk | 1 - examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile | 12 ------------ .../experimental/esp_mqtt_cxx/tcp/main/component.mk | 0 5 files changed, 30 deletions(-) delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/main/component.mk diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk deleted file mode 100644 index 9e4987ab4..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/component.mk +++ /dev/null @@ -1,5 +0,0 @@ -COMPONENT_ADD_INCLUDEDIRS := include - -COMPONENT_SRCDIRS := ./ - -CXXFLAGS += -std=gnu++17 diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile b/examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile deleted file mode 100644 index 392ad4a33..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/Makefile +++ /dev/null @@ -1,12 +0,0 @@ -# -# This is a project Makefile. It is assumed the directory this Makefile resides in is a -# project subdirectory. -# -PROJECT_NAME := mqtt_tcp_cxx - -EXTRA_COMPONENT_DIRS := $(IDF_PATH)/examples/common_components/protocol_examples_common -EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/esp_mqtt_cxx/components -EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/experimental_cpp_component - -CXXFLAGS += -std=gnu++17 -include $(IDF_PATH)/make/project.mk diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk deleted file mode 100644 index c0c0f87e6..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/component.mk +++ /dev/null @@ -1 +0,0 @@ -COMPONENT_EMBED_TXTFILES := mqtt_eclipseprojects_io.pem diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile b/examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile deleted file mode 100644 index 392ad4a33..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/Makefile +++ /dev/null @@ -1,12 +0,0 @@ -# -# This is a project Makefile. It is assumed the directory this Makefile resides in is a -# project subdirectory. -# -PROJECT_NAME := mqtt_tcp_cxx - -EXTRA_COMPONENT_DIRS := $(IDF_PATH)/examples/common_components/protocol_examples_common -EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/esp_mqtt_cxx/components -EXTRA_COMPONENT_DIRS += $(IDF_PATH)/examples/cxx/experimental/experimental_cpp_component - -CXXFLAGS += -std=gnu++17 -include $(IDF_PATH)/make/project.mk diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/component.mk b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/component.mk deleted file mode 100644 index e69de29bb..000000000 From 36db37ea2bbe65018a6d726b098d94a057619ac4 Mon Sep 17 00:00:00 2001 From: Anton Maklakov Date: Wed, 26 Jan 2022 13:33:14 +0700 Subject: [PATCH 03/10] examples/cxx: add missing header --- .../components/esp_mqtt_cxx/esp_mqtt_cxx.cpp | 19 ++++++------------- 1 file changed, 6 insertions(+), 13 deletions(-) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp index b5f705b18..9a134cdb6 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp @@ -1,19 +1,12 @@ -// Copyright 2021 Espressif Systems (Shanghai) CO LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. +/* + * SPDX-FileCopyrightText: 2021-2022 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ #include #include +#include #include "mqtt_client.h" #include "esp_log.h" From dda2722563d60998dc296edf75a30aa32f51cf17 Mon Sep 17 00:00:00 2001 From: Djordje Nedic Date: Fri, 27 May 2022 10:10:51 +0200 Subject: [PATCH 04/10] tools: Increase the minimal supported CMake version to 3.16 This updates the minimal supported version of CMake to 3.16, which in turn enables us to use more CMake features and have a cleaner build system. This is the version that provides most new features and also the one we use in our latest docker image for CI. --- examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt | 2 +- examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt index a5f94f087..01cc1fff5 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt @@ -1,6 +1,6 @@ # The following four lines of boilerplate have to be in your project's CMakeLists # in this exact order for cmake to work correctly -cmake_minimum_required(VERSION 3.5) +cmake_minimum_required(VERSION 3.16) # (Not part of the boilerplate) # This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt index 29bdec289..ef6daba53 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt @@ -1,6 +1,6 @@ # The following four lines of boilerplate have to be in your project's CMakeLists # in this exact order for cmake to work correctly -cmake_minimum_required(VERSION 3.5) +cmake_minimum_required(VERSION 3.16) # (Not part of the boilerplate) # This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. From 7b2470ddd61156f5401ee6d5da98ff523437b7b0 Mon Sep 17 00:00:00 2001 From: "Michael (XIAO Xufeng)" Date: Fri, 20 May 2022 17:50:08 +0800 Subject: [PATCH 05/10] ci: partially enable example build for esp32c2 --- examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md | 2 ++ examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md | 2 ++ 2 files changed, 4 insertions(+) create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md create mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md b/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md new file mode 100644 index 000000000..57433de18 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md @@ -0,0 +1,2 @@ +| Supported Targets | ESP32 | ESP32-S2 | ESP32-S3 | ESP32-C3 | ESP32-C2 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md b/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md new file mode 100644 index 000000000..57433de18 --- /dev/null +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md @@ -0,0 +1,2 @@ +| Supported Targets | ESP32 | ESP32-S2 | ESP32-S3 | ESP32-C3 | ESP32-C2 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | From 2865255ec006c0e794c97f05311cf758e32bcdc9 Mon Sep 17 00:00:00 2001 From: Ivan Grokhotkov Date: Fri, 3 Jun 2022 12:50:15 +0200 Subject: [PATCH 06/10] examples, components: remove C/C++ standard overrides ...where they are not necessary after switching to C17 and C++20. --- .../esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt | 2 -- examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt | 2 -- examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt | 1 - 3 files changed, 5 deletions(-) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt index 5dd0329d0..15809a21e 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt @@ -4,8 +4,6 @@ idf_component_register(SRCS "esp_mqtt_cxx.cpp" INCLUDE_DIRS "include" ) -target_compile_options(${COMPONENT_LIB} PRIVATE "-std=gnu++17") - if(TEST_BUILD) message(STATUS "Test build") idf_component_get_property(mqtt_dir mqtt COMPONENT_DIR) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt index 9871f4c78..e06e5975b 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt @@ -1,4 +1,2 @@ idf_component_register(SRCS "mqtt_ssl_example.cpp" INCLUDE_DIRS ".") - -target_compile_options(${COMPONENT_LIB} PRIVATE "-std=gnu++17") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt index 07fa3e75c..eeaa9534e 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt @@ -1,3 +1,2 @@ idf_component_register(SRCS "mqtt_tcp_example.cpp" INCLUDE_DIRS ".") -target_compile_options(${COMPONENT_LIB} PRIVATE "-std=gnu++17") From 256389613ffb1bb602117d21e0fee3f44e223a7f Mon Sep 17 00:00:00 2001 From: Fu Hanxi Date: Wed, 13 Jul 2022 10:41:36 +0800 Subject: [PATCH 07/10] docs: changes docs supported targets tables --- examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md | 2 +- examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md b/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md index 57433de18..b5be4985c 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md @@ -1,2 +1,2 @@ -| Supported Targets | ESP32 | ESP32-S2 | ESP32-S3 | ESP32-C3 | ESP32-C2 | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-S2 | ESP32-S3 | | ----------------- | ----- | -------- | -------- | -------- | -------- | diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md b/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md index 57433de18..b5be4985c 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md @@ -1,2 +1,2 @@ -| Supported Targets | ESP32 | ESP32-S2 | ESP32-S3 | ESP32-C3 | ESP32-C2 | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-S2 | ESP32-S3 | | ----------------- | ----- | -------- | -------- | -------- | -------- | From c674b8855d249ea169a5b65edc5b4bfc508a21db Mon Sep 17 00:00:00 2001 From: Euripedes Rocha Date: Mon, 13 Jun 2022 07:59:11 -0300 Subject: [PATCH 08/10] [MQTT] - Updates esp_mqtt configuration struct - Layered config struct - Fix examples. --- .../components/esp_mqtt_cxx/esp_mqtt_cxx.cpp | 24 +++++++++---------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp index 9a134cdb6..96cb290cc 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp @@ -36,13 +36,13 @@ void config_broker(esp_mqtt_client_config_t &mqtt_client_cfg, BrokerConfiguratio std::visit(overloaded{ [&mqtt_client_cfg](Host const & host) { - mqtt_client_cfg.host = host.address.c_str(); - mqtt_client_cfg.path = host.path.c_str(); - mqtt_client_cfg.transport = host.transport; + mqtt_client_cfg.broker.address.hostname = host.address.c_str(); + mqtt_client_cfg.broker.address.path = host.path.c_str(); + mqtt_client_cfg.broker.address.transport = host.transport; }, [&mqtt_client_cfg](URI const & uri) { - mqtt_client_cfg.uri = uri.address.c_str(); + mqtt_client_cfg.broker.address.uri = uri.address.c_str(); }, []([[maybe_unused ]]auto & unknown) { @@ -55,18 +55,18 @@ void config_broker(esp_mqtt_client_config_t &mqtt_client_cfg, BrokerConfiguratio []([[maybe_unused]]Insecure const & insecure) {}, [&mqtt_client_cfg](GlobalCAStore const & use_global_store) { - mqtt_client_cfg.use_global_ca_store = true; + mqtt_client_cfg.broker.verification.use_global_ca_store = true; }, [&mqtt_client_cfg](CryptographicInformation const & certificates) { std::visit(overloaded{ [&mqtt_client_cfg](PEM const & pem) { - mqtt_client_cfg.cert_pem = pem.data; + mqtt_client_cfg.broker.verification.certificate= pem.data; }, [&mqtt_client_cfg](DER const & der) { - mqtt_client_cfg.cert_pem = der.data; - mqtt_client_cfg.cert_len = der.len; + mqtt_client_cfg.broker.verification.certificate = der.data; + mqtt_client_cfg.broker.verification.certificate_len = der.len; }}, certificates); }, []([[maybe_unused]] PSK const & psk) {}, @@ -76,7 +76,7 @@ void config_broker(esp_mqtt_client_config_t &mqtt_client_cfg, BrokerConfiguratio } }, broker.security); - mqtt_client_cfg.port = broker.address.port; + mqtt_client_cfg.broker.address.port = broker.address.port; } /* @@ -85,12 +85,12 @@ void config_broker(esp_mqtt_client_config_t &mqtt_client_cfg, BrokerConfiguratio */ void config_client_credentials(esp_mqtt_client_config_t &mqtt_client_cfg, ClientCredentials const &credentials) { - mqtt_client_cfg.client_id = credentials.client_id.has_value() ? credentials.client_id.value().c_str() : nullptr ; - mqtt_client_cfg.username = credentials.username.has_value() ? credentials.username.value().c_str() : nullptr ; + mqtt_client_cfg.credentials.client_id = credentials.client_id.has_value() ? credentials.client_id.value().c_str() : nullptr ; + mqtt_client_cfg.credentials.username = credentials.username.has_value() ? credentials.username.value().c_str() : nullptr ; std::visit(overloaded{ [&mqtt_client_cfg](Password const & password) { - mqtt_client_cfg.password = password.data.c_str(); + mqtt_client_cfg.credentials.authentication.password = password.data.c_str(); }, [](ClientCertificate const & certificate) {}, [](SecureElement const & enable_secure_element) {}, From 34c6f52f7093e2e930e404c6ea8a19b2ac7030c7 Mon Sep 17 00:00:00 2001 From: Ivan Grokhotkov Date: Mon, 31 Jan 2022 23:05:03 +0100 Subject: [PATCH 09/10] build system: re-add -Wno-format as private flag for some example components --- .../esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt | 1 + examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt | 1 + examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt | 1 + 3 files changed, 3 insertions(+) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt index 15809a21e..8d40b820a 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt @@ -21,3 +21,4 @@ else() idf_component_get_property(experimental_cpp_component_lib experimental_cpp_component COMPONENT_LIB) target_link_libraries(${COMPONENT_LIB} PUBLIC ${log_lib} ${mqtt_lib} ${experimental_cpp_component_lib}) endif() +target_compile_options(${COMPONENT_LIB} PRIVATE "-Wno-format") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt index e06e5975b..020135ce8 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt @@ -1,2 +1,3 @@ idf_component_register(SRCS "mqtt_ssl_example.cpp" INCLUDE_DIRS ".") +target_compile_options(${COMPONENT_LIB} PRIVATE "-Wno-format") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt index eeaa9534e..f9c2aeec8 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt +++ b/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt @@ -1,2 +1,3 @@ idf_component_register(SRCS "mqtt_tcp_example.cpp" INCLUDE_DIRS ".") +target_compile_options(${COMPONENT_LIB} PRIVATE "-Wno-format") From 1407dfc2e7bec1d4e0b623b1b4947bf6fb346687 Mon Sep 17 00:00:00 2001 From: Euripedes Rocha Date: Thu, 13 Oct 2022 17:17:15 +0200 Subject: [PATCH 10/10] Adds esp_mqtt_cxx component - Component moved from esp-idf - Files moved to adjust to esp-protocol structure --- .github/workflows/target-test.yml | 21 +++ components/esp_mqtt_cxx/CMakeLists.txt | 8 + components/esp_mqtt_cxx/docs/Doxyfile | 73 +++++++++ components/esp_mqtt_cxx/docs/conf_common.py | 23 +++ .../docs/doxygen-known-warnings.txt | 25 ++++ components/esp_mqtt_cxx/docs/en/conf.py | 24 +++ components/esp_mqtt_cxx/docs/en/index.rst | 132 +++++++++++++++++ components/esp_mqtt_cxx/docs/generate_docs | 26 ++++ .../esp_mqtt_cxx/esp_mqtt_cxx.cpp | 12 +- .../esp_mqtt_cxx/examples/ssl/CMakeLists.txt | 14 ++ .../esp_mqtt_cxx/examples}/ssl/README.md | 0 .../examples}/ssl/main/CMakeLists.txt | 0 .../examples}/ssl/main/Kconfig.projbuild | 2 +- .../examples}/ssl/main/mqtt_eclipse_org.pem | 0 .../ssl/main/mqtt_eclipseprojects_io.pem | 0 .../examples}/ssl/main/mqtt_ssl_example.cpp | 5 + .../examples/ssl/pytest_mqtt_ssl.py | 8 + .../examples/ssl/sdkconfig.defaults | 21 +++ .../esp_mqtt_cxx/examples}/tcp/CMakeLists.txt | 6 +- .../esp_mqtt_cxx/examples}/tcp/README.md | 0 .../examples}/tcp/main/CMakeLists.txt | 0 .../examples}/tcp/main/Kconfig.projbuild | 2 +- .../examples}/tcp/main/mqtt_tcp_example.cpp | 5 + .../examples/tcp/pytest_mqtt_tcp.py | 8 + .../examples/tcp}/sdkconfig.defaults | 0 components/esp_mqtt_cxx/idf_component.yml | 8 + .../esp_mqtt_cxx/include/esp_mqtt.hpp | 139 +++++++++++++----- .../include/esp_mqtt_client_config.hpp | 28 ++-- .../examples/CMakeLists.txt | 2 +- .../components/esp_mqtt_cxx/CMakeLists.txt | 24 --- .../esp_mqtt_cxx/ssl/CMakeLists.txt | 14 -- .../esp_mqtt_cxx/tcp/sdkconfig.defaults | 3 - 32 files changed, 526 insertions(+), 107 deletions(-) create mode 100644 components/esp_mqtt_cxx/CMakeLists.txt create mode 100644 components/esp_mqtt_cxx/docs/Doxyfile create mode 100644 components/esp_mqtt_cxx/docs/conf_common.py create mode 100644 components/esp_mqtt_cxx/docs/doxygen-known-warnings.txt create mode 100644 components/esp_mqtt_cxx/docs/en/conf.py create mode 100644 components/esp_mqtt_cxx/docs/en/index.rst create mode 100755 components/esp_mqtt_cxx/docs/generate_docs rename {examples/cxx/experimental/esp_mqtt_cxx/components => components}/esp_mqtt_cxx/esp_mqtt_cxx.cpp (96%) create mode 100644 components/esp_mqtt_cxx/examples/ssl/CMakeLists.txt rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/ssl/README.md (100%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/ssl/main/CMakeLists.txt (100%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/ssl/main/Kconfig.projbuild (72%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/ssl/main/mqtt_eclipse_org.pem (100%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/ssl/main/mqtt_eclipseprojects_io.pem (100%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/ssl/main/mqtt_ssl_example.cpp (95%) create mode 100644 components/esp_mqtt_cxx/examples/ssl/pytest_mqtt_ssl.py create mode 100644 components/esp_mqtt_cxx/examples/ssl/sdkconfig.defaults rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/tcp/CMakeLists.txt (57%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/tcp/README.md (100%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/tcp/main/CMakeLists.txt (100%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/tcp/main/Kconfig.projbuild (74%) rename {examples/cxx/experimental/esp_mqtt_cxx => components/esp_mqtt_cxx/examples}/tcp/main/mqtt_tcp_example.cpp (95%) create mode 100644 components/esp_mqtt_cxx/examples/tcp/pytest_mqtt_tcp.py rename {examples/cxx/experimental/esp_mqtt_cxx/ssl => components/esp_mqtt_cxx/examples/tcp}/sdkconfig.defaults (100%) create mode 100644 components/esp_mqtt_cxx/idf_component.yml rename {examples/cxx/experimental/esp_mqtt_cxx/components => components}/esp_mqtt_cxx/include/esp_mqtt.hpp (65%) rename {examples/cxx/experimental/esp_mqtt_cxx/components => components}/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp (85%) delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt delete mode 100644 examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults diff --git a/.github/workflows/target-test.yml b/.github/workflows/target-test.yml index ab36415eb..9615087e5 100644 --- a/.github/workflows/target-test.yml +++ b/.github/workflows/target-test.yml @@ -179,6 +179,27 @@ jobs: ${{ env.TEST_DIR }}/build/config/sdkconfig.json if-no-files-found: error + build_esp_mqtt_cxx: + strategy: + matrix: + idf_ver: ["latest", "release-v5.0"] + idf_target: ["esp32"] + test: [ { app: example, path: "components/esp_mqtt_cxx/examples" }] + runs-on: ubuntu-20.04 + container: espressif/idf:${{ matrix.idf_ver }} + steps: + - name: Checkout esp-protocols + uses: actions/checkout@v3 + with: + submodules: recursive + - name: Build ${{ matrix.test.app }} with IDF-${{ matrix.idf_ver }} for ${{ matrix.idf_target }} + shell: bash + working-directory: ${{matrix.test.path}} + run: | + ${IDF_PATH}/install.sh --enable-pytest + . ${IDF_PATH}/export.sh + python $IDF_PATH/tools/ci/ci_build_apps.py . --target ${{ matrix.idf_target }} -vv --preserve-all --pytest-app + run-target-websocket: name: Run Websocket Example Test on target needs: build_websocket diff --git a/components/esp_mqtt_cxx/CMakeLists.txt b/components/esp_mqtt_cxx/CMakeLists.txt new file mode 100644 index 000000000..d5fc7eded --- /dev/null +++ b/components/esp_mqtt_cxx/CMakeLists.txt @@ -0,0 +1,8 @@ +idf_build_get_property(target IDF_TARGET) + +idf_component_register(SRCS "esp_mqtt_cxx.cpp" + INCLUDE_DIRS "include" + REQUIRES mqtt + ) + +target_compile_options(${COMPONENT_LIB} PRIVATE "-Wno-format") diff --git a/components/esp_mqtt_cxx/docs/Doxyfile b/components/esp_mqtt_cxx/docs/Doxyfile new file mode 100644 index 000000000..ae20e5feb --- /dev/null +++ b/components/esp_mqtt_cxx/docs/Doxyfile @@ -0,0 +1,73 @@ +# This is Doxygen configuration file +# +# Doxygen provides over 260 configuration statements +# To make this file easier to follow, +# it contains only statements that are non-default +# +# NOTE: +# It is recommended not to change defaults unless specifically required +# Test any changes how they affect generated documentation +# Make sure that correct warnings are generated to flag issues with documented code +# +# For the complete list of configuration statements see: +# http://doxygen.nl/manual/config.html + + +PROJECT_NAME = "MQTT C++ client" + +## The 'INPUT' statement below is used as input by script 'gen-df-input.py' +## to automatically generate API reference list files heder_file.inc +## These files are placed in '_inc' directory +## and used to include in API reference documentation + +INPUT = \ + $(PROJECT_PATH)/include/esp_mqtt.hpp \ + $(PROJECT_PATH)/include/esp_mqtt_client_config.hpp + +## Get warnings for functions that have no documentation for their parameters or return value +## +WARN_NO_PARAMDOC = YES + +## Enable preprocessing and remove __attribute__(...) expressions from the INPUT files +## +ENABLE_PREPROCESSING = YES +MACRO_EXPANSION = YES +EXPAND_ONLY_PREDEF = YES +PREDEFINED = \ + $(ENV_DOXYGEN_DEFINES) \ + __DOXYGEN__=1 \ + __attribute__(x)= \ + _Static_assert()= \ + IDF_DEPRECATED(X)= \ + IRAM_ATTR= \ + configSUPPORT_DYNAMIC_ALLOCATION=1 \ + configSUPPORT_STATIC_ALLOCATION=1 \ + configQUEUE_REGISTRY_SIZE=1 \ + configUSE_RECURSIVE_MUTEXES=1 \ + configTHREAD_LOCAL_STORAGE_DELETE_CALLBACKS=1 \ + configNUM_THREAD_LOCAL_STORAGE_POINTERS=1 \ + configUSE_APPLICATION_TASK_TAG=1 \ + configTASKLIST_INCLUDE_COREID=1 \ + "ESP_EVENT_DECLARE_BASE(x)=extern esp_event_base_t x" + +## Do not complain about not having dot +## +HAVE_DOT = NO + +## Generate XML that is required for Breathe +## +GENERATE_XML = YES +XML_OUTPUT = xml + +GENERATE_HTML = NO +HAVE_DOT = NO +GENERATE_LATEX = NO +GENERATE_MAN = YES + +## Skip distracting progress messages +## +QUIET = YES +## Enable Section Tags for conditional documentation +## +ENABLED_SECTIONS += \ + DOC_EXCLUDE_HEADER_SECTION ## To conditionally remove doc sections from IDF source files without affecting documentation in upstream files. diff --git a/components/esp_mqtt_cxx/docs/conf_common.py b/components/esp_mqtt_cxx/docs/conf_common.py new file mode 100644 index 000000000..abc2b53e3 --- /dev/null +++ b/components/esp_mqtt_cxx/docs/conf_common.py @@ -0,0 +1,23 @@ +# flake8: noqa +from esp_docs.conf_docs import * + +extensions += [ + 'sphinx_copybutton', + # Needed as a trigger for running doxygen + 'esp_docs.esp_extensions.dummy_build_system', + 'esp_docs.esp_extensions.run_doxygen', +] + +# link roles config +github_repo = 'espressif/esp-protocols' + +# context used by sphinx_idf_theme +html_context['github_user'] = 'espressif' +html_context['github_repo'] = 'esp-docs' + +# Extra options required by sphinx_idf_theme +project_slug = 'esp-idf' # >=5.0 +versions_url = 'https://github.com/espressif/esp-protocols/docs/docs_versions.js' + +idf_targets = ['esp32'] +languages = ['en'] diff --git a/components/esp_mqtt_cxx/docs/doxygen-known-warnings.txt b/components/esp_mqtt_cxx/docs/doxygen-known-warnings.txt new file mode 100644 index 000000000..69e27a626 --- /dev/null +++ b/components/esp_mqtt_cxx/docs/doxygen-known-warnings.txt @@ -0,0 +1,25 @@ +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::BrokerConfiguration is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::ClientCredentials is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::Configuration is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::Connection is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::Event is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::LastWill is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::Session is not documented. +esp_mqtt_client_config.hpp:line: warning: Compound idf::mqtt::Task is not documented. +esp_mqtt_client_config.hpp:line: warning: Member address (variable) of struct idf::mqtt::BrokerConfiguration is not documented. +esp_mqtt_client_config.hpp:line: warning: Member security (variable) of struct idf::mqtt::BrokerConfiguration is not documented. +esp_mqtt.hpp:line: warning: Member operator()(esp_mqtt_client *client_handler) (function) of struct idf::mqtt::Client::MqttClientDeleter is not documented. +esp_mqtt_client_config.hpp:line: warning: Member username (variable) of struct idf::mqtt::ClientCredentials is not documented. +esp_mqtt_client_config.hpp:line: warning: Member authentication (variable) of struct idf::mqtt::ClientCredentials is not documented. +esp_mqtt_client_config.hpp:line: warning: Member client_id (variable) of struct idf::mqtt::ClientCredentials is not documented. +esp_mqtt_client_config.hpp:line: warning: Member event (variable) of struct idf::mqtt::Configuration is not documented. +esp_mqtt_client_config.hpp:line: warning: Member task (variable) of struct idf::mqtt::Configuration is not documented. +esp_mqtt_client_config.hpp:line: warning: Member session (variable) of struct idf::mqtt::Configuration is not documented. +esp_mqtt_client_config.hpp:line: warning: Member connection (variable) of struct idf::mqtt::Configuration is not documented. +esp_mqtt_client_config.hpp:line: warning: Member data (variable) of struct idf::mqtt::DER is not documented. +esp_mqtt_client_config.hpp:line: warning: Member len (variable) of struct idf::mqtt::DER is not documented. +esp_mqtt_client_config.hpp:line: warning: Member ds_data (variable) of struct idf::mqtt::DigitalSignatureData is not documented. +esp_mqtt_client_config.hpp:line: warning: Member data (variable) of struct idf::mqtt::Password is not documented. +esp_mqtt_client_config.hpp:line: warning: Member data (variable) of struct idf::mqtt::PEM is not documented. +esp_mqtt_client_config.hpp:line: warning: Member hint_key (variable) of struct idf::mqtt::PSK is not documented. +esp_mqtt_client_config.hpp:line: warning: Member last_will (variable) of struct idf::mqtt::Session is not documented. diff --git a/components/esp_mqtt_cxx/docs/en/conf.py b/components/esp_mqtt_cxx/docs/en/conf.py new file mode 100644 index 000000000..cbc6ee614 --- /dev/null +++ b/components/esp_mqtt_cxx/docs/en/conf.py @@ -0,0 +1,24 @@ +# -*- coding: utf-8 -*- +# +# English Language RTD & Sphinx config file +# +# Uses ../conf_common.py for most non-language-specific settings. + +# Importing conf_common adds all the non-language-specific +# parts to this conf module + +try: + from conf_common import * # noqa: F403,F401 +except ImportError: + import os + import sys + sys.path.insert(0, os.path.abspath('../')) + from conf_common import * # noqa: F403,F401 + +# General information about the project. +project = u'ESP-Protocols' +copyright = u'2016 - 2023, Espressif Systems (Shanghai) Co., Ltd' + +# The language for content autogenerated by Sphinx. Refer to documentation +# for a list of supported languages. +language = 'en' diff --git a/components/esp_mqtt_cxx/docs/en/index.rst b/components/esp_mqtt_cxx/docs/en/index.rst new file mode 100644 index 000000000..0c4814a75 --- /dev/null +++ b/components/esp_mqtt_cxx/docs/en/index.rst @@ -0,0 +1,132 @@ +ESP MQTT C++ client +==================== + +Overview +-------- +The ESP MQTT client is a wrapper over the `esp_mqtt` client with the goal of providing a higher level API. + +Features +-------- + * Supports MQTT version 3.11 + * Adds a Filter validation class for topic filters + * Split the event handlers to member functions + +Configuration +------------- + +The current design uses exception as an error handling mechanism, therefore exceptions need to be enabled in menuconfig. + +Usage +----- + +User code needs to inherit fromm :cpp:class:`idf::mqtt::Client` and provide overloads for the event handlers. + +.. note:: The handler is available to allow user code to interact directly with it in case of need. This member will likely be made private in the future once the class API stabilizes. + + +.. doxygenclass:: idf::mqtt::Client + :members: + :protected-members: + +Event Handling +-------------- + +Events are dispatched throug calls to member functions each one dedicated to a type of event. + +Application Example +------------------- + +* :example:`tcp <../examples/tcp>` +* :example:`ssl <../examples/ssl>` + +API Reference +------------- + +Header File +^^^^^^^^^^^ + +* :project_file:`include/esp_mqtt.hpp` + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: idf::mqtt::MQTTException + :members: + +.. doxygenstruct:: idf::mqtt::Message + :members: + +Classes +^^^^^^^ + + +.. doxygenclass:: idf::mqtt::Filter + :members: + +Header File +^^^^^^^^^^^ + +* :project_file:`include/esp_mqtt_client_config.hpp` + +Structures +^^^^^^^^^^ + +.. doxygenstruct:: idf::mqtt::Host + :members: + +.. doxygenstruct:: idf::mqtt::URI + :members: + +.. doxygenstruct:: idf::mqtt::BrokerAddress + :members: + +.. doxygenstruct:: idf::mqtt::PEM + :members: + +.. doxygenstruct:: idf::mqtt::DER + :members: + +.. doxygenstruct:: idf::mqtt::Insecure + :members: + +.. doxygenstruct:: idf::mqtt::GlobalCAStore + :members: + +.. doxygenstruct:: idf::mqtt::PSK + :members: + +.. doxygenstruct:: idf::mqtt::Password + :members: + +.. doxygenstruct:: idf::mqtt::ClientCertificate + :members: + +.. doxygenstruct:: idf::mqtt::SecureElement + :members: + +.. doxygenstruct:: idf::mqtt::DigitalSignatureData + :members: + +.. doxygenstruct:: idf::mqtt::BrokerConfiguration + :members: + +.. doxygenstruct:: idf::mqtt::ClientCredentials + :members: + +.. doxygenstruct:: idf::mqtt::Event + :members: + +.. doxygenstruct:: idf::mqtt::LastWill + :members: + +.. doxygenstruct:: idf::mqtt::Session + :members: + +.. doxygenstruct:: idf::mqtt::Task + :members: + +.. doxygenstruct:: idf::mqtt::Connection + :members: + +.. doxygenstruct:: idf::mqtt::Configuration + :members: diff --git a/components/esp_mqtt_cxx/docs/generate_docs b/components/esp_mqtt_cxx/docs/generate_docs new file mode 100755 index 000000000..def507c5e --- /dev/null +++ b/components/esp_mqtt_cxx/docs/generate_docs @@ -0,0 +1,26 @@ +build-docs --target esp32 --language en + +cp -rf _build/en/esp32/html . +rm -rf _build __pycache__ + +# Modifes some version and target fields of index.html +echo "" >> html/index.html diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp b/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp similarity index 96% rename from examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp rename to components/esp_mqtt_cxx/esp_mqtt_cxx.cpp index 96cb290cc..cd8c7d2c1 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp +++ b/components/esp_mqtt_cxx/esp_mqtt_cxx.cpp @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2021-2022 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2021-2023 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -62,7 +62,7 @@ void config_broker(esp_mqtt_client_config_t &mqtt_client_cfg, BrokerConfiguratio std::visit(overloaded{ [&mqtt_client_cfg](PEM const & pem) { - mqtt_client_cfg.broker.verification.certificate= pem.data; + mqtt_client_cfg.broker.verification.certificate = pem.data; }, [&mqtt_client_cfg](DER const & der) { mqtt_client_cfg.broker.verification.certificate = der.data; @@ -278,15 +278,15 @@ const std::string &Filter::get() return filter; } -[[nodiscard]] bool Filter::match(char const *const first, int size) const noexcept +[[nodiscard]] bool Filter::match(char *const begin, int size) const noexcept { - auto it = static_cast(first); + auto it = static_cast(begin); return match(it, it + size); } -std::string::const_iterator Filter::advance(std::string::const_iterator first, std::string::const_iterator last) const +std::string::const_iterator Filter::advance(std::string::const_iterator begin, std::string::const_iterator end) const { constexpr auto separator = '/'; - return std::find(first, last, separator); + return std::find(begin, end, separator); } } diff --git a/components/esp_mqtt_cxx/examples/ssl/CMakeLists.txt b/components/esp_mqtt_cxx/examples/ssl/CMakeLists.txt new file mode 100644 index 000000000..32809b4df --- /dev/null +++ b/components/esp_mqtt_cxx/examples/ssl/CMakeLists.txt @@ -0,0 +1,14 @@ +# The following four lines of boilerplate have to be in your project's +# CMakeLists in this exact order for cmake to work correctly +cmake_minimum_required(VERSION 3.16) + +# (Not part of the boilerplate) This example uses an extra component for common +# functions such as Wi-Fi and Ethernet connection. +# The path to esp_mqtt_cxx is also added. +set(EXTRA_COMPONENT_DIRS + "../../../../common_components/protocol_examples_common" "../../") + +include($ENV{IDF_PATH}/tools/cmake/project.cmake) +project(mqtt_ssl_cxx) + +target_add_binary_data(mqtt_ssl_cxx.elf "main/mqtt_eclipseprojects_io.pem" TEXT) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md b/components/esp_mqtt_cxx/examples/ssl/README.md similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/README.md rename to components/esp_mqtt_cxx/examples/ssl/README.md diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt b/components/esp_mqtt_cxx/examples/ssl/main/CMakeLists.txt similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/main/CMakeLists.txt rename to components/esp_mqtt_cxx/examples/ssl/main/CMakeLists.txt diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild b/components/esp_mqtt_cxx/examples/ssl/main/Kconfig.projbuild similarity index 72% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild rename to components/esp_mqtt_cxx/examples/ssl/main/Kconfig.projbuild index 6d8dc0a35..9d8f549d6 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/Kconfig.projbuild +++ b/components/esp_mqtt_cxx/examples/ssl/main/Kconfig.projbuild @@ -2,7 +2,7 @@ menu "Example Configuration" config BROKER_URI string "Broker URL" - default "mqtts://mqtt.eclipse.org:8883" + default "mqtts://mqtt.eclipseprojects.io:8883" help URL of the broker to connect to diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipse_org.pem b/components/esp_mqtt_cxx/examples/ssl/main/mqtt_eclipse_org.pem similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipse_org.pem rename to components/esp_mqtt_cxx/examples/ssl/main/mqtt_eclipse_org.pem diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipseprojects_io.pem b/components/esp_mqtt_cxx/examples/ssl/main/mqtt_eclipseprojects_io.pem similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_eclipseprojects_io.pem rename to components/esp_mqtt_cxx/examples/ssl/main/mqtt_eclipseprojects_io.pem diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp b/components/esp_mqtt_cxx/examples/ssl/main/mqtt_ssl_example.cpp similarity index 95% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp rename to components/esp_mqtt_cxx/examples/ssl/main/mqtt_ssl_example.cpp index 8493d52d0..ecd420c4b 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/main/mqtt_ssl_example.cpp +++ b/components/esp_mqtt_cxx/examples/ssl/main/mqtt_ssl_example.cpp @@ -1,3 +1,8 @@ +/* + * SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ /* C++ MQTT (over TCP) Example This example code is in the Public Domain (or CC0 licensed, at your option.) diff --git a/components/esp_mqtt_cxx/examples/ssl/pytest_mqtt_ssl.py b/components/esp_mqtt_cxx/examples/ssl/pytest_mqtt_ssl.py new file mode 100644 index 000000000..040f29fa5 --- /dev/null +++ b/components/esp_mqtt_cxx/examples/ssl/pytest_mqtt_ssl.py @@ -0,0 +1,8 @@ +# SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD +# SPDX-License-Identifier: Unlicense OR CC0-1.0 +import pytest + + +@pytest.mark.esp32 +def test_dummy() -> None: + pass diff --git a/components/esp_mqtt_cxx/examples/ssl/sdkconfig.defaults b/components/esp_mqtt_cxx/examples/ssl/sdkconfig.defaults new file mode 100644 index 000000000..56117c87b --- /dev/null +++ b/components/esp_mqtt_cxx/examples/ssl/sdkconfig.defaults @@ -0,0 +1,21 @@ +# Enable C++ exceptions and set emergency pool size for exception objects +CONFIG_COMPILER_CXX_EXCEPTIONS=y +CONFIG_COMPILER_CXX_EXCEPTIONS_EMG_POOL_SIZE=1024 +CONFIG_EXAMPLE_CONNECT_ETHERNET=y +CONFIG_EXAMPLE_CONNECT_WIFI=n +CONFIG_EXAMPLE_USE_INTERNAL_ETHERNET=y +CONFIG_EXAMPLE_ETH_PHY_IP101=y +CONFIG_EXAMPLE_ETH_MDC_GPIO=23 +CONFIG_EXAMPLE_ETH_MDIO_GPIO=18 +CONFIG_EXAMPLE_ETH_PHY_RST_GPIO=5 +CONFIG_EXAMPLE_ETH_PHY_ADDR=1 +CONFIG_EXAMPLE_CONNECT_IPV6=y +CONFIG_EXAMPLE_CONNECT_ETHERNET=y +CONFIG_EXAMPLE_CONNECT_WIFI=n +CONFIG_EXAMPLE_USE_INTERNAL_ETHERNET=y +CONFIG_EXAMPLE_ETH_PHY_IP101=y +CONFIG_EXAMPLE_ETH_MDC_GPIO=23 +CONFIG_EXAMPLE_ETH_MDIO_GPIO=18 +CONFIG_EXAMPLE_ETH_PHY_RST_GPIO=5 +CONFIG_EXAMPLE_ETH_PHY_ADDR=1 +CONFIG_EXAMPLE_CONNECT_IPV6=y diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt b/components/esp_mqtt_cxx/examples/tcp/CMakeLists.txt similarity index 57% rename from examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt rename to components/esp_mqtt_cxx/examples/tcp/CMakeLists.txt index ef6daba53..146f3592d 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/CMakeLists.txt +++ b/components/esp_mqtt_cxx/examples/tcp/CMakeLists.txt @@ -4,9 +4,9 @@ cmake_minimum_required(VERSION 3.16) # (Not part of the boilerplate) # This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. -set(EXTRA_COMPONENT_DIRS $ENV{IDF_PATH}/examples/common_components/protocol_examples_common - $ENV{IDF_PATH}/examples/cxx/experimental/experimental_cpp_component - $ENV{IDF_PATH}/examples/cxx/experimental/esp_mqtt_cxx/components) +# The path to esp_mqtt_cxx is also added. +set(EXTRA_COMPONENT_DIRS + "../../../../common_components/protocol_examples_common" "../../") include($ENV{IDF_PATH}/tools/cmake/project.cmake) project(mqtt_tcp_cxx) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md b/components/esp_mqtt_cxx/examples/tcp/README.md similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/tcp/README.md rename to components/esp_mqtt_cxx/examples/tcp/README.md diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt b/components/esp_mqtt_cxx/examples/tcp/main/CMakeLists.txt similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/tcp/main/CMakeLists.txt rename to components/esp_mqtt_cxx/examples/tcp/main/CMakeLists.txt diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild b/components/esp_mqtt_cxx/examples/tcp/main/Kconfig.projbuild similarity index 74% rename from examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild rename to components/esp_mqtt_cxx/examples/tcp/main/Kconfig.projbuild index 34c04a02c..e9f684b85 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/Kconfig.projbuild +++ b/components/esp_mqtt_cxx/examples/tcp/main/Kconfig.projbuild @@ -2,7 +2,7 @@ menu "Example Configuration" config BROKER_URL string "Broker URL" - default "mqtt://mqtt.eclipse.org" + default "mqtt://mqtt.eclipseprojects.io" help URL of the broker to connect to diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp b/components/esp_mqtt_cxx/examples/tcp/main/mqtt_tcp_example.cpp similarity index 95% rename from examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp rename to components/esp_mqtt_cxx/examples/tcp/main/mqtt_tcp_example.cpp index edfb53550..bd749c50c 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/main/mqtt_tcp_example.cpp +++ b/components/esp_mqtt_cxx/examples/tcp/main/mqtt_tcp_example.cpp @@ -1,3 +1,8 @@ +/* + * SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ /* C++ MQTT (over TCP) Example This example code is in the Public Domain (or CC0 licensed, at your option.) diff --git a/components/esp_mqtt_cxx/examples/tcp/pytest_mqtt_tcp.py b/components/esp_mqtt_cxx/examples/tcp/pytest_mqtt_tcp.py new file mode 100644 index 000000000..040f29fa5 --- /dev/null +++ b/components/esp_mqtt_cxx/examples/tcp/pytest_mqtt_tcp.py @@ -0,0 +1,8 @@ +# SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD +# SPDX-License-Identifier: Unlicense OR CC0-1.0 +import pytest + + +@pytest.mark.esp32 +def test_dummy() -> None: + pass diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/sdkconfig.defaults b/components/esp_mqtt_cxx/examples/tcp/sdkconfig.defaults similarity index 100% rename from examples/cxx/experimental/esp_mqtt_cxx/ssl/sdkconfig.defaults rename to components/esp_mqtt_cxx/examples/tcp/sdkconfig.defaults diff --git a/components/esp_mqtt_cxx/idf_component.yml b/components/esp_mqtt_cxx/idf_component.yml new file mode 100644 index 000000000..b5232c934 --- /dev/null +++ b/components/esp_mqtt_cxx/idf_component.yml @@ -0,0 +1,8 @@ +version: "0.1.0" +description: esp mqtt cxx +url: https://github.com/espressif/esp-protocols/tree/master/components/esp_mqtt_cxx +dependencies: + espressif/esp-idf-cxx: "^1.0.0-beta" + # Required IDF version + idf: + version: ">=5.0" diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp b/components/esp_mqtt_cxx/include/esp_mqtt.hpp similarity index 65% rename from examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp rename to components/esp_mqtt_cxx/include/esp_mqtt.hpp index 9d071f247..4a5b9d286 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt.hpp +++ b/components/esp_mqtt_cxx/include/esp_mqtt.hpp @@ -1,16 +1,8 @@ -// Copyright 2021 Espressif Systems (Shanghai) CO LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. +/* + * SPDX-FileCopyrightText: 2021-2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ #pragma once #include @@ -43,6 +35,9 @@ struct MQTTException : ESPException { * AtLeastOnce : Guaranteed delivery of messages. Duplicates can occur. * ExactlyOnce : Guaranteed delivery of messages exactly once. * + * @note + * When subscribing to a topic the QoS means the maximum QoS that should be sent to + * client on this topic */ enum class QoS { AtMostOnce = 0, AtLeastOnce = 1, ExactlyOnce = 2 }; @@ -75,7 +70,6 @@ using StringMessage = Message; /** * @brief Filter for mqtt topic subscription. - * @throws std::domain_error if the filter is invalid. * * Topic filter. * @@ -83,25 +77,31 @@ using StringMessage = Message; class Filter { public: + /** + * @brief Constructs the topic filter from the user filter + * @throws std::domain_error if the filter is invalid. + * + * @param user_filter Filter to be used. + */ explicit Filter(std::string user_filter); /** * @brief Get the filter string used. * + * @return Reference to the topic filter. */ const std::string &get(); /** * @brief Checks the filter string against a topic name. * - * @param first Iterator to the beginning of the sequence. - * @param last Iterator to the end of the sequence. + * @param topic_begin Iterator to the beginning of the sequence. + * @param topic_end Iterator to the end of the sequence. * * @return true if the topic name match the filter */ - [[nodiscard]] bool match(std::string::const_iterator first, - std::string::const_iterator last) const noexcept; + [[nodiscard]] bool match(std::string::const_iterator topic_begin, std::string::const_iterator topic_end) const noexcept; /** * @brief Checks the filter string against a topic name. @@ -115,12 +115,12 @@ public: /** * @brief Checks the filter string against a topic name. * - * @param first Char array with topic name. - * @param last Size of given topic name. + * @param begin Char array with topic name. + * @param size Size of given topic name. * * @return true if the topic name match the filter */ - [[nodiscard]] bool match(const char *const begin, int size) const noexcept; + [[nodiscard]] bool match(char *begin, int size) const noexcept; private: @@ -149,31 +149,44 @@ enum class MessageID : int {}; */ class Client { public: + /** + * @brief Constructor of the client + * + * @param broker Configuration for broker connection + * @param credentials client credentials to be presented to the broker + * @param config Mqtt client configuration + */ + Client(const BrokerConfiguration &broker, const ClientCredentials &credentials, const Configuration &config); - Client(const BrokerConfiguration &broker,const ClientCredentials &credentials,const Configuration &config); - + /** + * @brief Constructs Client using the same configuration used for + * `esp_mqtt_client` + * @param config config struct to `esp_mqtt_client` + */ Client(const esp_mqtt_client_config_t &config); /** * @brief Subscribe to topic * - * @param filter + * @param topic_filter MQTT topic filter * @param qos QoS subscription, defaulted as QoS::AtLeastOnce * * @return Optional MessageID. In case of failure std::nullopt is returned. */ - std::optional subscribe(const std::string &filter, QoS qos = QoS::AtLeastOnce); + std::optional subscribe(const std::string &topic_filter, QoS qos = QoS::AtLeastOnce); /** * @brief publish message to topic * * @tparam Container Type for data container. Must be a contiguous memory. * @param topic Topic name - * @param message Message struct containing data, qos and retain configuration. + * @param message Message struct containing data, qos and retain + * configuration. * * @return Optional MessageID. In case of failure std::nullopt is returned. */ - template std::optional publish(const std::string &topic, const Message& message) + template + std::optional publish(const std::string &topic, const Message &message) { return publish(topic, std::begin(message.data), std::end(message.data), message.qos, message.retain); } @@ -184,7 +197,8 @@ public: * @tparam InputIt Input data iterator type. * @param topic Topic name * @param first, last Iterator pair of data to publish - * @param message Message struct containing data, qos and retain configuration. + * @param qos Set qos message + * @param retain Set if message should be retained * * @return Optional MessageID. In case of failure std::nullopt is returned. */ @@ -203,6 +217,9 @@ public: virtual ~Client() = default; protected: + /** + * @brief Helper type to be used as custom deleter for std::unique_ptr. + */ struct MqttClientDeleter { void operator()(esp_mqtt_client *client_handler) { @@ -210,20 +227,70 @@ protected: } }; + /** + * @brief Type of the handler for the underlying mqtt_client handler. + * It uses std::unique_ptr for lifetime management + */ using ClientHandler = std::unique_ptr; + /** + * @brief esp_mqtt_client handler + * + */ ClientHandler handler; + /** + * @brief Called if there is an error event + * + * @param event mqtt event data + */ + virtual void on_error(const esp_mqtt_event_handle_t event); + /** + * @brief Called if there is an disconnection event + * + * @param event mqtt event data + */ + virtual void on_disconnected(const esp_mqtt_event_handle_t event); + /** + * @brief Called if there is an subscribed event + * + * @param event mqtt event data + */ + virtual void on_subscribed(const esp_mqtt_event_handle_t event); + /** + * @brief Called if there is an unsubscribed event + * + * @param event mqtt event data + */ + virtual void on_unsubscribed(const esp_mqtt_event_handle_t event); + /** + * @brief Called if there is an published event + * + * @param event mqtt event data + */ + virtual void on_published(const esp_mqtt_event_handle_t event); + /** + * @brief Called if there is an before connect event + * + * @param event mqtt event data + */ + virtual void on_before_connect(const esp_mqtt_event_handle_t event); + /** + * @brief Called if there is an connected event + * + * @param event mqtt event data + * + */ + virtual void on_connected(const esp_mqtt_event_handle_t event) = 0; + /** + * @brief Called if there is an data event + * + * @param event mqtt event data + * + */ + virtual void on_data(const esp_mqtt_event_handle_t event) = 0; private: static void mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, void *event_data) noexcept; void init(const esp_mqtt_client_config_t &config); - virtual void on_error(const esp_mqtt_event_handle_t event); - virtual void on_disconnected(const esp_mqtt_event_handle_t event); - virtual void on_subscribed(const esp_mqtt_event_handle_t event); - virtual void on_unsubscribed(const esp_mqtt_event_handle_t event); - virtual void on_published(const esp_mqtt_event_handle_t event); - virtual void on_before_connect(const esp_mqtt_event_handle_t event); - virtual void on_connected(const esp_mqtt_event_handle_t event) = 0; - virtual void on_data(const esp_mqtt_event_handle_t event) = 0; }; } // namespace idf::mqtt diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp b/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp similarity index 85% rename from examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp rename to components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp index 0fbba636f..1466b941f 100644 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp +++ b/components/esp_mqtt_cxx/include/esp_mqtt_client_config.hpp @@ -1,16 +1,8 @@ -// Copyright 2021 Espressif Systems (Shanghai) CO LTD -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. +/* + * SPDX-FileCopyrightText: 2021-2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ #pragma once #include @@ -53,8 +45,8 @@ struct URI { * */ struct BrokerAddress { - std::variant address; /*!< Address, defined by URI or Host struct */ - uint32_t port = 0; /*!< Port used, defaults to 0 to select common port for the scheme used */ + std::variant address; /*!< Address, defined by URI or Host struct */ + uint32_t port = 0; /*!< Port used, defaults to 0 to select common port for the scheme used */ }; /** @@ -135,9 +127,9 @@ struct Password { * */ struct ClientCertificate { - CryptographicInformation certificate; /*!< Certificate in PEM or DER format.*/ - CryptographicInformation key; /*!< Key data in PEM or DER format.*/ - std::optional key_password = std::nullopt; /*!< Optional password for key */ + CryptographicInformation certificate; /*!< Certificate in PEM or DER format.*/ + CryptographicInformation key; /*!< Key data in PEM or DER format.*/ + std::optional key_password = std::nullopt; /*!< Optional password for key */ }; /** diff --git a/components/esp_websocket_client/examples/CMakeLists.txt b/components/esp_websocket_client/examples/CMakeLists.txt index 4f5b8aaaf..6394830fb 100644 --- a/components/esp_websocket_client/examples/CMakeLists.txt +++ b/components/esp_websocket_client/examples/CMakeLists.txt @@ -2,7 +2,7 @@ # in this exact order for cmake to work correctly cmake_minimum_required(VERSION 3.5) -set(EXTRA_COMPONENT_DIRS "../..") +set(EXTRA_COMPONENT_DIRS "..") # This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. list(APPEND EXTRA_COMPONENT_DIRS "../../../common_components/protocol_examples_common") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt deleted file mode 100644 index 8d40b820a..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/components/esp_mqtt_cxx/CMakeLists.txt +++ /dev/null @@ -1,24 +0,0 @@ -idf_build_get_property(target IDF_TARGET) - -idf_component_register(SRCS "esp_mqtt_cxx.cpp" - INCLUDE_DIRS "include" - ) - -if(TEST_BUILD) - message(STATUS "Test build") - idf_component_get_property(mqtt_dir mqtt COMPONENT_DIR) - idf_component_get_property(experimental_cpp_component_dir experimental_cpp_component COMPONENT_DIR) - idf_component_get_property(esp_common_dir esp_common COMPONENT_DIR) - idf_component_get_property(esp_event_dir esp_event COMPONENT_DIR) - target_include_directories(${COMPONENT_LIB} PUBLIC ${mqtt_dir}/esp-mqtt/include - ${esp_event_dir}/include - ${experimental_cpp_component_dir}/include - ${esp_common_dir}/include) - -else() - idf_component_get_property(mqtt_lib mqtt COMPONENT_LIB) - idf_component_get_property(log_lib log COMPONENT_LIB) - idf_component_get_property(experimental_cpp_component_lib experimental_cpp_component COMPONENT_LIB) - target_link_libraries(${COMPONENT_LIB} PUBLIC ${log_lib} ${mqtt_lib} ${experimental_cpp_component_lib}) -endif() -target_compile_options(${COMPONENT_LIB} PRIVATE "-Wno-format") diff --git a/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt b/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt deleted file mode 100644 index 01cc1fff5..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/ssl/CMakeLists.txt +++ /dev/null @@ -1,14 +0,0 @@ -# The following four lines of boilerplate have to be in your project's CMakeLists -# in this exact order for cmake to work correctly -cmake_minimum_required(VERSION 3.16) - -# (Not part of the boilerplate) -# This example uses an extra component for common functions such as Wi-Fi and Ethernet connection. -set(EXTRA_COMPONENT_DIRS $ENV{IDF_PATH}/examples/common_components/protocol_examples_common - $ENV{IDF_PATH}/examples/cxx/experimental/experimental_cpp_component - $ENV{IDF_PATH}/examples/cxx/experimental/esp_mqtt_cxx/components) - -include($ENV{IDF_PATH}/tools/cmake/project.cmake) -project(mqtt_ssl_cxx) - -target_add_binary_data(mqtt_ssl_cxx.elf "main/mqtt_eclipseprojects_io.pem" TEXT) diff --git a/examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults b/examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults deleted file mode 100644 index a365ac658..000000000 --- a/examples/cxx/experimental/esp_mqtt_cxx/tcp/sdkconfig.defaults +++ /dev/null @@ -1,3 +0,0 @@ -# Enable C++ exceptions and set emergency pool size for exception objects -CONFIG_COMPILER_CXX_EXCEPTIONS=y -CONFIG_COMPILER_CXX_EXCEPTIONS_EMG_POOL_SIZE=1024