Automatisation de la Pompe de Filtration de Piscine en Fonction de la Température

Bonjour à tous,

Je souhaite partager avec vous une solution que j’ai mise en place pour l’automatisation de la pompe de filtration de ma piscine en fonction de la température de l’eau. Cette solution utilise des blueprints pour Home Assistant et intègre la gestion des événements dans un calendrier pour une automatisation complète et dynamique.

Screenshot 2024-05-15 224925

Fonctionnalités :

  • Calcul dynamique de la durée de filtration en fonction de la température de l’eau.
  • Planification automatique des périodes de filtration dans un calendrier.
  • Activation et désactivation automatique de la pompe de filtration selon les événements du calendrier.
  • Possibilité de déclenchement manuel des automatisations pour ajuster les périodes de filtration si nécessaire.

1. Blueprints

Blueprint pour la filtration dynamique ajustée de la piscine : Ce blueprint calcule la durée de filtration à 8h, programme un 1/3 de filtration avant 15h et recalcul après 15h en fonction de la nouvelle température de l’eau pour les 2/3 de filtration restant.

blueprint:
  name: Filtration dynamique ajustée de la piscine en fonction de la température
  description: Calcule la durée de filtration à 8h, programme un tiers avant 15h et recalcul après 15h en fonction de la nouvelle température de l'eau.
  domain: automation
  input:
    sensor_temperature_piscine:
      name: Capteur de température de la piscine
      description: Entité du capteur de température de la piscine.
      selector:
        entity:
          domain: sensor
    calendar_id:
      name: ID de Calendrier
      description: Identifiant du calendrier pour enregistrer les événements de filtration.
      selector:
        entity:
          domain: calendar
    input_number_total_filtration:
      name: Nombre total d'heures de filtration
      description: Entité pour stocker le nombre total d'heures de filtration.
      selector:
        entity:
          domain: input_number
    input_number_temps_filtration_avant_15:
      name: Temps de Filtration avant 15h
      description: Entité pour stocker le temps de filtration avant 15h.
      selector:
        entity:
          domain: input_number
    input_text_filtration_debut_matin:
      name: Entité pour stocker l'heure de début de la filtration matin
      description: Entité pour stocker l'heure de début de la filtration du matin.
      selector:
        entity:
          domain: input_text
    input_text_filtration_fin_apres_midi:
      name: Entité pour stocker l'heure de fin de la filtration après-midi
      description: Entité pour stocker l'heure de fin de la filtration de l'après-midi.
      selector:
        entity:
          domain: input_text

trigger:
  - platform: time
    at: "08:00:00"
  - platform: time
    at: "15:00:00"
  - platform: event
    event_type: 'MANUAL_TRIGGER'

action:
  - choose:
      - conditions:
          - condition: template
            value_template: "{{ now().hour == 8 or (trigger.event.event_type == 'MANUAL_TRIGGER' and trigger.event.data.get('manual_trigger_time') == 'morning') }}"
        sequence:
          - variables:
              sensor_temperature_piscine: !input sensor_temperature_piscine
              calendar_id: !input calendar_id
              input_number_total_filtration: !input input_number_total_filtration
              input_number_temps_filtration_avant_15: !input input_number_temps_filtration_avant_15
              input_text_filtration_debut_matin: !input input_text_filtration_debut_matin
              temperature_eau_matin: >
                {{ states(sensor_temperature_piscine) | float if states(sensor_temperature_piscine) not in ['unknown', 'unavailable', None] else 0 }}
          - variables:
              temps_filtration_total_matin: >
                {% if temperature_eau_matin < 10 %}
                  0
                {% elif 10 <= temperature_eau_matin <= 14 %}
                  {{ temperature_eau_matin / 3 }}
                {% elif 14 < temperature_eau_matin <= 30 %}
                  {{ temperature_eau_matin / 2 }}
                {% else %}
                  24
                {% endif %}
              temps_filtration_avant_15: "{{ (temps_filtration_total_matin / 3) | round(2) | float }}"
              current_date_time_15: "{{ (now().date() ~ ' 15:00:00') | as_timestamp }}"
              start_time_matin: "{{ (current_date_time_15 - (temps_filtration_avant_15 * 3600)) | timestamp_custom('%Y-%m-%d %H:%M:%S', True) }}"
              end_time_matin: "{{ current_date_time_15 | timestamp_custom('%Y-%m-%d %H:%M:%S', True) }}"
          - service: input_number.set_value
            target:
              entity_id: "{{ input_number_total_filtration }}"
            data:
              value: "{{ temps_filtration_total_matin }}"
          - service: input_number.set_value
            target:
              entity_id: "{{ input_number_temps_filtration_avant_15 }}"
            data:
              value: "{{ temps_filtration_avant_15 }}"
          - service: calendar.create_event
            target:
              entity_id: "{{ calendar_id }}"
            data:
              summary: "Filtration piscine matin (avant 15h)"
              start_date_time: "{{ start_time_matin }}"
              end_date_time: "{{ end_time_matin }}"
          - service: input_text.set_value
            target:
              entity_id: "{{ input_text_filtration_debut_matin }}"
            data:
              value: "{{ start_time_matin }}"
      - conditions:
          - condition: template
            value_template: "{{ now().hour == 15 or (trigger.event.event_type == 'MANUAL_TRIGGER' and trigger.event.data.get('manual_trigger_time') == 'afternoon') }}"
        sequence:
          - variables:
              sensor_temperature_piscine: !input sensor_temperature_piscine
              calendar_id: !input calendar_id
              input_number_total_filtration: !input input_number_total_filtration
              input_number_temps_filtration_avant_15: !input input_number_temps_filtration_avant_15
              input_text_filtration_fin_apres_midi: !input input_text_filtration_fin_apres_midi
              temperature_eau_apres_midi: >
                {{ states(sensor_temperature_piscine) | float if states(sensor_temperature_piscine) not in ['unknown', 'unavailable', None] else 0 }}
          - variables:
              current_date_time_15: "{{ (now().date() ~ ' 15:00:00') | as_timestamp }}"
              temps_filtration_total_matin: "{{ states('input_number.total_filtration') | float }}"
              temps_filtration_avant_15: "{{ states('input_number.temps_filtration_avant_15') | float }}"
          - variables:
              temps_filtration_total_apres_midi: >
                {% if temperature_eau_apres_midi < 10 %}
                  0
                {% elif 10 <= temperature_eau_apres_midi <= 14 %}
                  {{ temperature_eau_apres_midi / 3 }}
                {% elif 14 < temperature_eau_apres_midi <= 30 %}
                  {{ temperature_eau_apres_midi / 2 }}
                {% else %}
                  24
                {% endif %}
              temps_filtration_apres_15: "{{ max((temps_filtration_total_apres_midi | float) - (temps_filtration_avant_15 | float), 0) | round(2) }}"
              end_time_apres_midi: "{{ (current_date_time_15 + (temps_filtration_apres_15 * 3600)) | timestamp_custom('%Y-%m-%d %H:%M:%S', True) }}"
          - service: input_number.set_value
            target:
              entity_id: "{{ input_number_total_filtration }}"
            data:
              value: "{{ temps_filtration_total_apres_midi }}"
          - service: calendar.create_event
            target:
              entity_id: "{{ calendar_id }}"
            data:
              summary: "Filtration piscine après-midi (après 15h)"
              start_date_time: "{{ current_date_time_15 | timestamp_custom('%Y-%m-%d %H:%M:%S', True) }}"
              end_date_time: "{{ end_time_apres_midi }}"
          - service: input_text.set_value
            target:
              entity_id: "{{ input_text_filtration_fin_apres_midi }}"
            data:
              value: "{{ end_time_apres_midi }}"

Blueprint pour le contrôle de la pompe de filtration : Ce blueprint active ou désactive la pompe de filtration de la piscine selon les événements du calendrier.

blueprint:
  name: Contrôle de la pompe de filtration de piscine
  description: Active ou désactive la pompe de filtration de la piscine selon les événements du calendrier.
  domain: automation
  input:
    calendar_entity:
      name: Entité du calendrier
      description: Entité du calendrier pour suivre les événements de filtration.
      selector:
        entity:
          domain: calendar
    switch_pompe_filtration:
      name: Entité de la pompe de filtration
      description: Entité contrôlant la pompe de filtration.
      selector:
        entity:
          domain: switch

trigger:
  - platform: state
    entity_id: !input calendar_entity

action:
  - variables:
      calendar_entity: !input calendar_entity
      switch_pompe_filtration: !input switch_pompe_filtration
  - choose:
      - conditions:
          - condition: template
            value_template: "{{ is_state(calendar_entity, 'on') }}"
        sequence:
          - service: switch.turn_on
            target:
              entity_id: "{{ switch_pompe_filtration }}"
      - conditions:
          - condition: template
            value_template: "{{ is_state(calendar_entity, 'off') }}"
        sequence:
          - service: switch.turn_off
            target:
              entity_id: "{{ switch_pompe_filtration }}"

2. Sensors

Ces sensors permettent de récupérer les horaires de début et de fin de filtration ainsi que le temps total de filtration.

- platform: template
  sensors:
      filtration_debut_matin:
        friendly_name: "Filtration Début Matin"
        value_template: >
          {% set time = states('input_text.filtration_debut_matin') %}
          {% if time != 'unknown' and time != 'unavailable' %}
            {{ as_timestamp(time) | timestamp_custom('%H:%M', true) }}
          {% else %}
            N/A
          {% endif %}
      filtration_fin_apres_midi:
        friendly_name: "Filtration Fin Après-Midi"
        value_template: >
          {% set time = states('input_text.filtration_fin_apres_midi') %}
          {% if time != 'unknown' and time != 'unavailable' %}
            {{ as_timestamp(time) | timestamp_custom('%H:%M', true) }}
          {% else %}
            N/A
          {% endif %}
      filtration_total:
        friendly_name: "Temps de Filtration Total"
        value_template: >
          {% set total = states('input_number.total_filtration') | float %}
          {% set hours = total // 1 %}
          {% set minutes = ((total - hours) * 60) | round(0) %}
          {{ '%02d:%02d' | format(hours, minutes) }}

3. Input Numbers et Input Texts

Ces entités sont utilisées pour stocker les valeurs calculées pour les temps de filtration.

temps_filtration_avant_15:
    name: Temps Filtration Avant 15h
    min: 0
    max: 24
    step: 0.01
    unit_of_measurement: 'hours'

total_filtration:
    name: Nombre total d'heures de filtration
    min: 0
    max: 48
    step: 0.01
    unit_of_measurement: 'hours'
filtration_debut_matin:
    name: Filtration Début Matin
filtration_fin_apres_midi:
    name: Filtration Fin Après-Midi

4. Scripts pour le déclenchement manuel

Ces scripts permettent de déclencher manuellement les automatisations de filtration.

manual_filtration_trigger_morning:
    alias: Déclencheur manuel de filtration (matin)
    sequence:
      - event: MANUAL_TRIGGER
        event_data:
          manual_trigger_time: "morning"
          
manual_filtration_trigger_afternoon:
    alias: Déclencheur manuel de filtration (après-midi)
    sequence:
      - event: MANUAL_TRIGGER
        event_data:
          manual_trigger_time: "afternoon"

5. Carte du Dashboard

Voici la carte du dashboard Home Assistant pour gérer et visualiser l’état de la piscine.

type: vertical-stack
cards:
  - type: horizontal-stack
    cards:
      - type: custom:mini-graph-card
        entities:
          - sensor.temperature_piscine
        name: Température de la piscine
        align_state: center
        align_icon: left
        line_color: '#3498db'
        line_width: 3
        hours_to_show: 24
        points_per_hour: 0.5
        color_thresholds:
          - value: 25
            color: '#0acdff'
          - value: 30
            color: '#40f99b'
          - value: 40
            color: '#E76D83'
      - type: custom:button-card
        entity: switch.pompe_piscine
        name: Pompe de la Piscine
        icon: mdi:water-pump
        show_state: true
        state:
          - value: 'on'
            color: '#3498db'
            icon: mdi:water-pump
            name: En Fonctionnement
          - value: 'off'
            color: '#e74c3c'
            icon: mdi:water-pump-off
            name: Arrêtée
        styles:
          card:
            - height: 165px
          name:
            - font-size: 16px
          state:
            - font-size: 0px
          icon:
            - width: 50px
            - height: 50px
            - color: var(--primary-color)
        tap_action:
          action: toggle
  - type: entities
    title: Gestion de la Piscine
    entities:
      - entity: sensor.filtration_debut_matin
        name: Début Filtration
      - entity: sensor.filtration_fin_apres_midi
        name: Fin Filtration
      - entity: sensor.filtration_total
        name: Temps Total de Filtration

J’espère que cela vous sera utile ! N’hésitez pas à poser des questions ou à partager vos retours.

8 « J'aime »

Bonjour,
Un grand merci pour ce partage, qui est exactement ce que je cherchais.
Est-ce qu’il vous serait possible d’ajouter pour chaque élément une petite ligne descriptive expliquant ou le placer (ajout dans un fichier particulier, ou création de fichier et emplacement de celui-ci) ?
Merci pour votre aide…
Patrice

J’ai dans mon fichier configuration.yaml ces lignes :
input_number: !include input_numbers.yaml
input_text: !include input_text.yaml
sensor: !include sensor.yaml
scripts: !include scripts.yaml

C’est dans ces fichiers que tu vas mettre tous les sensors input et scripts

Pour ce qui est des blueprints il faut les mettre dans /blueprints/automation/

1 « J'aime »

Bonjour, quelle sonde de température utilises-tu?

Celle ci :
Owon

J’en avais acheté une l’année dernière, elle a très bien fonctionné, mais j’ai voulu la réappairer pour cette saison et je n’ai plus de remonter de température.

Je t’avoue que je viens de l’acheter pour l’instant cela fonctionne parfaitement.

Pour une autre solution il y a ça:

Ce n’est pas tout a fait la même chose car il faut un shelly pour le mettre en place, mais ça a l’avantage ( entre autre) de pouvoir fonctionner même si HA est down ( ou les sondes). Le but est d’avoir un truc autonome, mais avec des remontés et un piltage dans HA

Merci, j’ai pu compléter la configuration sans trop de souci.
Il me manquait l’intégration button-card, installée sans trop de souci via HACS.
Il faut aussi l’intégration calendar. Peut être pouvez vous ajouter les dépendances pour être complet.
Un dernier souci : je ne vois pas ou se raccroche le Blueprint à la valeur de la sonde de température.
Côté UI j’ai modifié la carte pour récupérer la valeur de ma sonde (sensor.pool_temp) pour la courbe; c’est OK.
Par contre les valeurs calculées restent à N/A ou 00:00. Je suppose que c’est bien la température qui n’est pas récupérée de façon correcte.
Lors de l’utilisation du Blueprint, on doit spécifier le Calendar & le switch de la pompe, mais pas vu la sonde de température.
Merci pour votre aide…
Cordialement

Seul 1 des 2 blueprint utilise la température de la sonde, le deuxième sert juste à récupérer les valeurs horaire pour déclencher la pompe.

Mais bien sûr, suis-je bête… Il faut configurer les 2 Blueprints !!!
Il faut aussi adapter la carte avec le bon identifiant du switch de la pompe.
Pour finir, et voir le résultat, lancer les deux scripts.
Et voila, ça tourne !!
Merci encore pour ce partage…