ユーザ登録を行ったときにメールアドレスの検証を終えるまではログインできないようにしたい.ここではその前段階として,ユーザ登録してもログインができないように設定を変更します.
  このためには,users_user テーブルの is_active 属性を 0 にします.実装の方法はいくつか考えられますが,forms.py の中で行うことにします.
users/forms.py
class UserCreationForm(forms.ModelForm):
    """
    A form that creates a user, with no privileges, from the given username and
    password.
    """
    error_messages = {
        "password_mismatch": _("The two password fields didn’t match."),
    }
    password1 = forms.CharField(
        label=_("Password"),
        strip=False,
        widget=forms.PasswordInput(attrs={"autocomplete": "new-password", 'class': 'form-control'}),
        help_text=password_validation.password_validators_help_text_html(),
    )
    password2 = forms.CharField(
        label=_("Password confirmation"),
        widget=forms.PasswordInput(attrs={"autocomplete": "new-password", 'class': 'form-control'}),
        strip=False,
        help_text=_("Enter the same password as before, for verification."),
    )
    class Meta:
        model = UserModel
        fields = ("username", 'first_name', 'last_name', 'email')
        field_classes = {"username": UsernameField}
        widgets = {
            'first_name': forms.TextInput(attrs={
                'class': 'form-control',
                'required' : True
            }),
            'last_name': forms.TextInput(attrs={
                'class': 'form-control',
                'required' : True
            }),
            'email': forms.EmailInput(attrs={
                "autocomplete": "email",
                'class': 'form-control',
                'required' : True
            }),
        }
        labels = {
            'first_name': 'First Name',
            'last_name': 'Last Name',
            'email': 'Email',
        }
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        if self._meta.model.USERNAME_FIELD in self.fields:
            self.fields[self._meta.model.USERNAME_FIELD].widget.attrs[
                "autofocus"
            ] = True
    def clean(self):
        data = super().clean()
        first_name = data.get('first_name')
        last_name = data.get('last_name')
        if len(first_name) == 0:
            msg = "First Name が入力されていません"
            self.add_error('first_name', msg)
        elif len(first_name) > 20:
            msg = "First Name の最大文字数は20文字です"
            self.add_error('first_name', msg)
        if len(last_name) == 0:
            msg = "Last Name が入力されていません"
            self.add_error('last_name', msg)
        elif len(last_name) > 20:
            msg = "Last Name の最大文字数は20文字です"
            self.add_error('last_name', msg)
    def clean_password2(self):
        password1 = self.cleaned_data.get("password1")
        password2 = self.cleaned_data.get("password2")
        if password1 and password2 and password1 != password2:
            raise ValidationError(
                self.error_messages["password_mismatch"],
                code="password_mismatch",
            )
        return password2
    def _post_clean(self):
        super()._post_clean()
        # Validate the password after self.instance is updated with form data
        # by super().
        password = self.cleaned_data.get("password2")
        if password:
            try:
                password_validation.validate_password(password, self.instance)
            except ValidationError as error:
                self.add_error("password2", error)
    def save(self, commit=True):
        user = super().save(commit=False)
        user.is_active = False  # まだログインできないようにする
        user.set_password(self.cleaned_data["password1"])
        if commit:
            user.save()
        return user
ユーザ登録後に表示されるフラッシュメッセージを変更しておきます.
users/views.py
class UserCreateView(CreateView):
    template_name = 'users/create_form.html'
    form_class = UserCreationForm
    def form_valid(self, form):
        messages.success(self.request, 'ユーザ登録しましたが,まだログインはできません')
        user = form.save()
        return HttpResponseRedirect("/")
新たにユーザ登録したユーザ ID ではログインできないことが確認できます.なお,ログインできない理由がパスワードが異なるからなのか,アカウントが有効化されていないからなのかが,現時点のエラーメッセージでは理解できません.このあたりはあとで修正しましょう.