diff --git a/components/esp_matter/esp_matter.h b/components/esp_matter/esp_matter.h index fda20102b..38173f030 100644 --- a/components/esp_matter/esp_matter.h +++ b/components/esp_matter/esp_matter.h @@ -120,8 +120,18 @@ enum kCommissioningSessionStopped, /** Signals that Commissioning window is now opend */ kCommissioningWindowOpened, - /** Signals that Commissioning window is now closed */ + /** Signals that Commissioning window is now closed */ kCommissioningWindowClosed, + /** Signals that a fabric is about to be deleted. This allows actions to be taken that need the + fabric to still be around before we delete it */ + kFabricWillBeRemoved, + /** Signals that a fabric is deleted */ + kFabricRemoved, + /** Signals that a fabric in Fabric Table is persisted to storage, by CommitPendingFabricData */ + kFabricCommitted, + /** Signals that operational credentials are changed, which may not be persistent. + Can be used to affect what is needed for UpdateNOC prior to commit */ + kFabricUpdated, }; } // DeviceEventType diff --git a/components/esp_matter/esp_matter_core.cpp b/components/esp_matter/esp_matter_core.cpp index bab81d9a5..588b027d3 100644 --- a/components/esp_matter/esp_matter_core.cpp +++ b/components/esp_matter/esp_matter_core.cpp @@ -33,6 +33,7 @@ #include #include #include +#include #include #include #include @@ -82,6 +83,16 @@ chip::DeviceLayer::ESP32FactoryDataProvider factory_data_provider; chip::DeviceLayer::ESP32DeviceInfoProvider device_info_provider; #endif +void PostEvent(uint16_t eventType) +{ + chip::DeviceLayer::ChipDeviceEvent event; + event.Type = eventType; + CHIP_ERROR error = chip::DeviceLayer::PlatformMgr().PostEvent(&event); + if (error != CHIP_NO_ERROR) + { + ESP_LOGE(TAG, "Failed to post event for event type:%u, err:%" CHIP_ERROR_FORMAT, eventType, error.Format()); + } +} class AppDelegateImpl : public AppDelegate { @@ -105,22 +116,36 @@ public: { PostEvent(chip::DeviceLayer::DeviceEventType::kCommissioningWindowClosed); } +}; -private: - void PostEvent(uint16_t eventType) +class FabricDelegateImpl : public chip::FabricTable::Delegate +{ +public: + void FabricWillBeRemoved(const chip::FabricTable & fabricTable,chip::FabricIndex fabricIndex) { - chip::DeviceLayer::ChipDeviceEvent event; - event.Type = eventType; - CHIP_ERROR error = chip::DeviceLayer::PlatformMgr().PostEvent(&event); - if (error != CHIP_NO_ERROR) - { - ESP_LOGE(TAG, "Failed to post event from AppDelegate, err:%" CHIP_ERROR_FORMAT, error.Format()); - } + PostEvent(chip::DeviceLayer::DeviceEventType::kFabricWillBeRemoved); + } + + void OnFabricRemoved(const chip::FabricTable & fabricTable,chip::FabricIndex fabricIndex) + { + PostEvent(chip::DeviceLayer::DeviceEventType::kFabricRemoved); + } + + void OnFabricCommitted(const chip::FabricTable & fabricTable, chip::FabricIndex fabricIndex) + { + PostEvent(chip::DeviceLayer::DeviceEventType::kFabricCommitted); + } + + void OnFabricUpdated(const chip::FabricTable & fabricTable, chip::FabricIndex fabricIndex) + { + PostEvent(chip::DeviceLayer::DeviceEventType::kFabricUpdated); } }; AppDelegateImpl s_app_delegate; +FabricDelegateImpl s_fabric_delegate; + } // namespace typedef struct _attribute { @@ -769,6 +794,11 @@ static void esp_matter_chip_init_task(intptr_t context) static chip::CommonCaseDeviceServerInitParams initParams; initParams.InitializeStaticResourcesBeforeServerInit(); initParams.appDelegate = &s_app_delegate; + CHIP_ERROR ret = chip::Server::GetInstance().GetFabricTable().AddFabricDelegate(&s_fabric_delegate); + if (ret != CHIP_NO_ERROR) + { + ESP_LOGE(TAG, "Failed to add fabric delegate, err:%" CHIP_ERROR_FORMAT, ret.Format()); + } chip::Server::GetInstance().Init(initParams); #if CHIP_DEVICE_CONFIG_ENABLE_THREAD diff --git a/examples/light/main/app_main.cpp b/examples/light/main/app_main.cpp index ca9e50df7..3549cb777 100644 --- a/examples/light/main/app_main.cpp +++ b/examples/light/main/app_main.cpp @@ -17,6 +17,8 @@ #include #include +#include +#include static const char *TAG = "app_main"; uint16_t light_endpoint_id = 0; @@ -25,6 +27,8 @@ using namespace esp_matter::attribute; using namespace esp_matter::endpoint; using namespace chip::app::Clusters; +constexpr auto k_timeout_seconds = 300; + static void app_event_cb(const ChipDeviceEvent *event, intptr_t arg) { switch (event->Type) { @@ -56,6 +60,36 @@ static void app_event_cb(const ChipDeviceEvent *event, intptr_t arg) ESP_LOGI(TAG, "Commissioning window closed"); break; + case chip::DeviceLayer::DeviceEventType::kFabricRemoved: + { + ESP_LOGI(TAG, "Fabric removed successfully"); + if (chip::Server::GetInstance().GetFabricTable().FabricCount() == 0) + { + chip::CommissioningWindowManager & commissionMgr = chip::Server::GetInstance().GetCommissioningWindowManager(); + constexpr auto kTimeoutSeconds = chip::System::Clock::Seconds16(k_timeout_seconds); + if (!commissionMgr.IsCommissioningWindowOpen()) + { + CHIP_ERROR err = commissionMgr.OpenBasicCommissioningWindow(kTimeoutSeconds); + if (err != CHIP_NO_ERROR) + { + ESP_LOGE(TAG, "Failed to open commissioning window, err:%" CHIP_ERROR_FORMAT, err.Format()); + } + } + } + break; + } + + case chip::DeviceLayer::DeviceEventType::kFabricWillBeRemoved: + ESP_LOGI(TAG, "Fabric will be removed"); + break; + + case chip::DeviceLayer::DeviceEventType::kFabricUpdated: + ESP_LOGI(TAG, "Fabric is updated"); + break; + + case chip::DeviceLayer::DeviceEventType::kFabricCommitted: + ESP_LOGI(TAG, "Fabric is committed"); + break; default: break; }