h2 db 에 member 정보 2개 정도 입력을 해보고나서
Controller, Service, Repository, 3-tier 를 이용해서 data 를 서로 어떻게 연결하는지 확인해보자.
입력을 해주고 나서, Run Selected 를 눌러주자.
select * from member, member의 모든 것(*) 을 불러오는 것 까지 해봤다.
행 하나를 추가해보자.
실행을 할 때, 드래그해서 선택한 후에 run, 그래서 Run Selected 라는 것.
자, 이제 우리가 만들어야 하는 건,
FrontController, HandlerMapping, ViewResolver 는 framework에서 제공해주는 것이라서
우리는 Controller, Service, Repository 를 만들어서 연결해서 쓰는 것.
먼저 정리를 좀 해보자면,
Controller - HomeController
Service - HomeService 라는 interface가 하나 있고, impl 구현체가 하나가 있다
Repository - 는 JpaRepository 에서 제공해주는 interface를 상속받아가지고 HomeRepository 라는 interface를 만들어놓았다.
참고 - @Repository 어노테이션은 생략이 가능하다.
왜냐면 repository에 오는 건 거의 다 interface 만 오게 될 것이다. 다른 class 를 넣지 않는다.
그래서 일반적으로 repository 패키지 안에는 interface 들이 일반적으로 오기 때문에
자동으로 스캔을 해가지고 메모리에 올리게 되어 있기 때문임.
자, 이제 HomeController로 가보자.
클라이언트 요청을 받을 때 @GetMapping("/memberList")
view가 있는 형태로 갈려면, public String 으로 해줘야 한다. String 을 리턴 해줘야 하는데, 그 이유는?
public String을 사용하는 이유는 컨트롤러 메서드가 뷰(view)의 이름을 반환하기 때문입니다.
설명
- Spring MVC에서 @GetMapping과 같은 어노테이션은 클라이언트의 요청을 컨트롤러 메서드에 매핑합니다.
- 메서드 반환 타입이 public String이면, 이 반환값은 뷰의 이름으로 해석됩니다.
- 뷰는 주로 HTML 파일이나 JSP 파일과 같은 화면 파일입니다.
- Spring은 반환된 뷰 이름을 바탕으로 해당 뷰 파일을 찾아서 화면에 표시합니다.
- 따라서 public String을 사용하면 메서드의 반환값이 화면을 렌더링할 파일의 이름이 됩니다.
- 클라이언트가 /memberList로 요청을 보내면,
- showMemberList() 메서드가 실행되고,
- "memberList"라는 문자열이 반환됩니다.
- Spring은 이 반환값을 보고 memberList.html 또는 memberList.jsp와 같은 파일을 찾아 렌더링한 뒤 클라이언트에게 화면을 보여줍니다. (여기서는 JSP 가 아니고 Thymeleaf 로 할거니까 html)
핵심 포인트
- 메서드의 반환 타입이 String이면 뷰의 이름을 반환합니다.
- 반환된 뷰 이름에 따라 Spring이 적절한 뷰 파일을 찾아 클라이언트에게 화면을 렌더링합니다.
이와 같은 구조 덕분에 요청에 대한 결과를 화면(View)으로 반환할 수 있습니다.
이 때는 ViewResolver가 필요가 없다. view 가 들어갈 디렉토리는, templates에 들어갈 것.
이제 컨트롤러는 서비스한테 회원 전체 목록 요청을 해야 한다.
그러면 HomeService 를 손봐야 한다.
서비스 인터페이스를 이제 임플리멘테이션 했으니까 오버라이드를 해줘야 한다.
Impl 로 가보면, 마우스를 가져다가 가만히 있으면, 임플리먼트할 메서드를 선택하라고 뜬다.
지금 여기서 자동으로 return 을 List.of() 이라고 했다.
하지만 여기서는, repository 에 있는 메서드를 이용해서 DB 에서 회원 전체의 목록을 받아서 리턴을 해줘야 한다.
일단 repository를 손보기 전에, return null 로 바꿔주자.
Jpa에서 DB 의 Member 테이블에 있는 전체 목록을 가지고 오려면,
메서드를 만들어야 하는데, 만들 필요가 없다.
JpaRepository 에 전체 목록을 가지고 오는 메서드, findAll 이라는 메서드를 제공해주고 있다.
EntityManagerFactory 는 구현체인데, EntityManagerFactory 가 HomeRepository 라는 인터페이스를 자동으로 상속 받아가지고, 인터페이스 안에 있는 메서드를 구현을 한다.
그럼 findAll 은 무엇을 하냐면, SQL 을 뭔가 내부적으로 만들 것.
어레이 리스트 List<Member> 에다가 전체 회원 목록을 묶어가지고 return 을 해줄 것.
findAll 구현체를 우리가 직접 만드는 게 아니다. 이미 다 만들어져있다.
지금 HomeRepository 에 보면 아무것도 입력해놓은게 없지만, findAll을 쓰면 전체회원목록을 가지고 갈 수 있다는 것.
DB 쪽은 이해만 한다면, 간단하게 끝이 난다. extends JpaRepository 만, extends 로 상속받으면 끝이다. 구현체가 다 만들어지기 때문.
이제 다시 service 로 가보자. service 는 repository가 필요하다.
HomeServiceImpl 서비스 클래스는 HomeRepository 객체가 필요해서,
@Autowired 해서 Dependancy Injection (의존선 주입) 기법으로 메모리에 올라와 있는 HomeRepository 객체를 연결해가지고 사용을 하는 것.
그럼 이제 이 서비스는 누가 연동하는 것인가?
HomeController는 이제 service가 필요하다.
List<Member> member = homeService.memberList();
에서, 회원전체목록을 받아낸 member를 view 에서 뿌릴려면,
객체 바인딩을 해야 한다. 객체를 연결해야 한다.
Model model 객체를 생성해가지고 모델에 연결시켜야 한다.
* Model 은 springboot framework의 ui 다.
"member", member - 연결할 객체 이름과 문자열.
지금까지 한 걸 한 번 정리를 하고 넘어가자.
객체 바인딩은 뭔가?
그리고 Autowired 는 뭔가?
간단하게 정리만 하고 넘어가자.
객체 바인딩이란?
- 객체 바인딩은 클라이언트가 보낸 데이터를 객체에 자동으로 연결(바인딩) 하는 것을 의미합니다.
- 주로 Form 데이터나 JSON 데이터를 자바 객체로 변환할 때 사용됩니다.
예시
public class Member {
private String name;
private int age;
// getter, setter
}
@PostMapping("/addMember")
public String addMember(@ModelAttribute Member member) {
// 클라이언트가 보낸 name과 age 값을 Member 객체에 바인딩
System.out.println(member.getName());
return "success";
}
- 클라이언트가 name=John&age=25를 보내면 Member 객체에 자동으로 값이 바인딩됩니다.
@Autowired란?
- @Autowired는 Spring이 객체를 자동으로 주입(Dependency Injection) 해주는 어노테이션입니다.
- 개발자가 객체를 수동으로 생성하지 않아도 Spring이 빈(Bean)을 찾아서 주입해줍니다.
예시
@Service
public class MemberService {
public void printService() {
System.out.println("MemberService 실행");
}
}
@Controller
public class HomeController {
@Autowired
private MemberService memberService;
@GetMapping("/test")
public String test() {
memberService.printService(); // 객체 주입 후 메서드 호출
return "test";
}
}
- @Autowired를 사용하면 MemberService 객체가 자동으로 주입됩니다.
- Spring이 해당 타입의 Bean을 찾아서 연결해 줍니다.
정리
- 객체 바인딩: 클라이언트의 데이터를 자바 객체에 자동으로 연결하는 것.
- @Autowired: 객체(Bean)를 자동으로 주입해주는 어노테이션.
이제, memberList.html 을 templates에다가 만들어야 한다.
그 전에,
이걸 update 로 바꿔줘야, 기존에 만들었던 게 날라가지가 않는다.
run 해보자.
일단, 연결이 된 걸 확인할 수 있다!
select 문이 실행이 된 걸 확인할 수 있다.
그런데 우리는 쿼리를 작성한 적이 없지만, findAll 이라는 메서드가 select 하고 연관이 되어 있다.
findAll() 하게 되면은 Hibernate 가 findAll 을 select 메서드로 generation 해서 처리해가지고 return 해주기 때문에,
findAll 이 호출되게 되면은, 내부적으로 저렇게 select 문이 만들어지는 것.
이제, html 에다가, 회원 목록을 실제로 뿌려주면 되겠다.
그건 다음 게시물로 넘어가도록 하겠다.
'Spring Boot (+ RESTful)' 카테고리의 다른 글
Spring Boot - Starter / MVN Repository / (0) | 2024.12.15 |
---|---|
Spring Boot - '프로젝트 구조 이해' / 데이터 흐름에 대한 이해 / Thymeleaf에 대한 이해 / view 처리 (0) | 2024.12.14 |
Spring Boot - H2 Database - DB 연결 / Entity / Hibernate / Lombok (2) | 2024.12.13 |
Spring Boot - POJO = Controller? / 3-tier Architecture / (2) | 2024.12.13 |
Spring Boot - @EnableAutoConfiguration의 동작 원리 / @ComponentScan의 동작 원리 (0) | 2024.12.13 |