Django: использовать ImageField в модельных формах - PullRequest
1 голос
/ 01 августа 2020

Итак, у меня есть следующие формы модели:

User = get_user_model()
class UserRegisterForm(forms.ModelForm):
    username = forms.CharField(label='', widget=forms.TextInput(attrs={'placeholder': 'Username'}))
    email = forms.EmailField(label='', widget=forms.TextInput(attrs={'placeholder': 'Email Address'}))
    email2 = forms.EmailField(label='', widget=forms.TextInput(attrs={'placeholder': 'Confirm Email'}))
    password = forms.CharField(label='', widget=forms.PasswordInput(attrs={'placeholder': 'Password'}))
    avatar = forms.ImageField(upload_to='profile_images')

class Meta:
    model = User 
    fields = [
        'username',
        'email',
        'email2',
        'password'
    ]

Но это появляется

TypeError: __init__() got an unexpected keyword argument 'upload_to'

Проблема в том, что я думаю, что это сработает, если я добавлю в модель объект ImageField, но у меня нет модели. Как видите, я использую get_user_model (), есть ли способ использовать upload_to в формах модели или как я могу добавить объект ImageField к 'get_user_model' по умолчанию?

1 Ответ

0 голосов
/ 02 августа 2020

Вы должны сделать дополнительную модель, чтобы сохранить аватар, или вы можете создать пользовательскую модель .

Если вы сделаете дополнительную модель, например Profile, вы можно определить это как:

# app/models.py

from django.conf import settings
from django.db import models

class Profile(models.Model):
    user = models.OneToOneField(
        settings.AUTH_USER_MODEL,
        on_delete=models.CASCADE,
        editable=False
    )
    avatar = models.ImageField(upload_to='profile_images/')

Тогда вы можете, например, сделать два ModelForm. Фактически, для User вам лучше использовать UserCreationForm [Django -doc] , поскольку он уже реализует logi c для проверки совпадения паролей, и он также будет прозрачно иметь sh пароль.

Таким образом, вы можете определить ModelForm для Profile и работать с:

# app/forms.py

from django import forms
from app.models import Profile

class ProfileForm(forms.ModelForm):
    class Meta:
        model = Profile
        fields = ['avatar']

В представлении вы затем работайте с двумя формами:

# app/views.py

from app.forms import ProfileForm
from django.contrib.auth.forms import UserCreationForm

def some_view(request):
    if request.method == 'POST':
        form = UserCreationForm(request.POST, request.FILES)
        form2 = ProfileForm(request.POST, request.FILES)
        if form.is_valid() and form2.is_valid():
            user = form.save()
            form2<b>.instance.user = user</b>
            form2.save()
            return redirect(<i>'name-of-some-other-view'</i>)
    else:
        form = UserCreationForm()
        form2 = ProfileForm()
    return render(request, <i>'name-of-some-template.html'</i>, {'form': form, 'form2': form2})

и, таким образом, вы визуализируете обе формы в одном теге <form>:

<form action="{% url 'some_view' %}" method="post" enctype="multipart/form-data">
    {% csrf_token %}
    {{ <b>form</b> }}
    {{ <b>form2</b> }}
</form>
...