|
1 | 1 | from django.db import transaction |
2 | 2 |
|
3 | | -from celery.exceptions import MaxRetriesExceededError |
4 | 3 | import logging |
5 | 4 | from uuid import uuid4 |
6 | 5 | from notifications.models import SentEmail |
|
11 | 10 | logger = logging.getLogger(__name__) |
12 | 11 |
|
13 | 12 |
|
| 13 | +def send_pending_email_failed(self, task_id, args, kwargs, einfo): |
| 14 | + sent_email_id = args[0] |
| 15 | + |
| 16 | + sent_email = SentEmail.objects.get(id=sent_email_id) |
| 17 | + sent_email.mark_as_failed() |
| 18 | + logger.error( |
| 19 | + "Failed to send email sent_email_id=%s", |
| 20 | + sent_email.id, |
| 21 | + ) |
| 22 | + |
| 23 | + |
14 | 24 | @app.task( |
15 | 25 | bind=True, |
| 26 | + autoretry_for=(Exception,), |
16 | 27 | retry_backoff=5, |
17 | 28 | max_retries=5, |
18 | 29 | default_retry_delay=2, |
| 30 | + on_failure=send_pending_email_failed, |
19 | 31 | ) |
| 32 | +@transaction.atomic() |
20 | 33 | def send_pending_email(self, sent_email_id: int): |
21 | 34 | logger.info( |
22 | | - "Sending sent_email=%s (retry=%s of %s)", |
| 35 | + "Sending sent_email=%s (attempt=%s of %s)", |
23 | 36 | sent_email_id, |
24 | 37 | self.request.retries, |
25 | 38 | self.max_retries, |
26 | 39 | ) |
27 | 40 |
|
28 | | - try: |
29 | | - with transaction.atomic(): |
30 | | - sent_email = ( |
31 | | - SentEmail.objects.select_for_update(skip_locked=True) |
32 | | - .pending() |
33 | | - .filter(id=sent_email_id) |
34 | | - .first() |
35 | | - ) |
| 41 | + sent_email = ( |
| 42 | + SentEmail.objects.select_for_update(skip_locked=True) |
| 43 | + .pending() |
| 44 | + .filter(id=sent_email_id) |
| 45 | + .first() |
| 46 | + ) |
36 | 47 |
|
37 | | - if not sent_email: |
38 | | - return |
| 48 | + if not sent_email: |
| 49 | + return |
39 | 50 |
|
40 | | - email_backend_connection = get_connection() |
| 51 | + email_backend_connection = get_connection() |
41 | 52 |
|
42 | | - message_id = send_email(sent_email, email_backend_connection) |
43 | | - sent_email.mark_as_sent(message_id) |
| 53 | + message_id = send_email(sent_email, email_backend_connection) |
| 54 | + sent_email.mark_as_sent(message_id) |
44 | 55 |
|
45 | | - logger.info( |
46 | | - "Email sent_email_id=%s sent with message_id=%s", |
47 | | - sent_email.id, |
48 | | - message_id, |
49 | | - ) |
50 | | - except Exception as e: |
51 | | - try: |
52 | | - raise self.retry(exc=e) |
53 | | - except MaxRetriesExceededError: |
54 | | - sent_email = SentEmail.objects.get(id=sent_email_id) |
55 | | - sent_email.mark_as_failed() |
56 | | - logger.error( |
57 | | - "Failed to send email sent_email_id=%s", |
58 | | - sent_email.id, |
59 | | - ) |
60 | | - return |
| 56 | + logger.info( |
| 57 | + "Email sent_email_id=%s sent with message_id=%s", |
| 58 | + sent_email.id, |
| 59 | + message_id, |
| 60 | + ) |
61 | 61 |
|
62 | 62 |
|
63 | 63 | def send_email(sent_email, email_backend_connection): |
|
0 commit comments