mirror of
https://github.com/esphome/esphome.git
synced 2025-10-03 10:32:21 +01:00
Merge branch 'dev' into client_info_flash
This commit is contained in:
@@ -7,24 +7,20 @@ namespace hdc1080 {
|
|||||||
|
|
||||||
static const char *const TAG = "hdc1080";
|
static const char *const TAG = "hdc1080";
|
||||||
|
|
||||||
static const uint8_t HDC1080_ADDRESS = 0x40; // 0b1000000 from datasheet
|
|
||||||
static const uint8_t HDC1080_CMD_CONFIGURATION = 0x02;
|
static const uint8_t HDC1080_CMD_CONFIGURATION = 0x02;
|
||||||
static const uint8_t HDC1080_CMD_TEMPERATURE = 0x00;
|
static const uint8_t HDC1080_CMD_TEMPERATURE = 0x00;
|
||||||
static const uint8_t HDC1080_CMD_HUMIDITY = 0x01;
|
static const uint8_t HDC1080_CMD_HUMIDITY = 0x01;
|
||||||
|
|
||||||
void HDC1080Component::setup() {
|
void HDC1080Component::setup() {
|
||||||
const uint8_t data[2] = {
|
const uint8_t config[2] = {0x00, 0x00}; // resolution 14bit for both humidity and temperature
|
||||||
0b00000000, // resolution 14bit for both humidity and temperature
|
|
||||||
0b00000000 // reserved
|
|
||||||
};
|
|
||||||
|
|
||||||
if (!this->write_bytes(HDC1080_CMD_CONFIGURATION, data, 2)) {
|
// if configuration fails - there is a problem
|
||||||
// as instruction is same as powerup defaults (for now), interpret as warning if this fails
|
if (this->write_register(HDC1080_CMD_CONFIGURATION, config, 2) != i2c::ERROR_OK) {
|
||||||
ESP_LOGW(TAG, "HDC1080 initial config instruction error");
|
this->mark_failed();
|
||||||
this->status_set_warning();
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void HDC1080Component::dump_config() {
|
void HDC1080Component::dump_config() {
|
||||||
ESP_LOGCONFIG(TAG, "HDC1080:");
|
ESP_LOGCONFIG(TAG, "HDC1080:");
|
||||||
LOG_I2C_DEVICE(this);
|
LOG_I2C_DEVICE(this);
|
||||||
@@ -35,39 +31,51 @@ void HDC1080Component::dump_config() {
|
|||||||
LOG_SENSOR(" ", "Temperature", this->temperature_);
|
LOG_SENSOR(" ", "Temperature", this->temperature_);
|
||||||
LOG_SENSOR(" ", "Humidity", this->humidity_);
|
LOG_SENSOR(" ", "Humidity", this->humidity_);
|
||||||
}
|
}
|
||||||
|
|
||||||
void HDC1080Component::update() {
|
void HDC1080Component::update() {
|
||||||
uint16_t raw_temp;
|
// regardless of what sensor/s are defined in yaml configuration
|
||||||
|
// the hdc1080 setup configuration used, requires both temperature and humidity to be read
|
||||||
|
|
||||||
|
this->status_clear_warning();
|
||||||
|
|
||||||
if (this->write(&HDC1080_CMD_TEMPERATURE, 1) != i2c::ERROR_OK) {
|
if (this->write(&HDC1080_CMD_TEMPERATURE, 1) != i2c::ERROR_OK) {
|
||||||
this->status_set_warning();
|
this->status_set_warning();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
delay(20);
|
|
||||||
if (this->read(reinterpret_cast<uint8_t *>(&raw_temp), 2) != i2c::ERROR_OK) {
|
this->set_timeout(20, [this]() {
|
||||||
|
uint16_t raw_temperature;
|
||||||
|
if (this->read(reinterpret_cast<uint8_t *>(&raw_temperature), 2) != i2c::ERROR_OK) {
|
||||||
this->status_set_warning();
|
this->status_set_warning();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
raw_temp = i2c::i2ctohs(raw_temp);
|
|
||||||
float temp = raw_temp * 0.0025177f - 40.0f; // raw * 2^-16 * 165 - 40
|
|
||||||
this->temperature_->publish_state(temp);
|
|
||||||
|
|
||||||
uint16_t raw_humidity;
|
if (this->temperature_ != nullptr) {
|
||||||
|
raw_temperature = i2c::i2ctohs(raw_temperature);
|
||||||
|
float temperature = raw_temperature * 0.0025177f - 40.0f; // raw * 2^-16 * 165 - 40
|
||||||
|
this->temperature_->publish_state(temperature);
|
||||||
|
}
|
||||||
|
|
||||||
if (this->write(&HDC1080_CMD_HUMIDITY, 1) != i2c::ERROR_OK) {
|
if (this->write(&HDC1080_CMD_HUMIDITY, 1) != i2c::ERROR_OK) {
|
||||||
this->status_set_warning();
|
this->status_set_warning();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
delay(20);
|
|
||||||
|
this->set_timeout(20, [this]() {
|
||||||
|
uint16_t raw_humidity;
|
||||||
if (this->read(reinterpret_cast<uint8_t *>(&raw_humidity), 2) != i2c::ERROR_OK) {
|
if (this->read(reinterpret_cast<uint8_t *>(&raw_humidity), 2) != i2c::ERROR_OK) {
|
||||||
this->status_set_warning();
|
this->status_set_warning();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (this->humidity_ != nullptr) {
|
||||||
raw_humidity = i2c::i2ctohs(raw_humidity);
|
raw_humidity = i2c::i2ctohs(raw_humidity);
|
||||||
float humidity = raw_humidity * 0.001525879f; // raw * 2^-16 * 100
|
float humidity = raw_humidity * 0.001525879f; // raw * 2^-16 * 100
|
||||||
this->humidity_->publish_state(humidity);
|
this->humidity_->publish_state(humidity);
|
||||||
|
}
|
||||||
ESP_LOGD(TAG, "Got temperature=%.1f°C humidity=%.1f%%", temp, humidity);
|
});
|
||||||
this->status_clear_warning();
|
});
|
||||||
}
|
}
|
||||||
float HDC1080Component::get_setup_priority() const { return setup_priority::DATA; }
|
|
||||||
|
|
||||||
} // namespace hdc1080
|
} // namespace hdc1080
|
||||||
} // namespace esphome
|
} // namespace esphome
|
||||||
|
@@ -12,13 +12,11 @@ class HDC1080Component : public PollingComponent, public i2c::I2CDevice {
|
|||||||
void set_temperature(sensor::Sensor *temperature) { temperature_ = temperature; }
|
void set_temperature(sensor::Sensor *temperature) { temperature_ = temperature; }
|
||||||
void set_humidity(sensor::Sensor *humidity) { humidity_ = humidity; }
|
void set_humidity(sensor::Sensor *humidity) { humidity_ = humidity; }
|
||||||
|
|
||||||
/// Setup the sensor and check for connection.
|
|
||||||
void setup() override;
|
void setup() override;
|
||||||
void dump_config() override;
|
void dump_config() override;
|
||||||
/// Retrieve the latest sensor values. This operation takes approximately 16ms.
|
|
||||||
void update() override;
|
void update() override;
|
||||||
|
|
||||||
float get_setup_priority() const override;
|
float get_setup_priority() const override { return setup_priority::DATA; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
sensor::Sensor *temperature_{nullptr};
|
sensor::Sensor *temperature_{nullptr};
|
||||||
|
@@ -62,6 +62,11 @@ SPIRAM_SPEEDS = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def supported() -> bool:
|
||||||
|
variant = get_esp32_variant()
|
||||||
|
return variant in SPIRAM_MODES
|
||||||
|
|
||||||
|
|
||||||
def validate_psram_mode(config):
|
def validate_psram_mode(config):
|
||||||
esp32_config = fv.full_config.get()[PLATFORM_ESP32]
|
esp32_config = fv.full_config.get()[PLATFORM_ESP32]
|
||||||
if config[CONF_SPEED] == "120MHZ":
|
if config[CONF_SPEED] == "120MHZ":
|
||||||
@@ -95,7 +100,7 @@ def get_config_schema(config):
|
|||||||
variant = get_esp32_variant()
|
variant = get_esp32_variant()
|
||||||
speeds = [f"{s}MHZ" for s in SPIRAM_SPEEDS.get(variant, [])]
|
speeds = [f"{s}MHZ" for s in SPIRAM_SPEEDS.get(variant, [])]
|
||||||
if not speeds:
|
if not speeds:
|
||||||
return cv.Invalid("PSRAM is not supported on this chip")
|
raise cv.Invalid("PSRAM is not supported on this chip")
|
||||||
modes = SPIRAM_MODES[variant]
|
modes = SPIRAM_MODES[variant]
|
||||||
return cv.Schema(
|
return cv.Schema(
|
||||||
{
|
{
|
||||||
|
@@ -40,7 +40,13 @@ void RemoteTransmitterComponent::await_target_time_() {
|
|||||||
if (this->target_time_ == 0) {
|
if (this->target_time_ == 0) {
|
||||||
this->target_time_ = current_time;
|
this->target_time_ = current_time;
|
||||||
} else if ((int32_t) (this->target_time_ - current_time) > 0) {
|
} else if ((int32_t) (this->target_time_ - current_time) > 0) {
|
||||||
|
#if defined(USE_LIBRETINY)
|
||||||
|
// busy loop for libretiny is required (see the comment inside micros() in wiring.c)
|
||||||
|
while ((int32_t) (this->target_time_ - micros()) > 0)
|
||||||
|
;
|
||||||
|
#else
|
||||||
delayMicroseconds(this->target_time_ - current_time);
|
delayMicroseconds(this->target_time_ - current_time);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -1,9 +1,10 @@
|
|||||||
|
from ast import literal_eval
|
||||||
import logging
|
import logging
|
||||||
import math
|
import math
|
||||||
import re
|
import re
|
||||||
|
|
||||||
import jinja2 as jinja
|
import jinja2 as jinja
|
||||||
from jinja2.nativetypes import NativeEnvironment
|
from jinja2.sandbox import SandboxedEnvironment
|
||||||
|
|
||||||
TemplateError = jinja.TemplateError
|
TemplateError = jinja.TemplateError
|
||||||
TemplateSyntaxError = jinja.TemplateSyntaxError
|
TemplateSyntaxError = jinja.TemplateSyntaxError
|
||||||
@@ -70,7 +71,7 @@ class Jinja:
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, context_vars):
|
def __init__(self, context_vars):
|
||||||
self.env = NativeEnvironment(
|
self.env = SandboxedEnvironment(
|
||||||
trim_blocks=True,
|
trim_blocks=True,
|
||||||
lstrip_blocks=True,
|
lstrip_blocks=True,
|
||||||
block_start_string="<%",
|
block_start_string="<%",
|
||||||
@@ -90,6 +91,15 @@ class Jinja:
|
|||||||
**SAFE_GLOBAL_FUNCTIONS,
|
**SAFE_GLOBAL_FUNCTIONS,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def safe_eval(self, expr):
|
||||||
|
try:
|
||||||
|
result = literal_eval(expr)
|
||||||
|
if not isinstance(result, str):
|
||||||
|
return result
|
||||||
|
except (ValueError, SyntaxError, MemoryError, TypeError):
|
||||||
|
pass
|
||||||
|
return expr
|
||||||
|
|
||||||
def expand(self, content_str):
|
def expand(self, content_str):
|
||||||
"""
|
"""
|
||||||
Renders a string that may contain Jinja expressions or statements
|
Renders a string that may contain Jinja expressions or statements
|
||||||
@@ -106,7 +116,7 @@ class Jinja:
|
|||||||
override_vars = content_str.upvalues
|
override_vars = content_str.upvalues
|
||||||
try:
|
try:
|
||||||
template = self.env.from_string(content_str)
|
template = self.env.from_string(content_str)
|
||||||
result = template.render(override_vars)
|
result = self.safe_eval(template.render(override_vars))
|
||||||
if isinstance(result, Undefined):
|
if isinstance(result, Undefined):
|
||||||
# This happens when the expression is simply an undefined variable. Jinja does not
|
# This happens when the expression is simply an undefined variable. Jinja does not
|
||||||
# raise an exception, instead we get "Undefined".
|
# raise an exception, instead we get "Undefined".
|
||||||
|
@@ -829,15 +829,28 @@ void WebServer::handle_cover_request(AsyncWebServerRequest *request, const UrlMa
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto call = obj->make_call();
|
auto call = obj->make_call();
|
||||||
if (match.method_equals("open")) {
|
|
||||||
call.set_command_open();
|
// Lookup table for cover methods
|
||||||
} else if (match.method_equals("close")) {
|
static const struct {
|
||||||
call.set_command_close();
|
const char *name;
|
||||||
} else if (match.method_equals("stop")) {
|
cover::CoverCall &(cover::CoverCall::*action)();
|
||||||
call.set_command_stop();
|
} METHODS[] = {
|
||||||
} else if (match.method_equals("toggle")) {
|
{"open", &cover::CoverCall::set_command_open},
|
||||||
call.set_command_toggle();
|
{"close", &cover::CoverCall::set_command_close},
|
||||||
} else if (!match.method_equals("set")) {
|
{"stop", &cover::CoverCall::set_command_stop},
|
||||||
|
{"toggle", &cover::CoverCall::set_command_toggle},
|
||||||
|
};
|
||||||
|
|
||||||
|
bool found = false;
|
||||||
|
for (const auto &method : METHODS) {
|
||||||
|
if (match.method_equals(method.name)) {
|
||||||
|
(call.*method.action)();
|
||||||
|
found = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!found && !match.method_equals("set")) {
|
||||||
request->send(404);
|
request->send(404);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -1483,15 +1496,28 @@ void WebServer::handle_valve_request(AsyncWebServerRequest *request, const UrlMa
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto call = obj->make_call();
|
auto call = obj->make_call();
|
||||||
if (match.method_equals("open")) {
|
|
||||||
call.set_command_open();
|
// Lookup table for valve methods
|
||||||
} else if (match.method_equals("close")) {
|
static const struct {
|
||||||
call.set_command_close();
|
const char *name;
|
||||||
} else if (match.method_equals("stop")) {
|
valve::ValveCall &(valve::ValveCall::*action)();
|
||||||
call.set_command_stop();
|
} METHODS[] = {
|
||||||
} else if (match.method_equals("toggle")) {
|
{"open", &valve::ValveCall::set_command_open},
|
||||||
call.set_command_toggle();
|
{"close", &valve::ValveCall::set_command_close},
|
||||||
} else if (!match.method_equals("set")) {
|
{"stop", &valve::ValveCall::set_command_stop},
|
||||||
|
{"toggle", &valve::ValveCall::set_command_toggle},
|
||||||
|
};
|
||||||
|
|
||||||
|
bool found = false;
|
||||||
|
for (const auto &method : METHODS) {
|
||||||
|
if (match.method_equals(method.name)) {
|
||||||
|
(call.*method.action)();
|
||||||
|
found = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!found && !match.method_equals("set")) {
|
||||||
request->send(404);
|
request->send(404);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -1555,17 +1581,28 @@ void WebServer::handle_alarm_control_panel_request(AsyncWebServerRequest *reques
|
|||||||
auto call = obj->make_call();
|
auto call = obj->make_call();
|
||||||
parse_string_param_(request, "code", call, &decltype(call)::set_code);
|
parse_string_param_(request, "code", call, &decltype(call)::set_code);
|
||||||
|
|
||||||
if (match.method_equals("disarm")) {
|
// Lookup table for alarm control panel methods
|
||||||
call.disarm();
|
static const struct {
|
||||||
} else if (match.method_equals("arm_away")) {
|
const char *name;
|
||||||
call.arm_away();
|
alarm_control_panel::AlarmControlPanelCall &(alarm_control_panel::AlarmControlPanelCall::*action)();
|
||||||
} else if (match.method_equals("arm_home")) {
|
} METHODS[] = {
|
||||||
call.arm_home();
|
{"disarm", &alarm_control_panel::AlarmControlPanelCall::disarm},
|
||||||
} else if (match.method_equals("arm_night")) {
|
{"arm_away", &alarm_control_panel::AlarmControlPanelCall::arm_away},
|
||||||
call.arm_night();
|
{"arm_home", &alarm_control_panel::AlarmControlPanelCall::arm_home},
|
||||||
} else if (match.method_equals("arm_vacation")) {
|
{"arm_night", &alarm_control_panel::AlarmControlPanelCall::arm_night},
|
||||||
call.arm_vacation();
|
{"arm_vacation", &alarm_control_panel::AlarmControlPanelCall::arm_vacation},
|
||||||
} else {
|
};
|
||||||
|
|
||||||
|
bool found = false;
|
||||||
|
for (const auto &method : METHODS) {
|
||||||
|
if (match.method_equals(method.name)) {
|
||||||
|
(call.*method.action)();
|
||||||
|
found = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!found) {
|
||||||
request->send(404);
|
request->send(404);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -1731,24 +1768,24 @@ bool WebServer::canHandle(AsyncWebServerRequest *request) const {
|
|||||||
const auto &url = request->url();
|
const auto &url = request->url();
|
||||||
const auto method = request->method();
|
const auto method = request->method();
|
||||||
|
|
||||||
// Simple URL checks
|
// Static URL checks
|
||||||
if (url == "/")
|
static const char *const STATIC_URLS[] = {
|
||||||
return true;
|
"/",
|
||||||
|
|
||||||
#ifdef USE_ARDUINO
|
#ifdef USE_ARDUINO
|
||||||
if (url == "/events")
|
"/events",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef USE_WEBSERVER_CSS_INCLUDE
|
#ifdef USE_WEBSERVER_CSS_INCLUDE
|
||||||
if (url == "/0.css")
|
"/0.css",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef USE_WEBSERVER_JS_INCLUDE
|
#ifdef USE_WEBSERVER_JS_INCLUDE
|
||||||
if (url == "/0.js")
|
"/0.js",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
for (const auto &static_url : STATIC_URLS) {
|
||||||
|
if (url == static_url)
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef USE_WEBSERVER_PRIVATE_NETWORK_ACCESS
|
#ifdef USE_WEBSERVER_PRIVATE_NETWORK_ACCESS
|
||||||
if (method == HTTP_OPTIONS && request->hasHeader(HEADER_CORS_REQ_PNA))
|
if (method == HTTP_OPTIONS && request->hasHeader(HEADER_CORS_REQ_PNA))
|
||||||
@@ -1768,92 +1805,87 @@ bool WebServer::canHandle(AsyncWebServerRequest *request) const {
|
|||||||
if (!is_get_or_post)
|
if (!is_get_or_post)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// GET-only components
|
// Use lookup tables for domain checks
|
||||||
if (is_get) {
|
static const char *const GET_ONLY_DOMAINS[] = {
|
||||||
#ifdef USE_SENSOR
|
#ifdef USE_SENSOR
|
||||||
if (match.domain_equals("sensor"))
|
"sensor",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_BINARY_SENSOR
|
#ifdef USE_BINARY_SENSOR
|
||||||
if (match.domain_equals("binary_sensor"))
|
"binary_sensor",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_TEXT_SENSOR
|
#ifdef USE_TEXT_SENSOR
|
||||||
if (match.domain_equals("text_sensor"))
|
"text_sensor",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_EVENT
|
#ifdef USE_EVENT
|
||||||
if (match.domain_equals("event"))
|
"event",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
}
|
};
|
||||||
|
|
||||||
// GET+POST components
|
static const char *const GET_POST_DOMAINS[] = {
|
||||||
if (is_get_or_post) {
|
|
||||||
#ifdef USE_SWITCH
|
#ifdef USE_SWITCH
|
||||||
if (match.domain_equals("switch"))
|
"switch",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_BUTTON
|
#ifdef USE_BUTTON
|
||||||
if (match.domain_equals("button"))
|
"button",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_FAN
|
#ifdef USE_FAN
|
||||||
if (match.domain_equals("fan"))
|
"fan",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_LIGHT
|
#ifdef USE_LIGHT
|
||||||
if (match.domain_equals("light"))
|
"light",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_COVER
|
#ifdef USE_COVER
|
||||||
if (match.domain_equals("cover"))
|
"cover",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_NUMBER
|
#ifdef USE_NUMBER
|
||||||
if (match.domain_equals("number"))
|
"number",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_DATETIME_DATE
|
#ifdef USE_DATETIME_DATE
|
||||||
if (match.domain_equals("date"))
|
"date",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_DATETIME_TIME
|
#ifdef USE_DATETIME_TIME
|
||||||
if (match.domain_equals("time"))
|
"time",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_DATETIME_DATETIME
|
#ifdef USE_DATETIME_DATETIME
|
||||||
if (match.domain_equals("datetime"))
|
"datetime",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_TEXT
|
#ifdef USE_TEXT
|
||||||
if (match.domain_equals("text"))
|
"text",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_SELECT
|
#ifdef USE_SELECT
|
||||||
if (match.domain_equals("select"))
|
"select",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_CLIMATE
|
#ifdef USE_CLIMATE
|
||||||
if (match.domain_equals("climate"))
|
"climate",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_LOCK
|
#ifdef USE_LOCK
|
||||||
if (match.domain_equals("lock"))
|
"lock",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_VALVE
|
#ifdef USE_VALVE
|
||||||
if (match.domain_equals("valve"))
|
"valve",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_ALARM_CONTROL_PANEL
|
#ifdef USE_ALARM_CONTROL_PANEL
|
||||||
if (match.domain_equals("alarm_control_panel"))
|
"alarm_control_panel",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef USE_UPDATE
|
#ifdef USE_UPDATE
|
||||||
if (match.domain_equals("update"))
|
"update",
|
||||||
return true;
|
|
||||||
#endif
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
// Check GET-only domains
|
||||||
|
if (is_get) {
|
||||||
|
for (const auto &domain : GET_ONLY_DOMAINS) {
|
||||||
|
if (match.domain_equals(domain))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check GET+POST domains
|
||||||
|
if (is_get_or_post) {
|
||||||
|
for (const auto &domain : GET_POST_DOMAINS) {
|
||||||
|
if (match.domain_equals(domain))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
|
@@ -5,6 +5,9 @@ substitutions:
|
|||||||
var21: '79'
|
var21: '79'
|
||||||
value: 33
|
value: 33
|
||||||
values: 44
|
values: 44
|
||||||
|
position:
|
||||||
|
x: 79
|
||||||
|
y: 82
|
||||||
|
|
||||||
esphome:
|
esphome:
|
||||||
name: test
|
name: test
|
||||||
@@ -26,3 +29,7 @@ test_list:
|
|||||||
- Literal $values ${are not substituted}
|
- Literal $values ${are not substituted}
|
||||||
- ["list $value", "${is not}", "${substituted}"]
|
- ["list $value", "${is not}", "${substituted}"]
|
||||||
- {"$dictionary": "$value", "${is not}": "${substituted}"}
|
- {"$dictionary": "$value", "${is not}": "${substituted}"}
|
||||||
|
- |-
|
||||||
|
{{{ "x", "79"}, { "y", "82"}}}
|
||||||
|
- '{{{"AA"}}}'
|
||||||
|
- '"HELLO"'
|
||||||
|
@@ -8,6 +8,9 @@ substitutions:
|
|||||||
var21: "79"
|
var21: "79"
|
||||||
value: 33
|
value: 33
|
||||||
values: 44
|
values: 44
|
||||||
|
position:
|
||||||
|
x: 79
|
||||||
|
y: 82
|
||||||
|
|
||||||
test_list:
|
test_list:
|
||||||
- "$var1"
|
- "$var1"
|
||||||
@@ -27,3 +30,7 @@ test_list:
|
|||||||
- !literal Literal $values ${are not substituted}
|
- !literal Literal $values ${are not substituted}
|
||||||
- !literal ["list $value", "${is not}", "${substituted}"]
|
- !literal ["list $value", "${is not}", "${substituted}"]
|
||||||
- !literal {"$dictionary": "$value", "${is not}": "${substituted}"}
|
- !literal {"$dictionary": "$value", "${is not}": "${substituted}"}
|
||||||
|
- |- # Test parsing things that look like a python set of sets when rendered:
|
||||||
|
{{{ "x", "${ position.x }"}, { "y", "${ position.y }"}}}
|
||||||
|
- ${ '{{{"AA"}}}' }
|
||||||
|
- ${ '"HELLO"' }
|
||||||
|
Reference in New Issue
Block a user