-
Django Template System (DTL 문법, 템플릿 상속)Django 2024. 8. 13. 03:38
Django Template Language (DTL)
Django Template에서 사용하는 문법으로 Python과 비슷하게 만들어졌다. 하지만 파이썬과 비슷할 뿐 파이썬 코드를 넣으면 동작하지 않으므로 주의해야 한다.
DTL 문법
변수, Variable
- 변수의 기본 형태
{{ variable }}
- view의 context로 넘긴 데이터를 접근할 수 있음
- . 을 사용하여 변수의 속성값에 접근 가능
- render() 의 세번째 인자인 context에 dict 형태로 넘겨진 데이터 중 key 값이 template에서 사용 가능한 변수가
필터, Filters
- 필터의 기본 형태
{{ variable|filter }}
- 변수에 어떠한 작업을 추가적으로 더해 수정하고 싶을때 사용
- 약 60개의 built-in template filter가 제공되며 일부 필터는 인자를 받기도 함.
- 모든 건 공식문서에 (바로가기)
- 필터 사용 예시
- view에서 넘겨준 데이터는 Aiden Lim 이런식이지만 보여줄때는 소문자로 보이게 하고 싶다면
{{ first_name|lower }}
태그, Tags
- 태그의 기본 형태
{% tag %}
- 반복문 또는 논리, 조건문을 수행하여 제어 흐름을 만들거나 특수한 기능을 수행
- 일부는 시작 태그와 종료 태그가 있음
{% if ~ %} {% endif %}
주석, Comments
{# 한 줄 주석 #} {% comment %} 여러줄 주석 {% endcomment %}
예제 문제
/hello 로 들어오면 아래의 화면이 나오도록 작성해 주세요. (힌트: urls, view, template 작성 필요)
일단 /hello 로 들어와야 하니까
urls.py 열어서 path(경로)를 추가해준다.
path("hello/", views.hello),
그리고,
views.py 들어가서 hello.html 파일을 작성해준다.
def hello(request): return render(request, "hello.html")
마지막으로,
templates 폴더 안에 hello.html 파일 만들고 코드를 작성한다.
<body> <div style="margin-top: 20px;"> <h1>Hello, Aiden😊</h1> </div> </body>
혹시나해서 이모티콘 넣어봤는데 되네ㅎㅎ 신기🫢
runserver해보면 잘 나온다.
📌 그럼 여기서, Aiden 대신 다른 이름을 쓰고 싶으면 어떻게 하면 좋을까?
context 넘기기
templates에서 사용할 data를 view의 context에 담아서 → templates로 넘겨줄거다.
✏️ 하나씩 해보자!
먼저 템플릿에서 사용할 데이터를 뷰의 컨텍스트에 담아서 넘겨주기로 했으니까,
views.py 를 열고, context에 담고자 하는 내용을 담아준다.
templates 폴더의 hello.html 파일을 열어준다 → view에서 만든 "name" 이라는 context 파일을 입력해준다.
# 원래코드 <h1>Hello, Aiden!</h1> <h1>Hello, {{ name }}!</h1>
서버에 연결해서 확인해보면 잘 반영된 걸 볼 수 있다.
그럼 다른 내용들도 추가해볼까?
views.py 를 열어서 context 에 내용을 추가로 더 적어보자.
def hello(request): name = "Saeye" tags = ["무라카미 하루키", "박민규"] books = ["1Q84", "도시와 그 불확실한 벽", "카스테라", "죽은 왕녀를 위한 파반느"] context = { "name": name, "tags": tags, "books": books, } return render(request, "hello.html", context)
이제 templates 폴더로 이동해서 → hello.html 를 연다.
바디태그<body> 안에 내용을 수정해서 넣어주면 되는데, html 에서도 파이썬 코드처럼 for문으로 반복문을 돌릴 수 있다.
다만 그 형태가 조금 다르므로 잘 봐야한다. (궁금한 건 장고 공식문서를 보거나 구글링해봐야 한다.)
우리가 쓴 for문 구조
<ul> {% for item in items %} <li>{{ item }}</li> {% endfor %} </ul>
· 참고: <ul> 태그는 "unordered list" 즉, 순서 없는 목록을 뜻한다. 서버에 연결했을때 항목들이 동그란 점(불릿)으로 구분되어 표시된다.
<li> 태그는 이 목록의 각 항목을 정의하며, 이 태그 안에 들어간 텍스트 등의 개별 항목을 구성한다.
이렇게 바디태그 안에 내용을 작성해주고
<body> <h1>Hello, {{ name }}!</h1> <p>좋아하는 작가: {{ tags.0 }}</p> <p>기억에 남는 책</p> <ul> {% for book in books %} <li>{{ book }}</li> {% endfor %} </ul> </body>
서버에 연결해서 확인해보면 잘 나온다.
뷰에서 books에 항목을 추가해도
hello.html 파일에서 반복문을 써주었기 때문에, 따로 수정하지 않아도
새로고침 하면 내용이 잘 추가 된다.
예제문제
아래와 같이 이렇게 만들어보기
views.py 들어와서 태그랑 북 목록들 바꿔주고
tags는 첫번째꺼인 tags.0 으로 books는 최근 독서한 책인 books.today로 해주면 된다.
잘 나옴😀
다음 예제문제
힌트: length, join
다른 건 동일하게 두고,
모든 태그를 join: ', ' 으로 합쳐주고, 대표 태그의 글자수는 length 로 구해주는게 포인트
{{ tags | join:", " }}
글자수: {{ tags.0 | length }}
서버에 연결하면 잘 나옴
템플릿 태그 사용하기
필터가 아닌 태그를 사용할 수도 있다.
뷰는 아까와 비슷하다. yesterday, today, tomorrow순서만 바꿔줬다
hello.html 에서 태그 추가
<p>읽은 도서</p> <ul> {% for book in books.items %} <li>{{ book.0 }} - {{ book.1 }}</li> {% endfor %} </ul>
서버 연결하면 잘 나옴
Django Template 상속
중복되는 코드가 많긴 했다.. 🤔 계속 같은 작업을 반복하는 느낌.. 이러다 팀프로젝트가 시작되면... 부트스트랩 넣기 시작하면.. 언제 다 써..
그래서 우리가 배워야 하는게 바로 템플릿 상속이다.
코드 중복 문제를 해결하기 위해 Django는 Template Inheritance을 지원한다😎
상위 템플릿에 → 공통이 될 부분을 정의하고, 하위 템플릿에서 → 달라질 부분을 블록(Block)으로 만드는
Skeleton 형태라는 걸 생각하면서 아래 설명을 보자👌
기본적인 문법
- 상위 템플릿: 아래 코드로 템플릿 마다 공통적으로 달라질 부분을 정의
{% block block_name %} {% endblock block_name %}
- 하위 템플릿:
일단, 템플릿의 가장 최상단에서 아래 코드로 상위 템플릿을 상속받고 난 후에 코드를 적어준다.
{% extends 'template_name' %}
그 후, 블록태그를 이용해 달라진 부분만 다시 코드를 작성해준다. 다중상속 지원 안 함.
{% block block_name %} {% endblock block_name %}
일단 해보자. 프레임워크는 실전임👌
일단 templates 폴더 안에 상위 템플릿을 만들자. 지금 만들 html 파일이 상속을 해줄 부모 템플릿이다.
이름은 base.html 로 만들어주자.
그리고 우리가 지금껏 만들어왔던 모든 html 파일에는 반복적으로 body 태그 안에 내용을 넣어줬다.
그렇기 때문에 지금 만들 base.html 안에도 중복된 위치인 바디태그 안에 블록을 넣어준다. 블록이름은 그냥 content로 하자.
{% block content %} {% endblock content %}
그럼 부모 템플릿 끝!
이제 상속받을 자식들만 코드 바꿔주면 된다.
일단, 템플릿 맨 상단에서 이 코드로 상속받아야 한다고 했으니까
{% extends 'template_name' %}
↓ 우리 부모 템플릿 이름은 base.html 니까 이게 ①번
{% extends 'base.html' %}
②번 이 블록 안에, 입력하고자 하는 내용, 즉 우리가 그동안 계속해서 적어왔던 코드을 넣어주면 된다.
{% block content %} {% endblock content %}
hello.html을 예로 들어 하나하나 해보면,
① hello.html 에 작성했던 원래 코드는 이렇다.
② 맨 상단에 이 코드 복붙 ( == 상속했다)
{% extends 'base.html' %}
③ 블럭 코드 복붙 (== 상속받은 자식들이 코드 작성할 자리 만들어준거)
{% block content %} {% endblock content %}
현재 hello.html의 맨 상단 ↓ (복붙한거 밖에 없음)
④ 아래 바디태그 안에 입력했던 코드 복사해서 저 블록 안에 넣어주면 된다.
⑤ 이렇게 넣어주고 원래 있던 코드들은 다 지우면 끝!
같은 방법으로 index.html 과 users.html 도 모두 수정해주었다.
서버 연결 해보면
모두 잘 나온다. 그런데...🤔
base.html은 atricles라는 앱 안에 있는 파일인데.. 만약, 다른 앱이 추가됐을 때도 base.html을 쓰고싶으면 어떡하지?
그래서 꼭 해야할 게 있다.
일단, articles 폴더도 닫아주고 my_first_pjt 폴더도 다 닫아주고
일단 나와보면, 이렇게 아무것도 선택 안된 상태가 될텐데
여기서 폴더 하나를 생성해준다.
↓
폴더명은 templates로.
↓
그 다음에
새로 만든 templates 폴더 안에 우리가 만든 base.html 파일을 넣어준다.
← 그럼 이런 식의 폴더구조가 될거다.
그럼 이제 다른 앱 만들어도 같이 쓸 수 있겠지?🤭
잘 되는지 다시 서버 연결해볼까?
???
base.html 못찾음..🫠
진짜 마지막으로, 이것만 해주면 끝이다🥹
settings.py 파일 열어서
56번째 줄 정도에 보면 TEMPLATES Code가 있는데 여기 두번째 줄 쯤에
'DIRS' : []
여기에 BASE_DIR / "templates" 을 추가해주면 된다.
'DIRS : [BASE_DIR / "templates"],
이 코드는 Django가 템플릿 파일을 찾을 디렉토리 위치를 지정해주는 건데,
BASE_DIR은 프로젝트의 최상위 디렉토리를 의미하고, templates는 그 하위에 있는 templates라는 서브 디렉토리를 의미한다고 이해하면 된다.
이렇게 코드를 추가해주고 다시 서버 새로고침해보면 잘 나온는 걸 확인할 수 있다.🫠
'Django' 카테고리의 다른 글
Django Model, Migration, ORM, Database API (0) 2024.08.16 Django HTTP Form (0) 2024.08.14 Django MTV 패턴, Templates 작성 (0) 2024.08.12 django 프로젝트 생성, 서버 연결, App 생성 & 등록 (0) 2024.08.10 Django 장고 설치, 가상환경, 프로젝트 생성 (1) 2024.08.09