[java] Spring @ResponseBody 주석은 어떻게 작동합니까?

다음과 같은 방법으로 주석이 달린 메서드가 있습니다.

/**
* Provide a list of all accounts.
*/
//  TODO 02: Complete this method.  Add annotations to respond
//  to GET /accounts and return a List<Account> to be converted.
//  Save your work and restart the server.  You should get JSON results when accessing 
//  http://localhost:8080/rest-ws/app/accounts
@RequestMapping(value="/orders", method=RequestMethod.GET)
public @ResponseBody List<Account> accountSummary() {
    return accountManager.getAllAccounts();
}

그래서 저는이 주석으로 알고 있습니다.

@RequestMapping(value="/orders", method=RequestMethod.GET)

이 메서드 는 URL / orders로 표시되는 리소스에 대한 GET HTTP 요청을 처리 합니다 .

이 메서드는 List 를 반환하는 DAO 개체를 호출합니다 .

여기서 Account 는 시스템의 사용자를 나타내며 다음과 같이이 사용자를 나타내는 일부 필드가 있습니다.

public class Account {

    @Id
    @Column(name = "ID")
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    private Long entityId;

    @Column(name = "NUMBER")
    private String number;

    @Column(name = "NAME")
    private String name;

    @OneToMany(cascade=CascadeType.ALL)
    @JoinColumn(name = "ACCOUNT_ID")
    private Set<Beneficiary> beneficiaries = new HashSet<Beneficiary>();

    ...............................
    ...............................
    ...............................
}

내 질문은 : 주석 이 정확히 어떻게 @ResponseBody작동합니까?

반환 된 List<Account>객체 앞에 위치하므로이 목록을 참조한다고 생각합니다. 코스 문서에는이 주석이 다음과 같은 기능을 제공한다고 명시되어 있습니다.

결과가 HTTP 메시지 변환기 (MVC보기 대신)에 의해 HTTP 응답에 기록되는지 확인하십시오.

또한 공식 Spring 문서에서 읽기 : http://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/web/bind/annotation/ResponseBody.html

그것은 List<Account>객체를 가져 와서 Http Response. 이것이 맞습니까 아니면 오해입니까?

이전 accountSummary()방법 의 주석 에는 다음이 기록됩니다.

http : // localhost : 8080 / rest-ws / app / accounts에 액세스 할 때 JSON 결과를 받아야
합니다.

이것이 정확히 무엇을 의미합니까? 것을 그것은 뜻 List<Account>에 의해 반환 된 객체 accountSummary()메소드가 자동으로 변환되어 JSON포맷 한 다음에 넣어 Http Response? 또는 무엇을?

이 어설 션이 참이면 개체가 자동으로 JSON형식 으로 변환되도록 지정하는 곳은 어디 입니까? @ResponseBody주석이 사용될 때 표준 형식이 채택 됩니까 아니면 다른 곳에 지정되어 있습니까?



답변

우선, 주석은 주석을 달지 않습니다 List. 마찬가지로 방법에 주석을 답니다 RequestMapping. 귀하의 코드는

@RequestMapping(value="/orders", method=RequestMethod.GET)
@ResponseBody
public List<Account> accountSummary() {
    return accountManager.getAllAccounts();
}

이제 주석이 의미하는 것은 메서드의 반환 된 값이 HTTP 응답의 본문을 구성한다는 것입니다. 물론 HTTP 응답에는 Java 개체가 포함될 수 없습니다. 따라서이 계정 목록은 REST 애플리케이션에 적합한 형식 (일반적으로 JSON 또는 XML)으로 변환됩니다.

형식의 선택은의 값에 설치된 메시지 컨버터에 따라 produces속성@RequestMapping주석, 클라이언트가 받아들이는 콘텐츠 형식에 (즉, HTTP 요청 헤더에서 사용할 수 있습니다). 예를 들어, 요청이 XML을 받아들이지 만 JSON은 받아들이지 않는다고 말하고 목록을 XML로 변환 할 수있는 메시지 변환기가 설치되어있는 경우 XML이 반환됩니다.


답변

이해해야 할 첫 번째 기본 사항은 아키텍처의 차이입니다.

한쪽 끝에는 웹 페이지를 사용하는 일반 웹 앱을 기반으로하는 MVC 아키텍처가 있으며 브라우저는 페이지를 요청합니다.

Browser <---> Controller <---> Model
               |      |
               +-View-+

브라우저가 요청을하고 컨트롤러 (@Controller)가 모델 (@Entity)을 가져 와서 모델에서보기 (JSP)를 생성하고보기가 클라이언트로 다시 반환됩니다. 이것이 기본 웹 앱 아키텍처입니다.

반면에 RESTful 아키텍처가 있습니다. 이 경우에는보기가 없습니다. 컨트롤러는 모델 (또는보다 RESTful 용어로 리소스 표현) 만 다시 보냅니다. 클라이언트는 JavaScript 애플리케이션, Java 서버 애플리케이션, REST API를 노출하는 모든 애플리케이션이 될 수 있습니다. 이 아키텍처를 통해 클라이언트는이 모델로 수행 할 작업을 결정합니다. 예를 들어 트위터를 보자. Twitter as the Web (REST) ​​API는 애플리케이션이 API를 사용하여 상태 업데이트와 같은 정보를 얻을 수 있도록하여 해당 데이터를 애플리케이션에 넣을 수 있도록합니다. 해당 데이터는 JSON과 같은 형식으로 제공됩니다.

즉, Spring MVC로 작업 할 때 기본 웹 애플리케이션 아키텍처를 처리하기 위해 처음 빌드되었습니다. 우리의 메소드에서 뷰를 생성 할 수있는 다양한 메소드 시그니처 플레이버가있을 수 있습니다. 메서드 ModelAndView는 명시 적으로 생성 한 위치를 반환 하거나 모델 속성으로 설정되는 임의의 객체를 반환 할 수있는 암시 적 방법이 있습니다. 그러나 어느 쪽이든 요청-응답주기의 어딘가에 뷰가 생성됩니다.

그러나를 사용할 때 우리 @ResponseBody는 뷰가 생성되는 것을 원하지 않는다는 의미입니다. 지정하는 형식에 관계없이 반환 객체를 본문으로 보내려고합니다. (가능하지만) 직렬화 된 Java 객체가되는 것을 원하지 않습니다. 따라서 예, 다른 일반적인 유형으로 변환해야합니다 (이 유형은 일반적으로 콘텐츠 협상을 통해 처리됩니다. 아래 링크 참조). 솔직히 여기저기서 다루지 만 Spring과 많이 일하지 않는다. 일반적으로 나는

@RequestMapping(..., produces = MediaType.APPLICATION_JSON_VALUE)

콘텐츠 유형을 설정하지만 JSON이 기본값 일 수 있습니다. 저를 인용하지 마십시오.하지만 JSON을 받고 있고을 지정하지 않은 경우 produces기본값 일 수 있습니다. JSON은 유일한 형식이 아닙니다. 예를 들어, 위의 쉽게 XML로 전송 될 수 있지만, 당신은이해야 producesMediaType.APPLICATION_XML_VALUE나는 당신이를 구성 할 필요가 생각 HttpMessageConverterJAXB를 위해. MappingJacksonHttpMessageConverter구성된 JSON의 경우 클래스 경로에 Jackson이있을 때.

콘텐츠 협상 에 대해 배우려면 시간이 좀 걸릴 것 입니다. REST의 매우 중요한 부분입니다. 다양한 응답 형식과이를 방법에 매핑하는 방법을 배우는 데 도움이됩니다.


답변

또한 반환 유형은 다음과 같이 결정됩니다.

  1. HTTP 요청이 원하는 내용-Accept 헤더에서. Accept가 무엇으로 설정되어 있는지 확인하기 위해 초기 요청을 살펴보십시오.

  2. HttpMessageConverters Spring이 설정하는 것. Spring MVC는 Jackson 라이브러리가 클래스 경로에있는 경우 XML (JAXB 사용) 및 JSON에 대한 변환기를 설정합니다.

선택 사항이 있으면 하나를 선택합니다.이 예에서는 JSON이됩니다.

이것은 되는 과정을 노트에 덮여. 메시지 변환기 및 콘텐츠 협상에 대한 참고 사항을 찾으십시오.


답변