I am currently working on a Django project. This is my first introduction to Python / Django, so I'm currently learning the ropes. Hope you all can help!

I'm currently trying to update some custom fields I have setup in my UserProfile model via the Models, View, and Template. Right now it seems that no matter what I do to the View, the returning form is always coming back as not valid. I've been staring at this for quite some time, so that probably doesn't help. Here is the code:

models.py:

 class UserProfile(models.Model):
    #inherit the base User model
    user = models.OneToOneField(User)

    #custom fields to be in the User model
    phoneNumber = models.IntegerField(null=True)
    about = models.TextField(null=True)
    gitHubLink = models.URLField(null=True)
    linkedInLink = models.URLField(null=True)
    gravitarLink = models.URLField(null=True)
    facebookLink = models.URLField(null=True)
    rating = models.PositiveSmallIntegerField(default=0)

    def __unicode__(self):
        return u'Profile of user: %s' % self.user.username

User.profile = property(lambda u: UserProfile.objects.get_or_create(user=u)[0])


def create_user_profile(sender, instance, created, **kwargs):
    if created:
        UserProfile.objects.create(user=instance)

post_save.connect(create_user_profile, sender=User)

views.py:

@login_required
def edit_profile(request):
    profile = request.user.get_profile()

    if request.method == 'POST':
        form = UserProfileForm(request.POST, instance=profile)
        if form.is_valid():
            userprofile = form.save(commit=False)
            userprofile.user = request.user
            userprofile.save()
            messages.success(request, "Account Updated!")
            return render_to_response('profile/edit.html', {"form": form}, context_instance=RequestContext(request))
        else:
            form = UserProfileForm()
            messages.error(request, "There are form errors.")
            return render_to_response('profile/edit.html', {"form": form}, context_instance=RequestContext(request))
    else:
        form = UserProfileForm(instance=profile)
        return render_to_response('profile/edit.html', {"form": form}, context_instance=RequestContext(request))

forms.py:

class UserProfileForm(forms.ModelForm):

    class Meta:
        model = UserProfile
        fields = ('phoneNumber', 'about', 'gitHubLink', 'linkedInLink', 'gravitarLink', 'facebookLink')

    def save(self, commit=True):
        userprofile = super(UserProfileForm, self).save(commit=False)
        userprofile.phoneNumber = self.cleaned_data['phoneNumber']

        if commit:
            userprofile.save()
        return userprofile

edit.html(template):

<form action="/profile/edit/" method="post" class="form-signin">
    {% csrf_token %}
    <div class="form-group">{{ form.phoneNumber|add_class:"form-control"|attr:"placeholder:Phone Number" }} </div>
    <div class="form-group">{{ form.gitHubLink|add_class:"form-control"|attr:"placeholder:GitHub Account URL" }} </div>
    <div class="form-group">{{ form.facebookLink|add_class:"form-control"|attr:"placeholder:Facebook Account URL" }} </div>
    <div class="form-group">{{ form.linkedInLink|add_class:"form-control"|attr:"placeholder:LinkedIn Account URL" }} </div>
    <div class="form-group">{{ form.about|add_class:"form-control"|attr:"placeholder:About Yourself. Interests, Hobbies, etc.." }} </div>
    <button class="btn btn-lg btn-success btn-block" type="submit">Save Changes</button>
</form>

Appreciate you taking the time to read this. Any help / pointers are much appreciated!

有帮助吗?

解决方案

Your template doesn't include your gravitarLink field. Because the model field is not declared with blank=True, this field is required, so your form can never be valid.

Note that it's generally considered a better practice not to use null=True with character fields, of which URLField is a subset. Instead, if you want them to be optional set blank=True and leave null at its default value of False so that the empty string is the empty value. blank=True is required for them to be optional; null just controls what database representations are valid.

Also, it is a better practice to pass the bound form object back to the template when there are errors rather than creating a new empty one. That not only includes the values you previously submitted, so that the user doesn't have to reenter the valid ones, but it can show the errors per field. The Django docs on "using a form in a view" demonstrate the usual pattern.

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top