Solar benefit calculations

Many friends have been curious about the returns from my photovoltaic (PV) investment, often asking about the financial benefits it has brought. While it’s straightforward to mention the earnings from the energy sold back to the grid, a significant portion of the value actually comes from the solar energy I utilize directly. By consuming the energy produced by my PV system, I save on electricity costs, including the network tariffs, which is a considerable advantage.

To thoroughly understand and communicate the total benefits of my PV system, I’ve developed an Apex chart dashboard. This tool goes beyond just tracking energy sold; it provides a comprehensive overview of the entire PV system’s performance, including the cost savings from using solar energy directly. This holistic approach allows me to quantify and visualize the true value of my investment, encompassing both the energy exported to the grid and the savings from reduced reliance on external power sources.

Screenshot 2023-11-29 at 12.06.40

Probably took too complex route, but got the result. As i have 3phase system and in Estonia our grid will count every phase separately, meaning that if i export 1kw and 1kw on 2 phases and import 2kw on 1 phase, I still have to pay the tariff on the 2kw. It’s quite unique approach in our country. Usually grid will sum phases.

What you need:

  1. Inverter production power (in my case power for each phase). My huawei is not giving this information and i needed to calculate it from the phases currents:
  - platform: template
    sensors:
      inverter_phase_1_power:
        friendly_name: "Inverter Phase 1 Power"
        unit_of_measurement: "W"
        value_template: >-
          {{ (states('sensor.inverter_phase_a_current') | float * 
              states('sensor.inverter_phase_a_voltage') | float *
              states('sensor.inverter_power_factor') | float) }}

  - platform: template
    sensors:
      inverter_phase_2_power:
        friendly_name: "Inverter Phase 2 Power"
        unit_of_measurement: "W"
        value_template: >-
          {{ (states('sensor.inverter_phase_b_current') | float * 
              states('sensor.inverter_phase_b_voltage') | float *
              states('sensor.inverter_power_factor') | float) }}

  - platform: template
    sensors:
      inverter_phase_3_power:
        friendly_name: "Inverter Phase 3 Power"
        unit_of_measurement: "W"
        value_template: >-
          {{ (states('sensor.inverter_phase_c_current') | float * 
              states('sensor.inverter_phase_c_voltage') | float *
              states('sensor.inverter_power_factor') | float) }}
  1. Power back to grid. I have Shelly EM3 and it gives a power entities for each phase. Negative result means power is going back to grid. I made template sensor that will show value when it’s negative and show it as as a positive number (Note: absolute value would be better than -1)
  - platform: template
    sensors:
      phase_1_power_back_to_grid:
        friendly_name: "Phase 1 Power Back to Grid"
        unit_of_measurement: "W"
        value_template: >-
          {% set power = states('sensor.phase_1_power') | float %}
          {{ [0, power * -1] | max }}

      phase_2_power_back_to_grid:
        friendly_name: "Phase 2 Power Back to Grid"
        unit_of_measurement: "W"
        value_template: >-
          {% set power = states('sensor.phase_2_power') | float %}
          {{ [0, power * -1] | max }}

      phase_3_power_back_to_grid:
        friendly_name: "Phase 3 Power Back to Grid"
        unit_of_measurement: "W"
        value_template: >-
          {% set power = states('sensor.phase_3_power') | float %}
          {{ [0, power * -1] | max }}
  1. Total back to grid power
  - platform: template
    sensors:
       total_power_back_to_grid:
        friendly_name: "Total Power Back to Grid"
        unit_of_measurement: "W"
        value_template: >
          {{ states('sensor.phase_1_power_back_to_grid') | float
          + states('sensor.phase_2_power_back_to_grid') | float
          + states('sensor.phase_3_power_back_to_grid') | float }}
  1. Total own used PV power
  - platform: template
    sensors:
      pv_own_usage_total_power:
        friendly_name: "Total PV Own Usage Power"
        unit_of_measurement: "W"
        value_template: >
          {% set phase_1_power = states('sensor.inverter_phase_1_power') | float %}
          {% set phase_1_back_to_grid = states('sensor.phase_1_power_back_to_grid') | float %}
          {% set phase_2_power = states('sensor.inverter_phase_2_power') | float %}
          {% set phase_2_back_to_grid = states('sensor.phase_2_power_back_to_grid') | float %}
          {% set phase_3_power = states('sensor.inverter_phase_3_power') | float %}
          {% set phase_3_back_to_grid = states('sensor.phase_3_power_back_to_grid') | float %}          
          {{ (phase_1_power - phase_1_back_to_grid) + (phase_2_power - phase_2_back_to_grid) + (phase_3_power - phase_3_back_to_grid)| round(2) }}

  1. Current benefit calculations. Needed for the Utility meter step to start counting. Back to grid I use Nordpool price without VAT. Own usage I use nordpool with VAT + networks tariffs.
  - platform: template
    sensors:
      pv_to_grid_benefit_now:
        friendly_name: 'PV to grid now'
        unit_of_measurement: "EUR"
        value_template: "{{ states('sensor.nordpool_kwh_ee_eur_3_10_0') | float * states('sensor.total_power_back_to_grid') | float / 1000 }}"

  - platform: template
    sensors:
      pv_own_usage_benefit_now:
        friendly_name: 'PV Own Usage Now'
        unit_of_measurement: "EUR"
        value_template: "{{ states('sensor.total_el_price') | float * states('sensor.pv_own_usage_total_power') | float / 1000 }}"
  1. Make Reiman Sum helpers to calculate cumulative benefit from the current benefit entities from last step. Settings > Devices & Services > Helpers > Create Helper > Integration - Reiman sum integral sensor
1.
Name: PV Own Usage Benefit Cumulative
Input Sensor: sensor.pv_own_usage_benefit_now
Integration method: Left
Precicion: 2
Time Unit: hours

2.  
Name: PV to grid cumulative Benefit
Input Sensor: sensor.pv_to_grid_benefit_now
Integration method: Left
Precicion: 2
Time Unit: hours
  1. (optional) Template sensor that will sum the cumulative own use and back to gid together
  - platform: template
    sensors:
      total_pv_all_time_benefit:
        friendly_name: "Total PV All Time Benefit"
        unit_of_measurement: '€' 
        value_template: >
          {% set pv_own_usage = states('sensor.pv_own_usage_benefit_cumulative') %}
          {% set pv_to_grid = states('sensor.pv_to_grid_cumulative_benefit') %}
          {% set pv_own_value = 0 if pv_own_usage == "unknown" else pv_own_usage | float %}
          {% set pv_to_grid_value = 0 if pv_to_grid == "unknown" else pv_to_grid | float %}
          {{ (pv_own_value + pv_to_grid_value) | round(2) }}
  1. So now we have entities that will cumulative current own usage and back to grid benefits. Next step is to make utility meters. You can do it in UI, but i preferres configuration.yaml, as there are quite a few of them (daily, monthly, yearly or all time if you want). Daily and Monthly are needed in my setup to show the apex chart corectly.
utility_meter:
  pv_own_usage_benefit_daily:
    source: sensor.pv_own_usage_benefit_cumulative
    name: PV Own Usage Benefit Daily
    cycle: daily
  pv_to_grid_benefit_daily:
    source: sensor.pv_to_grid_cumulative_benefit
    name: PV to Grid Benefit Daily
    cycle: daily

  pv_own_usage_benefit_monthly:
    source: sensor.pv_own_usage_benefit_cumulative
    name: PV Own Usage Benefit Monthly
    cycle: monthly
  pv_to_grid_benefit_monthly:
    source: sensor.pv_to_grid_cumulative_benefit
    name: PV to Grid Benefit Monthly
    cycle: monthly

  pv_own_usage_benefit_yearly:
    source: sensor.pv_own_usage_benefit_cumulative
    name: PV Own Usage Benefit Yearly
    cycle: yearly
  pv_to_grid_benefit_yearly:
    source: sensor.pv_to_grid_cumulative_benefit
    name: PV to Grid Benefit Yearly
    cycle: yearly
  1. Template to calculate the totals of daily, monthly and yearly benefits
  - platform: template
    sensors:
      total_pv_daily_benefit:
        friendly_name: "Total PV Daily Benefit"
        unit_of_measurement: '€' 
        value_template: >
          {% set pv_own_usage = states('sensor.pv_own_usage_benefit_daily') %}
          {% set pv_to_grid = states('sensor.pv_to_grid_benefit_daily') %}
          {% set pv_own_value = 0 if pv_own_usage == "unknown" else pv_own_usage | float %}
          {% set pv_to_grid_value = 0 if pv_to_grid == "unknown" else pv_to_grid | float %}
          {{ (pv_own_value + pv_to_grid_value) | round(2) }}

  - platform: template
    sensors:
      total_pv_monthly_benefit:
        friendly_name: "Total PV Monthly Benefit"
        unit_of_measurement: '€' 
        value_template: >
          {% set pv_own_usage = states('sensor.pv_own_usage_benefit_monthly') %}
          {% set pv_to_grid = states('sensor.pv_to_grid_benefit_monthly') %}
          {% set pv_own_value = 0 if pv_own_usage == "unknown" else pv_own_usage | float %}
          {% set pv_to_grid_value = 0 if pv_to_grid == "unknown" else pv_to_grid | float %}
          {{ (pv_own_value + pv_to_grid_value) | round(2) }}

  - platform: template
    sensors:
      total_pv_yearly_benefit:
        friendly_name: "Total PV Yearly Benefit"
        unit_of_measurement: '€' 
        value_template: >
          {% set pv_own_usage = states('sensor.pv_own_usage_benefit_yearly') %}
          {% set pv_to_grid = states('sensor.pv_to_grid_benefit_yearly') %}
          {% set pv_own_value = 0 if pv_own_usage == "unknown" else pv_own_usage | float %}
          {% set pv_to_grid_value = 0 if pv_to_grid == "unknown" else pv_to_grid | float %}
          {{ (pv_own_value + pv_to_grid_value) | round(2) }}

  1. Apex chart code:
type: custom:apexcharts-card
graph_span: 31d
span:
  start: month
stacked: true
header:
  show: true
  title: PV Savings Current Month
  show_states: true
  colorize_states: true
series:
  - entity: sensor.pv_own_usage_benefit_daily
    name: Own usage
    yaxis_id: first
    type: column
    group_by:
      func: max
      duration: 1d
    show:
      in_header: false
      legend_value: false
  - entity: sensor.pv_to_grid_benefit_daily
    name: To Grid
    yaxis_id: first
    type: column
    group_by:
      func: max
      duration: 1d
    show:
      in_header: false
      legend_value: false
  - entity: sensor.total_pv_daily_benefit
    name: Total
    yaxis_id: first
    type: line
    stroke_width: 0
    unit: €
    show:
      extremas: true
      in_header: false
      legend_value: false
    group_by:
      func: max
      duration: 1d
  - entity: sensor.total_pv_monthly_benefit
    unit: €
    yaxis_id: second
    name: Total
    show:
      legend_value: false
      in_chart: false
  - entity: sensor.pv_own_usage_benefit_monthly
    unit: €
    yaxis_id: second
    name: Own Usage
    show:
      legend_value: false
      in_chart: false
  - entity: sensor.pv_to_grid_benefit_monthly
    unit: €
    yaxis_id: second
    name: PV to Grid
    show:
      legend_value: false
      in_chart: false
yaxis:
  - id: first
    decimals: 2
    apex_config:
      tickAmount: 2
      logarithmic: false
  - id: second
    show: false

And the result should be like this (Its’ winter in Estonia, so no sun):
Screenshot 2023-11-29 at 12.06.40

And to have investment VS benefit you should to utility meter that will not reset and then compare this number to your investment. Make some template sensor that will just subtract from the investment or does a presentage calculation or if you have bought the PV system with financing compare monthly and yearly cost vs benefit or whatever you can think of.

5 Likes

If I have a smart meter with the following sensors, I don’t need to make all your templates right?
As you have seen, the Power meter Phase A voltage is negative values ​​when it consumes electricity and positive values ​​when I have excess

1 Like

[quote=“arva, post:1, topic:682868”]
sensor.pv_own_usage_benefit_cumulative
[/quote]

Hello
I don’t know if I missed something but I can’t find where to create sensor.pv_own_usage_benefit_cumulate anywhere?

Sorry missed it.

1 Like

Hi Arva this looks great and exactly what I need, thank you for this. I’m new to HA and when trying to paste your code into my configuration.yaml I’m getting loads of syntax errors. Is there a new format for the templates now?

Also, would your method work if I only have yesterdays data available? Thanks

It works only with current power entitities in watts.

Format should be ok, i’m using it as it is.

Wanted to say thank you so much!

This was very well explained and a really nice addition to my home energy setup.

For anyone based in sweden, remember to add transmission cost for money saved by using own PV

1 Like

You can now do the points 5 to 8 more easily using my dynamic electricity cost custom integration:

Also reccomend to use energy (kwh) sensors instead of power (kw) sensors for more precice calculations. This means changing the points 3 and 4 to use energy sensors and then feeding in “energy back to grid” and “own used PV energy” sensors to the integration which will make daily, monthly and yearly cost sensors.

When I have some more time, i will write new tutorial

Thanks for sharing!

I used the integration to calculate income of my panels and costs of my heat pump, works good. Only challenge I had is that one of my devices reports in wh rather than kwh, hence added a helper with the converted amount. The average rate in the attributes is also cool (personal challenge to get this rate for the heat pump as low as possible by using the right moment of the day to heat the water)

Thank you very much for your manual! It looks very promising.
@arva
But I got one problem- for some reason I get negative values, which, in my opinion, should never happen.
Maybe you have any idea?
For me, It looks like data is out of sync?

Hi there,
I’am trying to implement your templates into my HA, but at the total pv own usage power, i get error not available. I’am on a 1 phase grid, so don’t have phase 2 and 3.
When i’am templating step 4, HA only look’s at the inverter sensor.