필드만을 사용하도록 Jackson을 지정하는 방법-전역 적으로


191

기본 jackon 동작은 속성 (getter 및 setter)과 필드를 모두 사용하여 json을 직렬화하고 역 직렬화하는 것으로 보입니다.

필드를 직렬화 구성의 정식 소스로 사용하고 싶기 때문에 잭슨이 속성을 전혀 보지 않기를 바랍니다.

주석을 사용하여 개별 클래스 별로이 작업을 수행 할 수 있습니다.

 @JsonAutoDetect(fieldVisibility = Visibility.ANY, getterVisibility = Visibility.NONE, setterVisibility = Visibility.NONE)

그러나 나는 이것을 모든 단일 수업에 배치하고 싶지는 않습니다 ...

이것을 전역 적으로 구성 할 수 있습니까? 객체 매퍼에 일부를 추가하는 것처럼?


1
팀은 좋은 대답을했습니다. 또 다른 가능성은 공통 기본 클래스가있는 경우 클래스 주석을 해당 클래스에 넣을 수 있다는 것입니다. 주석은 Jackson에 의해 상속됩니다.
StaxMan

1
나는 그것을 시도했다고 생각하지만, 기본 사례가 정의한 것을 사용하도록 하위 클래스에 지시 해야하는 것 같습니다 ...
Michael Wiles

2
하위 클래스가 클래스 주석을 재정의하지 않는 한 상위 클래스의 주석은 하위 클래스 정의의 일부인 것처럼 보입니다 (그렇지 않으면 버그 일 수 있습니다). 이것이 JDK가 주석을 처리하는 방식 일 필요는 없지만 Jackson은 주석에 대한 전체 상속을 구현합니다 (메소드 주석에 대해서도).
StaxMan

INFER_PROPERTY_MUTATORS깃발을 조심하십시오 . 보이는 게터 또는 필드가있는 경우 세터의 가시성을 강제로 설정합니다.
Ondra Žižka

답변:


157

다음과 같이 개별 ObjectMappers를 구성 할 수 있습니다.

ObjectMapper mapper  = new ObjectMapper();
mapper.setVisibility(mapper.getSerializationConfig().getDefaultVisibilityChecker()
                .withFieldVisibility(JsonAutoDetect.Visibility.ANY)
                .withGetterVisibility(JsonAutoDetect.Visibility.NONE)
                .withSetterVisibility(JsonAutoDetect.Visibility.NONE)
                .withCreatorVisibility(JsonAutoDetect.Visibility.NONE));

전역으로 설정하려면 일반적으로 래퍼 클래스를 통해 구성된 매퍼에 액세스합니다.


3
검사기를 설정해야 할 수도 있지만 (withXxx () 메서드는 일반적으로 새 객체를 만듭니다) 좋습니다. 그래서 'mapper.setVisibilityChecker (mapper.getVisibilityChecker (). with ...);'와 같은 것
StaxMan

setVisibilityChecker에 @StaxMan 좋은 전화, 나는 반영하기 위해 답변을 편집했습니다.
Kevin Bowersox

42
withGetterVisibility수행은 포함되지 is*방법을하지만, 거기에 withIsGetterVisibility그들을 위해.
qerub

13
setVisibilityChecker더 이상 사용되지 않습니다. setVisibility대신 사용하십시오 .
0x7d7b

1
이것은 내가 필요한 것입니다! 이 구성을 통해 Mixin을 사용하여 Hibernate 엔티티를 DTO로 쉽게 변환 할 수있었습니다. 기본적으로 ObjectMapper는 모든 것을 직렬화하고 Mixin은 무시할 속성을 지정해야합니다 (즉, 교차 대신 빼기).
TastyWheat

150

Jackson 2.0 이상에서는 다음을 간단히 사용할 수 있습니다.

import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.PropertyAccessor;
import com.fasterxml.jackson.databind.ObjectMapper;   

...

ObjectMapper mapper = new ObjectMapper();    
mapper.setVisibility(PropertyAccessor.ALL, Visibility.NONE);
mapper.setVisibility(PropertyAccessor.FIELD, Visibility.ANY);

자동 감지 기능을 해제합니다.


1
안녕하세요, Jackson 1.9.0 jar를 사용하고 있습니다. 객체를 json 문자열로 직렬화하는 동안 추가 json 속성이 표시됩니다. @JsonProperty로 언급 된 변수 만 포함하는 json 문자열을 가져와야합니다. 이것 좀 도와 주실 래요?
jrhamza

7
OP 질문에 언급 된 클래스 주석으로 시작할 수 있습니다. @JsonAutoDetect(fieldVisibility = Visibility.NONE, getterVisibility = Visibility.NONE, setterVisibility = Visibility.NONE)다음으로 포함 할 각 속성에 주석을 @JsonProperty
달아야합니다

감사! 이전에는 PropertyAccessor 대신 JsonMethod가 참조 된 많은 코드 예제를 발견했습니다. JsonMethod를 검색하면 PropertyAccessor에 대한 링크가 거의없는 경우 ... 후속 아티팩트에서 대체 클래스 이름을 찾는 가장 좋은 방법은 무엇입니까? 힘들고 불쾌 할 수 있습니까?
philburns

38

boolean is*()게터를 위해 특별히 :

나는 왜 아래에 많은 시간을 보냈지

  @JsonAutoDetect(fieldVisibility = Visibility.ANY, getterVisibility = Visibility.NONE, setterVisibility = Visibility.NONE)

이건

  setVisibility(PropertyAccessor.SETTER, JsonAutoDetect.Visibility.NONE);
  setVisibility(PropertyAccessor.GETTER, JsonAutoDetect.Visibility.NONE);
  setVisibility(PropertyAccessor.FIELD, JsonAutoDetect.Visibility.ANY);

부울 Getter / Setter에서 일했습니다.

해결책은 간단합니다.

  @JsonAutoDetect(isGetterVisibility = Visibility.NONE, ...          
  setVisibility(PropertyAccessor.IS_GETTER, JsonAutoDetect.Visibility.NONE);

업데이트 : 스프링 부트 허용 구성 :

jackson:
  visibility.field: any
  visibility.getter: none
  visibility.setter: none
  visibility.is-getter: none

참조 일반적인 응용 프로그램 속성 # JACKSON


1
Bean 클래스에 간단한 솔루션을 적용하는 방법을 자세히 설명해 주시겠습니까?
Pavel Niedoba

1
감사합니다. 그것은 Getter가 나를 위해 하루를 구했습니다.
grinch

이것은 질문에 대한 답변이 아니며 오해의 소지가 있습니다.
Ondra Žižka

14

jackson 1.9.10의 경우 사용합니다

ObjectMapper mapper = new ObjectMapper();

mapper.setVisibility(JsonMethod.ALL, Visibility.NONE);
mapper.setVisibility(JsonMethod.FIELD, Visibility.ANY);

자동 제거 기능을 켜십시오.


2
그 방법입니다. 감사.
cuneytykaya

이를 수행하는 것과 "자동 감지"를 비활성화하는 것 사이에 차이점이 있는지 궁금합니다.
xenoterracide

10

어떻습니까 : 믹스 인과 함께 사용했습니다.

비준수 객체

@Entity
@Getter
@NoArgsConstructor
public class Telemetry {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long pk;
    private String id;
    private String organizationId;
    private String baseType;
    private String name;
    private Double lat;
    private Double lon;
    private Instant updateTimestamp;
}

믹스 인 :

@JsonAutoDetect(fieldVisibility = ANY, getterVisibility = NONE, setterVisibility = NONE)
public static class TelemetryMixin {}

용법:

    ObjectMapper om = objectMapper.addMixIn(Telemetry.class, TelemetryMixin.class);
    Telemetry[] telemetries = om.readValue(someJson, Telemetry[].class);

당신이 클래스를 가르 칠 수없고 같은 믹스 인을 적용 할 수 없다는 말은 없습니다.

믹스 인에 익숙하지 않다면, 그것들은 개념적으로 간단합니다 : 믹스 인의 구조는 (JVM에 관한 한 잭슨에 따르면) 대상 클래스에 슈퍼 임 포즈 됩니다.


3

의 구성에 대해 걱정하지 않고 전 세계적 으로이 작업을 수행하는 방법을 원한다면 ObjectMapper고유 한 주석을 만들 수 있습니다.

@Target({ElementType.ANNOTATION_TYPE, ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@JacksonAnnotationsInside
@JsonAutoDetect(
        getterVisibility = JsonAutoDetect.Visibility.NONE, isGetterVisibility = JsonAutoDetect.Visibility.NONE,
        setterVisibility = JsonAutoDetect.Visibility.NONE, fieldVisibility = JsonAutoDetect.Visibility.NONE,
        creatorVisibility = JsonAutoDetect.Visibility.NONE
)
public @interface JsonExplicit {
}

이제 수업에 주석을 달아야합니다 @JsonExplicit.

또한 위의 호출을 편집하여 @JsonAutoDetect값이 프로그램에서 작동하는 값으로 설정되어 있는지 확인하십시오.

에 신용 https://stackoverflow.com/a/13408807 저를 도와 주셔서 대해 알아@JacksonAnnotationsInside


3

Spring Boot를 사용하는 경우 다음과 같이 Jackson을 전역 적 으로 구성 할 수 있습니다 .

import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.PropertyAccessor;
import org.springframework.boot.autoconfigure.jackson.Jackson2ObjectMapperBuilderCustomizer;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.converter.json.Jackson2ObjectMapperBuilder;

@Configuration
public class JacksonObjectMapperConfiguration implements Jackson2ObjectMapperBuilderCustomizer {

    @Override
    public void customize(Jackson2ObjectMapperBuilder jacksonObjectMapperBuilder) {
        jacksonObjectMapperBuilder.visibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.NONE);
        jacksonObjectMapperBuilder.visibility(PropertyAccessor.FIELD, JsonAutoDetect.Visibility.ANY);
        jacksonObjectMapperBuilder.visibility(PropertyAccessor.CREATOR, JsonAutoDetect.Visibility.ANY);
    }

}
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.