Raise HomeAssistantError when retries are exhausted in STMP legacy notify action (#176165)

This commit is contained in:
Manu
2026-07-10 08:03:55 +02:00
committed by GitHub
parent e325be6f87
commit b9da56c76e
2 changed files with 52 additions and 6 deletions
+18 -6
View File
@@ -315,25 +315,37 @@ class MailNotificationService(SmtpClient, BaseNotificationService):
def _send_email(self, msg: MIMEMultipart | MIMEText, recipients: list[str]) -> None:
"""Send the message."""
mail = self.connect()
for _ in range(self.tries):
for attempt in range(self.tries):
try:
mail.sendmail(self._sender, recipients, msg.as_string())
break
except SMTPServerDisconnected:
except SMTPServerDisconnected as e:
with suppress(SMTPException):
mail.quit()
if attempt == self.tries - 1:
_LOGGER.debug("Full exception:", exc_info=True)
raise HomeAssistantError(
translation_domain=DOMAIN,
translation_key="send_mail_connection_error",
) from e
_LOGGER.warning(
"SMTPServerDisconnected sending mail: retrying connection",
exc_info=_LOGGER.isEnabledFor(logging.DEBUG),
)
mail = self.connect()
except SMTPException as e:
with suppress(SMTPException):
mail.quit()
mail = self.connect()
except SMTPException:
if attempt == self.tries - 1:
_LOGGER.debug("Full exception:", exc_info=True)
raise HomeAssistantError(
translation_domain=DOMAIN,
translation_key="send_mail_connection_error",
) from e
_LOGGER.warning(
"SMTPException sending mail: retrying connection",
exc_info=_LOGGER.isEnabledFor(logging.DEBUG),
)
with suppress(SMTPException):
mail.quit()
mail = self.connect()
with suppress(SMTPException):
mail.quit()
+34
View File
@@ -4,6 +4,7 @@ from pathlib import Path
import re
from smtplib import (
SMTPAuthenticationError,
SMTPException,
SMTPHeloError,
SMTPSenderRefused,
SMTPServerDisconnected,
@@ -16,6 +17,7 @@ from syrupy.assertion import SnapshotAssertion
from homeassistant.components.notify import (
ATTR_MESSAGE,
ATTR_TARGET,
DOMAIN as NOTIFY_DOMAIN,
SERVICE_SEND_MESSAGE,
)
@@ -360,3 +362,35 @@ async def test_notify_retry_on_disconnect_with_broken_quit(
)
assert smtp.sendmail.call_count == 2
@pytest.mark.parametrize("exception", [SMTPServerDisconnected, SMTPException])
async def test_legacy_notify_exception(
hass: HomeAssistant,
config_entry: MockConfigEntry,
smtp: MagicMock,
exception: Exception,
) -> None:
"""Test legacy notify action raises when retries are exhausted."""
config_entry.add_to_hass(hass)
await hass.config_entries.async_setup(config_entry.entry_id)
await hass.async_block_till_done()
assert config_entry.state is ConfigEntryState.LOADED
smtp.sendmail.side_effect = exception
with pytest.raises(HomeAssistantError) as e:
await hass.services.async_call(
NOTIFY_DOMAIN,
"home_assistant",
{
ATTR_TARGET: ["recipient@example.com"],
ATTR_MESSAGE: "Hello World",
},
blocking=True,
)
assert e.value.translation_key == "send_mail_connection_error"
assert smtp.sendmail.call_count == 2