I have a django project that uses a worker process that sends emails to users. The worker processes listens to a rabbitmq server and gets all the details about the email to send, the template variables, the email address to send to etc. The email body is created with django templates and render_to_string.
However I want to internationalize this. Some of our users are going to be using the website in English, some in other languages. They should get emails in their language. I have tried to i18n the email worker process (using django.utils.translations.ugettext/ugettext_lazy), so that the email subject and email body has _(...) or {% blocktrans %} resp.
However since the email is rendered and sent in a different background worker process, the normal django language detection process doesn't seem to apply. There is no user session, no cookies or no http headers for it to look at. When sending the message to the rabbitmq server, I can store the language code
But how do I tell django/gettext to use that language at a point.
e.g. My function that sends email might look like this:
def send_email(details):
lang = details['lang']
name = details['name']
email_address = details['email_address']
switch_gettext_to_this_language_what_goes_here(lang):
# ?????
email_subject = _("Welcome to $SITE")
What do I put in to switch django translations/gettext to a specific language code so that the _()
will use that language code?
Django then provides utilities to extract the translation strings into a message file. This file is a convenient way for translators to provide the equivalent of the translation strings in the target language. Once the translators have filled in the message file, it must be compiled.
Django offers multiple language support out-of-the-box. In fact, Django is translated into more than 100 languages. This tutorial looks at how to add multiple language support to your Django project.
This header is sent by your browser and tells the server which language(s) you prefer, in order by priority. Django tries each language in the header until it finds one with available translations. Failing that, it uses the global LANGUAGE_CODE setting.
{% load i18n %} is needed for internationalization. The purpose of internationalization is to allow a single application to read in multiple languages. In order to do this: you need a few hooks called translation strings. To give your template access to these tags, put {% load i18n %} toward the top of your template..
As @SteveMayne pointed out in comment (but it worth an answer), you can now use the context manager translation.override
(works with Django 1.6, didn't check with earlier versions):
from django.utils import translation
print(_("Hello")) # Will print to Hello if default = 'en'
# Make a block where the language will be Danish
with translation.override('dk'):
print(_("Hello")) # print "Hej"
It basically uses the same thing than @bitrut answer but it's built-in in Django, so it makes less dependencies...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With