I have 20 Django simple "foo.html" template files.
Do I need 20 TemplateViews and 20 entries in url_patterns or is there a simpler solution?
I have 20 Django simple "foo.html" template files.
Do I need 20 TemplateViews and 20 entries in url_patterns or is there a simpler solution?
Using Django 2.1 and class-based views, your urls.py should be like this:
from django.urls import path
from your_app import views
app_name = 'your_app'
urlpatterns = [
path('foo/<str:name>/', views.Foo.as_view(), name='foo'),
]
And your views.py like this:
from django.views import generic
class Foo(generic.TemplateView):
def get_template_names(self)
name = self.kwargs.get('name')
# compute the template you want, for the example, I just take the name
template_name = f'your_app/{name}.html'
return [template_name]
And that's all ;)
You can have a path like path('pages/<str:page>, views.pages)
And then in the view do something similar to:
from django.template.loader import get_template
from django.template import TemplateDoesNotExist
def pages(request, page):
template_name = f'your-app/{page}.html'
try:
get_template(template_name)
return render(request, template_name)
except TemplateDoesNotExist:
# returns 404
Since you sound newer to django, this solution should be much easier. There's no reason to use f strings and try/except blocks with simple things. And I know when I started, class based views made no sense because there was no control flow.
from django.urls import path
from . import views
app_name = 'article_app'
urlpatterns = [
path('', views.article_list, name='article_list'),
path('new/', views.article_new, name='article_new'),
path('<int:art_pk>/', views.article_detail, name='article_detail'),
path('<int:art_pk>/update/', views.article_update, name='article_update'),
path('<int:art_pk>/delete/', views.article_delete, name='article_delete'),
# and so on....
]
from django.shortcuts import render
from .models import Article
def article_detail(request, art_pk):
article = Article.objects.get(pk=art_pk)
return render(request, 'articles_app/article_detail.html', {'article': article})
{% block maincontent %}
<div class="article">
<h2><u>{{ article.title }}</u></h2>
<h3>By: {{ article.author }} --- Posted / Updated on: {{ article.date }}</h3>
<p>{{ article.body }}</p>
<p><a href="{% url 'article_app:article_update' article.pk %}">Update</a> | <a href="{% url 'article_app:article_delete' article.pk %}">Delete</a></p>
<p><a href="{% url 'article_app:article_list' %}">Back to all articles</a></p>
</div>
{% endblock maincontent %}
Lets say it's something that requires a few if/else statements to describe a Food model. Example:
class Food(models.Model):
FLAVOR_CHOICES = (
('tasty', 'Very yummy'),
('disgusting', 'Nasty AF bro!'),
('super_sweet', 'For little kids'),
('bitter', 'Sure to grow hair on you balls!'),
)
food_choice = models.CharField(max_length=30, choices=FLAVOR_CHOICES, default='super_sweet')
# and any other attribute for a Food
app_name = 'food_app'
urlpatterns = [
# ....
path('<int:food_id>/', views.show_food, name='show_food'),
]
def show_food(request, food_id):
food = Food.objects.get(id=food_id)
if food.food_choice == 'tasty':
return render(request, 'food_app/food_stats.html', {'tasty': 'Everyone likes tasty things'})
elif food.food_choice == 'bitter':
return render(request, 'food_app/food_stats.html', {'bitter': 'Girls do not want to have balls. Sure way to end the gene pool.'})
# .... and so on with other choices
else:
return render(request, 'food_app/food_stats.html')
Note that this should be used instead of creating separate pages for 'bitter.html', 'tasty.html', 'super_sweet.html', etc.
{% block maincontent %}
<h1>Your choice of food:</h1>
{% if tasty %}
<p>{{ tasty.food_choice }}</p> {# this attribute would show the 2nd value for 'tasty' in the tuple of FLAVOR_CHOICES - 'Very yummy' #}
<p>{{ tasty }}</p> {# The value that shows here is the key I set in the view #}
{% elif disgusting %}
<p>{{ disgusting.food_choice }}</p>
<p>{{ disgusting }}</p>
{% elif super_sweet %}
<p>{{ super_sweet.food_choice }}</p>
<p>{{ super_sweet }}</p>
{% elif bitter %}
<p>{{ bitter.food_choice }}</p>
<p>{{ bitter }}</p>
{% else %}
<p>No foods bro. You're lame.</p>
{% endif %}
{% endblock maincontent %}
from django.conf.urls import url from .import views
urlpatterns = [ # url(r'^/$', views.function_name, name="Page")
url(r'^$', views.home, name="Home Page"),
]
use this patterns match to show your .html pages