如何将数据插入Django用户模型?

时间:2015-10-10 16:08:21

标签: python django django-models django-views

我有一个UserProfile模型,它与Django用户模型有一对一的关系。

我想通过视图AddStory将数据插入到UserProfile模型中,但我得到IntegrityError at /AddStory/ NOT NULL constraint failed: portal_userprofile.user_id

更具体地说,我想通过主页上给出的表单将一些文本添加到UserProfile模型的ShoppingHistory属性中。我有另一个页面,其中列出了ShoppingHistory.html上此属性的值(如果用户提供)。

所有用户都是唯一的,一旦该用户登录,我如何确保为特定用户添加此属性?如何在用户登录后引用该用户?

models.py

from django.db import models
from django.contrib.auth.models import AbstractUser
class UserProfile(AbstractUser):      
    profile_pic = models.ImageField(upload_to='profile_images', blank=True)
    StaffMember = models.BooleanField(default=False)
    ShoppingHistory = models.TextField()
    ShoppingWishList = models.TextField()

    def __unicode__(self):
        return self.user.username

views.py:

from django.shortcuts import render
from django import forms
from portal import models
from portal.forms import UserProfileForm
from django.contrib.auth import authenticate, login
from django.http import HttpResponseRedirect, HttpResponse
from django.contrib.auth.decorators import login_required
# Create your views here.
def register(request):

regStatus = False

if request.method == 'POST':
    #grab info from raw information
    profile_form=UserProfileForm(data=request.POST)

    if profile_form.is_valid():
        user=profile_form.save(commit=False)

        #hash the password for security using the djangohash default method
        user.set_password(user.password)


        if 'profile_pic' in request.FILES:
            profile_pic = request.FILES['profile_pic']
        user.save()

        regStatus = True

    else:
        print profile_form.errors

else:
    profile_form = UserProfileForm()

return render(request, 'register.html', {'profile_form': profile_form, 'registered': regStatus})

def user_login(request):

if request.method == 'POST':
    username = request.POST.get('username')
    password = request.POST.get('password')

    user = authenticate(username=username, password=password)

    if user:
        login(request, user)
        return HttpResponseRedirect('/home/')
    else:
        return HttpResponse('Invalid login credentials')

else:
    return render(request, 'login.html', {})

@login_required
def homepage(request):


return render(request, 'home.html', {})


def AddStory(request):
if request.method == 'POST':
    story = request.POST.get('ShoppingHistory')
    username = request.POST.get('username')
    p=models.UserProfile(ShoppingHistory=story, username=username)
    p.save()

    return render(request, 'ShoppingHistory.html', {'story': p})
return render(request, 'ShoppingHistory.html', {})

Home.html中:

    {% if user.is_authenticated %}
    <p> WELCOME, thanks for logging in {{user.username}} </p>
    <form id="user_form" method="post" action="/AddStory/" enctype="multipart/form-data">      
        {% csrf_token %}
    <input type="text" name="ShoppingHistory" value="" />
    <input  name="username" value="{{user.username}}" DISABLED />
    <input type="submit" name="submit" value="Add Story" />

    {% endif %}

ShoppingHistory.html:

  {% if user.is_authenticated %}
        {% csrf_token %}

    <p> WELCOME, thanks for logging in {{user.username}} </p>
    <p> Your Shopping Stories: </p>
    <p>{{user.ShoppingHistory}}</p>

    {% endif %}

forms.py

from django import forms
from portal.models import UserProfile
class UserProfileForm(forms.ModelForm):

    password = forms.CharField(widget=forms.PasswordInput())

class Meta:
    model = UserProfile
    fields = ('username', 'first_name', 'last_name', 'email', 'password', 'profile_pic')

1 个答案:

答案 0 :(得分:1)

使用AbstractUser创建自定义用户要好得多:

from django.contrib.auth.models import AbstractUser


class UserProfile(AbstractUser):
    pass

您的问题是,当您创建UserProfle实例时,您必须将User设置为它,但实际上您想要创建它,因此您需要先创建用户,然后您必须在DB中使用用户表。为了什么?

有关自定义用户的更多信息:docs

<强>更新

错误在此行p=models.UserProfile(ShoppingHistory='story',)中。您的UserProfile模型要求用户创建UserProfile,而您不需要设置用户实例。但我想说你有一个错误的方法来创建自定义用户。这个想法是你的数据库中有两个用户表。一个用户,另一个用于UserProfile。它们通过OneToOne关系连接,但它不是继承。每当您想要创建UserProfile实例时,您都需要为其创建一个User实例。这就是为什么我肯定会建议您使用AbstractUser创建自定义用户模型的原因。然后,您不需要考虑在创建用户时指定用户。

更新2

如果您想为他创建故事,则无需创建新用户。你可以:

def AddStory(request):
    if request.method == 'POST':
        story = request.POST.get('ShoppingHistory')
        request.user.ShoppingStory = story
        request.user.save()

        return render(request, 'ShoppingHistory.html', {'story': story})
    return render(request, 'ShoppingHistory.html', {})