M. Gar
M. Gar

Reputation: 887

Use variables in send_email()

I use html as message in one email and pass some variables like this:

subject = 'Some Subject'
plain = render_to_string('templates/email/message.txt',{'name':variableWithSomeValue,'email':otherVariable})
html = render_to_string('templates/email/message.html',{'name':variableWithSomeValue,'email':otherVariable})
from_email = setting.EMAIL_HOST_USER
send_email(subject, plain, from_email, [variableToEmail], fail_silently=False, html_message=html)

That works good but now I need to take the message content from one table from the database, the table have three columns, in the first register have this values in each column. Column subject have Account Info, column plain have Hello {{name}}. Now you can access to the site using this email address {{email}}. and the column html have <p>Hello <strong>{{name}}</strong>.</p> <p>Now you can access to the site using this email address <strong>email</strong>.</p>.

So to take the values from the database I do this obj = ModelTable.objects.get(id=1) then this:

subject = obj.subject
plain = (obj.plain,{'name':variableWithSomeValue,'email':otherVariable})
html = (obj.html,{'name':variableWithSomeValue,'email':otherVariable})
from_email = setting.EMAIL_HOST_USER
send_email(subject, plain, from_email, [variableToEmail], fail_silently=False, html_message=html)

But this give me the error

AttributeError: 'tuple' object has no attribute 'encode'

so I tried to passing .encode(´utf-8´) for the values and gives me the same error, then change the value for each variable and find that the problem comes from plain = (obj.plain,{'name':variableWithSomeValue,'email':otherVariable}) and html = (obj.html,{'name':variableWithSomeValue,'email':otherVariable}) so I think that I passing the variables in the wrong way, so How can I do it in the right way? or maybe is for the encoding of the database but I think that using .encode(utf-8) should solve that problem but I really think that I pass the variables name and email in the wrong way.

Sorry for the long post and my bad grammar, if need more info please let me know.

Upvotes: 0

Views: 225

Answers (1)

Jordan Haines
Jordan Haines

Reputation: 216

I'm assuming that obj.plain and obj.html are strings representing your templates (as stored in the database)?

If that is the case, then you still need to render your email content. However, instead of using render_to_string, which takes as it's first argument a template path, you will want to create a template based on your string, and then render that template. Consider something like the following:

...
from django.template import Context, Template
plain_template = Template(obj.plain)
context = Context({'name':variableWithSomeValue,'email':otherVariable})
email_context = plain_template.render(context)
...
send_email(...)

Here's a link that better explains rendering string templates, as opposed to rendering template files.

https://docs.djangoproject.com/en/1.7/ref/templates/api/#rendering-a-context

Upvotes: 1

Related Questions