🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
Django

DjangoはPythonで書かれた、オープンソースウェブアプリケーションのフレームワークです。複雑なデータベースを扱うウェブサイトを開発する際に必要な労力を減らす為にデザインされました。

SMTP

SMTP(Simple Mail Transfer Protocol)はIPネットワークでemailを伝送する為のプロトコルです。

メール

メールは、コンピュータネットワークを利用し、 情報等を交換する手段のことです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

2回答

3766閲覧

djangoでSMTPサーバを指定したメール送信がうまくいかない。

s-hara

総合スコア52

Django

DjangoはPythonで書かれた、オープンソースウェブアプリケーションのフレームワークです。複雑なデータベースを扱うウェブサイトを開発する際に必要な労力を減らす為にデザインされました。

SMTP

SMTP(Simple Mail Transfer Protocol)はIPネットワークでemailを伝送する為のプロトコルです。

メール

メールは、コンピュータネットワークを利用し、 情報等を交換する手段のことです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2018/04/29 04:31

編集2018/05/03 10:02

前提・実現したいこと

djangoにて社内のsmtpサーバを指定してWEBからパスワードリセットメールが送信できない。
以下、長文となりますが、実装した機能の要点(コード)と、問題点をまとめました。

■djangoシェル上でメール送信テスト

setting.pyの設定 EMAIL_HOST = '<社内のSMTPサーバ名を指定>' EMAIL_PORT = '25' EMAIL_HOST_USER = '' EMAIL_HOST_PASSWORD = '' EMAIL_USE_TLS = False EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend'

■python manage.py shellで以下を実行。

In [1]: from django.core.mail import send_mail In [2]: send_mail( ...: 'Subject here_mailhub', ...: 'Here is the message.', ...: 'fromアドレスを指定', ...: ['toアドレスを指定'], ...: ) Out[2]: 1

⇒問題なくメール送信される(OK)

■パスワードリセット用機能を実装し、WEBからパスワードリセット用メールを送信するとメールが配信されない。

※setting.pyは上記と同じ内容。

※パスワードリセットは以下の構成(要点だけ記載)

●url.py path('password_reset/', views.PasswordReset.as_view(), name='password_reset'), path('password_reset/done/', views.PasswordResetDone.as_view(), name='password_reset_done'), path('reset/<uidb64>/<token>/', views.PasswordResetConfirm.as_view(), name='password_reset_confirm'), path('reset/done/', views.PasswordResetComplete.as_view(), name='password_reset_complete'),
●views.py from .forms import (MyPasswordResetForm, MySetPasswordForm) from django.contrib.auth.views import (PasswordChangeDoneView, PasswordResetView, PasswordResetDoneView, PasswordResetConfirmView, PasswordResetCompleteView ) from django.urls import reverse_lazy class PasswordReset(PasswordResetView): """パスワード変更用URLの送付ページ""" subject_template_name = 'accounts/subject.txt' email_template_name = 'accounts/message.txt' template_name = 'accounts/password_reset_form.html' form_class = MyPasswordResetForm success_url = reverse_lazy('password_reset_done') class PasswordResetDone(PasswordResetDoneView): """パスワード変更用URLを送りましたページ""" template_name = 'accounts/password_reset_done.html'
●forms.py from django import forms from django.contrib.auth.models import User from django.contrib.auth.forms import PasswordChangeForm, PasswordResetForm, SetPasswordForm class MyPasswordResetForm(PasswordResetForm): """パスワード忘れたときのフォーム""" def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) for field in self.fields.values(): field.widget.attrs['class'] = 'form-control' class MySetPasswordForm(SetPasswordForm): """パスワード再設定用フォーム(パスワード忘れて再設定)""" def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) for field in self.fields.values(): field.widget.attrs['class'] = 'form-control' class PasswordResetConfirm(PasswordResetConfirmView): """新パスワード入力ページ""" form_class = MySetPasswordForm success_url = reverse_lazy('password_reset_complete') template_name = 'accounts/password_reset_confirm.html' class PasswordResetComplete(PasswordResetCompleteView): """新パスワード設定しましたページ""" template_name = 'accounts/password_reset_complete.html'
●password_reset_form.html <form action="" method="POST"> {{ form.non_field_errors }} {% for field in form %} <div class="form-group"> <label for="{{ field.id_for_label }}">{{ field.label_tag }}</label> {{ field }} {{ field.errors }} </div> {% endfor %} {% csrf_token %} <button type="submit" class="btn btn-primary btn-lg">送信</button> </form>
●password_reset_done.html <p> パスワード再設定用のメールを送信しました。<br> メールに記載されているリンクから再設定を行ってください。 </p>
●message.txt {{ user.username }} 様 下記URLよりサイトにアクセスの上、パスワードの再設定を行ってください。 再設定用URL {{ protocol}}://{{ domain }}{% url 'password_reset_confirm' uid token %} テストです。
●subject.txt パスワードの再登録

<その他に試したこと>
setting.pyで以下の通りコンソールモードにしてからパスワードリセットを実行

EMAIL_BACKEND = 'django.core.mail.backends.console.EmailBackend'

結果:コンソールに以下のようにパスワードリセット用のURLが表示される(OK)

Message-ID: <152515770692.2608.2202147284301657819@<PC名> xxxxx 様 下記URLよりサイトにアクセスの上、パスワードの再設定を行ってください。 再設定用URL http://127.0.0.1:8000/accounts/reset/Mg/4vt-61b46d5e192e0d5ee144/ xxxxxx

上記URLにアクセスすると問題なくパスワード変更ができるので、問題個所は
WEBページから社内SMTPサーバを使ったスワードリセットをお知らせするメール送信部分に問題がありそう。
但し、python managep.py shell上でsend_mailメソッドを使って社内SMTPサーバを指定してメール送信した場合は問題なくメール送信できる。

上記状況から、何が原因として考えられますでしょうか。

以上、よろしくお願いいたします。

補足情報(FW/ツールのバージョンなど)

django 2.0

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

自己解決

以下と同じ原因でした。

https://teratail.com/questions/127706

投稿2018/05/30 07:50

s-hara

総合スコア52

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

USER,PASSWORDのパラメータはフリーメールのサービスのものを
指定し、シェルからフリーメールに送信できました。

イメージ説明

メールが送信できない原因としてほかにどのようなことが

USER,PASSWORDのパラメータは空
で指定

が気になります。
USER,PASSWORDのパラメータを今度は実際のメールのもので指定。これで試してみてください。

またはその送信時にポート25番を使うsmtpのプロセス、サービスが起動していなかった。
フィルタリング機能のある中継サーバ画置かれているとか。

投稿2018/04/30 18:29

kawakawa2018

総合スコア1195

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

s-hara

2018/05/01 07:48 編集

回答ありがとうございます。 その後再確認したところ、send_mailメソッドでは普通にメール送信ができました。(なぜメール送信できなかったかは謎ですが今は問題ありません) 単体レベルで社内SMTPサーバを使ってメール送信できることが確認できましたので、別途、パスワードリセット用機能を実装してWEBからリセット用メールを送信しようとするとメールが配信されない問題が発生しました。 パスワードリセットの実装内容と問題内容を整理して記事を更新しました。 もし原因について情報がありましたらご回答いただけますと幸いです。 以上、よろしくお願いいたします。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問