Taking a Form and saving it into a model - django

I got this form working Ok but i can't figure out how to save it to the database via the model i know this is a semantic question that i can't figure out Please Help. I'm using django The error is
D = Donation(user=request.user,name=form.cleaned_data['name'],description=cd['descri‌​ption']) D.save()
views.py
def donate(request):
if request.method == 'POST':
form = DonationForm(request.POST)
if form.is_valid():
cd = form.cleaned_data
D = Donation(user=request.user,name=form.cleaned_data['name'],description=cd['description'])
D.save()
return HttpResponseRedirect('/test/')
else:
form =DonationForm()
return render_to_response('addaDonation.html',{'form': form},context_instance=RequestContext(request))
`
Donation is my Model and i need to get the information from my form into the Donation Model so i can D.save
class DonationForm(forms.Form):
name = forms.CharField(max_length=50)
description = forms.CharField(max_length=3000)
towards = forms.CharField()
#image = forms.ImageField()
class Donation (models.Model):
user = models.ForeignKey(User)
name = models.CharField(max_length=50)
description = models.CharField(max_length=3000)
towards = models.ForeignKey(NonProfit)
image = models.ImageField(upload_to='photos/%Y/%m/%d')
The error I get is
(1054, "Unknown column 'name' in 'field list'")
Request information
GET
No GET data
POST
Variable Value
csrfmiddlewaretoken u'nXGN4gdZwk2qxNpP9YIXzvNQI7lKQe5r'
towards u'this'
name u'this'
description u'that'

change your form class to the following;
from django.forms import ModelForm
class DonationForm(ModelForm):
class Meta:
class = Donation
exclude = ("user", )
def save(self, user):
donation = super(DonationForm, self).save(commit=False)
donation.user = user
donation.save()
return donation
Then you should be able to change the view.py to the following;
def donate(request):
if request.method == 'POST':
form = DonationForm(request.POST, request.FILES)
if form.is_valid():
form.save(request.user)
return HttpResponseRedirect('/test/')
else:
form = DonationForm()
return render_to_response('addaDonation.html',{'form': form},context_instance=RequestContext(request))
See official documentation Creating forms from Models

Related

how to look over all form fields provided and updating the model

I've created a Django view that does 2 things:
Create a new account
Modify a account
Works:
Creating new account and submitting the HTML form data to the database. Also works: showing a prefilled HTML form if user wants to modify an account with the account data that is known in the database.
Doesnt work:
When the user submits his/her form to update an account (user modified the info in the form), nothing is updated in the database.
I know how to update one single static value in the database like so:
a = accounts.objects.filter(pk=account_id).update(name='static value here')
but I don't know how to update the database with all the form data that the user submits when using Django Modelforms. Does anyone knows how to update the database with the submitted form data?
Code
#login_required(login_url='/dashboard/')
def dashboard_accounts_new_modify(request, account_id=None):
if request.method == 'POST':
# POST DETECTED
form = MyModelForm(request.POST, request.FILES)
if account_id:
# POST DETECTED
# ACCOUNT ID FOUND
# USER WANTS TO MODIFY A ACCOUNT
# WITH THIS QUERY I CAN UPDATE 1 STATIC VALUE IN THE DATABASE
# HOW DO I UPDATE THE VALUES FROM THE FORM IN THE DATABASE?? :(
a = accounts.objects.filter(pk=account_id).update(name='static value here')
return HttpResponseRedirect('/dashboard/accounts/')
else:
# POST DETECTED
# ACCOUNT ID NOT FOUND
# USER WANTS TO CREATE A NEW ACCOUNT
if form.is_valid():
if request.POST.get("name").lower() == 'new':
raise Http404("New account name may not be named NEW.")
# DATAHASE QUERY: ADD NEW ACCOUNT TO DATABASE
form.save()
# REDIRECT
return HttpResponseRedirect('/dashboard/accounts/')
elif account_id:
# NO POST DETECTED
# ACCOUNT ID FOUND
# PREFILL FORM WITH DATA
try:
from django.forms.models import model_to_dict
a = accounts.objects.get(pk=account_id)
form = MyModelForm(initial=model_to_dict(a))
except:
raise Http404("Account not found.")
else:
# NO POST DETECTED
# MODIFICATION IS NOT DETECTED
# LOAD EMPTY FORM
form = MyModelForm()
return render(request, 'backend/base_accounts_new.html', {'Title': 'Accounts', 'form' : form})
Model
# Clientdatabase
class accounts(models.Model):
name = models.CharField(max_length=200)
url = models.CharField(max_length=200)
website_title = models.CharField(max_length=200)
website_h1_text = models.CharField(max_length=200)
website_h2_text = models.CharField(max_length=200)
website_search_text = models.CharField(max_length=200)
website_font = models.CharField(max_length=200)
website_footer_left = models.CharField(max_length=600)
website_footer_right = models.CharField(max_length=600)
website_color_code_search_button = models.CharField(max_length=200)
website_color_code_banner = models.CharField(max_length=200)
website_logo_height_pixels = models.PositiveIntegerField()
website_logo_width_pixels = models.PositiveIntegerField()
filepath_favicon = models.FileField()
filepath_logo_vector = models.FileField()
filepath_logo_normal = models.FileField()
filepath_background_1 = models.FileField()
filepath_background_2 = models.FileField(blank=True, null=True)
filepath_background_3 = models.FileField(blank=True, null=True)
filepath_background_4 = models.FileField(blank=True, null=True)
setting_background_1_active = models.BooleanField()
setting_background_2_active = models.BooleanField()
setting_background_3_active = models.BooleanField()
setting_background_4_active = models.BooleanField()
def __str__(self):
return self.name
class AccountsForm(ModelForm):
class Meta:
model = accounts
fields = '__all__'
You can do like:
from django.shortcuts import get_object_or_404
if request.method == 'POST':
if account_id::
account = get_object_or_404(accounts, pk=account_id)
form = MyModelForm(request.POST,request.FILES, instance=account)
if form.is_valid():
...
form.save()
return HttpResponseRedirect('/dashboard/accounts/')
else:
form = MyModelForm(request.POST, request.FILES)
if form.is_valid():
if request.POST.get("name").lower() == 'new':
raise Http404("New account name may not be named NEW.")
form.save()
Learn more about forms here

django forms - how to filter number of available options in a form

I'm trying to limit number of "categories" that user have available when entering new "feed" only to categories that he owns and he created. The way it works now is that user can add "feed" to other users' "categories" as this is what the form displays. How can I fix it ?
thanks!
-M
models.py
from django.db import models
from django.contrib.auth.models import User
class Category(models.Model):
name = models.CharField(max_length=50)
user = models.ForeignKey(User)
class Feed(models.Model):
url = models.URLField()
name = models.CharField(max_length=50)
created = models.DateTimeField(auto_now_add=True)
description = models.TextField(blank=True)
category = models.ForeignKey(Category)
user = models.ForeignKey(User)
forms.py
class FeedForm(forms.ModelForm):
class Meta:
model = Feed
exclude = ['user']
views.py
def addfeed(request, user):
user = request.user
page_title = "Add feed"
instance = Category.objects.filter(user=request.user)
if request.method == 'POST':
form = FeedForm(request.POST, instance=instance)
if form.is_valid():
feed = form.save(commit=False)
feed.user = request.user
feed.save()
return HttpResponseRedirect("/user/" + user.username + "/manage")
else:
form = FeedForm()
return render(request, "form_manage.html", {
'page_title': page_title,
'form': form,
})
Set the queryset attribute of the field somewhere. Because it depends on your user, it's something you have to set during or after instantiating the form. For instance, here's how to do it in the view:
def addfeed(request, user):
user = request.user # why does this view take user as an arg and then reassign?
page_title = "Add feed"
categories = Category.objects.filter(user=request.user)
if request.method == 'POST':
form = FeedForm(request.POST)
form.fields['category'].queryset = categories
if form.is_valid():
feed = form.save(commit=False)
feed.user = request.user
feed.save()
return HttpResponseRedirect("/user/" + user.username + "/manage")
else:
form = FeedForm()
form.fields['category'].queryset = categories
return render(request, "form_manage.html", {
'page_title': page_title,
'form': form,})
I removed the instance argument to your POST case's form construction because that's meant for passing in an existing Feed instance, not a categories queryset.
You could also do this in the form's __init__ if you pass in the correct categories queryset.
I use javascript to do this. For example, you could pass a list of the relevant categories as extra context in your view then use javascript in your template to empty the pre-populated option field in the form and replace it with your extra context.

Django Error form submission

I have an app that let you create a profile.
One of my app feature is it's let you edit your name and upload a image.
The problem is the user cannot submit the image unless he type his name.How can I fix this page to make it so If the user submit an image but doesn't submit a name . He will still have his old name
or if he doesn't submit an image and changes his name . He will still have his old picture?
I tried adding blank=True and null = False , null = True but doesn't seem to do the job
My models.py
class Person(models.Model):
user = models.ForeignKey(User)
name = models.CharField(max_length=100,null=True,blank=False)
image = models.FileField(upload_to="images/")
def __unicode__(self):
return self.name
My forms.py
class PersonForm(forms.ModelForm):
class Meta:
model = Person
fields = ('image','name',)
My views.py
def Display(request):
if not request.user.is_authenticated():
return HttpResponseRedirect(reverse('world:LoginRequest'))
if request.method == 'POST':
form = PersonForm(request.POST, request.FILES)
if form.is_valid():
person = Person.objects.get(user=request.user)
person.image = form.cleaned_data['image']
person.name = form.cleaned_data['name']
person.save()
return render(request,'edit.html',{'form': PersonForm()})
class Person(models.Model):
user = models.ForeignKey(User)
name = models.CharField(max_length=100, blank=True)
image = models.FileField(upload_to="images/", blank=True)
def __unicode__(self):
return self.name
def Display(request):
if not request.user.is_authenticated():
return HttpResponseRedirect(reverse('world:LoginRequest'))
if request.method == 'POST':
form = PersonForm(request.POST, request.FILES)
if form.is_valid():
image = form.cleaned_data['image']
name = form.cleaned_data['name']
person = Person.objects.get(user=request.user)
if image:
person.image = form.cleaned_data['image']
if name:
person.name = form.cleaned_data['name']
person.save()
return render(request,'edit.html',{'form': PersonForm()})
django forms does validation on the users data
validation is done on two levels:
the field level:
if the field is required and the user didn't enter any data it will raise an error
if the user entered improperly formatted data for that field it will raise an error
you can override the behavior of field validation by implementing functions named as clean_fieldname
this type of validation results in form.field.errors
the form level:
checks for any (non-field specific) validation errors
you can override the behavior by implementing clean method
this type of validation results in form.non_field_errors
from your models:
image is not allowed to be blank which means it is required. not entering an image will raise an error
let blank=True for both name and image
also I recommend using form.save() over saving models from the views
also there is a built in ImageField for saving images

modifying django model forms after post

I would like to modify a user submitted form to automatically insert the project_id, but I keep getting the error that project_id in the Employee model cannot be null;
My model:
class Project(models.Model):
name = models.CharField(max_length=100)
date_started = models.DateTimeField()
class Employee(models.Model):
name = models.CharField(max_length=200)
project = models.ForeignKey(Project)
class AddEmployeeForm(ModelForm):
class Meta:
model = Employee
exclude = ('project',)
My view:
def emp_add(request, project_id):
if request.method == 'POST':
post = request.POST.copy() # make the POST QueryDict mutable
post('project', project_id)
form = AddEmployeeForm(post)
if form.is_valid():
saved = form.save()
Like this?
if form.is_valid():
employee = form.save(commit=False)
employee.project = Project.objects.get(pk=project_id)
employee.save()
#maciag.artur's answer, to save with commit=False will work. Another way is to instantiate an Employee with the required project_id, and use it to construct the form.
This is useful if your model form's custom clean method relies on the Employee.project field.
def emp_add(request, project_id)
if request.method == 'POST':
# create a new employee with the given project id
employee = Employee(project_id) = project_id
form = AddEmployeeForm(request.POST, instance=employee)
if form.is_valid():
saved = form.save()
<snip>
For reference, see the note box below Using a subset of fields on the form in the Django docs.
Add the project ID to the form as a hidden input. When the request comes back as a POST, it will exist in the POST object, from the form.
def emp_add(request, project_id):
if request.method == 'POST':
post = request.POST.copy() # make the POST QueryDict mutable
post('project', project_id)
form = AddEmployeeForm(post)
if form.is_valid():
saved = form.save()
else:
form = AddEmployeeForm(initial={'project_id':'my_id_value'})

Django ModelForms: Trying to save a form with a foreign key

Django will just go to the else condition.
here's the code:
models.py
class StakeholderProfile(models.Model):
types = models.ForeignKey(Stakeholder)
name = models.CharField(blank=False, max_length=50)
forms.py
class SPForm(forms.ModelForm):
class Meta:
model = StakeholderProfile
exclude = ('key_contact_person',)
views.py
def profile(request):
stakeholderprofile = StakeholderProfile.objects.all()
if request.method == 'POST':
form = SPForm(request.POST)
if form.is_valid():
form.save()
return HttpResponseRedirect('/profile/')
else:
form = SPForm()
return render_to_response('profile.html',{'form':form,'sp':stakeholderprofile})
I really need your help sir/maam.
You are excluding a field that doesn't exist in StakeHolderProfile.
Also be sure you added method='POST' in your form tag.