mirror of
https://github.com/esphome/esphome.git
synced 2026-02-03 12:59:40 -07:00
Compare commits
1 Commits
progmem_st
...
action_cal
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b22a8b00bf |
@@ -639,6 +639,14 @@ bool APIServer::teardown() {
|
|||||||
#define USE_API_ACTION_CALL_TIMEOUT_MS 30000 // NOLINT
|
#define USE_API_ACTION_CALL_TIMEOUT_MS 30000 // NOLINT
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// SSO-friendly action call key - hex format guarantees max 11 chars ("ac_ffffffff")
|
||||||
|
// which fits in any std::string SSO buffer (typically 12-15 bytes)
|
||||||
|
static inline std::string make_action_call_key(uint32_t id) {
|
||||||
|
char buf[12];
|
||||||
|
size_t len = snprintf(buf, sizeof(buf), "ac_%x", id);
|
||||||
|
return std::string(buf, len);
|
||||||
|
}
|
||||||
|
|
||||||
uint32_t APIServer::register_active_action_call(uint32_t client_call_id, APIConnection *conn) {
|
uint32_t APIServer::register_active_action_call(uint32_t client_call_id, APIConnection *conn) {
|
||||||
uint32_t action_call_id = this->next_action_call_id_++;
|
uint32_t action_call_id = this->next_action_call_id_++;
|
||||||
// Handle wraparound (skip 0 as it means "no call")
|
// Handle wraparound (skip 0 as it means "no call")
|
||||||
@@ -648,18 +656,17 @@ uint32_t APIServer::register_active_action_call(uint32_t client_call_id, APIConn
|
|||||||
this->active_action_calls_.push_back({action_call_id, client_call_id, conn});
|
this->active_action_calls_.push_back({action_call_id, client_call_id, conn});
|
||||||
|
|
||||||
// Schedule automatic cleanup after timeout (client will have given up by then)
|
// Schedule automatic cleanup after timeout (client will have given up by then)
|
||||||
this->set_timeout(str_sprintf("action_call_%u", action_call_id), USE_API_ACTION_CALL_TIMEOUT_MS,
|
this->set_timeout(make_action_call_key(action_call_id), USE_API_ACTION_CALL_TIMEOUT_MS, [this, action_call_id]() {
|
||||||
[this, action_call_id]() {
|
ESP_LOGD(TAG, "Action call %u timed out", action_call_id);
|
||||||
ESP_LOGD(TAG, "Action call %u timed out", action_call_id);
|
this->unregister_active_action_call(action_call_id);
|
||||||
this->unregister_active_action_call(action_call_id);
|
});
|
||||||
});
|
|
||||||
|
|
||||||
return action_call_id;
|
return action_call_id;
|
||||||
}
|
}
|
||||||
|
|
||||||
void APIServer::unregister_active_action_call(uint32_t action_call_id) {
|
void APIServer::unregister_active_action_call(uint32_t action_call_id) {
|
||||||
// Cancel the timeout for this action call
|
// Cancel the timeout for this action call
|
||||||
this->cancel_timeout(str_sprintf("action_call_%u", action_call_id));
|
this->cancel_timeout(make_action_call_key(action_call_id));
|
||||||
|
|
||||||
// Swap-and-pop is more efficient than remove_if for unordered vectors
|
// Swap-and-pop is more efficient than remove_if for unordered vectors
|
||||||
for (size_t i = 0; i < this->active_action_calls_.size(); i++) {
|
for (size_t i = 0; i < this->active_action_calls_.size(); i++) {
|
||||||
@@ -676,7 +683,7 @@ void APIServer::unregister_active_action_calls_for_connection(APIConnection *con
|
|||||||
for (size_t i = 0; i < this->active_action_calls_.size();) {
|
for (size_t i = 0; i < this->active_action_calls_.size();) {
|
||||||
if (this->active_action_calls_[i].connection == conn) {
|
if (this->active_action_calls_[i].connection == conn) {
|
||||||
// Cancel the timeout for this action call
|
// Cancel the timeout for this action call
|
||||||
this->cancel_timeout(str_sprintf("action_call_%u", this->active_action_calls_[i].action_call_id));
|
this->cancel_timeout(make_action_call_key(this->active_action_calls_[i].action_call_id));
|
||||||
|
|
||||||
std::swap(this->active_action_calls_[i], this->active_action_calls_.back());
|
std::swap(this->active_action_calls_[i], this->active_action_calls_.back());
|
||||||
this->active_action_calls_.pop_back();
|
this->active_action_calls_.pop_back();
|
||||||
|
|||||||
Reference in New Issue
Block a user