How to access a helper as an input in a blueprint template?

You cannot put an !input parameter inside a template in a blueprint definition. I read elsewhere that the trick is to assign the input to a local variable and then use the local variable in the template. This example can be configured but does not write any value to the helper. What is wrong with it?

input:
    event_description:
      name: Event description
      description: The global variable (helper) to hold the description of the current event (if any)
      selector:
        entity:
          domain: input_text
    event_temperature:
      name: Event temperature
      description: The global variable (helper) to hold the temperature specified in the current event (if any)
      selector:
        entity:
          domain: input_number

variables:
  local_event_description: !input event_description

          - service: input_number.set_value
            data:
              value: >-
                {% set temperature_text = states('local_event_description').split('#')[1] %}
                {{ '%0.1f' | format(float(temperature_text)) }}
            target:
              entity_id: !input event_temperature

The template was originally tested in an automation (where no local variable is needed), but failed when transferring it to a blueprint.

Does it have to do with the scope of the local variable? It is defined at the outer level of the blueprint as I could not get it accepted closer to the template.

I am not even sure how to debug this; how do I see inside local variables and templates?

Here is the full blueprint definition code at the present state of testing


### ----------------------------------------------------------------------------
### ANDY'S RADIATOR CONTROLLER
###
### Andy Symons 31-Jan-23
###
### Controls radiator temperature from a calendar,
###   allows temporary manual override,
###   and turns off radiator if a door or window is opened,
###   or if the room is unoccupied for a while
### ----------------------------------------------------------------------------

blueprint:
  name: Andys Radiator Controller
  description: Controls radiator temperature from a calendar, allows temporary manual override, and turns off radiator if a door or window is opened or if the room is unoccupied for a while
  domain: automation

  ### ----------------------------------------------------------------------------
  ### INPUTS
  ### ----------------------------------------------------------------------------

  input:

    radiator_thermostat:
      name: Radiator thermostat
      description: The device that controls the radiator TRV
      selector:
        entity:
          domain: climate

    radiator_set_temperature_sensor:
      name: Radiator thermostat set temperature
      description: A (template) sensor that reads the set temperature from the radiator thermostat
      selector:
        entity:
          domain: sensor

    radiator_calendar:
      name: Radiator calendar
      description: The calendar dedicated to scheduling events for this radiator
      selector:
        entity:
          domain: calendar

    door_or_window_opening_sensor:
      name: Door or window opening sensor
      description: The sensor [group] that detects whether any external door or window is open
      selector:
        entity:
          domain: binary_sensor
          device_class: opening

    door_or_window_open_recognition_time:
      name: Door or window open recognition time
      description: The time for which a door or window can be open before the heating switches off
      selector:
        time:
      default: "00:03:00"

    door_or_window_closed_recognition_time:
      name: Door or window closed recognition time
      description: The time for which a door or window has to be closed before the fact is used
      selector:
        time:
      default: "00:03:00"

    room_occupancy_sensor:
      name: Room occupancy sensor
      description: The sensor [group] that detects whether there is anyone in the room
      selector:
        entity:
          domain: binary_sensor
          device_class: occupancy

    room_occupancy_recognition_time:
      name: Room occupancy recognition time
      description: The time for which the room has to be unoccupied before the fact is used
      selector:
        time:
      default: "00:00:10"

    room_unoccupancy_recognition_time:
      name: Room unoccupancy recognition time
      description: The time for which the room can be unoccupied before the heating switches off (except suring the warm-up period)
      selector:
        time:
      default: "01:00:00"

    warmup_timer:
      name: Warmup timer
      description: The global variable (helper) to hold the timer for the event warmup period
      selector:
        entity:
          domain: timer

    warmup_period:
      name: Warmup period
      description: The period of time from the start of a new event for which room unoccupancy will be ignored
      selector:
        time:
      default: "02:00:00"

    event_name:
      name: Event name
      description: The global variable (helper) to hold the name (aka Summary) of the current event (if any)
      selector:
        entity:
          domain: input_text

    event_description:
      name: Event description
      description: The global variable (helper) to hold the description of the current event (if any)
      selector:
        entity:
          domain: input_text

    event_start:
      name: Event start
      description: The global variable (helper) to hold the start date and time of the current event (if any)
      selector:
        entity:
          domain: input_datetime

    event_end:
      name: Event end
      description: The global variable (helper) to hold the end date and time of the current event (if any)
      selector:
        entity:
          domain: input_datetime

    event_end_offset_time:
      name: Event end recognition time
      description: The time for which acting on an event end is deferred in order to detect a contiguous event
      selector:
        time:
      default: "00:01:00"

    event_temperature:
      name: Event temperature
      description: The global variable (helper) to hold the temperature specified in the current event (if any)
      selector:
        entity:
          domain: input_number

    manual_temperature:
      name: Manual temperature
      description: The global variable (helper) to hold the temperature specified by manual control of the device or the dashboard
      selector:
        entity:
          domain: input_number

    manual_mode_recognition_period:
      name: Manual mode recognition time
      description: The time period for which a manual setting has to be stable before it is taken as a new manual setting
      selector:
        time:
      default: "00:00:03"

    manual_override_timer:
      name: Manual override timer
      description: The global variable (helper) to hold the timer for a manual intervention
      selector:
        entity:
          domain: timer

    manual_override_period:
      name: Manual override period
      description: The time period for which a manual intervention will override the schedule
      selector:
        time:
      default: "01:00:00"

    setting_reason:
      name: Setting reason
      description: The global variable (helper) into which the automation writes the reason for the current setting (for use on a dashboard)
      selector:
        entity:
          domain: input_text

    echoblock_timer:
      name: Echoblock timer
      description: The timer for use inside the automation to disinguish genuine manual changes of the set temperature from those set by the automation
      selector:
        entity:
          domain: timer

    echoblock_period:
      name: Echoblock period
      description: The time period for which am echo may be received from the automation setting the thermostat 
      selector:
        time:
      default: "00:00:10"

mode: single

## ----------------------------------------------------------------------------
## LOCAL VARİABLES
## needed to capture global varable values for use in templates
## ----------------------------------------------------------------------------
variables:
  local_event_name: !input event_name
  local_event_description: !input event_description
  local_radiator_set_temperature: !input radiator_set_temperature_sensor

## ----------------------------------------------------------------------------
## TRIGGERS
## ----------------------------------------------------------------------------

trigger:
  # 1. Calendar event start
  - platform: calendar
    event: start
    entity_id: !input radiator_calendar
    id: event_start

  # 2. Calendar state to on
  # (Similar to event start but can be around 30 seconds later)
  - platform: state
    entity_id: !input radiator_calendar
    from: "off"
    to: "on"
    id: calendar_state_to_on

  # 3. Calendar event end
  - platform: calendar
    event: end
    offset: !input event_end_offset_time
    entity_id: !input radiator_calendar
    id: event_end

  # 4. Calendar state from on to off
  # (Similar to event end but can be around 30 seconds later)
  - platform: state
    entity_id: !input radiator_calendar
    from: "on"
    to: "off"
    id: calendar_state_to_off

  # 5. Change in the thermostat set temperature
  # (could be manual override but could also be an echo at this stage)
  - platform: state
    entity_id: !input radiator_set_temperature_sensor
    #for: !input manual_mode_recognition_period
    id: set_temperature_change
    
  # 6. End of manual override  
  - platform: state
    entity_id: !input manual_override_timer
    from: active
    to: idle
    id: manual_override_end
    
  # 7. Room becomes unoccupied
  - type: not_occupied
    platform: device
    device_id: 737e8f81fcac51fcdcdce5629ff6cb1a
    entity_id: !input room_occupancy_sensor
    domain: binary_sensor
    id: room_unoccupied
    #for: !input room_unoccupancy_recognition_time

  # 8. Room becomes occupied
  - type: occupied
    platform: device
    device_id: 737e8f81fcac51fcdcdce5629ff6cb1a
    entity_id: !input room_occupancy_sensor
    domain: binary_sensor
    id: room_occupied
    #for: "00:00:00" #!input room_occupancy_recognition_time

  # 9. A door or window is opened
  - type: opened
    id: door_or_window_opened
    platform: device
    device_id: 4b75acd529cf91315e5fe62a43a1a2b3
    entity_id: !input door_or_window_opening_sensor
    domain: binary_sensor
    #for: !input door_or_window_open_recognition_time

  # 10. All doors and windows closed
  - type: not_opened
    platform: device
    device_id: 4b75acd529cf91315e5fe62a43a1a2b3
    entity_id: !input door_or_window_opening_sensor
    domain: binary_sensor
    #for: "00:00:00" #!input door_or_window_closed_recognition_time
    id: doors_and_windows_closed


## ----------------------------------------------------------------------------
## ACTIONS STEP 1 -- SET THE STATE VARİABLES
## ----------------------------------------------------------------------------
action:
  - choose:
      #
      # a. Calendar event start
      #
      - conditions:
          - condition: trigger
            id: event_start
        sequence:
          # i. capture the event name, start, end and description
          - service: input_text.set_value
            data:
              value: "{{ trigger.calendar_event.summary }}"
            target:
              entity_id: !input event_name
          - service: input_datetime.set_datetime
            data:
              datetime: "{{ trigger.calendar_event.start }}"
            target:
              entity_id: !input event_start
          - service: input_datetime.set_datetime
            data:
              datetime: "{{ trigger.calendar_event.end }}"
            target:
              entity_id: !input event_end
          - service: input_text.set_value
            data:
              value: "{{ trigger.calendar_event.description }}"
            target:
              entity_id: !input event_description

          # ii. Extract the temperature from the description (enclosed in hashes) and round to one decimal place
          - service: input_number.set_value
            data:
              value: >-
                {% set temperature_text = states('local_event_description').split('#')[1] %}
                {{ '%0.1f' | format(float(temperature_text)) }}
            target:
              entity_id: !input event_temperature

          # iii. start the warmup period timer
          - service: timer.start
            data:
              duration: !input warmup_period
            target:
              entity_id: !input warmup_timer
      #
      # b. Calendar event end
      #
      - conditions:
          - condition: trigger
            id: event_end
          # Only act if the ending event is the current one; otherwise a consecutive event has already started
          - condition: template
            value_template: >-
              {{ trigger.calendar_event.summary == states('local_event_name') }}
        sequence:
          # i. Clear the event name 
          - service: input_text.set_value
            data:
              value: (none)
            target:
              entity_id: !input event_name
          # ii. Clear the event description 
          - service: input_text.set_value
            data:
              value: (none)
            target:
              entity_id: !input event_description
          # iii. Clear the event temperature 
          - service: input_number.set_value
            data:
              value: 5
            target:
              entity_id: !input event_temperature
          # iv. Clear the warmup timer 
          - service: timer.cancel
            data: {}
            target:
              entity_id: !input warmup_timer
      #
      # c. Manual override start
      #
      - conditions:
          - condition: trigger
            id: set_temperature_change
          #ignore if it is just an echo from a setting from this automation
          - condition: state
            entity_id: !input echoblock_timer
            state: idle
        sequence:
          - service: timer.start
            data:
              duration: !input manual_override_period
            target:
              entity_id: !input manual_override_timer
          - service: input_number.set_value
            data:
              value: "{{ states('local_radiator_set_temperature') }}"
            target:
              entity_id: !input manual_temperature
      #
      # d. Manual override end
      #
      - conditions:
          - condition: trigger
            id: manual_override_end
        sequence:
          - service: input_number.set_value
            data:
              value: 5
            target:
              entity_id: !input manual_temperature 


  ## ----------------------------------------------------------------------------
  ## ACTIONS STEP 2 -- SET THE TEMPERATURE ON THE THERMOSTAT AND RECORD WHY
  ## ----------------------------------------------------------------------------
  - choose:
      # 1. If a door or window has been open for the set time, turn the heating off
      - conditions:
          - condition: state
            state: "on"
            #for: "00:00:00" #!input door_or_window_open_recognition_time
            entity_id: !input door_or_window_opening_sensor
        sequence:
          - service: climate.set_temperature
            data:
              temperature: 5
            target:
              entity_id: !input radiator_thermostat
          - service: input_text.set_value
            data:
              value: Turned off because a door or window is open
            target:
              entity_id: !input setting_reason

      # 2. If the room has been unoccupied for the set time, turn the heating off
      - conditions:
          - condition: state
            entity_id: !input room_occupancy_sensor
            state: "off"
            #for: "00:00:00" #!input room_unoccupancy_recognition_time
            # Do not act on unoccupancy during the warmup period 
          - condition: state
            entity_id: !input warmup_timer
            state: idle
        sequence:
          - service: climate.set_temperature
            data:
              temperature: 5
            target:
              entity_id: !input radiator_thermostat
          - service: input_text.set_value
            data:
              value: Turned off because the room is unoccupied
            target:
              entity_id: !input setting_reason

      # 3. If there is a manual override in operation
      - conditions:
          - condition: state
            entity_id: !input manual_override_timer
            state: active
        sequence:
          - service: climate.set_temperature
            data:
              temperature: !input manual_temperature
            target:
              entity_id: !input radiator_thermostat
          - service: input_text.set_value
            data:
              value: Set manually
            target:
              entity_id: !input setting_reason

      # 4. If there is an active calendar event
      - conditions:
          - condition: state
            entity_id: !input radiator_calendar 
            state: "on"
        sequence:
          - service: climate.set_temperature
            data:
              temperature: !input event_temperature
            target:
              entity_id: !input radiator_thermostat
          - service: input_text.set_value
            data:
              value: Set according to a calendar event
            target:
              entity_id: !input setting_reason

      # 5. If there is no active calendar event
      - conditions:
          - condition: state
            entity_id: !input radiator_calendar
            state: "off"
        sequence:
          - service: climate.set_temperature
            data:
              temperature: 5
            target:
              entity_id: !input radiator_thermostat
          - service: input_text.set_value
            data:
              value: Turned off because nothing is scheduled
            target:
              entity_id: !input setting_reason

    # Default should never happen!
    default:
      - service: climate.set_temperature
        data:
          temperature: 5
        target:
          entity_id: !input radiator_thermostat
      - service: input_text.set_value
        data:
          value: Turned off by default
        target:
          entity_id: !input setting_reason

  # Start the echo-block timer
  - service: timer.start
    data:
      duration: !input echoblock_period
    target:
      entity_id: !input echoblock_timer



(The For: statements are commented out to circumvent another problem that I raised as a separate post)

Putting this in a template outputs the state of an entity with the ID local_event_description. As in that literal text. Since that’s not a valid entity ID that is always just going to output unknown.

Variables created with a variable step aren’t really different from variables created from set within a template, like you’re doing with temperature_text. You use it in the same way, by not wrapping it in quotes. So this:

{% set temperature_text = states(local_event_description).split('#')[1] %}
{{ '%0.1f' | format(float(temperature_text)) }}

@CentralCommand Great! That fixed it, thanks.