Skip to content

Commit ca7332f

Browse files
authored
Add event entity for Telegram bot (home-assistant#154383)
1 parent eafedeb commit ca7332f

File tree

8 files changed

+213
-1
lines changed

8 files changed

+213
-1
lines changed

homeassistant/components/telegram_bot/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -359,7 +359,7 @@
359359
PLATFORM_WEBHOOKS: webhooks,
360360
}
361361

362-
PLATFORMS: list[Platform] = [Platform.NOTIFY]
362+
PLATFORMS: list[Platform] = [Platform.EVENT, Platform.NOTIFY]
363363

364364

365365
async def async_setup(hass: HomeAssistant, config: ConfigType) -> bool:

homeassistant/components/telegram_bot/bot.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@
4444
)
4545
from homeassistant.core import Context, HomeAssistant
4646
from homeassistant.exceptions import HomeAssistantError, ServiceValidationError
47+
from homeassistant.helpers.dispatcher import async_dispatcher_send
4748
from homeassistant.util.ssl import get_default_context, get_default_no_verify_context
4849

4950
from .const import (
@@ -107,6 +108,7 @@
107108
SERVICE_SEND_STICKER,
108109
SERVICE_SEND_VIDEO,
109110
SERVICE_SEND_VOICE,
111+
SIGNAL_UPDATE_EVENT,
110112
)
111113

112114
_FILE_TYPES = ("animation", "document", "photo", "sticker", "video", "voice")
@@ -167,6 +169,7 @@ async def handle_update(self, update: Update, context: CallbackContext) -> bool:
167169

168170
_LOGGER.debug("Firing event %s: %s", event_type, event_data)
169171
self.hass.bus.async_fire(event_type, event_data, context=event_context)
172+
async_dispatcher_send(self.hass, SIGNAL_UPDATE_EVENT, event_type, event_data)
170173
return True
171174

172175
@staticmethod
@@ -547,6 +550,9 @@ async def _send_msg(
547550
self.hass.bus.async_fire(
548551
EVENT_TELEGRAM_SENT, event_data, context=context
549552
)
553+
async_dispatcher_send(
554+
self.hass, SIGNAL_UPDATE_EVENT, EVENT_TELEGRAM_SENT, event_data
555+
)
550556
except TelegramError as exc:
551557
if not suppress_error:
552558
raise HomeAssistantError(

homeassistant/components/telegram_bot/const.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@
5151
SERVICE_DELETE_MESSAGE = "delete_message"
5252
SERVICE_LEAVE_CHAT = "leave_chat"
5353

54+
SIGNAL_UPDATE_EVENT = "telegram_bot_update_event"
5455
EVENT_TELEGRAM_CALLBACK = "telegram_callback"
5556
EVENT_TELEGRAM_COMMAND = "telegram_command"
5657
EVENT_TELEGRAM_TEXT = "telegram_text"
Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
"""Event platform for Telegram bot integration."""
2+
3+
from typing import Any
4+
5+
from homeassistant.components.event import EventEntity, EventEntityDescription
6+
from homeassistant.core import HomeAssistant, callback
7+
from homeassistant.helpers.dispatcher import async_dispatcher_connect
8+
from homeassistant.helpers.entity_platform import AddConfigEntryEntitiesCallback
9+
10+
from .bot import TelegramBotConfigEntry
11+
from .const import (
12+
EVENT_TELEGRAM_ATTACHMENT,
13+
EVENT_TELEGRAM_CALLBACK,
14+
EVENT_TELEGRAM_COMMAND,
15+
EVENT_TELEGRAM_SENT,
16+
EVENT_TELEGRAM_TEXT,
17+
SIGNAL_UPDATE_EVENT,
18+
)
19+
from .entity import TelegramBotEntity
20+
21+
22+
async def async_setup_entry(
23+
hass: HomeAssistant,
24+
config_entry: TelegramBotConfigEntry,
25+
async_add_entities: AddConfigEntryEntitiesCallback,
26+
) -> None:
27+
"""Set up the event platform."""
28+
async_add_entities([TelegramBotEventEntity(config_entry)])
29+
30+
31+
class TelegramBotEventEntity(TelegramBotEntity, EventEntity):
32+
"""An event entity."""
33+
34+
_attr_event_types = [
35+
EVENT_TELEGRAM_ATTACHMENT,
36+
EVENT_TELEGRAM_CALLBACK,
37+
EVENT_TELEGRAM_COMMAND,
38+
EVENT_TELEGRAM_TEXT,
39+
EVENT_TELEGRAM_SENT,
40+
]
41+
42+
def __init__(
43+
self,
44+
config_entry: TelegramBotConfigEntry,
45+
) -> None:
46+
"""Initialize the entity."""
47+
48+
super().__init__(
49+
config_entry,
50+
EventEntityDescription(key="update_event", translation_key="update_event"),
51+
)
52+
53+
async def async_added_to_hass(self) -> None:
54+
"""Register callbacks."""
55+
self.async_on_remove(
56+
async_dispatcher_connect(
57+
self.hass,
58+
SIGNAL_UPDATE_EVENT,
59+
self._async_handle_event,
60+
)
61+
)
62+
63+
@callback
64+
def _async_handle_event(self, event_type: str, event_data: dict[str, Any]) -> None:
65+
"""Handle the event."""
66+
self._trigger_event(event_type, event_data)
67+
self.async_write_ha_state()

homeassistant/components/telegram_bot/icons.json

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,11 @@
11
{
2+
"entity": {
3+
"event": {
4+
"update_event": {
5+
"default": "mdi:message-reply"
6+
}
7+
}
8+
},
29
"services": {
310
"answer_callback_query": {
411
"service": "mdi:check"

homeassistant/components/telegram_bot/strings.json

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -213,6 +213,75 @@
213213
}
214214
}
215215
},
216+
"entity": {
217+
"event": {
218+
"update_event": {
219+
"name": "Update event",
220+
"state_attributes": {
221+
"event_type": {
222+
"state": {
223+
"telegram_attachment": "Attachment received",
224+
"telegram_callback": "Callback query received",
225+
"telegram_command": "Command received",
226+
"telegram_text": "Text message received",
227+
"telegram_sent": "Message sent"
228+
}
229+
},
230+
"args": {
231+
"name": "Received command arguments"
232+
},
233+
"chat_id": {
234+
"name": "Chat ID"
235+
},
236+
"command": {
237+
"name": "Received command"
238+
},
239+
"data": {
240+
"name": "Received callback query"
241+
},
242+
"date": {
243+
"name": "Received datetime"
244+
},
245+
"file_id": {
246+
"name": "Received file ID"
247+
},
248+
"file_mime_type": {
249+
"name": "Received file MIME type"
250+
},
251+
"file_name": {
252+
"name": "Received file name"
253+
},
254+
"file_size": {
255+
"name": "Received file size (bytes)"
256+
},
257+
"from_first": {
258+
"name": "Received From first name"
259+
},
260+
"from_last": {
261+
"name": "Received from last name"
262+
},
263+
"id": {
264+
"name": "ID"
265+
},
266+
"message_id": {
267+
"name": "Sent message ID"
268+
},
269+
"message_tag": {
270+
"name": "Sent message tag"
271+
},
272+
"message_thread_id": {
273+
"name": "Received message thread ID"
274+
},
275+
"text": {
276+
"name": "Received text/caption"
277+
},
278+
"user_id": {
279+
"name": "Received from user ID"
280+
}
281+
}
282+
}
283+
}
284+
},
216285
"services": {
217286
"answer_callback_query": {
218287
"description": "Responds to a callback query originated by clicking on an online keyboard button. The answer will be displayed to the user as a notification at the top of the chat screen or as an alert.",
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
# serializer version: 1
2+
# name: test_send_message
3+
ReadOnlyDict({
4+
'bot': dict({
5+
'first_name': 'Testbot',
6+
'id': 123456,
7+
'last_name': 'mock last name',
8+
'username': 'mock username',
9+
}),
10+
'chat_id': 123456,
11+
'event_type': 'telegram_sent',
12+
'event_types': list([
13+
'telegram_attachment',
14+
'telegram_callback',
15+
'telegram_command',
16+
'telegram_text',
17+
'telegram_sent',
18+
]),
19+
'friendly_name': 'Mock Title Update event',
20+
'message_id': 12345,
21+
})
22+
# ---
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
"""Test the telegram bot event platform."""
2+
3+
from syrupy.assertion import SnapshotAssertion
4+
from syrupy.filters import props
5+
6+
from homeassistant.components.telegram_bot.const import (
7+
ATTR_MESSAGE,
8+
ATTR_TARGET,
9+
DOMAIN,
10+
SERVICE_SEND_MESSAGE,
11+
)
12+
from homeassistant.core import HomeAssistant
13+
14+
from tests.common import MockConfigEntry
15+
16+
17+
async def test_send_message(
18+
hass: HomeAssistant,
19+
mock_broadcast_config_entry: MockConfigEntry,
20+
mock_external_calls: None,
21+
snapshot: SnapshotAssertion,
22+
) -> None:
23+
"""Test send message for entries with multiple chat_ids."""
24+
25+
mock_broadcast_config_entry.add_to_hass(hass)
26+
await hass.config_entries.async_setup(mock_broadcast_config_entry.entry_id)
27+
await hass.async_block_till_done()
28+
29+
await hass.services.async_call(
30+
DOMAIN,
31+
SERVICE_SEND_MESSAGE,
32+
{ATTR_TARGET: 123456, ATTR_MESSAGE: "test message"},
33+
blocking=True,
34+
return_response=True,
35+
)
36+
37+
await hass.async_block_till_done()
38+
39+
state = hass.states.get("event.mock_title_update_event")
40+
assert state.attributes == snapshot(exclude=props("config_entry_id"))

0 commit comments

Comments
 (0)