• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 package com.fasterxml.jackson.databind.introspect;
2 
3 import java.util.Objects;
4 
5 import com.fasterxml.jackson.annotation.*;
6 import com.fasterxml.jackson.annotation.JsonAutoDetect.Visibility;
7 
8 import com.fasterxml.jackson.core.*;
9 
10 import com.fasterxml.jackson.databind.*;
11 import com.fasterxml.jackson.databind.introspect.VisibilityChecker;
12 
13 public class TestAutoDetect
14     extends BaseMapTest
15 {
16     static class PrivateBean {
17         String a;
18 
PrivateBean()19         private PrivateBean() { }
20 
PrivateBean(String a)21         private PrivateBean(String a) { this.a = a; }
22     }
23 
24     // test for [databind#1347], config overrides for visibility
25     @JsonPropertyOrder(alphabetic=true)
26     static class Feature1347SerBean {
27         public int field = 2;
28 
getValue()29         public int getValue() { return 3; }
30     }
31 
32     // let's promote use of fields; but not block setters yet
33     @JsonAutoDetect(fieldVisibility=Visibility.NON_PRIVATE)
34     static class Feature1347DeserBean {
35         int value;
36 
setValue(int x)37         public void setValue(int x) {
38             throw new IllegalArgumentException("Should NOT get called");
39         }
40     }
41 
42     // [databind#1947]
43     static class Entity1947 {
44         public int shouldBeDetected;
45         public String shouldNotBeDetected;
46 
47         @JsonProperty
getShouldBeDetected()48         public int getShouldBeDetected() {
49             return shouldBeDetected;
50         }
51 
setShouldBeDetected(int shouldBeDetected)52         public void setShouldBeDetected(int shouldBeDetected) {
53             this.shouldBeDetected = shouldBeDetected;
54         }
55 
getShouldNotBeDetected()56         public String getShouldNotBeDetected() {
57             return shouldNotBeDetected;
58         }
59 
setShouldNotBeDetected(String shouldNotBeDetected)60         public void setShouldNotBeDetected(String shouldNotBeDetected) {
61             this.shouldNotBeDetected = shouldNotBeDetected;
62         }
63     }
64 
65     // For [databind#2789]
66 
67     @SuppressWarnings("unused")
68     @JsonAutoDetect(
69         getterVisibility = JsonAutoDetect.Visibility.NONE,
70         creatorVisibility = JsonAutoDetect.Visibility.NONE,
71         isGetterVisibility = JsonAutoDetect.Visibility.NONE,
72         fieldVisibility = JsonAutoDetect.Visibility.NONE,
73         setterVisibility = JsonAutoDetect.Visibility.NONE)
74     @JsonTypeInfo(
75         use = JsonTypeInfo.Id.NAME,
76         include = JsonTypeInfo.As.PROPERTY,
77         property = "type",
78         visible = true)
79     @JsonSubTypes({
80         @JsonSubTypes.Type(name = "CLASS_A", value = DataClassA.class)
81     })
82     private static abstract class DataParent2789 {
83 
84         @JsonProperty("type")
85         @JsonTypeId
86         private final DataType2789 type;
87 
DataParent2789()88         DataParent2789() {
89             super();
90             this.type = null;
91         }
92 
DataParent2789(final DataType2789 type)93         DataParent2789(final DataType2789 type) {
94             super();
95             this.type = Objects.requireNonNull(type);
96         }
97 
getType()98         public DataType2789 getType() {
99             return this.type;
100         }
101     }
102 
103     private static final class DataClassA extends DataParent2789 {
DataClassA()104         DataClassA() {
105             super(DataType2789.CLASS_A);
106         }
107     }
108 
109     private enum DataType2789 {
110         CLASS_A;
111     }
112 
113     /*
114     /********************************************************
115     /* Unit tests
116     /********************************************************
117      */
118 
119     private final ObjectMapper MAPPER = newJsonMapper();
120 
testPrivateCtor()121     public void testPrivateCtor() throws Exception
122     {
123         // first, default settings, with which construction works ok
124         ObjectMapper m = new ObjectMapper();
125         PrivateBean bean = m.readValue("\"abc\"", PrivateBean.class);
126         assertEquals("abc", bean.a);
127 
128         // then by increasing visibility requirement:
129         m = new ObjectMapper();
130         VisibilityChecker<?> vc = m.getVisibilityChecker();
131         vc = vc.withCreatorVisibility(JsonAutoDetect.Visibility.PUBLIC_ONLY);
132         m.setVisibility(vc);
133         try {
134             m.readValue("\"abc\"", PrivateBean.class);
135             fail("Expected exception for missing constructor");
136         } catch (JsonProcessingException e) {
137             verifyException(e, "no String-argument constructor/factory");
138         }
139     }
140 
141     // [databind#1347]
testVisibilityConfigOverridesForSer()142     public void testVisibilityConfigOverridesForSer() throws Exception
143     {
144         // first, by default, both field/method should be visible
145         final Feature1347SerBean input = new Feature1347SerBean();
146         assertEquals(aposToQuotes("{'field':2,'value':3}"),
147                 MAPPER.writeValueAsString(input));
148 
149         ObjectMapper mapper = new ObjectMapper();
150         mapper.configOverride(Feature1347SerBean.class)
151             .setVisibility(JsonAutoDetect.Value.construct(PropertyAccessor.GETTER,
152                             Visibility.NONE));
153         assertEquals(aposToQuotes("{'field':2}"),
154                 mapper.writeValueAsString(input));
155     }
156 
157     // [databind#1347]
testVisibilityConfigOverridesForDeser()158     public void testVisibilityConfigOverridesForDeser() throws Exception
159     {
160         final String JSON = aposToQuotes("{'value':3}");
161 
162         // by default, should throw exception
163         try {
164             /*Feature1347DeserBean bean =*/
165             MAPPER.readValue(JSON, Feature1347DeserBean.class);
166             fail("Should not pass");
167         } catch (JsonMappingException e) {
168             verifyException(e, "Should NOT get called");
169         }
170 
171         // but when instructed to ignore setter, should work
172         ObjectMapper mapper = new ObjectMapper();
173         mapper.configOverride(Feature1347DeserBean.class)
174             .setVisibility(JsonAutoDetect.Value.construct(PropertyAccessor.SETTER,
175                         Visibility.NONE));
176         Feature1347DeserBean result = mapper.readValue(JSON, Feature1347DeserBean.class);
177         assertEquals(3, result.value);
178     }
179 
180     // [databind#1947]
testDisablingAll()181     public void testDisablingAll() throws Exception
182     {
183         ObjectMapper mapper = jsonMapperBuilder()
184                 .disable(MapperFeature.AUTO_DETECT_SETTERS)
185                 .disable(MapperFeature.AUTO_DETECT_FIELDS)
186                 .disable(MapperFeature.AUTO_DETECT_GETTERS)
187                 .disable(MapperFeature.AUTO_DETECT_CREATORS)
188                 .disable(MapperFeature.AUTO_DETECT_IS_GETTERS)
189                 .build();
190         String json = mapper.writeValueAsString(new Entity1947());
191         JsonNode n = mapper.readTree(json);
192         assertEquals(1, n.size());
193         assertTrue(n.has("shouldBeDetected"));
194         assertFalse(n.has("shouldNotBeDetected"));
195     }
196 
197     // [databind#2789]
testAnnotatedFieldIssue2789()198     public void testAnnotatedFieldIssue2789() throws Exception {
199         final String json = MAPPER.writeValueAsString(new DataClassA());
200         final DataParent2789 copy = MAPPER.readValue(json, DataParent2789.class);
201         assertEquals(DataType2789.CLASS_A, copy.getType());
202     }
203 }
204