I have created form using ModelForm but its not saving data into database.
views.py
def answer(request):
if request.method == 'POST':
form = AnswerForm(request.POST)
if form.is_valid():
form.save()
else:
form = AnswerForm()
return render_to_response('quiz/index.html', {'form': form, })
template
<form action="." method="post">
{{ form.as_p }}
<input type="submit" value="Submit">
</form>
model
class Answer(models.Model):
answer = models.TextField()
class AnswerForm(ModelForm):
class Meta:
model = Answer
Where i was wrong ? :/
You forgot to handle the case where the form isn't valid.
Related
here is my code. I am using Modelforms and Crispy forms library to generate form.
when I click form submit everything is saved, except Category(manytomanyfield), that I have to specify manually from admin panel.
NOTE: I FOUND SOME SOLUTIONS ONLINE to do form.save_m2m() but I get Object has no attribute save_m2m()
my modelform.
from django.forms import ModelForm
from .models import Article
class ArticleForm (ModelForm):
class Meta:
model = Article
fields = '__all__'
exclude = ('user',)
my views.
def create(request):
if request.method =="POST":
form = ArticleForm(request.POST, request.FILES)
if form.is_valid():
form = form.save(commit=False)
form.user = request.user
return redirect('home')
form = ArticleForm()
context = {'form': form}
return render(request, 'article_form.html', context)
my template.
<form action="" enctype="multipart/form-data" method="post">
{% csrf_token %}
{{form|crispy}}
<button type="submit" class="btn btn-primary">Submit</button>
</form>
You're overwriting form:
The code should be:
if form.is_valid():
#form.save() returns a model instance, not another form
article = form.save(commit=False)
article.user = request.user
article.save()
form.save_m2m()
...
I cannot add a file in Django. When I click the "save" button, it does not save the database.
This is my view.py:
def add_product(request):
if request.method == "POST":
form = PostForm(request.POST, request.FILES)
if form.is_valid():
post = form.save(commit=False)
post.userprofile = request.user
post.save()
return redirect('kerajinan.views.add_product', pk=post.pk)
else:
form = PostForm()
return render(request, 'kerajinan/add_product.html', {'form': form})
add_product.html:
{% block content %}
<h1>New Product</h1>
<from method="POST" class="post-form" enctype="multiple/form-data">{% csrf_token %}
{{ form.as_p }}
<button type="submit" class="save btn btn-default">Save</button>
</from>
{% endblock %}
forms.py:
class PostForm(forms.ModelForm):
class Meta:
model = Product
fields = ('category','title', 'price','image', 'description')
and urls.py:
url(r'^add_product/$', views.add_product, name='add_product'),
Can you help me solve my problem?
You need to change your enctype to: enctype="multipart/form-data"
Your current value (multiple/form-data), is not a valid method of encoding.
From the docs:
Note that request.FILES will only contain data if...the <form> that posted the request has the attribute enctype="multipart/form-data". Otherwise, request.FILES will be empty.
The Problem:
I'm tying to post to a view and pass on a value from the template by using a hidden value field and a submit button. The values from the submit button (ie the csrf_token) gets through but the hidden value does not. I've checked from the Wezkrug debugger that request.POST only contains form values and not my 'id' value from the hidden field.
Background:
The button takes you to a form where you can enter a comment. I'm trying to include the review.id that the user is commenting on to make commenting easy. I have the value as 'test' not for test purposes.
My form:
<div>
<form method='POST' action='/add_comment/'>
{% csrf_token %}
<input type="hidden" name='id' value='test'>
<input type="submit" value="Make a Comment">
</form>
</div>
Comment View:
#login_required
def make_comment(request):
if request.method == 'POST':
form = CommentForm(request.POST)
if form.is_valid():
comment = form.save(commit=False)
comment.user = request.user
comment.save()
# render?
return HttpResponseRedirect('/results/', {
'restaurant': get_object_or_404(
Restaurant,
name=request.POST['name'],
address=request.POST['address']
)
})
else:
form = CommentForm()
return render(request, 'stamped/comment.html', {'form': form})
Comment Model:
class Comment(models.Model):
content = models.TextField()
review = models.ForeignKey(Review)
user = models.ForeignKey(User)
date_added = models.DateTimeField(auto_now_add=True)
Comment ModelForm Code:
class CommentForm(ModelForm):
class Meta:
model = Comment
exclude = ('user', 'review',)
I've been trying to follow the tactics in this question, but using the request.session dict is undesirable because Id have to store an id for every review regardless if they're are ever commented on.
What is a more efficient way to pass variables from Template to View in Django?
Any ideas on how to include the hidden value in the POST? Thanks!
views.py
def make_comment(request):
if request.method == 'POST':
if 'prepair_comment' in request.POST:
review = get_object_or_404(Review, pk=request.POST.get('id'))
form = CommentForm({'review': review.id})
return render(request, 'stamped/comment.html', {
'form': form,
})
else: # save the comment
models.py
class CommentForm(ModelForm):
class Meta:
model = Comment
exclude = ('user',)
widgets = {'review': forms.HiddenInput()}
restaurant.html
<form method='POST' action='/add_comment/'>
{% csrf_token %}
<input type='hidden' value='{{ r.id }}' name='id'>
<input type="submit" name='prepair_comment' value="Make a Comment">
</form>
You can access the form with form.cleaned_data. You could also use a if form.is_valid() or if you want to ignore the hidden test value when there is no comment, then you could use a if/else logic to ignore the hidden value if comment is None: logic.
To access the form and only record the test value if comment is not None, the views.py might look like this:
def form_view(request):
if request.method == 'POST'
form = form(request.POST)
if form.is_valid():
comment = form.cleaned_data['comment']
# do something with other fields
if comment is not None:
id = form.cleaned_data['test']
# do something with the hidden 'id' test value from the form
return HttpResponseRedirect('/thanks/')
else:
form = form()
return render(request, 'form.html', {'form': form})
Here are the Django Docs that I would reference for this:
https://docs.djangoproject.com/en/dev/topics/forms/
In my app I allow users to have a profile picture. And I would like them to be able to change it. Surprisingly, I didn't find anything on how to accomplish that.
Here is what I tried:
models.py
class UserProfile(FacebookProfileModel):
user = models.OneToOneField(User)
profilepic = models.ImageField(upload_to="profilepics/", default="blabla.jpg")
my html:
<form method='post' action='{%url myproject.views.changes %}>
<div class="controls">
<input type="file" name="image">
</div>
<input type="submit">
</form>
my view:
def changes(request):
if 'image' in request.POST:
image = request.POST.get('image')
userprofile.profilepic.url = image
userprofile.save()
When I do that, I get the following error message:
'AttributeError at /my/site/
can't set attribute'
Any idea on how I could accomplish that? Thank you
Make sure you request a UserProfile object first, then
Looks like you should use
image = request.FILES['image']
userprofile.profilepic = image
instead of
image = request.POST.get('image')
userprofile.profilepic.url = image
See This example, the views.py section, as Jake said
You need to include enctype="multipart/form-data" in your form. Here is an example of how to update an ImageField:
first the update_form.html:
<form method="POST" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<button type="submit" class="save btn btn-default">Update</button>
</form>
Then the form:
from django.contrib.auth import get_user_model
class EditProfile(UserChangeForm):
class Meta:
model = get_user_model()
fields = ('email', 'name', 'avatar')
And finally the view:
def user_edit(request):
if request.method == 'POST':
form = EditProfile(request.POST, instance=request.user)
if form.is_valid():
form.save()
if request.FILES.get('avatar', None) != None:
try:
os.remove(request.user.avatar.url)
except Exception as e:
print('Exception in removing old profile image: ', e)
request.user.avatar = request.FILES['avatar']
request.user.save()
return redirect('user:profile', id=request.user.id)
else:
form = EditProfile(instance=request.user)
return render(request, 'user/user-edit.html', {'form': form})
For some reason, I can't get form.save() to save to my database. I'm able to create the form, and have the form pass itself off to my template, but nothing is getting saved to the database. I've mucked around with it for many hours and haven't been able to get it to work.
Any help is appreciated.
Here is the relevant code..
This is my add/model.py
from django.db import models
from django.forms import ModelForm
class addTask(models.Model):
task = models.CharField('Task', max_length=60)
taskNotes = models.CharField('Notes', max_length=600)
def __unicode__(self):
return self.task
class addTaskForm(ModelForm):
class Meta:
model = addTask
template/addTHEtask.html. This is getting referenced correctly.
<form action="/todo/" method="post">
{{ form.as_p }}
<input type="submit" value="Add Task" />
</form>
add/views.py
from django.shortcuts import render_to_response
from django.template import RequestContext
from myToDo.add.models import addTask, addTaskForm
def create_task(request):
if request.method == 'POST':
form = addTaskForm(request.POST)
if form.is_valid():
form.save()
else:
form = addTaskForm()
return render_to_response('addTHEtask.html', {'form': form})
To properly debug your code, change your template to:
<form action="/todo/" method="post"> {{ csrf_token }}
{{ form.errors }}
{{ form.as_p }}
<input type="submit" value="Add Task" />
</form>
And your view to:
def create_task(request):
if request.method == 'POST':
form = addTaskForm(request.POST)
if form.is_valid():
form.save()
else:
form = addTaskForm()
return render_to_response(
'addTHEtask.html',
{'form': form},
context_instance=RequestContext(request))
I don't think the context_instance will do anything significant for you, but it is usually the right thing to pass when using render_to_response.
Showing the errors in the form may help you track down what the actual problem is. Your code looks (mostly) correct, except the missing csrf_token. Adding the token, and displaying any errors, should show you what is going wrong.