blueprint: name: Night Motion-activated Light description: Turn on a light when motion is detected at night (between sunset or specified time and sunrise or specified time) domain: automation source_url: https://github.com/jnrcorp/ha-blueprints/blob/main/night-motion-light/ha-blueprint-night-motion-light.yaml author: Joshua Ross input: motion_entity: name: Motion Sensor selector: entity: filter: device_class: motion domain: binary_sensor light_target: name: Light description: Light(s) to turn on when motion is detected selector: target: entity: - domain: light no_motion_wait: name: Wait time description: Time to leave the light on after last motion is detected. default: 120 selector: number: min: 0 max: 3600 unit_of_measurement: seconds start_choice: name: Start Boundary description: Choose whether the active window starts at sunset or at a specific time. default: sunset selector: select: options: - value: sunset label: Sunset - value: time label: Specific time start_time: name: Optional Start Time description: Explicit start time used when Start Boundary is set to "Specific time". default: "" selector: time: {} end_choice: name: End Boundary description: Choose whether the active window ends at sunrise or at a specific time. default: sunrise selector: select: options: - value: sunrise label: Sunrise - value: time label: Specific time end_time: name: Optional End Time description: Explicit end time used when End Boundary is set to "Specific time". default: "" selector: time: {} # If motion is detected within the delay, # we restart the script. mode: restart max_exceeded: silent trigger: platform: state entity_id: !input motion_entity from: "off" to: "on" variables: start_choice: !input start_choice end_choice: !input end_choice start_time: !input start_time end_time: !input end_time conditions: - condition: template value_template: >- {% set now_time = now().time() %} {# compute start time #} {% if start_choice == 'time' %} {% set start = strptime(start_time, '%H:%M:%S').time() if start_time else none %} {% else %} {# sunset logic: get last sunset's time #} {% set sunset = state_attr('sun.sun', 'next_setting') | as_datetime | as_local %} {% if sunset > now() %} {% set start = (sunset - timedelta(days=1)).time() %} {% else %} {% set start = sunset.time() %} {% endif %} {% endif %} {# compute end time #} {% if end_choice == 'time' %} {% set end = strptime(end_time, '%H:%M:%S').time() if end_time else none %} {% else %} {# sunrise logic: get next sunrise's time #} {% set end = (state_attr('sun.sun', 'next_rising') | as_datetime | as_local).time() %} {% endif %} {# if either boundary is missing, fail the condition #} {% if start is none or end is none %} false {% else %} {# check if current time is in the range, handling overnight ranges #} {% if start < end %} {{ start <= now_time < end }} {% else %} {{ now_time >= start or now_time < end }} {% endif %} {% endif %} action: - alias: "Turn on the light" service: light.turn_on target: !input light_target - alias: "Wait until there is no motion from device" wait_for_trigger: platform: state entity_id: !input motion_entity from: "on" to: "off" - alias: "Wait the number of seconds that has been set" delay: !input no_motion_wait - alias: "Turn off the light" service: light.turn_off target: !input light_target