이번 시간에는 mvc 패턴을 이용한 간단한 예제를 알아보겠다.
우선 설명의 이해를 돕기 위해 코드와 함께 알아보자.
--홈 화면--
package hello.hellospring.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class HomeController{
@GetMapping("/")
public String home(){
return "home";
}
}
새로운 컨트롤러를 하나 만들고 루트(/)에 대해 getmapping해준다.
그리고 html파일을 하나 만들어서 간단한 화면을 보여준다.(하단에 있는 소스코드)
그런데, 지난 시간에 만들었던 static 폴더에 있는 index.html은 어디로 갔을까?
static과 template 사이에는 우선순위가 존재한다. (컨트롤러가 정적 파일보다 높다!)
첫번째로 url에 대해 맞는 컨트롤러를 먼저 찾고 해당 컨트롤러에 맞는 템플릿 찾아서 뷰(화면에 띄워주기) 해주고, 만약 해당되는 컨트롤러가 없으면, 그 다음에 static파일에 있는 index.html을 연다.
그렇기에 home.html이 index.html을 제치고 화면에 나올 수 있는 것이다.
<!DOCTYPE HTML>
<html xmlns:th="http://www.thymeleaf.org">
<body>
<div class="container">
<div>
<h1>Hello Spring</h1>
<p>회원 기능</p>
<p>
<a href="/members/new">회원 가입</a>
<a href="/members">회원 목록</a>
</p>
</div>
</div> <!-- /container -->
</body>
</html>
--회원 등록--
@Controller
public class MemberController {
private final MemberService memberService;
@Autowired
public MemberController(MemberService memberService){
this.memberService = memberService;
}
@GetMapping("/members/new")
public String createForm(){
return "members/createMemberForm";
}
@PostMapping("/members/new")
public String create(MemberForm form){
Member member = new Member();
member.setName(form.getName());
memberService.join(member);
return "redirect:/";
}
}
}우선, 템플릿에 폴더(예제에서는 members)를 하나 만들어서 비슷한 웹페이지들을 모아놓는다. 굳이 하지 않아도 되지만, 하는 것을 강력 추천한다!
회원이 등록되는 방식은 다음과 같다.
-url에 get방식으로 들어오면 getmapping 어노테이션을 통해 매칭이 되어 createMemberForm.html으로 이동한다.
-html화면이 띄워지면 아무 이름을 입력하고 등록버튼을 누른다.
-등록버튼을 누르게 되면 폼이 submit이 되면서 html의 form안에 input태그 안에 있는 name과 MemberForm컨트롤러의 name변수가 매칭이 되면서 서버로 전송된다.
-form은 input 태그안에 값을 post방식을 이용하여, action url(/members/new)로 넘긴다. 이때name을 key로 해서 넘긴다!
-postmapping되어 멤버 객체를 하나 생성하고 form의 name을 가져와 member의 name으로 set하고 join을 통해 저장한다.
-redirect:/는 /로 돌아가는 것
추가 설명
-mapping된 컨트롤러가 return하는 값은 템플릿에서 찾는다.
-함수의 파라미터로 form을 넘겨주었는데, 이때 스프링이 MemberForm 컴트롤러의 setname 메소드를 통해 form안에 name을 private String name변수에 넣는다. 그래서 getter setter 필수 !
-get은 url에 값 입력(조회할 때 주로 사용), post는 form같은 곳 안에 데이터를 넣어서 전달(등록)할 때 사용
package hello.hellospring.controller;
public class MemberForm {
private String name;
public String getName(){
return name;
}
public void setName(String name){
this.name = name;
}
}
}<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<body>
<div class="container">
<form action="/members/new" method="post">
<div class="form-group">
<label for="name">이름</label>
<input type="text" id="name" name="name" placeholder="이름을
입력하세요">
</div>
<button type="submit">등록</button>
</form>
</div> <!-- /container -->
</body>
</html>
--회원 조회--
@GetMapping("/members")
public String list(Model model){
List<Member> members = memberService.findMembers();
model.addAttribute("members",members);
return "members/memberList";
}
상단의 MemberController에 추가해주면 된다.
memberList.html에서 타임리프(템플릿엔진)가 본격적으로 동작한다.
우선, model에 addAttribute를 통해 members의 값을 모조리 집어넣은 것을 "members"에 저장한다.
${~~~}는 model안에 있는 값을 꺼내주는 기능을 한다.
th:each는 일종의 반복문으로, members에 있는 객체들을 하나씩 꺼내서 member로 가져온다.
그리고 해당 member의 id와 name을 출력해준다.
id와 name 가져올 때도 이들은 모두 private변수이므로 getter,setter를 이용하여 접근한다.(스프링이 알아서 해준다!)
이를 property접근방식이라고 한다.
<!DOCTYPE HTML>
<html xmlns:th="http://www.thymeleaf.org">
<body>
<div class="container">
<div>
<table>
<thead>
<tr>
<th>#</th>
<th>이름</th>
</tr>
</thead>
<tbody>
<tr th:each="member : ${members}">
<td th:text="${member.id}"></td>
<td th:text="${member.name}"></td>
</tr>
</tbody>
</table>
</div>
</div> <!-- /container -->
</body>
</html>
'스프링(JAVA)' 카테고리의 다른 글
스프링 DB 접근 기술 #2 JPA (0) | 2022.09.25 |
---|---|
스프링 DB 접근 기술 #1 JDBC, JDBC Template (0) | 2022.09.25 |
Spring 스프링 빈과 의존관계 (0) | 2022.09.25 |
Spring 회원 관리 예제 - 테스트 코드 (0) | 2022.09.25 |
Spring 회원 관리 예제 (0) | 2022.07.12 |