복붙노트

[SPRING] 스프링 레스트 컨트롤러는 특정 필드를 반환합니다.

SPRING

스프링 레스트 컨트롤러는 특정 필드를 반환합니다.

Spring MVC를 사용하여 JSON API를 디자인하는 최선의 방법을 모색 해왔다. 우리 모두 IO는 비싸다는 것을 알고 있으므로 클라이언트가 필요한 것을 얻기 위해 여러 API 호출을하고 싶지는 않습니다. 그러나 동시에 나는 부엌 수채를 반드시 돌려 보내고 싶지 않다.

예를 들어 IMDB와 비슷한 게임 API를 사용하고 있지만 대신 비디오 게임을 사용했습니다.

게임에 연결된 모든 것을 반환하면 다음과 같이 보일 것입니다.

/ fire / game / 1

{
    "id": 1,
    "title": "Call of Duty Advanced Warfare",
    "release_date": "2014-11-24",
    "publishers": [
        {
            "id": 1,
            "name": "Activision"
        }
    ],
    "developers": [
        {
            "id": 1,
            "name": "Sledge Hammer"
        }
    ],
    "platforms": [
        {
            "id": 1,
            "name": "Xbox One",
            "manufactorer": "Microsoft",
            "release_date": "2013-11-11"
        },
        {
            "id": 2,
            "name": "Playstation 4",
            "manufactorer": "Sony",
            "release_date": "2013-11-18"
        },
        {
            "id": 3,
            "name": "Xbox 360",
            "manufactorer": "Microsoft",
            "release_date": "2005-11-12"
        }
    ],
    "esrbRating": {
        "id": 1,
        "code": "T",
        "name": "Teen",
        "description": "Content is generally suitable for ages 13 and up. May contain violence, suggestive themes, crude humor, minimal blood, simulated gambling and/or infrequent use of strong language."
    },
    "reviews": [
        {
            "id": 1,
            "user_id": 111,
            "rating": 4.5,
            "description": "This game is awesome"
        }
    ]
}

그러나 그들은이 모든 정보를 필요로하지 않을 수도 있지만, 다시는 그렇게 할 수도 있습니다. 모든 것을 요구하는 것은 I / O와 성능에서 나쁜 생각처럼 보입니다.

요청에 include 매개 변수를 지정하여이를 수행하려고 생각했습니다.

예를 들어 예를 들어, include를 지정하지 않은 경우 다시 얻는 것이 모두 다음과 같습니다.

{
    "id": 1,
    "title": "Call of Duty Advanced Warfare",
    "release_date": "2014-11-24"
}

그러나 당신은 당신의 요청이 이와 같이 보일 것이라는 모든 정보를 원합니다.

/api/game/1?include=publishers,developers,platforms,reviews,esrbRating

이 방법으로 클라이언트는 원하는 정보의 양을 지정할 수 있습니다. 그러나 나는 스프링 MVC를 사용하여이를 구현하는 최선의 방법을 잃어 버렸습니다.

나는 컨트롤러가 이와 같이 보일 것이라고 생각하고있다.

public @ResponseBody Game getGame(@PathVariable("id") long id, 
    @RequestParam(value = "include", required = false) String include)) {

        // check which include params are present

        // then someone do the filtering?
}

게임 개체를 어떻게 선택적으로 직렬화할지 잘 모르겠습니다. 이것도 가능합니다. Spring MVC에서 이것을 접근하는 가장 좋은 방법은 무엇입니까?

참고로, 잭슨을 직렬화에 포함하고있는 스프링 부트를 사용하고 있습니다.

해결법

  1. ==============================

    1.Game 객체를 반환하는 대신지도 처럼 직렬화 할 수 있습니다. 여기서지도 키는 속성 이름을 나타냅니다. 따라서 include 매개 변수에 따라지도에 값을 추가 할 수 있습니다.

    Game 객체를 반환하는 대신지도 처럼 직렬화 할 수 있습니다. 여기서지도 키는 속성 이름을 나타냅니다. 따라서 include 매개 변수에 따라지도에 값을 추가 할 수 있습니다.

    @ResponseBody
    public Map<String, Object> getGame(@PathVariable("id") long id, String include) {
    
        Game game = service.loadGame(id);
        // check the `include` parameter and create a map containing only the required attributes
        Map<String, Object> gameMap = service.convertGameToMap(game, include);
    
        return gameMap;
    
    }
    

    예를 들어 Map 이 다음과 같이있는 경우 :

    gameMap.put("id", game.getId());
    gameMap.put("title", game.getTitle());
    gameMap.put("publishers", game.getPublishers());
    

    다음과 같이 직렬화됩니다.

    {
      "id": 1,
      "title": "Call of Duty Advanced Warfare",
      "publishers": [
        {
            "id": 1,
            "name": "Activision"
        }
      ]
    }
    
  2. ==============================

    2.내 대답은 아주 늦다는 것을 알고 있기 때문에 나는 Projections를 보길 권한다.

    내 대답은 아주 늦다는 것을 알고 있기 때문에 나는 Projections를 보길 권한다.

    당신이 요구하는 것은 예측에 관한 것입니다.

    당신이 봄에 대해 묻기 때문에 나는이 것을 시도해 볼 것입니다 : https://docs.spring.io/spring-data/rest/docs/current/reference/html/#projections-excerpts

  3. from https://stackoverflow.com/questions/30558784/spring-rest-controller-return-specific-fields by cc-by-sa and MIT license