Набор форм, внешний ключ и OneToOne

Я хочу создать регистрационную форму без использования какого-либо внешнего приложения, но мне не удается сохранить отношения foregin и OneToOne с набором форм. Вот мои модели.py:

class UserProfile(models.Model):
user = models.OneToOneField(User)
avatar = models.ImageField(null=True, blank=True, upload_to='avatar/')
website = models.URLField(null=True, blank=True)
birthday = models.DateField()
country = CountryField()

GENDER_CHOICES = (
    ('M', 'Male'),
    ('F', 'Female'),
)
gender = models.CharField(max_length=1, choices=GENDER_CHOICES)

def __str__(self):
    return "UserProfile(models)"


class UserLanguage(models.Model):
    user = models.ForeignKey(User)
    language = models.CharField(max_length=7, choices=LANGUAGES)
    level = models.CharField(max_length=1)
    # http://stackoverflow.com/questions/3201018/django-language-codes

    def __str__(self):
        return "UserLanguage(models)"

Вот мои формы.py:

class RegisterForm(forms.ModelForm):
class Meta:
    model = User
    fields = ('username', 'password',)
    exclude = ('last_login',)
    widgets = {'password': forms.PasswordInput(), }


UserProfileFormSet = inlineformset_factory(User, UserProfile, can_delete=False)
UserLanguageFormSet = inlineformset_factory(User, UserLanguage, can_delete=False, extra=1)

И мои views.py:

def registration(request):
if request.method == "POST":
    user = RegisterForm(request.POST)
    user_profile = UserProfileFormSet(request.POST)
    user_language = UserLanguageFormSet(request.POST)

    if user.is_valid() and user_profile.is_valid() and user_language.is_valid():
        u = user.save()

        user_profile.user = u
        user_profile.save()

        user_language.user = u
        user_language.save()

else:
    user = RegisterForm()
    user_profile = UserProfileFormSet()
    user_language = UserLanguageFormSet()

return render(request, 'user/registration.html', locals())

И я получаю эту ошибку:

Столбец user_id не может быть нулевым

Что я могу сделать для решения моей проблемы? У вас есть другие замечания? Спасибо.


person Oyabi    schedule 10.07.2014    source источник


Ответы (1)


Вы неправильно назвали свои наборы форм user_profile и user_language. Но они не являются объектами профиля или языка, это наборы форм, поэтому установка их пользовательского атрибута не будет иметь никакого эффекта.

Это работает:

for profile_form in user_profile.forms:
    up = profile_form.save(commit=False)
    up.user = u
    up.save()

for language_form in user_language.forms:
    ul = language_form.save(commit=False)
    ul.user = u
    ul.save()

но на самом деле вы должны называть вещи такими, какие они есть.

person Daniel Roseman    schedule 10.07.2014
comment
Аааа, хорошо, спасибо, это довольно просто, и вы правы насчет имени переменной, я его изменю. ;) Однако у меня другая ошибка: 'list' object has no attribute 'user' в строке up.user = u. У вас есть идея? - person Oyabi; 11.07.2014
comment
Посмотрите мое редактирование - хотя я знал, что это наборы форм, а не формы, я дал вам синтаксис для сохранения форм. Наборы форм более сложны, когда вы добавляете атрибуты, так как вам нужно делать это для каждой формы. - person Daniel Roseman; 11.07.2014
comment
Большое спасибо, это работает очень хорошо. ;) Хорошего дня. - person Oyabi; 11.07.2014