Allow simpler automation syntax

This commit is contained in:
Otto Winter 2018-06-13 21:27:58 +02:00
parent 9bb06782b2
commit 6c6d21a7ab
No known key found for this signature in database
GPG key ID: DB66C0BE6013F97E
10 changed files with 70 additions and 51 deletions

View file

@ -132,6 +132,22 @@ OrCondition = esphomelib_ns.OrCondition
RangeCondition = esphomelib_ns.RangeCondition RangeCondition = esphomelib_ns.RangeCondition
LambdaCondition = esphomelib_ns.LambdaCondition LambdaCondition = esphomelib_ns.LambdaCondition
def validate_automation(extra_schema=None):
schema = AUTOMATION_SCHEMA.extend(extra_schema or {})
def validator(value):
if isinstance(value, list):
return schema({CONF_THEN: value})
elif isinstance(value, dict):
if CONF_THEN in value:
return schema(value)
return schema({CONF_THEN: value})
return schema(value)
return validator
AUTOMATION_SCHEMA = vol.Schema({ AUTOMATION_SCHEMA = vol.Schema({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(None), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(None),
cv.GenerateID(CONF_AUTOMATION_ID): cv.declare_variable_id(None), cv.GenerateID(CONF_AUTOMATION_ID): cv.declare_variable_id(None),
@ -391,18 +407,19 @@ def build_actions(config, arg_type):
def build_automation_(trigger, arg_type, config): def build_automation_(trigger, arg_type, config):
rhs = App.make_automation(trigger) rhs = App.make_automation(TemplateArguments(arg_type), trigger)
type = Automation.template(arg_type) type = Automation.template(arg_type)
obj = Pvariable(config[CONF_AUTOMATION_ID], rhs, type=type) obj = Pvariable(config[CONF_AUTOMATION_ID], rhs, type=type)
if CONF_IF in config: if CONF_IF in config:
conditions = None conditions = None
for conditions in build_conditions(config[CONF_IF], arg_type): for conditions in build_conditions(config[CONF_IF], arg_type):
yield yield None
add(obj.add_conditions(conditions)) add(obj.add_conditions(conditions))
actions = None actions = None
for actions in build_actions(config[CONF_THEN], arg_type): for actions in build_actions(config[CONF_THEN], arg_type):
yield yield None
add(obj.add_actions(actions)) add(obj.add_actions(actions))
yield obj
def build_automation(trigger, arg_type, config): def build_automation(trigger, arg_type, config):

View file

@ -47,19 +47,19 @@ BINARY_SENSOR_SCHEMA = cv.MQTT_COMPONENT_SCHEMA.extend({
vol.Optional(CONF_DEVICE_CLASS): vol.All(vol.Lower, cv.one_of(*DEVICE_CLASSES)), vol.Optional(CONF_DEVICE_CLASS): vol.All(vol.Lower, cv.one_of(*DEVICE_CLASSES)),
vol.Optional(CONF_FILTERS): FILTERS_SCHEMA, vol.Optional(CONF_FILTERS): FILTERS_SCHEMA,
vol.Optional(CONF_ON_PRESS): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_PRESS): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(PressTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(PressTrigger),
})]), })]),
vol.Optional(CONF_ON_RELEASE): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_RELEASE): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ReleaseTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ReleaseTrigger),
})]), })]),
vol.Optional(CONF_ON_CLICK): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_CLICK): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ClickTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ClickTrigger),
vol.Optional(CONF_MIN_LENGTH, default='50ms'): cv.positive_time_period_milliseconds, vol.Optional(CONF_MIN_LENGTH, default='50ms'): cv.positive_time_period_milliseconds,
vol.Optional(CONF_MAX_LENGTH, default='350ms'): cv.positive_time_period_milliseconds, vol.Optional(CONF_MAX_LENGTH, default='350ms'): cv.positive_time_period_milliseconds,
})]), })]),
vol.Optional(CONF_ON_DOUBLE_CLICK): vol.Optional(CONF_ON_DOUBLE_CLICK):
vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(DoubleClickTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(DoubleClickTrigger),
vol.Optional(CONF_MIN_LENGTH, default='50ms'): cv.positive_time_period_milliseconds, vol.Optional(CONF_MIN_LENGTH, default='50ms'): cv.positive_time_period_milliseconds,
vol.Optional(CONF_MAX_LENGTH, default='350ms'): cv.positive_time_period_milliseconds, vol.Optional(CONF_MAX_LENGTH, default='350ms'): cv.positive_time_period_milliseconds,

View file

@ -13,9 +13,9 @@ PLATFORM_SCHEMA = cv.nameable(cover.COVER_PLATFORM_SCHEMA.extend({
cv.GenerateID(CONF_MAKE_ID): cv.declare_variable_id(MakeTemplateCover), cv.GenerateID(CONF_MAKE_ID): cv.declare_variable_id(MakeTemplateCover),
vol.Optional(CONF_LAMBDA): cv.lambda_, vol.Optional(CONF_LAMBDA): cv.lambda_,
vol.Optional(CONF_OPTIMISTIC): cv.boolean, vol.Optional(CONF_OPTIMISTIC): cv.boolean,
vol.Optional(CONF_OPEN_ACTION): automation.ACTIONS_SCHEMA, vol.Optional(CONF_OPEN_ACTION): automation.validate_automation(),
vol.Optional(CONF_CLOSE_ACTION): automation.ACTIONS_SCHEMA, vol.Optional(CONF_CLOSE_ACTION): automation.validate_automation(),
vol.Optional(CONF_STOP_ACTION): automation.ACTIONS_SCHEMA, vol.Optional(CONF_STOP_ACTION): automation.validate_automation(),
}), cv.has_at_least_one_key(CONF_LAMBDA, CONF_OPTIMISTIC)) }), cv.has_at_least_one_key(CONF_LAMBDA, CONF_OPTIMISTIC))
@ -30,20 +30,14 @@ def to_code(config):
yield yield
add(make.Ptemplate_.set_state_lambda(template_)) add(make.Ptemplate_.set_state_lambda(template_))
if CONF_OPEN_ACTION in config: if CONF_OPEN_ACTION in config:
actions = None automation.build_automation(make.Ptemplate_.get_open_trigger(), NoArg,
for actions in automation.build_actions(config[CONF_OPEN_ACTION], NoArg): config[CONF_OPEN_ACTION])
yield
add(make.Ptemplate_.add_open_actions(actions))
if CONF_CLOSE_ACTION in config: if CONF_CLOSE_ACTION in config:
actions = None automation.build_automation(make.Ptemplate_.get_close_trigger(), NoArg,
for actions in automation.build_actions(config[CONF_CLOSE_ACTION], NoArg): config[CONF_CLOSE_ACTION])
yield
add(make.Ptemplate_.add_close_actions(actions))
if CONF_STOP_ACTION in config: if CONF_STOP_ACTION in config:
actions = None automation.build_automation(make.Ptemplate_.get_stop_trigger(), NoArg,
for actions in automation.build_actions(config[CONF_STOP_ACTION], NoArg): config[CONF_STOP_ACTION])
yield
add(make.Ptemplate_.add_stop_actions(actions))
if CONF_OPTIMISTIC in config: if CONF_OPTIMISTIC in config:
add(make.Ptemplate_.set_optimistic(config[CONF_OPTIMISTIC])) add(make.Ptemplate_.set_optimistic(config[CONF_OPTIMISTIC]))

View file

@ -72,7 +72,7 @@ CONFIG_SCHEMA = vol.Schema({
cv.ensure_list, [validate_fingerprint]), cv.ensure_list, [validate_fingerprint]),
vol.Optional(CONF_KEEPALIVE): cv.positive_time_period_seconds, vol.Optional(CONF_KEEPALIVE): cv.positive_time_period_seconds,
vol.Optional(CONF_REBOOT_TIMEOUT): cv.positive_time_period_milliseconds, vol.Optional(CONF_REBOOT_TIMEOUT): cv.positive_time_period_milliseconds,
vol.Optional(CONF_ON_MESSAGE): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_MESSAGE): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(MQTTMessageTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(MQTTMessageTrigger),
vol.Required(CONF_TOPIC): cv.publish_topic, vol.Required(CONF_TOPIC): cv.publish_topic,
vol.Optional(CONF_QOS, default=0): cv.mqtt_qos, vol.Optional(CONF_QOS, default=0): cv.mqtt_qos,

View file

@ -18,11 +18,21 @@ DUMPERS = {
'sony': remote_ns.SonyDumper, 'sony': remote_ns.SonyDumper,
} }
def validate_dumpers_all(value):
if not isinstance(value, (str, unicode)):
raise vol.Invalid("Not valid dumpers")
if value.upper() == "ALL":
return list(DUMPERS)
raise vol.Invalid("Not valid dumpers")
CONFIG_SCHEMA = vol.All(cv.ensure_list, [vol.Schema({ CONFIG_SCHEMA = vol.All(cv.ensure_list, [vol.Schema({
cv.GenerateID(): cv.declare_variable_id(RemoteReceiverComponent), cv.GenerateID(): cv.declare_variable_id(RemoteReceiverComponent),
vol.Required(CONF_PIN): pins.gpio_input_pin_schema, vol.Required(CONF_PIN): pins.gpio_input_pin_schema,
vol.Optional(CONF_DUMP, default=[]): vol.All(cv.ensure_list, vol.Optional(CONF_DUMP, default=[]):
[vol.All(vol.Lower, cv.one_of(*DUMPERS))]), vol.Any(validate_dumpers_all,
vol.All(cv.ensure_list, [vol.All(vol.Lower, cv.one_of(*DUMPERS))])),
vol.Optional(CONF_TOLERANCE): vol.All(cv.percentage_int, vol.Range(min=0)), vol.Optional(CONF_TOLERANCE): vol.All(cv.percentage_int, vol.Range(min=0)),
vol.Optional(CONF_BUFFER_SIZE): cv.validate_bytes, vol.Optional(CONF_BUFFER_SIZE): cv.validate_bytes,
vol.Optional(CONF_FILTER): cv.positive_time_period_microseconds, vol.Optional(CONF_FILTER): cv.positive_time_period_microseconds,

View file

@ -72,20 +72,19 @@ ValueRangeTrigger = sensor_ns.ValueRangeTrigger
SENSOR_SCHEMA = cv.MQTT_COMPONENT_SCHEMA.extend({ SENSOR_SCHEMA = cv.MQTT_COMPONENT_SCHEMA.extend({
cv.GenerateID(CONF_MQTT_ID): cv.declare_variable_id(MQTTSensorComponent), cv.GenerateID(CONF_MQTT_ID): cv.declare_variable_id(MQTTSensorComponent),
cv.GenerateID(): cv.declare_variable_id(Sensor), cv.GenerateID(): cv.declare_variable_id(Sensor),
vol.Required(CONF_NAME): cv.string,
vol.Optional(CONF_UNIT_OF_MEASUREMENT): cv.string_strict, vol.Optional(CONF_UNIT_OF_MEASUREMENT): cv.string_strict,
vol.Optional(CONF_ICON): cv.icon, vol.Optional(CONF_ICON): cv.icon,
vol.Optional(CONF_ACCURACY_DECIMALS): vol.Coerce(int), vol.Optional(CONF_ACCURACY_DECIMALS): vol.Coerce(int),
vol.Optional(CONF_EXPIRE_AFTER): vol.Any(None, cv.positive_time_period_milliseconds), vol.Optional(CONF_EXPIRE_AFTER): vol.Any(None, cv.positive_time_period_milliseconds),
vol.Optional(CONF_FILTERS): FILTERS_SCHEMA, vol.Optional(CONF_FILTERS): FILTERS_SCHEMA,
vol.Optional(CONF_ON_VALUE): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_VALUE): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(SensorValueTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(SensorValueTrigger),
})]), })]),
vol.Optional(CONF_ON_RAW_VALUE): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_RAW_VALUE): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(RawSensorValueTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(RawSensorValueTrigger),
})]), })]),
vol.Optional(CONF_ON_VALUE_RANGE): vol.All(cv.ensure_list, [vol.All( vol.Optional(CONF_ON_VALUE_RANGE): vol.All(cv.ensure_list, [vol.All(
automation.AUTOMATION_SCHEMA.extend({ automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ValueRangeTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ValueRangeTrigger),
vol.Optional(CONF_ABOVE): vol.Coerce(float), vol.Optional(CONF_ABOVE): vol.Coerce(float),
vol.Optional(CONF_BELOW): vol.Coerce(float), vol.Optional(CONF_BELOW): vol.Coerce(float),

View file

@ -22,6 +22,8 @@ PanasonicTransmitter = remote_ns.PanasonicTransmitter
RawTransmitter = remote_ns.RawTransmitter RawTransmitter = remote_ns.RawTransmitter
SonyTransmitter = remote_ns.SonyTransmitter SonyTransmitter = remote_ns.SonyTransmitter
validate_raw_data = [vol.Any(vol.Coerce(int), cv.time_period_microseconds)]
PLATFORM_SCHEMA = cv.nameable(switch.SWITCH_PLATFORM_SCHEMA.extend({ PLATFORM_SCHEMA = cv.nameable(switch.SWITCH_PLATFORM_SCHEMA.extend({
vol.Optional(CONF_LG): vol.Schema({ vol.Optional(CONF_LG): vol.Schema({
vol.Required(CONF_DATA): cv.hex_uint32_t, vol.Required(CONF_DATA): cv.hex_uint32_t,
@ -39,10 +41,10 @@ PLATFORM_SCHEMA = cv.nameable(switch.SWITCH_PLATFORM_SCHEMA.extend({
vol.Required(CONF_ADDRESS): cv.hex_uint16_t, vol.Required(CONF_ADDRESS): cv.hex_uint16_t,
vol.Required(CONF_COMMAND): cv.hex_uint32_t, vol.Required(CONF_COMMAND): cv.hex_uint32_t,
}), }),
vol.Optional(CONF_RAW): vol.Schema({ vol.Optional(CONF_RAW): vol.Any(validate_raw_data, vol.Schema({
vol.Required(CONF_DATA): [vol.Any(vol.Coerce(int), cv.time_period_microseconds)], vol.Required(CONF_DATA): validate_raw_data,
vol.Optional(CONF_CARRIER_FREQUENCY): vol.All(cv.frequency, vol.Coerce(int)), vol.Optional(CONF_CARRIER_FREQUENCY): vol.All(cv.frequency, vol.Coerce(int)),
}), })),
vol.Optional(CONF_REPEAT): vol.Any(cv.positive_not_null_int, vol.Schema({ vol.Optional(CONF_REPEAT): vol.Any(cv.positive_not_null_int, vol.Schema({
vol.Required(CONF_TIMES): cv.positive_not_null_int, vol.Required(CONF_TIMES): cv.positive_not_null_int,
vol.Required(CONF_WAIT_TIME): cv.positive_time_period_microseconds, vol.Required(CONF_WAIT_TIME): cv.positive_time_period_microseconds,
@ -69,8 +71,14 @@ def transmitter_base(config):
return SonyTransmitter.new(config[CONF_NAME], conf[CONF_DATA], conf[CONF_NBITS]) return SonyTransmitter.new(config[CONF_NAME], conf[CONF_DATA], conf[CONF_NBITS])
elif CONF_RAW in config: elif CONF_RAW in config:
conf = config[CONF_RAW] conf = config[CONF_RAW]
data = ArrayInitializer(*conf[CONF_DATA]) if isinstance(conf, dict):
return RawTransmitter.new(data, conf[CONF_CARRIER_FREQUENCY]) data = conf[CONF_DATA]
carrier_frequency = conf.get(CONF_CARRIER_FREQUENCY)
else:
data = conf
carrier_frequency = None
return RawTransmitter.new(config[CONF_NAME], ArrayInitializer(*data, multiline=False),
carrier_frequency)
else: else:
raise ValueError("Unknown transmitter type {}".format(config)) raise ValueError("Unknown transmitter type {}".format(config))

View file

@ -14,8 +14,8 @@ PLATFORM_SCHEMA = cv.nameable(switch.SWITCH_PLATFORM_SCHEMA.extend({
cv.GenerateID(CONF_MAKE_ID): cv.declare_variable_id(MakeTemplateSwitch), cv.GenerateID(CONF_MAKE_ID): cv.declare_variable_id(MakeTemplateSwitch),
vol.Optional(CONF_LAMBDA): cv.lambda_, vol.Optional(CONF_LAMBDA): cv.lambda_,
vol.Optional(CONF_OPTIMISTIC): cv.boolean, vol.Optional(CONF_OPTIMISTIC): cv.boolean,
vol.Optional(CONF_TURN_OFF_ACTION): automation.ACTIONS_SCHEMA, vol.Optional(CONF_TURN_OFF_ACTION): automation.validate_automation(),
vol.Optional(CONF_TURN_ON_ACTION): automation.ACTIONS_SCHEMA, vol.Optional(CONF_TURN_ON_ACTION): automation.validate_automation(),
}), cv.has_at_least_one_key(CONF_LAMBDA, CONF_OPTIMISTIC)) }), cv.has_at_least_one_key(CONF_LAMBDA, CONF_OPTIMISTIC))
@ -30,15 +30,11 @@ def to_code(config):
yield yield
add(make.Ptemplate_.set_state_lambda(template_)) add(make.Ptemplate_.set_state_lambda(template_))
if CONF_TURN_OFF_ACTION in config: if CONF_TURN_OFF_ACTION in config:
actions = None automation.build_automation(make.Ptemplate_.get_turn_off_trigger(), NoArg,
for actions in automation.build_actions(config[CONF_TURN_OFF_ACTION], NoArg): config[CONF_TURN_OFF_ACTION])
yield
add(make.Ptemplate_.add_turn_off_actions(actions))
if CONF_TURN_ON_ACTION in config: if CONF_TURN_ON_ACTION in config:
actions = None automation.build_automation(make.Ptemplate_.get_turn_on_trigger(), NoArg,
for actions in automation.build_actions(config[CONF_TURN_ON_ACTION], NoArg): config[CONF_TURN_ON_ACTION])
yield
add(make.Ptemplate_.add_turn_on_actions(actions))
if CONF_OPTIMISTIC in config: if CONF_OPTIMISTIC in config:
add(make.Ptemplate_.set_optimistic(config[CONF_OPTIMISTIC])) add(make.Ptemplate_.set_optimistic(config[CONF_OPTIMISTIC]))

View file

@ -11,11 +11,6 @@
"6052/tcp": 6052, "6052/tcp": 6052,
"6053/tcp": 6053 "6053/tcp": 6053
}, },
"arch": [
"amd64",
"armhf",
"i386"
],
"auto_uart": true, "auto_uart": true,
"map": [ "map": [
"config:rw" "config:rw"

View file

@ -32,11 +32,11 @@ CORE_SCHEMA = vol.Schema({
vol.Optional(CONF_SIMPLIFY, default=True): cv.boolean, vol.Optional(CONF_SIMPLIFY, default=True): cv.boolean,
vol.Optional(CONF_USE_BUILD_FLAGS, default=True): cv.boolean, vol.Optional(CONF_USE_BUILD_FLAGS, default=True): cv.boolean,
vol.Optional(CONF_BOARD_FLASH_MODE): vol.All(vol.Lower, cv.one_of(*BUILD_FLASH_MODES)), vol.Optional(CONF_BOARD_FLASH_MODE): vol.All(vol.Lower, cv.one_of(*BUILD_FLASH_MODES)),
vol.Optional(CONF_ON_BOOT): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_BOOT): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(StartupTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(StartupTrigger),
vol.Optional(CONF_PRIORITY): vol.Coerce(float), vol.Optional(CONF_PRIORITY): vol.Coerce(float),
})]), })]),
vol.Optional(CONF_ON_SHUTDOWN): vol.All(cv.ensure_list, [automation.AUTOMATION_SCHEMA.extend({ vol.Optional(CONF_ON_SHUTDOWN): vol.All(cv.ensure_list, [automation.validate_automation({
cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ShutdownTrigger), cv.GenerateID(CONF_TRIGGER_ID): cv.declare_variable_id(ShutdownTrigger),
})]), })]),
}) })