我正在尝试覆盖 PasswordResetForm 表单,以便在 save() 方法之后,电子邮件由 celery 任务异步发送,但不幸的是发生了错误。这是跟踪:
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/core/handlers/exception.py", line 34, in inner
response = get_response(request)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/core/handlers/base.py", line 115, in _get_response
response = self.process_exception_by_middleware(e, request)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/core/handlers/base.py", line 113, in _get_response
response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/views/generic/base.py", line 71, in view
return self.dispatch(request, *args, **kwargs)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/utils/decorators.py", line 43, in _wrapper
return bound_method(*args, **kwargs)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/utils/decorators.py", line 130, in _wrapped_view
response = view_func(request, *args, **kwargs)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/contrib/auth/views.py", line 222, in dispatch
return super().dispatch(*args, **kwargs)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/views/generic/base.py", line 97, in dispatch
return handler(request, *args, **kwargs)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/views/generic/edit.py", line 142, in post
return self.form_valid(form)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/lib/python3.8/site-packages/django/contrib/auth/views.py", line 235, in form_valid
form.save(**opts)
File "/mnt/c/users/huawei/desktop/adsboard_project_venv/tbads/reset_password_system/forms.py", line 52, in save
json.dumps(context), json.dumps(from_email), json.dumps(user.email),
File "/usr/lib/python3.8/json/__init__.py", line 231, in dumps
return _default_encoder.encode(obj)
File "/usr/lib/python3.8/json/encoder.py", line 199, in encode
chunks = self.iterencode(o, _one_shot=True)
File "/usr/lib/python3.8/json/encoder.py", line 257, in iterencode
return _iterencode(o, 0)
File "/usr/lib/python3.8/json/encoder.py", line 179, in default
raise TypeError(f'Object of type {o.__class__.__name__} '
TypeError: Object of type User is not JSON serializable
我的代码:
表格.py
from django.contrib.auth.forms import PasswordResetForm, SetPasswordForm
from django.contrib.auth import get_user_model
from django.contrib.auth.tokens import default_token_generator
from django.contrib.sites.shortcuts import get_current_site
from django.utils.encoding import force_bytes
from django.utils.http import urlsafe_base64_encode
from .tasks import send_mail_message
class GetUserEmailForm(PasswordResetForm):
email = forms.EmailField(
widget=forms.EmailInput(attrs={'class': 'input-login input-form', 'placeholder': 'Email'})
)
def clean_email(self):
email = self.cleaned_data.get('email')
try:
get_user_model().objects.get(email=email)
except get_user_model().DoesNotExist:
raise forms.ValidationError(
'Пользователь с таким адресом электронной почты не существует.'
)
return email
def save(self, domain_override=None,
subject_template_name='registration/password_reset_subject.txt',
email_template_name='registration/password_reset_email.html',
use_https=False, token_generator=default_token_generator,
from_email=None, request=None, html_email_template_name=None, **kwargs):
email = self.cleaned_data["email"]
for user in self.get_users(email):
if not domain_override:
current_site = get_current_site(request)
site_name = current_site.name
domain = current_site.domain
else:
site_name = domain = domain_override
context = {
'email': user.email,
'domain': domain,
'site_name': site_name,
'uid': urlsafe_base64_encode(force_bytes(user.pk)),
'user': user,
'token': token_generator.make_token(user),
'protocol': 'https' if use_https else 'http',
}
send_mail_message.delay(subject_template_name, email_template_name,
context, from_email, user.email,
html_email_template_name=html_email_template_name)
任务.py
from django.template import loader
from tbads.celery import celery_app
from django.core.mail import EmailMultiAlternatives
@celery_app.task
def send_mail_message(subject_template_name, email_template_name,
context, from_email, to_email, html_email_template_name=None):
subject = loader.render_to_string(subject_template_name, context)
subject = ''.join(subject.splitlines())
body = loader.render_to_string(email_template_name, context)
email_message = EmailMultiAlternatives(subject, body, from_email, [to_email])
if html_email_template_name is not None:
html_email = loader.render_to_string(html_email_template_name, context)
email_message.attach_alternative(html_email, 'text/html')
email_message.send()
我尝试使用 json.dumps 和 to.JSON 转换参数,但没有带来太多结果,请告诉我,有什么问题?
您的错误与无法将对象
User转换为适用于json. 或者,您可以'user': user从context. 如果将来需要您的对象user,请立即将其替换为必要的字段 - 例如first_name: user.first_name,并将它们添加到您的context.