ModelForm in Django not showing - python

I'm trying to display a basic form in django but does not render the form once I run the server, I would appreciate if you could help me with these, here my code.
models.py
STATUS_OPTIONS =(
('OP', 'OPEN'),
('CL', 'CLOSED')
)
class Employee(models.Model):
id = models.AutoField(primary_key=True)
first_name = models.CharField(max_length=100)
last_name = models.CharField(max_length=100)
email = models.EmailField(max_length=200)
status = models.CharField(max_length=50, choices=STATUS_OPTIONS)
password = models.CharField(max_length=100)
def __str__(self):
return self.first_name
forms.py
from django import forms
from .models import Employee
class EmployeeForm(forms.Form):
class Meta:
model = Employee
fields = "__all__"
urls.py
from django.urls import include, path
from . import views
urlpatterns = [
path('', views.create_employee),
]
views.py
from .forms import EmployeeForm
# Create your views here.
def create_employee(request):
form = EmployeeForm()
return render(request, 'employee/create_employee.html', {'form':form})
create_employee.html
<h1>Formu</h1>
<form action="" method='POST'>
{{form.as_p}}
<input type="submit">
</form>
When I run the program the only thing rendered is the tag, any idea?

In order to create forms out of models you need to use ModelForm not Form. Otherwise you end up with a regular form without any field.
from django.forms import ModelForm
from .models import Employee
class EmployeeForm(ModelForm):
#...
More about ModelForm here

Related

My django generic DetailView doens't show any data

Hello everyone I have just started developing my blog with django but I don't get to display my posts individually. DetailView doesn't work, please help!
here is my url
from django.urls import path
from .views import Home, ArticleDetailView
urlpatterns = [
path('', Home.as_view(), name='home'),
path('article/<int:pk>', ArticleDetailView.as_view(), name='article_details'),
]
Here is my view.
from django.shortcuts import render
from django.views.generic import ListView, DetailView
from .models import Article
# Create your views here.
class Home(ListView):
model = Article
template_name = 'home.html'
class ArticleDetailView(DetailView):
model = Article
template_name = 'article_detail_view.html'
My model
from django.db import models
from django.contrib.auth.models import User
# Create your models here.
class Article(models.Model):
title = models.CharField(max_length=255)
author = models.ForeignKey(User, on_delete=models.CASCADE)
body = models.TextField()
def __str__(self):
return self.title + '|' + str(self.author)
class Meta:
verbose_name = 'Article'
verbose_name_plural = 'Articles'
Home.html
<h2>Post</h2>
<ul>
{% for post in object_list %}
<li>{{post.title}} by {{ post.author }}</br>
<p>{{post.body}}</p></li>
{% endfor %}
</ul>
article_detail_view.html
<h2>Article Detail View</h2>
<h2>{{post.title}} By {{ post.author }}</h2></br>
<p>{{post.body}}</p>
Thanks for updating the question.
First add the get_absolute_url method to the model as follows:
class Article(models.Model):
title = models.CharField(max_length=255)
author = models.ForeignKey(User, on_delete=models.CASCADE)
body = models.TextField()
def __str__(self):
return self.title + '|' + str(self.author)
class Meta:
verbose_name = 'Article'
verbose_name_plural = 'Articles'
def get_absolute_url(self):
return reverse("article_details", kwargs={"pk": self.pk})
In your article_detail_view.html, you can access the article using the article instance:
<h2>Article Detail View</h2>
<h2>{{article.title}} By {{ article.author }}</h2></br>
<p>{{article.body}}</p>
in your article_detail_view.html
you can access the article by: {{object.title}}
you can also specify what to return in template and how you wanna name it by overriding get_context_data
check this
in models.py
class Meta:
managed = True
verbose_name = 'Article'
verbose_name_plural = 'Articles'

Setting up Online Booking form, getting this error - TypeError at /bookings/ 'OnlineForm' object is not callable

Can anyone please help. I am currently working through a project where I am attempting to create a website for a fictitious restaurant, including an online booking form.
I am getting the following error message:
TypeError at /bookings/
'OnlineForm' object is not callable
I have watched a number of videos and read through the Django documentation and I still have no idea what I am doing wrong. I am new to Django so this is all learning for me. Any advice you can give would be hugely appreciated. Thank you in advance
This is my code:
view.py:
class BookingForm(FormView):
form_class = OnlineForm()
args = {}
def booking_view(self, request):
if request.method == 'POST':
form = OnlineForm(request.POST)
return render(request, 'bookings.html')
models.py
OCCASION_CHOICE = (
('Birthday', 'BIRTHDAY'),
('Anniversary', 'ANNIVERSARY'),
('Graduation', 'GRADUATION'),
('Communion', 'COMMUNION'),
('Confirmation', 'CONFIRMATION'),
('Christening', 'CHRISTENING'),
('Date Night', 'DATE NIGHT'),
)
class Booking(models.Model):
name = models.CharField(max_length=50)
email_address = models.EmailField()
phone = models.IntegerField()
number_of_people = models.IntegerField(validators=[MinValueValidator(1), MaxValueValidator(10)],default='1', help_text='For parties of more than 10, please call us on 021 4569 782')
date = models.DateField()
time = models.TimeField()
occasion = models.CharField(max_length=100, choices=OCCASION_CHOICE, default='Birthday')
def __str__(self):
return self.name
forms.py:
from django.forms import ModelForm
from .models import Booking
class OnlineForm(ModelForm):
class Meta:
model = Booking
fields = '__all__'
urls.py:
from . import views
from .views import BookingForm
from django.urls import path
app_name = 'bookingsystem'
urlpatterns = [
path('', views.Home.as_view(), name='home'),
path('bookings/', BookingForm.as_view(), name='bookings'),
path('menus/', views.Menus.as_view(), name='menus'),
path('edit_bookings', views.editBooking.as_view(), name='edit_bookings'),
]
bookings.html:
{% extends "base.html" %}
{% block content %}
<form method="POST">
{% csrf_token %}
{{form}}
<button id="submit-button" class="btn btn-success">Book Now</button>
</form>
{%endblock%}
According to django description, of FormView you do not have an option of defining your own POST method. Rewriting your view to
class BookingForm(FormView):
template_name = 'bookings.html'
form_class = OnlineForm
will solve the issue. Though you'll need to add a form_valid method to define actions to carryout when a form with valid data is submitted.

Why is my django file submission not posting?

I am busy building a conference website application where is is necessary to be able to upload articles. These articles should also be able to assigned to reviewers to get downloaded and scored. My problem comes with the uploading of the files. I am not sure what I am doing wrong, but I think my form is submitting the incorrect data since it doesn't run through the 'if form.is_valid:' part. I am still a beginner at this. I have watched multiple tutorials.
This is what my model.py file looks like:
from django.db import models
from time import time
def get_upload_file_name(instance, filename):
return "uploaded_files/%s_%s" % (str(time()).replace('.','_'), filename)
class Article(models.Model):
title = models.CharField(max_length=50)
abstract = models.TextField()
pub_date = models.DateTimeField('Date published')
ffile = models.FileField(upload_to=get_upload_file_name)
def __str__(self):
return "%s" % (self.title)
This is my admin.py file:
from django.contrib import admin
from .models import Article
admin.site.register(Article)
This is my forms.py file:
from django import forms
from .models import Article
class ArticleForm(forms.ModelForm):
class Meta:
model = Article
fields = ('title','abstract','pub_date','ffile')
This is my views.py file:
from django.shortcuts import render, render_to_response
from django.http import HttpResponseRedirect
from .forms import ArticleForm
def upload_article(request):
if request.method == 'POST':
form = ArticleForm(request.POST, request.FILES)
if form.is_valid():
instance = ArticleForm(file_field=request.FILES[''])
form.save()
instance.save()
return HttpResponseRedirect('/articles/')
else:
form = ArticleForm()
return render_to_response('submit/form.html', {'form' : form})
And then my HTML template:
{% extends 'base.html' %}
{% block content %}
<form method="post" action="../upload/" enctype="multipart/form-data"> {% csrf_token %}
{{form.as_p}}
<input type="submit" value="Submit" />
</form>
{% endblock %}
There is no problems with my urls.. Can someone please help me. Or at least suggest a third party app that might make this easier?
I can post normal forms that is not uploading files, but I just can't seem to get this one.
Ok, so I found the solution to the posting problem.
models.py
from django.db import models
from django.forms import ModelForm
from time import time
# Function to determine where to place uploaded documents
# Taken from youtube tutorial: https://www.youtube.com/watch?v=b43JIn-OGZU&index=15&list=PLxxA5z-8B2xk4szCgFmgonNcCboyNneMD
def get_upload_file_name(instance, filename):
# return a string: folder_name/time-of-upload + seperated by underscore + filename
# Example: media_files/15-10-2015_Submission1
return "uploaded_files/%s_%s" % (str(time()).replace('.','_'), filename)
class Document(models.Model):
file = models.FileField( blank=False, null=True)
title = models.CharField(max_length=200, default=None)
def __str__(self):
return "%s" % self.title
class DocumentForm(ModelForm):
class Meta:
model = Document
fields = ['title', 'file']
forms.py
from django import forms
from .models import Document
class UploadFileForm(forms.ModelForm):
title = forms.CharField(max_length=200)
file = forms.FileField(
label = 'Select a file',
help_text = 'maximum file size: 50mb',
allow_empty_file=False
)
views.py
##login_required
def upload_file(request):
# Handle file upload
if request.POST:
form = DocumentForm(request.POST, request.FILES)
#print(request.POST['title'], ' ', request.POST['file'])
# print(request.FILES['file'])
if form.is_valid():
#newdoc = Document(title = request.FILES['title'])
form.save()
# Redirect to the document list after POST
# return HttpResponseRedirect(reverse('submissions.views.upload_file'))
return HttpResponseRedirect('/success/')
else:
form = DocumentForm() #A empty, unbound form
args = {}
args.update(csrf(request))
args['form'] = form
return render_to_response('submissions/submission.html', args, context_instance=RequestContext(request))
So one of the problems was that I had to create a FileField in the model as weel as in the form.

DJango - My forms.py elements are not showing up in the html template

I am a newbie for Django and working on a project. I am stucked with setting up a forms.py and integrate the same with my template. I did all the required things with the help of all sort of tutorial I got online but I was unable to see the fields I declared in form on the HTML Page. Below is the code I used for each of the module. It would be great if anyone can help me out with this.
models.py
from django.db import models
class EarlyBirds(models.Model):
name = models.CharField(max_length=200)
email = models.CharField(max_length=200)
contact_number = models.IntegerField()
def __str__(self):
return '%s - %s' % (self.name, self.email)
views.py
from django.shortcuts import render
from django.http import HttpResponse
from django.template import RequestContext, loader
from django.shortcuts import render_to_response
from .forms import EarlyBirdsForm
from .models import EarlyBirds
def register(request):
context = RequestContext(request)
success=''
if request.method == 'POST':
form = EarlyBirdsForm(request.POST)
if form.is_valid():
name = request.POST.get('name','')
email = request.POST.get('email','')
number = request.POST.get('number','')
if email:
email_exist = EarlyBirds.objects.filter(email=email)
if email_exist:
success = 'Thankyou for your intrest! This email is already registered with us. We will get back to you soon.'
else:
eb_obj = EarlyBirds(name=name,email=email,contact_number=number)
eb_obj.save()
success = 'Thankyou for your intrest! We will get back to you soon.'
else:
success = 'Please fill out the required fields'
else:
success = form.errors
else:
form = EarlyBirdsForm()
return render_to_response('ComingSoon.html', {'success':success}, context)
forms.py
from django import forms
from django.forms import ModelForm
from app_name.models import EarlyBirds
class EarlyBirdsForm(forms.Form):
name = forms.CharField(required=True,max_length=100)
email = forms.CharField(required=True,max_length=100)
number = forms.IntegerField(required=True)
class Meta:
model = EarlyBirds
fields = ("name", "email", "number")
template
<html xmlns="http://www.w3.org/1999/xhtml">
<body align="center">
<form method="POST" action="{%url 'comingsoon:register'%}">
{% csrf_token %}
<div class="header-blog-comingSoon" align="center">
<!--<form method="post">
<span>{{ form.as_p }}</span>
<br/>
<span><button class="comingsoon-Reg" type="submit">Register</button></span>
<br/><br/>
<br/><label class="successLabel">{{success}}</label>
</div>
</form>
</body>
</html>
project.urls.py
from django.conf.urls import include, url
from django.contrib import admin
urlpatterns = [
url(r'^ComingSoon/', include('app_name.urls', namespace="comingsoon")),
url(r'^admin/', include(admin.site.urls)),
]
When I try to execute this code, the all I was able to see in the "Register" button on my html page. The three text fields for Name, Email and Contact number were missing. Please let me know what I am missing over here.
You forgot to add the form to your context:
def register(request):
...
return render_to_response('ComingSoon.html', {'success':success, 'form': form}, context)
Maybe you should try writing your form like this:
class EarlyBirdsForm(forms.ModelForm):
class Meta:
model = EarlyBirds
fields = '__all__'
Much easier and simpler. Since you're using all the attributes in the model, might as well connect the form directly with the model.
And César Bustíos said it right. You didn't add the form in the context dictionary for your template.

Showing images on my homepage using the data from my Django Model

Would like to simplely show multiple pictures from my model data that I inputted via the Admin in my template file between the UL tag. I am having trouble rendering the data to show the image. I dont need to route anything in URL.py yet, just need to pollute the images on my homepage first. Can someone please help troubleshoot my issue? Thank you!
Models.py
class Product(models.Model):
name = models.CharField(max_length=254, blank=True, null=True)
description = models.TextField(blank=True, null=True)
color_name = models.CharField(max_length=254, null=True, blank=True)
size_types = models.CharField(max_length=7, null=True, blank=True)
product_price = models.DecimalField(max_digits=9,decimal_places=2)
old_price = models.DecimalField(max_digits=9,decimal_places=2, blank=True,default=0.00) #To show original price if, new price has been added
product_tags = models.CharField(max_length=254, null=True, blank=True, help_text='Comma-delimited set of SEO keywords for product tag area')
novelty = models.CharField(max_length=254, null=True, blank=True)
product_website = models.URLField(max_length=200, null=True, blank=True) #To show other sites to Users, where they can purchase the particular product
image = models.ImageField(upload_to='images/products/main',max_length=100, null=True) #For the argument upload_to, will add to the static folder and generated image will be stored in suing that path specified
slug = models.SlugField(max_length=255, unique=True, help_text='Unique value for product page URL, created from name.')
#This shows when each item was uploaded & by who, to the User
uploaded_by = models.CharField(max_length=254, blank=True, null=True)
uploaded_at = models.DateTimeField(auto_now=True)
#For Admin Purposes, to track and see which if still active by for administrative users only
is_active = models.BooleanField(default=True)
#Foreign Keys & other relationships
designer = models.ForeignKey(Designer)
boutique = models.ForeignKey(Boutique)
category = models.ForeignKey(ProductCategory)
#Metadata
class Meta:
verbose_name = _("Product")
verbose_name_plural = _("Products")
#Helps return something meaningful, to show within the admin interface for easy interaction
def __unicode__(self):
return "{0}".format(self.name)
Forms.py
from __future__ import unicode_literals
from django import forms
from django.forms import extras, ModelForm
from products.models import Designer, Product, ProductCategory, Boutique
class DesignerForm(ModelForm):
class Meta:
model = Designer
class ProductForm(ModelForm):
class Meta:
model = Product
class BoutiqueForm(ModelForm):
class Meta:
model = Boutique
class ProductCategoryForm(ModelForm):
class Meta:
model = ProductCategory
Views.py
from __future__ import unicode_literals
from django.http import Http404, HttpResponseForbidden
from django.shortcuts import redirect, get_object_or_404
from django.core.urlresolvers import reverse
from django.utils.translation import ugettext_lazy as _
from django.views.generic import DetailView
from django.contrib import auth, messages
from django.contrib.sites.models import get_current_site
from django.shortcuts import render
from products.forms import ProductForm, ProductCategoryForm
from products.forms import BoutiqueForm
from products.forms import DesignerForm
from products.models import Boutique, Product, ProductCategory, Designer
class ProductView(DetailView):
model = Product
context_object_name = "task"
Template
{% extends "site_base.html" %}
{% load i18n %}
{% block body %}
<div id="main" role="main">
<ul id="tiles">
<li>
{% for task in products %}
<img src="{{MEDIA_URL}}images/product/main {{task.image.url}}" />
{% endfor %}
</li>
</ul>
</div>
{% endblock %}
There are some odd things in this code.
Firstly, you want to do something with all products. So why are you using a DetailView, which is for selecting and displaying a single item? You need to use a ListView, which will pass a list of products.
Secondly, for some reason you override context_object_name to be "task". But then in the template, you iterate through "products" - a name that is not provided. If you've called the context object "task", that's what you should be iterating over.
Figured out what I was doing wrong!
Apparently I needed to go within my urls and change my already existing TemplateView in the first url tuple:
from django.conf.urls import patterns, include, url
from django.conf import settings
from django.conf.urls.static import static
from django.views.generic import TemplateView
from django.contrib import admin
urlpatterns = patterns('',
url(r"^$", TemplateView.as_view(template_name="homepage.html"), name="home"),
url(r'^admin/', include(admin.site.urls)),
url(r"^account/", include("account.urls")),
url(r'^likes/', include('likes.urls')),
)
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
and change the URL tuple to a ListView, to generate the image from my django models.
from django.conf.urls import patterns, include, url
from django.conf import settings
from django.conf.urls.static import static
from django.views.generic import ListView
from products.models import Product
from django.contrib import admin
urlpatterns = patterns('',
url(r"^$", ListView.as_view(
template_name="homepage.html",
model = Product,
context_object_name = "products",
), name="home"),
url(r'^admin/', include(admin.site.urls)),
url(r"^account/", include("account.urls")),
url(r'^likes/', include('likes.urls')),
)
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)

Categories