포켓몬 정보를 담고있는 포켓몬 도감 웹 사이트를 만든다고 가정해보자. 포켓몬 도감에는 포켓몬의 목록을 보여주는 리스트 페이지
와 포켓몬의 상세 정보를 보여주는 디테일 페이지
가 있을 것이다.
포켓몬 도감에는 총 3마리의 포켓몬 정보를 담고 있다고 가정하면 디렉토리 구조는 다음과 같을 것이다.
📂poketmon
📄manage.py
📄db.sqlite3
📂pokemon
📄__init__.py
📄settings.py
📄urls.py
📄wsgi.py
📂pokemon-book
📂static
📂templates
📂pokemon-book
📄pokemon-list.html 📌포켓몬 목록 템플릿
📄detail-pikachu.html 📌피카츄 상세정보 템플릿
📄detail-charmander.html 📌파이리 상세정보 템플릿
📄detail-squirtturtle.html 📌꼬부기 상세정보 템플릿
📂migrations
📄__init__.py
📄admin.py
📄apps.py
📄models.py
📄tests.py
📄views.py
📄urls.py
pokemon-book 앱 디렉토리
의urls.py
파일은 다음과 같을 것이다.
urlpatterns = [
path('', 'views.pokemon-list'), 📌주소/pokemon-book 으로 이동하면 views의 pokemon_list 함수를 확인
path('pikachu', views.pikachu), 📌주소/pokemon-book/pikachu 으로 이동하면 views의 pikachu 함수를 확인
path('charmander', views.charmander), 📌주소/pokemon-book/charmander 으로 이동하면 views의 charmander 함수를 확인
path('squirtturtle', views.squirtturtle), 📌주소/pokemon-book/squirtturtle 으로 이동하면 views의 squirtturtle 함수를 확인
]
pokemon-book 앱 디렉토리
의views.py
파일은 다음과 같을 것이다.
def pokemon_list(request):
return render(request, 'pokemon-book/pokemon-list.html')
def pikachu(request):
return render(request, 'pokemon-book/detail-pikachu.html')
def charmander(request):
return render(request, 'pokemon-book/detail-charmander.html')
def squirtturtle(request):
return render(request, 'pokemon-book/detail-squirtturtle.html')
그런데 만약 pokemon-list에 피카츄, 파이리, 꼬부기 뿐만 아니라 더 많은 포케몬 목록이 있다면? 그 목록이 100개 이상이라면?
urls.py
에 포케몬 수 만큼의 url 패턴을 작성하고,views.py
에 포케몬 수 만큼의 함수를 작성하며template
에 포케몬 수 만큼의 템플릿을 생성해야 한다.
우리는 코드를 더 효율적으로 작성하기 위해 동적 url을 사용할 것이다. 단계별로
동적 url
을 사용하는 방법을 설명하겠다.
urls.py
파일의 url 패턴을 변경한다.
urlpatterns = [
path('', 'views.pokemon-list'),
path('detail/<str:pokemon_name>', 'views.pokemon_detail'), 📌기존에 작성된 url 패턴을 변경
]
변경된 url 패턴은 detail/ 다음에 오는 url을
문자열(str)
로 보고pokemon_name
에 담아서 pokemon_detail 함수를 호출할 때인수
로 전달한는 의미다. 이때<str:{변수명}>
을경로 변수
라고 한다.
view.py의 함수를 변경한다.
def pokemon_list(request):
return render(request, 'pokemon-book/pokemon-list.html')
def pokemon_detail(request, pokemon_name): 📌기존에 작성된 함수를 변경
context = {"name":pokemon_name}
return render(request, 'pokemon-book/pokemon-detail.html', context=context)
작성된 함수를 설명하자면,
urls.py
에서 전달받은 인수pokemon_name
을 사전형 자료인변수 context
의 name키
에 매칭되는값
으로 지정한다. 이후render
함수의context 파라미터
에 매칭되는 인수로 전달하여 pokemon-detail.html템플릿
을 렌더한다는 의미다.
마지막으로
html 템플릿
을 변경하면 된다. 기존에 있던detail-pikachu.html
,detail-charmander.html
,detail-squirtturtle.html
을 삭제하고pokoemon-detail.html
템플릿을 생성한다.
📂poketmon
📄manage.py
📄db.sqlite3
📂pokemon
📄__init__.py
📄settings.py
📄urls.py
📄wsgi.py
📂pokemon-book
📂static
📂templates
📂pokemon-book
📄pokemon-list.html
📄pokemom-detail.html 📌새로 생성된 html 템플릿
📂migrations
📄__init__.py
📄admin.py
📄apps.py
📄models.py
📄tests.py
📄views.py
📄urls.py
url에 따라서 변경되는 포케몬의 이름을 호출할 수 있는 템플릿 내용을 작성한다.
<h2>{{name}}</h2>
정리하자면,
urls.py
의 url 패턴에서 detail/ 이후의 url을 문자열로 보고pokemon_name
이라는 인수에 담아view.py
의pokemon_detail
함수에 전달한다.pokemon_detail
함수는 전달받은pokemon_name
을변수 context
의키
name에 매칭되는값
으로 지정하고,context 파라미터
의인자
로 전달하여pokemon-detail.html
템플릿을 렌더한다.pokemon-detail.html
은 전달 받은 데이터에 접근할 수 있어 {{name}}템플릿 태그
를<h2>
태그에 작성하면 detail/ 이후의 url을 호출할 수 있는 방식이다.
헷갈려도 참아라. 너가 선택한 길이다.