Hi, I'm trying to develop a simple django app, and I'm having trouble accessing a form's data. I've looked at django's documentation extensively and many questions on here on the same topic but nothing is working. Here's my code inside my view, that is otherwise working:
def post(self, request):
"""Return only the games from the upcoming gameweek"""
form = GWForm(request.POST)
if form.is_valid():
curr_gw = form.cleaned_data['gweek']
args = {'form': form, 'this_gw_fixtures': Game.objects.filter(gweek=curr_gw), 'curr_gw': curr_gw}
return render(request, self.template_name, args)
else:
curr_gw = 17
form = GWForm()
args = {'form': form, 'this_gw_fixtures': Game.objects.filter(gweek=curr_gw), 'curr_gw': curr_gw}
return render(request, self.template_name, args)
And here's the code of my template:
<form action="/predict/" method="post">{% csrf_token %}
<label for="Gameweek">Gameweek: </label>
<input id="gwparam" type="number" value="{{ curr_gw }}" min="17" max="40">
<input type="submit" value="Go">
</form>
{% if this_gw_fixtures %}
<ul>
{% for game in this_gw_fixtures %}
<li>{{ game }}</li>
{% endfor %}
</ul>
{% else %}
<p>No game predictions are available for this gameweek.</p>
{% endif %}
What I'm trying to do is get the input of a choice form and render a list of games that are in the gameweek selected in the form. Minumum 17, max 40. Here's my form code.
class GWForm(forms.Form):
gweek = forms.ChoiceField(required = False, choices=[(x, x) for x in range(17, 40)])
But when I try to grab the gweek from the form, is_valid() returns true, but form.cleaned_data['gweek'] doesn't return any value at all. Any help would be appreciated. Thanks in advance.
forms.py
class GWForm(forms.Form):
gweek = forms.IntegerField(required=False, min_value=17, max_value=40)
template
<form action="/predict/" method="post">{% csrf_token %}
{{ form }}
<input type="submit" value="Go">
</form>
Related
I'm learning django and i'm blocked on a template syntax error.
I have this function in my views.py :
def AccountUpdateView(request):
template_name='portal/accountupdate.html'
context = {"forms":UserForm}
return render(request,template_name,context)
There is my template :
<form action="/account/update/" method="POST">
<ul>
{% csrf_token %}
{% for form in forms %}
<li>{{form.label}}
<input type="text" name="{{form.name}}" maxlength="32" required="" id="id_{{form.name}}" value="{{PLEASE HELP ME !!!}}">
</li>
{%endfor%}
</ul>
<input type="submit" value="Metre a jour" />
</form>
Well, i'm trying to get in the "value" of each form on my template by the current registered user known in django by the call {{user}}
And i would to auto place the values of each forms.
I think a solution is to use the form.name (for the example of the case 'username') and in the value call a thing like this :
user.form.username
It doesn't work and i know that i was dream to hope this exotic call don't work...
If any have a solution :)
Thank's you !
You shouldn't do this at all. Django will automatically output the whole field if you ask it.
For a start, use proper names for your objects. Secondly, if you want to prepopulate the form with data from the current user, then do so in the view. Note, you also need to deal with the posted data:
def AccountUpdateView(request):
template_name='portal/accountupdate.html'
if request.method == 'POST':
form = UserForm(request.POST, instance=request.user)
if form.is_valid():
form.save()
return redirect('/')
else:
form = UserForm(instance=request.user)
context = {"form":form}
return render(request,template_name,context)
Now, use the proper values and attributes in the template:
{% for field in form %}
<li>{{ field.label_tag }}
{{ field }}
{{ field.errors }}</li>
{% endfor %}
I am getting this error: ValidationError at /screen-many/
[u'ManagementForm data is missing or has been tampered with'] and I think it is due to the folling code in my view...
# e_pk_list is a list of id's that I got from POST
e_students = Student.objects.filter(pk__in=e_pk_list)
my_iterator = iter(e_students) # Each list item will correspond to a form.
SurveyFormset = formset_factory(SurveyForm, extra=len(e_students))
# Is this the tampering that I can't do??
SurveyFormset.form = staticmethod(curry(SurveyForm, item_iterator=my_iterator))
if request.method == 'POST':
survey_formset = SurveyFormset(request.POST)
if survey_formset.is_valid():
for form in survey_formset:
saved = form.save(commit=False)
saved.surveyset = ss
saved.save()
return HttpResponseRedirect('/')
else:
survey_formset = SurveyFormset()
Thanks
EDIT: I guess I should have mentioned that I already have a managementform in my template....
<form action="" method="POST">{% csrf_token %}
{{ survey_formset.management_form }}
{% for form in survey_formset %}
<div class="item">
{% crispy form %}
</div>
{% endfor %}
<input type="submit" value="Submit" class='button' />
</form>
Its seems that you didn't put management_form in your form .
Put this in your html form where your are displaying SurveyFormset
{{ SurveyFormset.management_form }}
A formset has many forms. Django keeps track of number of forms in formset using management form data. You should add management_form in the template too, which should be posted along with other POST data.
So, you should have:
<form method="POST" action=".">
{{survey_formset.management_form}}
{% comment %}Other form fields{% endcomment %}
</form>
I use Django Endless Paginator plugin.
I try to change the value of ENDLESS_PAGINATION_PER_PAGE from template side.
As default is 10.
I want to realize some dropbox where the user can change between (Example: 10,20,50,100 Objects).
Thanks for answer, but something not work property.
1. I have view.py
def adv_search(request):
objects = None
if request.GET.get('key'):
form = AdvancedSearchForm(request.GET)
if form.is_valid():
repo = Repository()
objects = list(repo.find_objects('*'+form.cleaned_data['key'] +'*', type=FileObject, chunksize=20))
return render(request, 'templates/adv_search.html', {'form': form, 'objects': objects })
return render(request, 'templates/adv_search.html', {'form': AdvancedSearchForm(), 'objects': objects})
2. Then forms.py
class AdvancedSearchForm(forms.Form):
key = forms.CharField(max_length=500, label="", widget= forms.TextInput(attrs={'class': 'label'}))
show_props = forms.MultipleChoiceField(choices = (("pid", "pid"),("title", "title"),("type","type"),("source","source"),("date","date"),("publisher","publisher"),("subject","subject"),("label","label"),("cDate","cDate"),("mDate","mDate")),required=False, widget=forms.CheckboxSelectMultiple(attrs={'class': 'my-class'}))
paginator = forms.ChoiceField(choices =(('10', '10'),('20','20'), ('50','50'), ('100','100')) ,required=False, )
3. adv_search.html
{% paginate paginator objects %}
{% for obj in objects %}
...
<div class="paginator">
{% get_pages %}
{{ pages.first_as_arrow }}
{% show_pages %}
{{ pages.last_as_arrow }}
<form method="get">
{{ form.paginator }}
<input type="submit" Value="Go">
</form>
{{ pages.total_count }} total objects
</div>
Everything works except select
Thanks Andrey
You can have a form which will set pagination per page and then use that submitted value in template. Here is an example:
View
from django.shortcuts import render
from .models import Entry
def endless_view(request):
pagination_per_page = request.GET.get('per_page', 10)
entries = Entry.objects.all()
return render(request, 'some_template.html', {'pagination_per_page':
pagination_per_page, 'entries': entries})
Template
{% extends 'base.html' %}
{% load endless %}
{% block content %}
{# #}
<form action="" method="get">
<select name="per_page">
<option value="10">10 per page</option>
<option value="20">20 per page</option>
<option value="50">50 per page</option>
<option value="100">100 per page</option>
</select>
<input type="submit" Value="Go">
</form>
{% paginate pagination_per_page entries %}
{% for entry in entries %}
{# your code to show the entry #}
{% endfor %}
{% show_pages %}
{% endblock content %}
Reference
http://django-endless-pagination.readthedocs.org/en/latest/templatetags_reference.html
I'm trying to do a feature that would allow the user to upload a file. That file would have information to insert into the database, that's why in the function I'm saving data. Not sure if it's the best option.
What I've done so far:
forms.py:
class UploadFileForm(forms.Form):
file = forms.FileField()
views:
def last_step(request, word):
if request.method == 'POST':
form = UploadFileForm(request.POST, request.FILES)
if form.is_valid():
msg = handle_uploaded_file(word, request.FILES['file'])
return render_to_response('final_insert.html', {'msg': msg})
else:
form = UploadFileForm()
return render_to_response('upload.html',
{
'word': word,
'form': form })
template:
<form enctype="multipart/form-data" action="{% url upload_done 'clinical' %}" method="post">
<div>
{% for field in form %}
{{ field }}
{% endfor %}
<input type="submit" value="Save" />
</div>
</form>
function:
def handle_uploaded_file(word, f):
msg = "first stop"
data = []
for chunk in f.chunks():
data.append(chunk)
msg = "after chunk"
if word == 'clinical':
pat = Patient.objects.values_list('patient', flat=True)
for i in data:
if i[0] not in pat:
b2 = Patient(patient=i[0])
b2.save()
msg = "number was inserted"
else:
msg = "something"
return msg
The problem is when I hit "save" in the template, it redirects well to another template, but I don't see any message, like I suppose to see (final_insert.html shows {{ msg }})
Can someone help me understand what I'm doing wrong?
Any help is welcome!
Thanks for your help!
I was able to understand my mistake.
sorry guys for my silly mistake
so this is the form:
<form enctype="multipart/form-data" action="{% url upload_done 'clinical' %}" method="post">
<div>
{% for field in form %}
{{ field }}
{% endfor %}
<input type="submit" value="Save" />
</div>
</form>
urls:
url(r'^insert/file/(?P<word>clinical)/upload/$', last_step, name="upload"),
url(r'^insert/file/(?P<word>clinical)/upload/result/$', final, name='upload_done'),
so the view last_step corresponds to the url "upload" and not "upload_done"
I wrote into the form action={% url upload_done 'clinical' %}, so when I hit save it will redirect me automatically to the other template. Without running the code!!
So I changed the form to:
<form enctype="multipart/form-data" action="{% url upload 'clinical' %}" method="post">
<div>
{% for field in form %}
{{ field.label_tag }}
{{ field }}
{% endfor %}
<input type="submit" value="Guardar" />
</div>
</form>
and now it works..
sorry guys, I thought I needed to redirect to the other page but when he redirects he doesn't run the code..
now im learning to validate form, "all" is working, im showing the erros of empty fields, but i have 2 questions:
how ill show the value in the filled fields when there are errors in another fields?, like <input ... value= {{ value }} > the problem is that my fields are not html forms fields.
how ill show the error exactly over the empty fields?
how i have this:
form.py
class NuevaDiligenciaForm(forms.Form):
titulo = forms.CharField(max_length=70)
tipo = forms.ChoiceField(choices=TIPO)
vias= forms.TypedChoiceField(widget=forms.RadioSelect(), choices=CHOICES)
view.py
def add(request):
form = NuevaDiligenciaForm()
errors =[]
if request.method =='POST':
if not request.POST.get('titulo',''):
errors.append('Titulo es requerido')
if not request.POST.get('vias',''):
errors.append('Vias es requerido')
#if not errors:
return render_to_response('account/add.html', { 'formulario':form ,'errors':errors},context_instance = RequestContext(request))
template.html
{% if errors %}
<ul>
{% for error in errors %}
<li>{{ error }}</li>
{% endfor %}
</ul>
{% endif %}
{% if message %}
<p style="color: red;">{{ message }}</p>
{% endif %}
<form action='.' method='POST' class="nueva-diligencia">
{{ formulario.as_p }}
<input type="submit" value="Continuar">
</form>
Thanks again :)
You form code looks fine here but your view needs to change to this:
def add(request):
if request.method =='POST':
form = NuevaDiligenciaForm(request.POST)
if form.is_valid():
clean_data = form.cleaned_data
# Now do something with the cleaned data...
else:
form = NuevaDiligenciaForm()
return render_to_response('account/add.html', { 'formulario': form }
and your template should look like this:
{% if message %}
<p style="color: red;">{{ message }}</p>
{% endif %}
<form action='.' method='POST' class="nueva-diligencia">
{{ formulario.as_p }}
<input type="submit" value="Continuar">
</form>
Now what happens is that if there is bad data from the POST, form.is_valid() will fail and the view will return the validated form, which will include errors next to fields that have them. Django takes care of all the error handling for you here! Try it out and let me know if it works as you expect it to.
This is a pretty good resource if you'd like to see how/why this simplified version actually works better: http://www.djangobook.com/en/2.0/chapter07/