1 package com.fasterxml.jackson.databind.ser.impl;
2
3 import java.util.Arrays;
4
5 import com.fasterxml.jackson.databind.BeanProperty;
6 import com.fasterxml.jackson.databind.JavaType;
7 import com.fasterxml.jackson.databind.JsonMappingException;
8 import com.fasterxml.jackson.databind.JsonSerializer;
9 import com.fasterxml.jackson.databind.SerializerProvider;
10
11
21 public abstract class PropertySerializerMap
22 {
23
30 protected final boolean _resetWhenFull;
31
32
35 protected PropertySerializerMap(boolean resetWhenFull) {
36 _resetWhenFull = resetWhenFull;
37 }
38
39 protected PropertySerializerMap(PropertySerializerMap base) {
40 _resetWhenFull = base._resetWhenFull;
41 }
42
43
48 public abstract JsonSerializer<Object> serializerFor(Class<?> type);
49
50
60 public final SerializerAndMapResult findAndAddPrimarySerializer(Class<?> type,
61 SerializerProvider provider, BeanProperty property)
62 throws JsonMappingException
63 {
64 JsonSerializer<Object> serializer = provider.findPrimaryPropertySerializer(type, property);
65 return new SerializerAndMapResult(serializer, newWith(type, serializer));
66 }
67
68 public final SerializerAndMapResult findAndAddPrimarySerializer(JavaType type,
69 SerializerProvider provider, BeanProperty property)
70 throws JsonMappingException
71 {
72 JsonSerializer<Object> serializer = provider.findPrimaryPropertySerializer(type, property);
73 return new SerializerAndMapResult(serializer, newWith(type.getRawClass(), serializer));
74 }
75
76
86 public final SerializerAndMapResult findAndAddSecondarySerializer(Class<?> type,
87 SerializerProvider provider, BeanProperty property)
88 throws JsonMappingException
89 {
90 JsonSerializer<Object> serializer = provider.findContentValueSerializer(type, property);
91 return new SerializerAndMapResult(serializer, newWith(type, serializer));
92 }
93
94 public final SerializerAndMapResult findAndAddSecondarySerializer(JavaType type,
95 SerializerProvider provider, BeanProperty property)
96 throws JsonMappingException
97 {
98 JsonSerializer<Object> serializer = provider.findContentValueSerializer(type, property);
99 return new SerializerAndMapResult(serializer, newWith(type.getRawClass(), serializer));
100 }
101
102
113 public final SerializerAndMapResult findAndAddRootValueSerializer(Class<?> type,
114 SerializerProvider provider)
115 throws JsonMappingException
116 {
117 JsonSerializer<Object> serializer = provider.findTypedValueSerializer(type, false, null);
118 return new SerializerAndMapResult(serializer, newWith(type, serializer));
119 }
120
121
124 public final SerializerAndMapResult findAndAddRootValueSerializer(JavaType type,
125 SerializerProvider provider)
126 throws JsonMappingException
127 {
128 JsonSerializer<Object> serializer = provider.findTypedValueSerializer(type, false, null);
129 return new SerializerAndMapResult(serializer, newWith(type.getRawClass(), serializer));
130 }
131
132
140 public final SerializerAndMapResult findAndAddKeySerializer(Class<?> type,
141 SerializerProvider provider, BeanProperty property)
142 throws JsonMappingException
143 {
144 JsonSerializer<Object> serializer = provider.findKeySerializer(type, property);
145 return new SerializerAndMapResult(serializer, newWith(type, serializer));
146 }
147
148
154 public final SerializerAndMapResult addSerializer(Class<?> type, JsonSerializer<Object> serializer) {
155 return new SerializerAndMapResult(serializer, newWith(type, serializer));
156 }
157
158
161 public final SerializerAndMapResult addSerializer(JavaType type, JsonSerializer<Object> serializer) {
162 return new SerializerAndMapResult(serializer, newWith(type.getRawClass(), serializer));
163 }
164
165 public abstract PropertySerializerMap newWith(Class<?> type, JsonSerializer<Object> serializer);
166
167
170 @Deprecated
171 public static PropertySerializerMap emptyMap() {
172 return emptyForProperties();
173 }
174
175
178 public static PropertySerializerMap emptyForProperties() {
179 return Empty.FOR_PROPERTIES;
180 }
181
182
185 public static PropertySerializerMap emptyForRootValues() {
186 return Empty.FOR_ROOT_VALUES;
187 }
188
189
194
195
199 public final static class SerializerAndMapResult
200 {
201 public final JsonSerializer<Object> serializer;
202 public final PropertySerializerMap map;
203
204 public SerializerAndMapResult(JsonSerializer<Object> serializer,
205 PropertySerializerMap map)
206 {
207 this.serializer = serializer;
208 this.map = map;
209 }
210 }
211
212
215 private final static class TypeAndSerializer
216 {
217 public final Class<?> type;
218 public final JsonSerializer<Object> serializer;
219
220 public TypeAndSerializer(Class<?> type, JsonSerializer<Object> serializer) {
221 this.type = type;
222 this.serializer = serializer;
223 }
224 }
225
226
231
232
236 private final static class Empty extends PropertySerializerMap
237 {
238
239 public final static Empty FOR_PROPERTIES = new Empty(false);
240
241
242 public final static Empty FOR_ROOT_VALUES = new Empty(true);
243
244 protected Empty(boolean resetWhenFull) {
245 super(resetWhenFull);
246 }
247
248 @Override
249 public JsonSerializer<Object> serializerFor(Class<?> type) {
250 return null;
251 }
252
253 @Override
254 public PropertySerializerMap newWith(Class<?> type, JsonSerializer<Object> serializer) {
255 return new Single(this, type, serializer);
256 }
257 }
258
259
265 private final static class Single extends PropertySerializerMap
266 {
267 private final Class<?> _type;
268 private final JsonSerializer<Object> _serializer;
269
270 public Single(PropertySerializerMap base, Class<?> type, JsonSerializer<Object> serializer) {
271 super(base);
272 _type = type;
273 _serializer = serializer;
274 }
275
276 @Override
277 public JsonSerializer<Object> serializerFor(Class<?> type)
278 {
279 if (type == _type) {
280 return _serializer;
281 }
282 return null;
283 }
284
285 @Override
286 public PropertySerializerMap newWith(Class<?> type, JsonSerializer<Object> serializer) {
287 return new Double(this, _type, _serializer, type, serializer);
288 }
289 }
290
291 private final static class Double extends PropertySerializerMap
292 {
293 private final Class<?> _type1, _type2;
294 private final JsonSerializer<Object> _serializer1, _serializer2;
295
296 public Double(PropertySerializerMap base,
297 Class<?> type1, JsonSerializer<Object> serializer1,
298 Class<?> type2, JsonSerializer<Object> serializer2)
299 {
300 super(base);
301 _type1 = type1;
302 _serializer1 = serializer1;
303 _type2 = type2;
304 _serializer2 = serializer2;
305 }
306
307 @Override
308 public JsonSerializer<Object> serializerFor(Class<?> type)
309 {
310 if (type == _type1) {
311 return _serializer1;
312 }
313 if (type == _type2) {
314 return _serializer2;
315 }
316 return null;
317 }
318
319 @Override
320 public PropertySerializerMap newWith(Class<?> type, JsonSerializer<Object> serializer) {
321
322 TypeAndSerializer[] ts = new TypeAndSerializer[3];
323 ts[0] = new TypeAndSerializer(_type1, _serializer1);
324 ts[1] = new TypeAndSerializer(_type2, _serializer2);
325 ts[2] = new TypeAndSerializer(type, serializer);
326 return new Multi(this, ts);
327 }
328 }
329
330 private final static class Multi extends PropertySerializerMap
331 {
332
340 private final static int MAX_ENTRIES = 8;
341
342 private final TypeAndSerializer[] _entries;
343
344 public Multi(PropertySerializerMap base, TypeAndSerializer[] entries) {
345 super(base);
346 _entries = entries;
347 }
348
349 @Override
350 public JsonSerializer<Object> serializerFor(Class<?> type)
351 {
352
353 TypeAndSerializer entry;
354 entry = _entries[0];
355 if (entry.type == type) return entry.serializer;
356 entry = _entries[1];
357 if (entry.type == type) return entry.serializer;
358 entry = _entries[2];
359 if (entry.type == type) return entry.serializer;
360
361 switch (_entries.length) {
362 case 8:
363 entry = _entries[7];
364 if (entry.type == type) return entry.serializer;
365 case 7:
366 entry = _entries[6];
367 if (entry.type == type) return entry.serializer;
368 case 6:
369 entry = _entries[5];
370 if (entry.type == type) return entry.serializer;
371 case 5:
372 entry = _entries[4];
373 if (entry.type == type) return entry.serializer;
374 case 4:
375 entry = _entries[3];
376 if (entry.type == type) return entry.serializer;
377 default:
378 }
379 return null;
380 }
381
382 @Override
383 public PropertySerializerMap newWith(Class<?> type, JsonSerializer<Object> serializer)
384 {
385 int len = _entries.length;
386
387
388 if (len == MAX_ENTRIES) {
389 if (_resetWhenFull) {
390 return new Single(this, type, serializer);
391 }
392 return this;
393 }
394 TypeAndSerializer[] entries = Arrays.copyOf(_entries, len+1);
395 entries[len] = new TypeAndSerializer(type, serializer);
396 return new Multi(this, entries);
397 }
398 }
399 }
400