EV Smart Charging

repository·main·Indexed 43 days ago

https://github.com/jonasbkarlsson/ev_smart_charging

A Home Assistant integration that automates electric vehicle charging to minimize costs by analyzing electricity price forecasts. It identifies the most cost-effective 15-minute intervals for charging and supports native price integrations like Nord Pool, Energi Data Service, GE-Spot, Entso-e, and TGE, or custom template sensors. Requires Home Assistant version 2023.4 or newer.

Tokens
8.6K
Snippets
6
Records
12
Agent score
6%

What's inside EV Smart Charging

  1. Overview of EV Smart Charging

    main

    EV Smart Charging is a Home Assistant integration that automatically manages electric vehicle (EV) charging to minimize costs. It identifies the most cost-effective 15-minute intervals for charging based on electricity price data.

    How it works

    • Price Sourcing: It retrieves electricity prices from supported native integrations or via a template sensor using a generic price format.
    • Optimization: By default, it calculates a continuous set of 15-minute intervals that offer the lowest price.
    • Timing: Calculations typically occur when tomorrow's electricity prices become available (usually between 13:00 CET/CEST and midnight) or before the configured charge completion time.
    • Note: Once an automatic charging session has started, changes to configuration settings will not take effect until the next cycle.
  2. Install EV Smart Charging via HACS

    main

    If you use the Home Assistant Community Store (HACS), follow these steps:

    1. In Home Assistant, navigate to HACS -> Integrations.
    2. Click + Explore & Download Repositories and search for "EV Smart Charging".
    3. Once downloaded, go to Settings -> Devices & Services -> Integrations.
    4. Click + Add integration and search for "EV Smart Charging" to complete the setup.
  3. Install EV Smart Charging manually

    main

    To install without HACS, perform the following steps:

    1. Open your Home Assistant configuration directory (where configuration.yaml is located).
    2. Create a custom_components folder if it does not already exist.
    3. Inside custom_components, create a folder named ev_smart_charging.
    4. Download all files from the custom_components/ev_smart_charging/ directory in the official repository.
    5. Place the downloaded files into your local ev_smart_charging folder.
    6. Restart Home Assistant.
    7. In Home Assistant, go to Settings -> Devices & Services -> Integrations.
    8. Click + Add integration and search for "EV Smart Charging".
  4. Requirements for EV Smart Charging

    main

    To use this integration, ensure your environment meets the following criteria:

    Price Data

    You must provide electricity price information through one of two methods:

    1. Native Support: The integration automatically detects several integrations, including:
      • Nord Pool (HACS)
      • Energi Data Service
      • GE-Spot
      • Entso-e
      • TGE
    2. Template Sensor: If your price source is not natively supported (e.g., the native Home Assistant Nord Pool integration), you must create a template sensor that follows the generic price format.

    Software

    • Home Assistant: Version 2023.4 or newer is required.
  5. Configure EV SOC and Target SOC via Helpers

    main

    If your EV's State of Charge (SOC) or Target SOC is provided as an attribute of a sensor rather than a standalone entity, you must bridge them using Home Assistant Helpers.

    For EV SOC

    1. Create a Number Helper (e.g., input_number.soc) via Settings -> Devices & Services -> Helpers.
    2. Create an automation to sync the attribute to the helper:
    alias: EV SOC
    description: ""
    triggers:
      - trigger: state
        entity_id:
          - sensor.my_ev
        attribute: ev_soc
    conditions: []
    actions:
      - action: input_number.set_value
        data:
          value: "{{ state_attr('sensor.my_ev', 'EV SOC') }}"
        target:
          entity_id: input_number.soc
    mode: single
    1. Use input_number.soc in the integration configuration.

    Note: If SOC data is unavailable, you can still use the integration by manually managing a Number Helper. For best results, set the SOC to 100 when charging completes and update it when a new cycle starts.

    For EV Target SOC

    Follow the same pattern: create a Number Helper (e.g., input_number.target_soc) and use an automation to update it if the value is provided as an attribute of another sensor.

  6. Configure the EV Smart Charging integration

    main

    The integration is configured via the Home Assistant user interface. After initial setup, you can modify most parameters by navigating to Settings -> Devices & Services -> Integrations -> EV Smart Charging -> [Your Device] -> Configure.

    Required Parameters

    • Name: The name of the instance.
    • Electricity price entity: A sensor providing the price in a generic format (e.g., sensor.average_electricity_price for the Entso-e integration).
    • EV SOC entity: An entity reporting the car's State-of-Charge (0-100). This is a critical entity for the integration's logic.
    • Charging control by EV integration: Select this if an EV integration (rather than a charger integration) is used to control the start/stop of charging. If selected, it is highly recommended to create an automation that controls switch.ev_smart_charging_ev_connected.

    Optional Parameters

    • EV target SOC entity: Target State-of-Charge (0-100). Defaults to 100 if not provided.
    • Charger control entity: A Switch or Input Boolean that the integration will turn on or off to control the charger.
    • Charging state entity: A Switch or Input Boolean used to verify if the charger is actually charging. The state must be on when charging. If the integration detects the charger is not charging when it should be, it will attempt to restart it.
  7. Integrate with chargers using automations

    main

    If your charger integration does not provide a switch entity that this integration can control directly, you can use Home Assistant automations to bridge the gap. You should trigger these automations based on the state changes of sensor.ev_smart_charging_charging.

    Start Charging Automation

    Trigger when sensor.ev_smart_charging_charging changes from off to on.

    Stop Charging Automation

    Trigger when sensor.ev_smart_charging_charging changes from on to off.

    EV Connection Status

    You can also inform the integration when an EV is connected to the charger (e.g., via an OCPP status sensor) to improve scheduling accuracy. This involves toggling switch.ev_smart_charging_ev_connected.

    # Example: Start Charging (Easee)
    alias: EV Smart Charging - Start
    description: ""
    mode: single
    triggers:
      - trigger: state
        entity_id:
          - sensor.ev_smart_charging_charging
        from: "off"
        to: "on"
    conditions: []
    actions:
      - action: easee.set_circuit_dynamic_limit
        data:
          charger_id: exxxxxxx
          currentP1: 16
    
    # Example: Stop Charging (Easee)
    alias: EV Smart Charging - Stop
    description: ""
    mode: single
    triggers:
      - trigger: state
        entity_id:
          - sensor.ev_smart_charging_charging
        from: "on"
        to: "off"
    conditions: []
    actions:
      - action: easee.set_circuit_dynamic_limit
        data:
          charger_id: exxxxxxx
          currentP1: 0
    
    # Example: Inform integration of EV connection
    alias: EV Smart Charging - EV connected
    description: ""
    triggers:
      - trigger: state
        entity_id:
          - sensor.ocpp_status_connector
    conditions: []
    actions:
      - if:
          - condition: state
            entity_id: sensor.ocpp_status_connector
            state: Preparing
        then:
          - action: switch.turn_on
            data: {}
            target:
              entity_id: switch.ev_smart_charging_ev_connected
        else:
          - if:
              - condition: state
                entity_id: sensor.ocpp_status_connector
                state: Available
            then:
              - action: switch.turn_off
                data: {}
                target:
                  entity_id: switch.ev_smart_charging_ev_connected
    mode: single
  8. Verify charging control configuration

    main

    To ensure the integration can successfully control your charger, perform a manual test:

    1. Navigate to Settings -> Devices & Services -> Integrations -> EV Smart Charging -> [Your Device] -> Controls.
    2. Connect your EV to the charger.
    3. Press Manually start charging and verify the charger starts.
    4. Press Manually stop charging and verify the charger stops.
    5. Repeat the start/stop sequence to confirm reliability.
  9. Create a Lovelace UI dashboard with ApexCharts

    main

    You can use the ApexCharts Card to visualize electricity prices and the charging schedule. The dashboard typically includes a graph showing the electricity price (as a line) and the charging schedule (as an area chart).

    Important: If your price unit is not öre/kWh (e.g., it is SEK/kWh), you must adjust the unit, float_precision, and color_threshold values in the card configuration to match your local currency and scale.

    type: vertical-stack
    cards:
      - type: custom:apexcharts-card
        now:
          show: true
          label: Now
          color: '#ffc0cb'
        locale: en
        header:
          show: true
          title: EV Smart Charging
          show_states: true
        graph_span: 2d
        yaxis:
          - min: ~0
            apex_config:
              forceNiceScale: true
        span:
          start: day
        apex_config:
          legend:
            show: false
          xaxis:
            labels:
              show: true
              format: HH
              rotate: -45
              rotateAlways: true
              hideOverlappingLabels: true
              style:
                fontSize: 10
                fontWeight: 10
        series:
          - entity: sensor.ev_smart_charging_charging
            name: Electricity price
            unit: ' öre/kWh'
            data_generator: >
              return entity.attributes.raw_two_days.map((entry) => { return [new
              Date(entry.start), entry.value]; });
            type: line
            float_precision: 0
            show:
              in_header: before_now
            extend_to: false
            color_threshold:
              - value: -100
                color: cyan
              - value: 0
                color: green
              - value: 40
                color: orange
              - value: 100
                color: red
              - value: 200
                color: magenta
              - value: 500
                color: black
          - entity: sensor.ev_smart_charging_charging
            name: Charging
            data_generator: >
              return entity.attributes.charging_schedule.map((entry) => { return
              [new Date(entry.start), entry.value]; });
            type: area
            curve: stepline
            color: black
            show:
              in_header: false
            extend_to: false
        experimental:
          color_threshold: true
      - type: entities
        entities:
          - entity: sensor.ev_smart_charging_charging
            name: Charging
          - entity: switch.ev_smart_charging_smart_charging_activated
            name: Smart charging activated
          - entity: switch.ev_smart_charging_apply_price_limit
            name: Apply price limit
          - entity: switch.ev_smart_charging_opportunistic_charging
            name: Opportunistic charging
          - entity: switch.ev_smart_charging_continuous_charging_preferred
            name: Continuous charging preferred
          - entity: switch.ev_smart_charging_keep_charger_on
            name: Keep charger on
          - entity: switch.ev_smart_charging_low_price_charging
            name: Low price charging
          - entity: switch.ev_smart_charging_low_soc_charging
            name: Low SOC charging
          - entity: button.ev_smart_charging_manually_start_charging
            name: Manually start charging
          - entity: button.ev_smart_charging_manually_stop_charging
            name: Manually stop charging
        title: EV Smart Charging
        show_header_toggle: false
      - type: entity
        entity: sensor.ev_smart_charging_status
        name: Status
      - type: entity
        entity: sensor.ev_smart_charging_charging
        attribute: ev_soc
        name: EV SOC
        icon: mdi:battery-70
        unit: '%'
  10. Reference: Integration entities and switches

    main

    The following entities are provided by the integration to monitor status, control features, or manually interact with the charging process.

    | Entity | Type | Description |
    | :--- | :--- | :--- |
    | `sensor.ev_smart_charging_charging` | Sensor | The state is "on" or "off". Can be used with automations to control the EV charger. |
    | `sensor.ev_smart_charging_status` | Sensor | The state is one of the following: "Waiting for new prices", "No charging planned", "Waiting for charging to begin", "Charging", "Keeping charger on", "Low price charging", "Low SOC charging", "Disconnected", and "Smart charging not active". In automations, these states are referred to as "waiting_for_new_prices", "no_charging_planned", "waiting_for_charging_to_begin", "charging", "keeping_charger_on", "low_price_charging", "low_soc_charging", "disconnected", and "smart_charging_not_active", independent of the configured language. |
    | `switch.ev_smart_charging_smart_charging_activated` | Switch | Turns the EV Smart Charging integration on and off. |
    | `switch.ev_smart_charging_apply_price_limit` | Switch | Applies the price limit. |
    | `switch.ev_smart_charging_opportunistic_charging` | Switch | Activates opportunistic charging, see the desciption of the configuration entity `number.ev_smart_charging_opportunistic_level`. This feature requires the feature `Electricity price limit` to be on. |
    | `switch.ev_smart_charging_opportunistic_type2_charging` | Switch | Activates opportunistic type 2 charging, see the desciption of the configuration entity `number.ev_smart_charging_opportunistic_type2_level`. The two types of opportunistic charging can not be used at the same time. |
    | `switch.ev_smart_charging_low_soc_charging` | Switch | Activates charging immediately if the EV SOC is lower than a configured level. It is highly recommended to create an automation that controls `switch.ev_smart_charging_ev_connected` if this switch is set to on. Note that this charging is not shown as a scheduled charging. A typical use case is to charge the EV directly when returning home to a minimum level, and then do a complete charging using the scheduled charging when the price is lowest. |
    | `switch.ev_smart_charging_low_price_charging` | Switch | Activates charging immediately if the electricity price is lower than a configured level. It is highly recommended to create an automation that controls `switch.ev_smart_charging_ev_connected` if this switch is set to on. Note that this charging is not shown as a scheduled charging. |
    | `switch.ev_smart_charging_continuous_charging_preferred` | Switch | If turned on, will as basis schedule one continuous charging session. If turned off, will schedule charging on the 15-minute intervals with lowest electricity price, even if they are not continuous. |
    | `switch.ev_smart_charging_keep_charger_on` | Switch | If "on", the `sensor.ev_smart_charging_charging` will not turn off after completed charge cycle. The feature is intended to enable preconditioning before departure, i.e. preheating/cooling can be done from the power grid instead of the battery. If this option is used, the feature `Electricity price limit` will be turned off, and vice versa. *NOTE* It is required that `switch.ev_smart_charging_ev_connected` is controlled in a proper way in order for this feature to work. Also, there is an assumption made that the EV itself will stop its charging when reaching the target SOC. |
    | `switch.ev_smart_charging_ev_connected` | Switch | Tells the integration that the EV is connected to the charger. Is preferable controlled by automations (see example below). Can avoid problems occuring when the EV is not connected to the charger at the time the charging should start. Using it will also ensure that the `sensor.ev_smart_charging_charging` is set to "off" when the EV is not connected to the charger. |
    | `button.ev_smart_charging_manually_start_charging` | Button | Manually start charging. This is totally independent of the automatic charging. |
    | `button.ev_smart_charging_manually_stop_charging` | Button | Manually stop charging. This is totally independent of the automatic charging. |
  11. Reference: Configuration entities for charging behavior

    main

    These entities allow you to fine-tune charging behavior via the Home Assistant dashboard or automations.

    | Entity | Type | Descriptions, valid value ranges and service calls |
    | :--- | :--- | :--- |
    | `select.ev_smart_charging_charge_start_time` | Select | The earliest time of the day for the charging to start. If `None` is selected, there will be no explicit limitation of the starting time. Valid options, "00:00", "00:15", ..., "23:45" and "None". Can be set by service call `select.select_option`. |
    | `select.ev_smart_charging_charge_completion_time` | Select | The latest time of the day for charging to reach the target State-of-Charge. If `None` is selected, charging will be optimized using all available price information, including before tomorrow's prices are available. Valid options, "00:00", "00:15", ..., "23:45" and "None". Can be set by service call `select.select_option`. |
    | `number.ev_smart_charging_charging_speed` | Number | The charging speed expressed as percent per hour. For example, if the EV has a 77 kWh battery and the charger can deliver 11 kW (3-phase 16 A), then set this parameter to 14.3 ((11/77)*100). If there are limitations in the charging power, it is preferred to choose a smaller number. Try and see what works for you! Valid values min=0.1, step=0.1, max=400. Can be set by service call `number.set_value`. |
    | `number.ev_smart_charging_electricity_price_limit` | Number | If the `switch.ev_smart_charging_apply_price_limit` switch is activated, charging will not be performed when the electricity price is above this limit. NOTE that this might lead to that the EV will not be charged to the target State-of-Charge. Valid values min=-10000, step=0.01, max=10000. Can be set by service call `number.set_value`. |
    | `number.ev_smart_charging_minimum_ev_soc` | Number | The minimum State-of-Charge level that should be reached by scheduled charging, independently of the electricity price. Valid values min=0, step=1, max=100. Can be set by service call `number.set_value`. |
    | `number.ev_smart_charging_opportunistic_level` | Number | If the `switch.ev_smart_charging_opportunistic_charging` switch is activated, the price limit will be even further reduced if the last available price is lower than `Electricity price limit * Opportunistic level / 100`. For example, if the `Opportunistic level` is set to 50, the price limit will be set to 50% of the `Electricity price limit`. Valid values min=0, step=1, max=100. Can be set by service call `number.set_value`. |
    | `number.ev_smart_charging_opportunistic_type2_level` | Number | If the `switch.ev_smart_charging_opportunistic_type2_charging` switch is activated, the price limit will be set based on `last available price * Opportunistic type2 level / 100`. For example, if the Opportunistic type2 level is set to 90, the price limit will be set to 90% of the last available price. If the last available price is negative, the price limit will be `last available price * (200 - Opportunistic type2 level) / 100`. If `switch.ev_smart_charging_apply_price_limit` is also activated, the lowest of the two price limits will be used. Valid values min=0, step=1, max=200. Can be set by service call `number.set_value`. |
    | `number.ev_smart_charging_low_soc_charging_level` | Number | If the `switch.ev_smart_charging_low_soc_charging` switch is activated, charging will be done immediately if the EV SOC is below this level. Valid values min=0.0, step=1.0, max=100. Can be set by service call `number.set_value`. |
    | `number.ev_smart_charging_low_price_charging_level` | Number | If the `switch.ev_smart_charging_low_price_charging` switch is activated, charging will be done immediately if the electricity price is below this level. Valid values min=-10000, step=0.01, max=10000. Can be set by service call `number.set_value`. |
  12. Reference: Attributes of `sensor.ev_smart_charging_charging`

    main

    The sensor.ev_smart_charging_charging entity contains several attributes that provide detailed information about the current charging state and planned schedule.

    | Attribute | Description |
    | :--- | :--- |
    | `current_price` | The current price from the electricity price entity. |
    | `ev_soc` | The current SOC of the electric vehicle, as reported by the EV SOC entity. |
    | `ev_target_soc` | The target SOC of the electric vehicle, as reported by the EV target SOC entity. |
    | `charging_is_planned` | `true` if charging is planned, otherwise `false`. Is set to `false` after charging is completed. |
    | `charging_start_time` | If charging is planned, the date and time when the charging will start. |
    | `charging_stop_time` | If charging is planned, the date and time when the charging will stop. |
    | `charging_number_of_hours` | If charging is planned, the number of hours that charging is planned. This might be less than the time between the start and stop times, if non-continuous charging is configured. |
    | `opportunistic` | `true` if an opportunistic charging feature has been triggered. |
    | `raw_two_days` | The electricity price today and tomorrow from the electricity price entity. |
    | `charging_schedule` | The calculated charging schedule. Can be used with an ApexCharts card to visualize the planned charging. |