Last active
September 20, 2025 03:48
-
-
Save yougotborked/2a61daa1015615dca4357794dc6355bf to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| blueprint: | |
| name: Universal Actionable Notification (fixed, entity selectors) | |
| description: > | |
| Send highly customizable notifications to iOS and Android devices, supporting | |
| critical notifications, dynamic actions, and optional camera snapshot/stream. | |
| domain: automation | |
| input: | |
| iphone_services: | |
| name: iPhone Notification Services | |
| description: Select one or more iPhone notify services. | |
| selector: | |
| entity: | |
| domain: notify | |
| multiple: true | |
| android_services: | |
| name: Android Notification Services | |
| description: Select one or more Android notify services. | |
| selector: | |
| entity: | |
| domain: notify | |
| multiple: true | |
| trigger_entity: | |
| name: Trigger Entity | |
| description: Entity to monitor for state changes. | |
| selector: | |
| entity: | |
| notification_title: | |
| name: Notification Title | |
| description: Title of the notification. | |
| default: "Alert" | |
| selector: | |
| text: | |
| notification_message: | |
| name: Notification Message | |
| description: Body of the notification. | |
| default: "Action required." | |
| selector: | |
| text: | |
| critical_ios: | |
| name: Enable Critical Notifications (iOS) | |
| description: Enable iOS critical notifications (uses `push.critical` and `interruption-level`). | |
| default: false | |
| selector: | |
| boolean: | |
| critical_android: | |
| name: Enable Critical Notifications (Android) | |
| description: Enable Android high-priority + alarm stream. | |
| default: false | |
| selector: | |
| boolean: | |
| tts_message: | |
| name: TTS Message (Android, Optional) | |
| description: Text-to-Speech message for Android critical notifications. | |
| default: "" | |
| selector: | |
| text: | |
| tts_volume_max: | |
| name: TTS at Max Volume (Android) | |
| description: Enable Text-To-Speech at maximum volume. | |
| default: false | |
| selector: | |
| boolean: | |
| dynamic_camera: | |
| name: Include Camera (Optional) | |
| description: Attach camera snapshot / stream in the notification (device support varies). | |
| default: false | |
| selector: | |
| boolean: | |
| camera_entity: | |
| name: Camera Entity | |
| description: The camera to attach (snapshot/stream depending on platform/app support). | |
| selector: | |
| entity: | |
| domain: camera | |
| action_1_title: | |
| name: First Action Name (Optional) | |
| default: "" | |
| selector: | |
| text: | |
| first_action: | |
| name: First Action Sequence (Optional) | |
| default: [] | |
| selector: | |
| action: | |
| action_2_title: | |
| name: Second Action Name (Optional) | |
| default: "" | |
| selector: | |
| text: | |
| second_action: | |
| name: Second Action Sequence (Optional) | |
| default: [] | |
| selector: | |
| action: | |
| action_3_title: | |
| name: Third Action Name (Optional) | |
| default: "" | |
| selector: | |
| text: | |
| third_action: | |
| name: Third Action Sequence (Optional) | |
| default: [] | |
| selector: | |
| action: | |
| action_4_title: | |
| name: Fourth Action Name (Optional) | |
| default: "" | |
| selector: | |
| text: | |
| fourth_action: | |
| name: Fourth Action Sequence (Optional) | |
| default: [] | |
| selector: | |
| action: | |
| mode: restart | |
| triggers: | |
| - id: send | |
| trigger: state | |
| entity_id: !input trigger_entity | |
| - id: action | |
| trigger: event | |
| event_type: mobile_app_notification_action | |
| variables: | |
| title: !input notification_title | |
| body: !input notification_message | |
| is_critical_ios: !input critical_ios | |
| is_critical_android: !input critical_android | |
| tts_text: !input tts_message | |
| tts_max: !input tts_volume_max | |
| include_camera: !input dynamic_camera | |
| cam: !input camera_entity | |
| a1_title: !input action_1_title | |
| a2_title: !input action_2_title | |
| a3_title: !input action_3_title | |
| a4_title: !input action_4_title | |
| iphone_services_list: !input iphone_services | |
| android_services_list: !input android_services | |
| actions_list: >- | |
| {% set acts = [] %} | |
| {% if a1_title %}{% set acts = acts + [{ 'action': 'ACTION_1', 'title': a1_title }] %}{% endif %} | |
| {% if a2_title %}{% set acts = acts + [{ 'action': 'ACTION_2', 'title': a2_title }] %}{% endif %} | |
| {% if a3_title %}{% set acts = acts + [{ 'action': 'ACTION_3', 'title': a3_title }] %}{% endif %} | |
| {% if a4_title %}{% set acts = acts + [{ 'action': 'ACTION_4', 'title': a4_title }] %}{% endif %} | |
| {{ acts }} | |
| ios_data: >- | |
| {% set push = {'interruption-level': ('critical' if is_critical_ios else 'active')} %} | |
| {% if is_critical_ios %} | |
| {% set push = dict(push, **{'critical': 1}) %} | |
| {% endif %} | |
| {% set d = { | |
| 'push': push, | |
| 'hide-thumbnail': false, | |
| 'content-type': 'image/jpeg', | |
| 'actions': actions_list | |
| } %} | |
| {% if include_camera and cam %} | |
| {% set d = dict(d, **{'entity_id': cam}) %} | |
| {% endif %} | |
| {{ d }} | |
| android_data: >- | |
| {% set ch = 'alarm_stream_max' if tts_max else 'alarm_stream' %} | |
| {% set d = { | |
| 'ttl': 0, | |
| 'priority': ('high' if is_critical_android else 'normal'), | |
| 'channel': ch, | |
| 'media_stream': 'alarm_stream', | |
| 'tts_text': (tts_text or ''), | |
| 'hide-thumbnail': false, | |
| 'content-type': 'image/jpeg', | |
| 'actions': actions_list | |
| } %} | |
| {% if include_camera and cam %} | |
| {% set d = dict(d, **{'entity_id': cam}) %} | |
| {% endif %} | |
| {{ d }} | |
| tapped_action: >- | |
| {{ (trigger.event.data.action if trigger.id == 'action' else '') | default('', true) }} | |
| condition: [] | |
| action: | |
| - choose: | |
| - conditions: "{{ trigger.id == 'action' and tapped_action != '' }}" | |
| sequence: | |
| - choose: | |
| - conditions: "{{ tapped_action == 'ACTION_1' }}" | |
| sequence: !input first_action | |
| - conditions: "{{ tapped_action == 'ACTION_2' }}" | |
| sequence: !input second_action | |
| - conditions: "{{ tapped_action == 'ACTION_3' }}" | |
| sequence: !input third_action | |
| - conditions: "{{ tapped_action == 'ACTION_4' }}" | |
| sequence: !input fourth_action | |
| - conditions: "{{ trigger.id == 'send' }}" | |
| sequence: | |
| - choose: | |
| - conditions: "{{ iphone_services_list | length > 0 }}" | |
| sequence: | |
| - repeat: | |
| for_each: "{{ iphone_services_list }}" | |
| sequence: | |
| - service: "{{ repeat.item }}" | |
| data: | |
| title: "{{ title }}" | |
| message: "{{ body }}" | |
| data: "{{ ios_data }}" | |
| - choose: | |
| - conditions: "{{ android_services_list | length > 0 }}" | |
| sequence: | |
| - repeat: | |
| for_each: "{{ android_services_list }}" | |
| sequence: | |
| - service: "{{ repeat.item }}" | |
| data: | |
| title: "{{ title }}" | |
| message: >- | |
| {{ tts_text if (is_critical_android and tts_text) else body }} | |
| data: "{{ android_data }}" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment