[Spring] 스프링 MVC 2편 - 백엔드 웹 개발 활용 기술 - 강의 정리 - 1

JJAM·2022년 10월 6일
0
post-thumbnail

📖 타임리프 - 기본 기능 1

📒 프로젝트 생성

스프링 부트 스타터에서 프로젝트를 생성한다.

📒 타임리프 소개

타임리프
백엔드 서버에서 HTML을 동적으로 렌더링
순수 HTML을 최대한 유지

타임리프를 사용할 때에 다음 코드를 선언해 준다.

<html xmlns:th="http://www.thymeleaf.org">

📒 텍스트 - text, utext

✏️ text - th:text, [[...]]

java/hello/thymeleaf/basic/BasicController

model에 "data"라는 이름으로 "hello Spring!"를 넣어서, 뷰 템플릿을 호출한다.

model.addAttribute("data","hello Spring!");
return "basic/text-basic";

resources/templates/basic/text-basic.html

model에 담은 data를 출력하기 위해
th:text="${data}" 또는 [[${data}]] 를 사용한다.

<li>th:text 사용 <span th:text="${data}"></span></li>
<li>컨텐츠 안에서 직접 출력하기 = [[${data}]]</li>

실행해보면 정상적으로 data의 내용이 찍히는 것을 볼 수 있다.

✏️ utext - th:utext, [(...)]

만약 model에 담긴 내용에 html 태그를 추가해서 실행하면

model.addAttribute("data","hello <b>Spring!</b>");

문자 그대로가 출력이 되고, 내가 원하는 html 태그로 렌더링 되지 않는다.
왜냐하면 타임리프의 이스케이스(escape) 기능 때문이다.

그래서 이스케이프(escape)를 사용하지 않는 기능을 사용할 수 있다.

resources/templates/basic/text-basic.html

model에 담은 data를 이스케이프(escape) 를 사용하지 않도록 출력하기 위해
th:utext="${data}" 또는 [(${data})] 를 사용한다.

<li>th:utext = <span th:utext="${data}"></span></li>
<li><span th:inline="none">[(...)] = </span>[(${data})]</li>

그러면 model에 담긴 html 태그가 정상적으로 작동하는 것을 볼 수 있다.

📒 변수 - SpringEL

✏️ SpringEL 표현식

타임리프에서 변수를 사용할 때는 변수 표현식을 사용한다.

java/hello/thymeleaf/basic/BasicController

변수 표현식을 사용하기 위해, User 객체를 새로 생성한다.

@Data
static class User {
	private String username;
	private int age;

메서드에 객체를 생성하여 값을 넣고
model에다가 객체, List, Map을 넣어 뷰 탬플릿을 호출한다.

// userA 객체 생성
User userA = new User("userA", 10);

// List에 userA 객체 넣음
List<User> list = new ArrayList<>();
list.add(userA);

// Map에 userA 객체 넣음
Map<String, User> map = new HashMap<>();
map.put("userA", userA);

// model에 객체, List, Map 넣음
model.addAttribute("user", userA);
model.addAttribute("users", list);
model.addAttribute("userMap", map);

return "basic/variable";

resources/templates/basic/variable.html

객체, List, Map 변수에 담긴 내용을 다음 문법을 사용하여 출력한다.

<!-- 객체 -->
<span th:text="${user.username}"></span>
<span th:text="${user['username']}"></span>
<span th:text="${user.getUsername()}"></span>
<!-- List -->
<span th:text="${users[0].username}"></span>
<span th:text="${users[0]['username']}"></span>
<span th:text="${users[0].getUsername()}"></span>
<!-- Map -->
<span th:text="${userMap['userA'].username}"></span>
<span th:text="${userMap['userA']['username']}"></span>
<span th:text="${userMap['userA'].getUsername()}"></span>

그러면 변수의 담긴 내용이 제대로 출력되는 것을 볼 수 있다.

✏️ 지역 변수

추가적으로 th:with를 사용하면 지역 변수를 선언해서 사용할 수 있으며,
이는 선언한 태그 안에서만 사용할 수 있다.

<div th:with="first=${users[0]}">
	<p>처음 사람의 이름은 <span th:text="${first.username}"></span></p>
</div>

실행을 하면 지역 변수가 출력되는 것을 볼 수 있다.

📒 기본 객체들

타임리프가 제공하는 객체

  • ${#request}
  • ${#response}
  • ${#session}
  • ${#servletContext}
  • ${#locale}

java/hello/thymeleaf/basic/BasicController

타임리프가 제공하는 기본 객체요청 파라미터, 세션, 스프링 빈을 사용하기 위해
세션 데이터를 넣고 스프링 빈을 생성한다.

@GetMapping("/basic-objects")
public String basicObjects(HttpSession session) {
	session.setAttribute("sessionData", "Hello Session"); // 세션
	return "basic/basic-objects";
}

@Component("helloBean") // 스프링빈 등록
static class HelloBean {
	public String hello(String data) {
		return "Hello " + data;
	}
}

resources/templates/basic/basic-objects.html

우선 기본적으로 제공하는 객체를 아래와 같이 사용할 수 있다.

<span th:text="${#request}"></span>
<span th:text="${#response}"></span>
<span th:text="${#session}"></span>
<span th:text="${#servletContext}"></span>
<span th:text="${#locale}"></span>

실행을 하면 해당 객체들의 정보가 출력된다.

그리고 HTTP 요청 파라미터 정보, 세션 정보, 스프링 빈 정보를 아래와 같이 사용해 출력할 수 있다.

<span th:text="${param.paramData}"></span>
<span th:text="${session.sessionData}"></span>
<span th:text="${@helloBean.hello('Spring!')}"></span>

📒 유틸리티 객체와 날짜

타임리프는 문자, 숫자, 날짜, URI 등을 편리하게 다루는 다양한 유틸리티 객체들을 제공한다.

java/hello/thymeleaf/basic/BasicController

타임리프가 제공하는 유틸리티 객체를 사용하기 위해 현재 시간을 model에 담는다.

model.addAttribute("localDateTime", LocalDateTime.now()); // 현재 시간 담음
return "basic/date";

resources/templates/basic/date.html

model에 넣은 현재 시간을 알려주는 localDateTime를 다음과 같이 사용하고, format을 지정하여 출력할 수 있다.

<span th:text="${localDateTime}"></span>
<span th:text="${#temporals.format(localDateTime, 'yyyy-MM-dd HH:mm:ss')}"></span>

그리고 타임리프가 제공하는 유틸리티 객체도 다음과 같이 사용한다.

<span th:text="${#temporals.day(localDateTime)}"></span>
<span th:text="${#temporals.month(localDateTime)}"></span>
<span th:text="${#temporals.monthName(localDateTime)}"></span>
<span th:text="${#temporals.monthNameShort(localDateTime)}"></span>
<span th:text="${#temporals.year(localDateTime)}"></span>
<span th:text="${#temporals.dayOfWeek(localDateTime)}"></span>
<span th:text="${#temporals.dayOfWeekName(localDateTime)}"></span>
<span th:text="${#temporals.dayOfWeekNameShort(localDateTime)}"></span>
<span th:text="${#temporals.hour(localDateTime)}"></span>
<span th:text="${#temporals.minute(localDateTime)}"></span>
<span th:text="${#temporals.second(localDateTime)}"></span>
<span th:text="${#temporals.nanosecond(localDateTime)}"></span>

📒 URL 링크

타임리프에서 URL 링크를 생성할 수 있다.

java/hello/thymeleaf/basic/BasicController

URL 링크를 생성할 때, 경로에 넣을 값을 model에 넣고 뷰 템플릿을 호출한다.

model.addAttribute("param1", "data1");
model.addAttribute("param2", "data2");
return "basic/link";

resources/templates/basic/link.html

일반적인 단일 경로는 아래와 같이 사용한다.

<!-- http://localhost:8080/hello -->
<a th:href="@{/hello}">

쿼리 파라미터를 넣은 경로는 아래와 같이 사용하며,
() 에 있는 부분은 쿼리 파라미터로 처리된다.

<!-- http://localhost:8080/hello?param1=data1&param2=data2 -->
<a th:href="@{/hello(param1=${param1}, param2=${param2})}">

다중 경로는 아래와 같이 사용하며,
경로에 변수가 있으면 () 부분이 경로 변수로 처리된다.

<!-- http://localhost:8080/hello/data1/data2 -->
<a th:href="@{/hello/{param1}/{param2}(param1=${param1}, param2=${param2})}">

쿼리 파라미터 + 다중경로는 아래와 같이 사용한다.

<!-- http://localhost:8080/hello/data1?param2=data2 -->
<a th:href="@{/hello/{param1}(param1=${param1}, param2=${param2})}">

📒 리터럴(Literals)

리터럴 - 소스 코드상에 고정된 값

  • 문자: 'hello' <- 항상 '작은 따옴표'로 감쌈(공백 없으면 생략 가능)
  • 숫자: 10
  • 불린: true , false
  • null: null

java/hello/thymeleaf/basic/BasicController

리터럴을 사용하기 위해 model에 문자열을 담아 뷰 템플릿을 호출한다.

model.addAttribute("data", "Spring!");
return "basic/literal";

resources/templates/basic/literal.html

+ 를 사용하여 리터럴을 연결할 수 있으며, 문자열 변수도 연결할 수 있고
th:text="|hello ${data}|"리터럴 대체 문법을 사용할 수도 있다.

<span th:text="'hello' + ' world!'"></span>
<span th:text="'hello world!'"></span>
<span th:text="'hello ' + ${data}"></span>
<span th:text="|hello ${data}|"></span>

📒 연산

타임리프에서 연산을 사용할 수 있으며, 자바와 크게 다르지 않다.

java/hello/thymeleaf/basic/BasicController

연산을 사용하기 위해 null 값과 문자열을 model에 넣고 뷰 템플릿을 호출한다.

model.addAttribute("nullData", null);
model.addAttribute("data", "Spring!");
return "basic/operation";

resources/templates/basic/operation.html

산술 연산을 하여 연산의 답과 연산의 결과가 true인지 false 인지 알 수 있다.

<span th:text="10 + 2"></span>
<span th:text="10 % 2 == 0"></span>

비교 연산을 할 때, html 태그인 >, <를 유의하며, 연산의 결과는 true, false로 출력된다.

<span th:text="1 &gt; 10"></span>
<span th:text="1 gt 10"></span>
<span th:text="1 >= 10"></span>
<span th:text="1 ge 10"></span>
<span th:text="1 == 10"></span>
<span th:text="1 != 10"></span>

조건식은 삼항연산자를 사용하여 조건에 따라 값이 출력된다.

<span th:text="(10 % 2 == 0)? '짝수':'홀수'"></span>

Elvis 연산자를 사용하여 true이면 해당 변수를, false이면 '데이터가 없습니다.'가 출력된다.

<span th:text="${data}?: '데이터가 없습니다.'"></span>
<span th:text="${nullData}?: '데이터가 없습니다.'"></span>

No-Operation을 사용하여 변수 값이 없으면 html의 값이 그대로, 있으면 변수가 출력된다.

<span th:text="${data}?: _">데이터가 없습니다.</span>
<span th:text="${nullData}?: _">데이터가 없습니다.</span>


지금까지 김영한 - 스프링 MVC 2편 - 백엔드 웹 개발 활용 기술(유료강의) 강의를 참고하여 타임리프 - 기본 기능 1 에 대해 공부하였다.

profile
☘️

0개의 댓글