ジャンゴでの電子メールのテンプレート
-
20-09-2019 - |
質問
私たちは皆知っている(または必要があります)、あなたは電子メールのボディをレンダリングするために、Djangoのテンプレートシステムを使用することができます:
def email(email, subject, template, context):
from django.core.mail import send_mail
from django.template import loader, Context
send_mail(subject, loader.get_template(template).render(Context(context)), 'from@domain.com', [email,])
これは私の心の内の1つの欠陥があります。電子メールの件名と内容を編集するには、ビューとテンプレートの両方を編集する必要があります。私は、テンプレートへの管理ユーザーのアクセス権を与えて正当化することができますが、私は彼らに生のpythonへのアクセス権を与えていないよ!
あなたは電子メールで、ブロックを指定してメールを送信するときに、それらを別々に引き出すことができれば、本当にクールになることはあります:
{% block subject %}This is my subject{% endblock %}
{% block plaintext %}My body{% endblock%}
{% block html %}My HTML body{% endblock%}
しかし、あなたはそれをどのように行うのでしょうか?どのようにして一度にただ一つのブロックをレンダリングするに行くか?
解決
これは私の第三作業の繰り返しです。それあなたがそうのような電子メールテンプレートを持っていると仮定します:
{% block subject %}{% endblock %}
{% block plain %}{% endblock %}
{% block html %}{% endblock %}
私は、デフォルトでは、リストの上送信した電子メールを反復するためにリファクタリングしてきましたし、単一の電子メールとdjango.contrib.auth
User
s(単一および複数)に送信するためのユーティリティメソッドがあります。私は賢明必要がありますが、そこに行くよりも、おそらく多くをカバーしています。
私はまた、Pythonの-愛とトップの上に行っている可能性があります。
def email_list(to_list, template_path, context_dict):
from django.core.mail import send_mail
from django.template import loader, Context
nodes = dict((n.name, n) for n in loader.get_template(template_path).nodelist if n.__class__.__name__ == 'BlockNode')
con = Context(context_dict)
r = lambda n: nodes[n].render(con)
for address in to_list:
send_mail(r('subject'), r('plain'), 'from@domain.com', [address,])
def email(to, template_path, context_dict):
return email_list([to,], template_path, context_dict)
def email_user(user, template_path, context_dict):
return email_list([user.email,], template_path, context_dict)
def email_users(user_list, template_path, context_dict):
return email_list([user.email for user in user_list], template_path, context_dict)
いつものように、あなたはその上で改善することができれば、行ってください。
他のヒント
ただ、2つのテンプレートを使用します。ボディ用と主題のための1つを
私はテンプレートの継承が{% body %}
タグを使用して動作させることができなかったので、私はこのようなテンプレートに切り替えます:
{% extends "base.txt" %}
{% if subject %}Subject{% endif %}
{% if body %}Email body{% endif %}
{% if html %}<p>HTML body</p>{% endif %}
今、私たちは、テンプレートを3回レンダリングする必要がありますが、継承が正常に動作します。
c = Context(context, autoescape = False)
subject = render_to_string(template_name, {'subject': True}, c).strip()
body = render_to_string(template_name, {'body': True}, c).strip()
c = Context(context, autoescape = True)
html = render_to_string(template_name, {'html': True}, c).strip()
私はまた、電子メールでのエスケープ文字を避けるために、非HTMLテキストをレンダリングするとき、それは必要なautoescapeをオフにすることが分かっ