Spring 4.3부터 그런 규칙이 적용된다.
No default Constuctor: 생성자가 여러 개 overloading 될 수 밖에 없게 @Autowired가 여러 생성자 중 어느 것에도 안 붙었을 경우
@Qualifer, @Primary 등으로 특정 이름의 bean 주입도 가능하다.
@Primary: 이렇게 정의된 애를 먼저 데려가세요, 하고 적어두는 것. 동일 타입의 bean이 여러 개 있을 때, 얘가 대표니까 데려가세요, 하는 것.
Field Injection은 최대한 비추합니다.
@Component: 일반적인 bean
@Controller: Spring MVC에서 Controller로 사용
@Service: Service 단으로 사용
@Repository: DAO, Persistence로 사용
Inversion of Control을 활용해 스프링 컨테이너에서는 주입받는 객체가 먼저 생성되고, 의존하는 객체를 나중에 생성하여 주입한다.
DI 설정 시 순환 참조(dependency cycle) 발생하지 않도록 주의해야 한다.
부트설정파일 application.properties에 있는 value를 가져올 수 있다.
Lombok의 Value와 헷갈려서 import하면 안된다.
environment: 개발환경이냐, 프로덕션 환경이냐를 나눌 때 쓰게 되는 변수. Boot의 등장 이전에 많이 썼던 환경변수
M: Model - Data
V: View - 사용자와의 interaction
C: Controller - 사용자 입력 처리, 출력 과정 컨트롤
Model
Controller
@RequestMapping
ViewResolver
- view file(template)을 찾아낸다
- prefix + "home" + suffix
- template/views/ + "home" + ".html"
- ViewResolver가 선택한 "template file", "Model Data"는 설정된 Template Engine(Thymeleaf, Mustache)에 넘어간다.
- Template engine: Template file + Data -> response할 데이터 생성
@HttpServletRequest (request 객체)
@ResponseBody
라우팅->request mapping
HttpEntity<T>
RequestEntity<T>
ResponseEntity<T>
// HttpEntity<T> 리턴 : T 는 response 할 body 의 타입
@RequestMapping("http01")
@ResponseBody
public HttpEntity<String> http01() {
String body = str1;
HttpEntity<String> entity = new HttpEntity<>(body); // HttpEntity(body)
return entity;
// 기본적으로 text/html;charset=UTF-8 로 response 된다.
}
// HttpHeaders : header 세팅 가능
@RequestMapping("http02")
@ResponseBody
public HttpEntity<String> http02() throws UnsupportedEncodingException {
HttpHeaders headers = new HttpHeaders();
//headers.setContentType(MediaType.TEXT_PLAIN); // text/plain 으로 response
headers.setContentType(new MediaType("text", "plain", Charset.forName("UTF-8")));
//headers.add("Content-type", "text/plain;charset=utf-8");
headers.add("user-secret", "xxxxx");
//headers.add("my-team", "삼성라이온즈"); // 에러, 헤더 정보는 반드시 url encoding 되어야 한다.
headers.add("my-team", URLEncoder.encode("삼성라이온즈", "utf-8"));
String body = str1;
HttpEntity<String> entity = new HttpEntity<>(body, headers); // HttpEntity(body, headers)
return entity;
}
// 일반적으로 response 로서 HttpEntity<T> 보다는 ResponseEntity<T> 사용
@RequestMapping("http03")
@ResponseBody
public ResponseEntity<String> http03() {
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON); // "application/json"
String body = jsonArr[0];
ResponseEntity<String> entity;
//entity = new ResponseEntity<>(body, headers, HttpStatus.OK); // (body, header, response code)
entity = ResponseEntity.ok().headers(headers).body(body);
return entity;
}
// body 에는 어떠한 Java 객체도 가능
@RequestMapping("http04")
@ResponseBody
public ResponseEntity<HomeController1.Product> http04() {
HomeController1.Product product = new HomeController1.Product(10, "자전거", false);
return new ResponseEntity<>(product, HttpStatus.OK);
// <T> 타입 명시하기 귀찮다.. 자주 바뀌기도 하고..
}
// type parameter 를 ? (혹은 Object) 로 작성해두면 편리하다 (일반적으로 많이 쓰임)
// ※ 개발단계에서 response body 의 타입은 유동적으로 변할수 있기 때문이다.
@RequestMapping("http05")
@ResponseBody
public ResponseEntity<?> http05() {
var product = new HomeController1.Product(10, "자전거", false);
return new ResponseEntity<>(product, HttpStatus.OK); // (body, statusCode)
}
// 다양한 statusCode 값 명시하여 response 가능.
@RequestMapping("http06")
@ResponseBody
public ResponseEntity<?> http06() {
return
//new ResponseEntity<>(null, HttpStatus.BAD_REQUEST);
//ResponseEntity.badRequest().build();
new ResponseEntity<>(null, HttpStatus.NOT_FOUND);
}
(/member/action/*/*/**)
(/member/*.do)
@Controller
@RequestMapping("/member") // ← 이 컨트롤러는 "/member" 로 시작하는 url 에 매핑된다.
public class MemberController {
@RequestMapping("/save") // URL mapping → /member + /save => /member/save
public String saveMember(){
return "member/save";
}
@RequestMapping("/load") // /member + /load => /member/load
public void loadMember(){
// return "/member/load" 를 리턴한것과 동일
}
// @RequestMapping("/search") // /member/search
// public void searchMember(){
// // url mapping 중복 시, server 가동 시 죽음!
// }
}