Django URLs
Django URLs map incoming web requests to the Python functions or classes that handle them, using a urls.py file and the path() function.
The Project URLconf
Every Django project has a ROOT_URLCONF setting pointing at a Python module - by convention called urls.py - that defines a list named urlpatterns. When a request comes in, Django walks this list from top to bottom and uses the first pattern that matches the request path.
Example
from django.urls import path
from . import views
urlpatterns = [
path('', views.home, name='home'),
path('about/', views.about, name='about'),
]The path() Function
path(route, view, kwargs=None, name=None) ties a URL pattern to a view. route is a string pattern matched against the request path (Django already strips the domain and leading slash for you), view is the callable that handles matching requests, and name lets you refer to this URL from templates and other Python code without hardcoding the string.
- str - matches any non-empty string, excluding the / character
- int - matches zero or any positive integer
- slug - matches slug strings: ASCII letters, numbers, hyphens and underscores
- uuid - matches a formatted UUID, e.g. 075194d3-6885-417e-a8a8-6c931e272f00
- path - matches any non-empty string, including the / character
Example
# urls.py
path('article/<int:article_id>/', views.article_detail, name='article_detail')
# views.py
def article_detail(request, article_id):
# article_id arrives as a Python int, not a string
...Including Other URLconfs
As a project grows, it's common to keep each app's routes in its own urls.py and pull them into the project with include(). This keeps routing modular - an app's URLs can be reused or moved without editing the project-level file.
Example
# project/urls.py
from django.urls import include, path
urlpatterns = [
path('blog/', include('blog.urls')),
]
# blog/urls.py
from django.urls import path
from . import views
app_name = 'blog'
urlpatterns = [
path('', views.post_list, name='post_list'),
path('<int:pk>/', views.post_detail, name='post_detail'),
]Exercise: Django URLs
How does Django decide which view handles an incoming request?