Сложности при создании нового пользователя через форму django
Я работаю над регистрацией на сайте. Моя проблема заключается в том, что встроенная модель User сохраняется удачно, а элемент другой связанной модели не может сохраниться и где-то теряется (kind). Предполагаю, что проблема с самой неправильной организацией .save(), но точно не понимаю в чем проблема. Тест на создание нового пользователя проходит хорошо. В результате создается пользователь с введенными данными, за исключением Kind. Делал частично по этому туториалу: https://tproger.ru/translations/extending-django-user-model/ , но видимо где-то допустил ошибку. Очень надеюсь на помощь!
Models.py
from django.db import models
from django.contrib.auth.models import User
from django.db.models.signals import post_save
from django.dispatch import receiver
class Kind(models.Model):
class Kinds(models.TextChoices):
M = '1', "М"
F = '2', "Ж"
class Confirmations(models.TextChoices):
S = '1', "Не подтвержден"
N = '2', "Подтвержден"
user = models.OneToOneField(User, on_delete=models.CASCADE, related_name='profile')
avatar = models.ImageField(null=True, blank=True, upload_to="avatars/", verbose_name='Изображение')
kind = models.CharField(max_length=1, choices=Kinds.choices, verbose_name='Пол')
confirmation = models.CharField(max_length=1, default='1', choices=Confirmations.choices, verbose_name='Подтверждение')
@receiver(post_save, sender=User)
def create_user_profile(sender, instance, created, **kwargs):
if created:
Kind.objects.create(user=instance)
@receiver(post_save, sender=User)
def save_user_profile(sender, instance, **kwargs):
instance.profile.save()
Views.py
from django.contrib.auth import authenticate, login
from django.shortcuts import render, redirect
from django.core.files.storage import FileSystemStorage
from Вход.forms import *
from .models import *
def registrationn(request):
if request.method == 'POST':
user_form = UserRegistrationForm(request.POST)
kind_form = UserKindForm(request.POST, instance=request.user.profile)
if user_form.is_valid() and kind_form.is_valid():
new_user = user_form.save()
new_user.set_password(user_form.cleaned_data['password'])
new_user.save()
new_kind = kind_form.save()
new_kind.save()
return render(request, 'registration/registration_done.html', {'new_user': new_user, 'new_kind': new_kind})
else:
user_form = UserRegistrationForm()
kind_form = UserKindForm()
return render(request, 'registration/registration.html', {'user_form': user_form, 'kind_form': kind_form})
...
Forms.py
from .models import Kind
from django.forms import ModelForm
from django import forms
from django.contrib.auth.models import User
class UserRegistrationForm(forms.ModelForm):
password = forms.CharField(label='Password', widget=forms.PasswordInput)
password2 = forms.CharField(label='Repeat password', widget=forms.PasswordInput)
class Meta:
model = User
fields = ('username', 'first_name', 'email')
def clean_password2(self):
cd = self.cleaned_data
if cd['password'] != cd['password2']:
raise forms.ValidationError('Passwords don\'t match.')
return cd['password2']
class UserKindForm(forms.ModelForm):
class Meta:
model = Kind
fields = ('kind', )
Шаблон 1
{% extends "Главная/Общее.html" %}
{% load static %}
{% load crispy_forms_tags %}
{% block title %}Create an account{% endblock %}
{% block content %}
<h2>Register</h2>
<form id="formm" method="post">
{% csrf_token %}
{{ user_form.as_p }}
{{ kind_form.as_p }}
</form>
<input form="formm" type="submit" value="Register">
{% endblock %}
Шаблон 2
{% extends "Главная/Общее.html" %}
{% block title %}Welcome{% endblock %}
{% block content %}
<h1>Уважаемый пользователь {{ new_user.first_name }}, мы рассмотрим вашу заявку в течении суток!</h1>
<p><a href="/">На главную</a>.</p>
{% endblock %}
У меня получилось получить ответ на свой вопрос. Оказывается моя форма работала вообще не с новым пользователем, а другим пользователем из базы данных. Кто делает регистрацию, никогда не указывайте instance=... это большая ошибка. Еще не создан пользователь чтобы работать с ним.
Мне помог этот код:
if request.method == 'POST':
user_form = UserRegistrationForm(request.POST)
kind_form = UserKindForm(request.POST)
if user_form.is_valid() and kind_form.is_valid():
new_user = user_form.save()
new_user.set_password(user_form.cleaned_data['password'])
new_user.save()
new_user.profile.kind = kind_form.cleaned_data.get('kind')
new_user.profile.save()
return render(request, 'registration/registration_done.html', {'new_user': new_user, 'kind_form': kind_form})
else:
user_form = UserRegistrationForm()
kind_form = UserKindForm()
return render(request, 'registration/registration.html', {'user_form': user_form, 'kind_form': kind_form})