Skip to content

Commit d4f1a2a

Browse files
committed
Update readme
1 parent 0a13932 commit d4f1a2a

File tree

11 files changed

+397
-302
lines changed

11 files changed

+397
-302
lines changed

README.md

Lines changed: 40 additions & 302 deletions
Original file line numberDiff line numberDiff line change
@@ -2,11 +2,13 @@
22

33
A Home Assistant integration to track your load schedding schedule.
44

5-
> ℹ️ **_NOTE:_** Versions of this integration before v0.6.0 make use of [this Python library](https://gitlab.com/wernerhp/load-shedding) which only supports schedules for Eskom Direct customers. If you can find your schedule on https://loadshedding.eskom.co.za/ then you'll have schedule info available.
5+
> ℹ️ **_NOTE:_** Prior to v0.6.0 this integration made use of [this Python library](https://gitlab.com/wernerhp/load-shedding) which only supports schedules for Eskom Direct customers. If you can find your schedule on https://loadshedding.eskom.co.za/ then you'll have schedule info available.
6+
>
67
> If you are not an Eskom Direct customer, then a work-around is to find an Eskom Direct schedule which matches yours and use that instead. There are no immediate plans to add other municipalities, but Merge Requests on [the library](https://gitlab.com/wernerhp/load-shedding) to expand support are welcome.
7-
> Version v0.6.1 makes use of Eskom SePush API. You can sign up for $0 monthly key [here](https://eskomsepush.gumroad.com/l/api). The free key has a request limit of 50 API calls per day. Keep this in mind when using the integration. You can also pay to get a higher request limit.
8+
>
9+
> v0.6.1 makes use of Eskom SePush API. Get a Free (50 requests per day) API Key from [Eskom Se Push](https://eskomsepush.gumroad.com/l/api). The free key has a request limit of 50 API calls per day. Keep this in mind when using the integration. You can also pay to get a higher request limit.
810
9-
![img_3.png](img_3.png)
11+
![img_8.png](img_8.png)
1012

1113
# HACS
1214
[![hacs_badge](https://img.shields.io/badge/HACS-Default-41BDF5.svg)](https://github.com/hacs/integration)
@@ -57,8 +59,7 @@ Bitcoin: 3EGnQKKbF6AijqW9unyBuW8YeEscY5wMSE
5759

5860
# Sensor
5961
The load shedding sensor State will always reflect the current load shedding stage.
60-
i.e When load shedding is suspended, it will show **No Load Shedding**. When Stage 2 is active, it will show **Stage 2**.
61-
> Since the schedules differ depending on the Stage, the correct `start_time`, `end_time`, `starts_in`, `ends_in` and `schedule` times only show once there is an active Stage as it needs to know which stage to query. When there is No Load Shedding the Stage 1 schedule will be shown.
62+
i.e When load shedding is suspended, it will show **No Load Shedding**. When Stage 2 is active, it will show **Stage 2**.
6263

6364
<details>
6465
<summary>Screenshot</summary>
@@ -72,326 +73,63 @@ i.e When load shedding is suspended, it will show **No Load Shedding**. When St
7273
# Cards
7374
I created this card with the help of [template-entity-row](https://github.com/thomasloven/lovelace-template-entity-row)
7475
<details>
75-
<summary>Screenshot</summary>
76+
<summary>Card 1</summary>
7677

78+
[Code](examples/card2.yaml)
7779
![img.png](img.png)
80+
</details>
7881

79-
</details>
8082
<details>
81-
<summary>Code</summary>
82-
83-
```yaml
84-
type: entities
85-
entities:
86-
- type: custom:template-entity-row
87-
icon: mdi:lightning-bolt-outline
88-
name: Status
89-
entity: sensor.load_shedding_stage
90-
active: '{{ not is_state("sensor.load_shedding_stage", "No Load Shedding") }}'
91-
state: '{{states("sensor.load_shedding_stage")}}'
92-
- type: custom:template-entity-row
93-
icon: mdi:timer-outline
94-
name: Milnerton
95-
active: '{{ states("sensor.load_shedding_milnerton") == "on" }}'
96-
state: >-
97-
{{ (state_attr("sensor.load_shedding_milnerton", "start_time") | as_datetime | as_local).strftime("%H:%M") }} - {{ (state_attr("sensor.load_shedding_milnerton", "end_time") | as_datetime | as_local).strftime("%H:%M") }}
98-
secondary: >-
99-
{% if states("sensor.load_shedding_milnerton") == "off" %}
100-
Starts in {{ timedelta(minutes=state_attr("sensor.load_shedding_milnerton", "starts_in")) }}
101-
{% else %}
102-
Ends in {{ timedelta(minutes=state_attr("sensor.load_shedding_milnerton", "ends_in")) }}
103-
{% endif %}
104-
entity: sensor.load_shedding_milnerton
105-
```
83+
<summary>Card 2</summary>
10684

85+
[Code](examples/card3.yaml)
10786
![img_1.png](img_1.png)
87+
</details>
10888

109-
```yaml
110-
type: markdown
111-
entity_ids:
112-
- sensor.load_shedding_south_africa_stage
113-
- sensor.load_shedding_milnerton_14
114-
content: >-
115-
{% set stage_sensor = "sensor.load_shedding_south_africa_stage" %}
116-
{% set area_sensor = "sensor.load_shedding_milnerton_14" %}
117-
118-
{% set start_time = state_attr(stage_sensor, "start_time") %}
119-
{% set end_time = state_attr(stage_sensor, "end_time") %}
120-
121-
{% set area_schedule = state_attr(area_sensor, "forecast") %}
122-
{% if area_schedule %}
123-
{% set start_time = area_schedule[0].start_time %}
124-
{% set end_time = area_schedule[0].end_time %}
125-
126-
{% if is_state(area_sensor, "off") %}
127-
{% set starts_in = timedelta(minutes=state_attr(area_sensor, "starts_in")) %}
128-
{% if is_state_attr(stage_sensor, "stage", 0) or starts_in.seconds > 86400 %}
129-
<ha-alert alert-type="success">{{ states(stage_sensor) }}</ha-alert>
130-
{% elif not is_state_attr(stage_sensor, "stage", 0) and 0 < starts_in.seconds <= 86400 %}
131-
<ha-alert alert-type="warning">Load Shedding starts in {{ starts_in.seconds // 3600 }}h{{ (starts_in.seconds // 60) - (starts_in.seconds // 3600 * 60) }}m ({{ as_timestamp(start_time) | timestamp_custom("%H:%M", True) }})</ha-alert>
132-
{% endif %}
133-
{% else %}
134-
{% set ends_in = timedelta(minutes=state_attr(area_sensor, "ends_in")) %}
135-
{% if is_state_attr(stage_sensor, "stage", 0) or ends_in.seconds > 86400 %}
136-
<ha-alert alert-type="success">{{ states(stage_sensor) }}</ha-alert>
137-
{% elif not is_state_attr(stage_sensor, "stage", 0) and 0 < ends_in.seconds <= 86400 %}
138-
<ha-alert alert-type="error">Load Shedding ends in {{ ends_in.seconds // 3600 }}h{{ (ends_in.seconds // 60) - (ends_in.seconds // 3600 * 60) }}m ({{ as_timestamp(end_time) | timestamp_custom("%H:%M", True) }})</ha-alert>
139-
{% endif %}
140-
{% endif %}
141-
{% endif %}
142-
143-
144-
{% set area_forecast = state_attr(area_sensor, "forecast" )%}
145-
{% if area_forecast %}
146-
<table width="100%" border=0>
147-
<tbody>
148-
<tr>
149-
<td width="34px"><ha-icon icon="mdi:calendar"></ha-icon></td>
150-
<td align="left" colspan=3>Forecast : : {{ state_attr(area_sensor, "friendly_name") }}</td>
151-
</tr>
152-
{% for forecast in area_forecast[:3] %}
153-
<tr>
154-
<td></td>
155-
<td align="left">
156-
{{ as_timestamp(forecast.start_time) | timestamp_custom("%-d %B", True) }}
157-
</td>
158-
<td align="left">
159-
{{ as_timestamp(forecast.start_time) | timestamp_custom("%H:%M", True) }} - {{ as_timestamp(forecast.end_time) | timestamp_custom("%H:%M", True) }}
160-
</td>
161-
<td align="right">Stage {{ forecast.stage }}</td>
162-
</tr>
163-
{% endfor %}
164-
</tbody>
165-
</table>
166-
{% endif %}
167-
89+
<details>
90+
<summary>Card 3 (v0.6.0)</summary>
16891

169-
{% set area_schedule = state_attr(area_sensor, "schedule" )%}
170-
{% if area_schedule %}
171-
<table width="100%" border=0>
172-
<tbody>
173-
<tr>
174-
<td width="34px"><ha-icon icon="mdi:calendar"></ha-icon></td>
175-
<td align="left" colspan=3>Schedule : : {{ state_attr(area_sensor, "friendly_name") }}</td>
176-
</tr>
177-
{% for slot in area_schedule[:3] %}
178-
<tr>
179-
<td></td>
180-
<td align="left">
181-
{{ as_timestamp(slot.start_time) | timestamp_custom("%-d %B", True) }}
182-
</td>
183-
<td align="left">
184-
{{ as_timestamp(slot.start_time) | timestamp_custom("%H:%M", True) }} - {{ as_timestamp(slot.end_time) | timestamp_custom("%H:%M", True) }}
185-
</td>
186-
<td align="right">Stage {{ slot.stage }}</td>
187-
</tr>
188-
{% endfor %}
189-
</tbody>
190-
</table>
191-
{% endif %}
192-
```
92+
[Code](examples/card2.yaml)
93+
![img_2.png](img_2.png)
94+
</details>
19395

194-
</details>
19596

19697
# Automation Ideas
197-
These are just some automations I've got set up. They are not perfect and will require some tweaking on your end. Feel free to contribute your automations ideas and custom panels by posting them on [this Issue thread](https://github.com/wernerhp/ha_integration_load_shedding/issues/5)
98+
These are just some automations I've got set up. They are not perfect and will require some tweaking on your end.
99+
Replace `sensor.load_shedding_south_africa_stage`, `sensor.load_shedding_milnerton_14` and other `entity_id` with your own.
198100

199101
### Announce Load Shedding stage changes on speakers and push notifications.
200-
<details>
201-
<summary>Code</summary>
202-
203-
```yaml
204-
alias: Load Shedding (Stage)
205-
description: ''
206-
trigger:
207-
- platform: state
208-
entity_id:
209-
- sensor.load_shedding_stage
210-
condition:
211-
- condition: template
212-
value_template: >-
213-
{{ trigger.from_state.state != 'unavailable' and trigger.to_state.state != 'unavailable' }}
214-
action:
215-
- choose:
216-
- conditions:
217-
- condition: or
218-
conditions:
219-
- condition: time
220-
after: input_datetime.sleep
221-
weekday:
222-
- mon
223-
- tue
224-
- wed
225-
- thu
226-
- fri
227-
- sat
228-
- sun
229-
- condition: time
230-
before: input_datetime.wake
231-
weekday:
232-
- sun
233-
- sat
234-
- fri
235-
- thu
236-
- wed
237-
- tue
238-
- mon
239-
sequence:
240-
- wait_for_trigger:
241-
- platform: time
242-
at: input_datetime.wake
243-
continue_on_timeout: false
244-
default: []
245-
- service: notify.mobile_app_nokia_8_sirocco
246-
data:
247-
title: Load Shedding
248-
message: '{{ states.sensor.load_shedding_stage.state }}'
249-
- service: tts.home_assistant_say
250-
data:
251-
entity_id: media_player.assistant_speakers
252-
cache: true
253-
message: >-
254-
{% if is_state("sensor.load_shedding_stage", "No Load Shedding") %} Load
255-
Shedding suspended {% else %} Load Shedding {{
256-
states.sensor.load_shedding_stage.state }} {% endif %}
257-
enabled: false
258-
mode: single
259-
```
260-
</details>
102+
- [Load Shedding (Stage)](examples/automation1.yaml)
261103

262104
### 15 minutes warning on speaker and telegram before load shedding starts.
263-
<details>
264-
<summary>Code</summary>
265-
266-
```yaml
267-
alias: Load Shedding (Warning)
268-
description: ''
269-
trigger:
270-
- platform: template
271-
value_template: >-
272-
{{ timedelta(minutes=(state_attr("sensor.load_shedding_milnerton", "starts_in"))) == timedelta(minutes=15) }}
273-
condition:
274-
- condition: and
275-
conditions:
276-
- condition: time
277-
after: input_datetime.alarm
278-
before: input_datetime.sleep
279-
- condition: not
280-
conditions:
281-
- condition: state
282-
entity_id: sensor.load_shedding_stage
283-
state: Unknown
284-
- condition: state
285-
entity_id: sensor.load_shedding_stage
286-
state: No Load Shedding
287-
action:
288-
- service: telegram_bot.send_message
289-
data:
290-
message: Load Shedding starts in 15 minutes.
291-
title: Load Shedding
292-
- service: media_player.volume_set
293-
data:
294-
volume_level: 0.7
295-
target:
296-
entity_id: media_player.assistant_speakers
297-
- service: tts.home_assistant_say
298-
data:
299-
entity_id: media_player.assistant_speakers
300-
message: Load Shedding starts in 15 minutes.
301-
cache: true
302-
mode: single
303-
```
304-
</details>
105+
- [Load Shedding (Warning)](examples/automation2.yaml)
305106

306-
307-
### Dim lights or turn off devices before load shedding and turn them back on afterwards.
107+
### 2 hour warning on speaker
108+
- [Load Shedding (Warning) (2hr)](examples/automation3.yaml)
308109

309110
### Update your Slack status
310111

311-
Setup a REST Command and two automations to set your Slack status when Load Shedding starts and ends.
312-
112+
Setup a [REST Command](https://www.home-assistant.io/integrations/rest_command/) and two automations to set your Slack status when Load Shedding starts and ends.
313113
<details>
314-
<summary>Code</summary>
315-
114+
<summary>Example</summary>
115+
316116
`secrets.yaml`
317117
```yaml
318118
slack_token: Bearer xoxp-XXXXXXXXXX-XXXXXXXXXXXX-XXXXXXXXXXXXX-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
319119
```
320-
321-
[rest_command](https://www.home-assistant.io/integrations/rest_command/)
322-
323-
```yaml
324-
slack_status:
325-
url: https://slack.com/api/users.profile.set
326-
method: POST
327-
headers:
328-
authorization: !secret slack_token
329-
accept: "application/json, text/html"
330-
payload: '{"profile":{"status_text": "{{ status }}","status_emoji": "{{ emoji }}"}}'
331-
content_type: "application/json; charset=utf-8"
332-
verify_ssl: true
333-
```
334-
</details>
335-
336-
<details>
337-
<summary>Code</summary>
338-
120+
`configuration.yaml`
339121
```yaml
340-
alias: Load Shedding (Start)
341-
description: ''
342-
trigger:
343-
- platform: state
344-
entity_id:
345-
- sensor.load_shedding_milnerton
346-
to: 'on'
347-
from: 'off'
348-
condition:
349-
- condition: not
350-
conditions:
351-
- condition: state
352-
entity_id: sensor.load_shedding_stage
353-
state: Unknown
354-
- condition: state
355-
entity_id: sensor.load_shedding_stage
356-
state: No Load Shedding
357-
action:
358-
- service: rest_command.slack_status
359-
data:
360-
emoji: ':loadsheddingtransparent:'
361-
status: >-
362-
Load Shedding until {{
363-
(state_attr('sensor.load_shedding_milnerton','end_time') | as_datetime |
364-
as_local).strftime('%H:%M (%Z)') }}
365-
mode: single
122+
rest_command:
123+
slack_status:
124+
url: https://slack.com/api/users.profile.set
125+
method: POST
126+
headers:
127+
authorization: !secret slack_token
128+
accept: "application/json, text/html"
129+
payload: '{"profile":{"status_text": "{{ status }}","status_emoji": "{{ emoji }}"}}'
130+
content_type: "application/json; charset=utf-8"
131+
verify_ssl: true
366132
```
367-
</details>
368-
369-
<details>
370-
<summary>Code</summary>
371-
372-
```yaml
373-
alias: Load Shedding (End)
374-
description: ''
375-
trigger:
376-
- platform: state
377-
entity_id:
378-
- sensor.load_shedding_stage
379-
from: 'on'
380-
to: 'off'
381-
condition:
382-
- condition: not
383-
conditions:
384-
- condition: state
385-
entity_id: sensor.load_shedding_stage
386-
state: Unknown
387-
- condition: state
388-
entity_id: sensor.load_shedding_stage
389-
state: No Load Shedding
390-
action:
391-
- service: rest_command.slack_status
392-
data:
393-
emoji: ':speech_balloon:'
394-
status: is typing...
395-
mode: single
396-
```
397-
</details>
133+
- [Load Shedding (Start)](examples/automation3.yaml)
134+
- [Load Shedding (End)](examples/automation4.yaml)
135+
</details>

0 commit comments

Comments
 (0)