1 package com.fasterxml.jackson.databind.node;
2
3 import java.math.BigDecimal;
4 import java.math.BigInteger;
5
6 import com.fasterxml.jackson.databind.JsonNode;
7 import com.fasterxml.jackson.databind.util.RawValue;
8
9 /**
10  * Base class that specifies methods for getting access to
11  * Node instances (newly constructed, or shared, depending
12  * on type), as well as basic implementation of the methods.
13  * Designed to be sub-classed if extended functionality (additions
14  * to behavior of node types, mostly) is needed.
15  */

16 public class JsonNodeFactory
17     implements java.io.Serializable, // since 2.1
18         JsonNodeCreator // since 2.3
19 {
20     // with 2.2
21     private static final long serialVersionUID = 1L;
22
23     private final boolean _cfgBigDecimalExact;
24
25     private static final JsonNodeFactory decimalsNormalized
26         = new JsonNodeFactory(false);
27     private static final JsonNodeFactory decimalsAsIs
28         = new JsonNodeFactory(true);
29
30     /**
31      * Default singleton instance that construct "standard" node instances:
32      * given that this class is stateless, a globally shared singleton
33      * can be used.
34      */

35     public final static JsonNodeFactory instance = decimalsNormalized;
36
37     /**
38      * Main constructor
39      *
40      * <p>The only argument to this constructor is a boolean telling whether
41      * {@link DecimalNode} instances must be built with exact representations of
42      * {@link BigDecimal} instances.</p>
43      *
44      * <p>This has quite an influence since, for instance, a BigDecimal (and,
45      * therefore, a DecimalNode) constructed from input string {@code "1.0"} and
46      * another constructed with input string {@code "1.00"} <b>will not</b> be
47      * equal, since their scale differs (1 in the first case, 2 in the second
48      * case).</p>
49      *
50      * <p>Note that setting the argument to {@code true} does <i>not</i>
51      * guarantee a strict inequality between JSON representations: input texts
52      * {@code "0.1"} and {@code "1e-1"}, for instance, yield two equivalent
53      * BigDecimal instances since they have the same scale (1).</p>
54      *
55      * <p>The no-arg constructor (and the default {@link #instance}) calls this
56      * constructor with {@code false} as an argument.</p>
57      *
58      * @param bigDecimalExact see description
59      *
60      * @see BigDecimal
61      */

62     public JsonNodeFactory(boolean bigDecimalExact)
63     {
64         _cfgBigDecimalExact = bigDecimalExact;
65     }
66
67     /**
68      * Default constructor
69      *
70      * <p>This calls {@link #JsonNodeFactory(boolean)} with {@code false}
71      * as an argument.</p>
72      */

73     protected JsonNodeFactory()
74     {
75         this(false);
76     }
77
78     /**
79      * Return a factory instance with the desired behavior for BigDecimals
80      * <p>See {@link #JsonNodeFactory(boolean)} for a full description.</p>
81      *
82      * @param bigDecimalExact see description
83      * @return a factory instance
84      */

85     public static JsonNodeFactory withExactBigDecimals(boolean bigDecimalExact)
86     {
87         return bigDecimalExact ? decimalsAsIs : decimalsNormalized;
88     }
89
90     /*
91     /**********************************************************
92     /* Factory methods for literal values
93     /**********************************************************
94      */

95
96     /**
97      * Factory method for getting an instance of JSON boolean value
98      * (either literal 'true' or 'false')
99      */

100     @Override
101     public BooleanNode booleanNode(boolean v) {
102         return v ? BooleanNode.getTrue() : BooleanNode.getFalse();
103     }
104
105     /**
106      * Factory method for getting an instance of JSON null node (which
107      * represents literal null value)
108      */

109     @Override
110     public NullNode nullNode() { return NullNode.getInstance(); }
111
112     public JsonNode missingNode() {
113         return MissingNode.getInstance();
114     }
115     
116     /*
117     /**********************************************************
118     /* Factory methods for numeric values
119     /**********************************************************
120      */

121
122     /**
123      * Factory method for getting an instance of JSON numeric value
124      * that expresses given 8-bit value
125      */

126     @Override
127     public NumericNode numberNode(byte v) { return IntNode.valueOf(v); }
128
129     /**
130      * Alternate factory method that will handle wrapper value, which may
131      * be null.
132      * Due to possibility of null, returning type is not guaranteed to be
133      * {@link NumericNode}, but just {@link ValueNode}.
134      */

135     @Override
136     public ValueNode numberNode(Byte value) {
137         return (value == null) ? nullNode() : IntNode.valueOf(value.intValue());
138     }
139
140     /**
141      * Factory method for getting an instance of JSON numeric value
142      * that expresses given 16-bit integer value
143      */

144     @Override
145     public NumericNode numberNode(short v) { return ShortNode.valueOf(v); }
146
147     /**
148      * Alternate factory method that will handle wrapper value, which may
149      * be null.
150      * Due to possibility of null, returning type is not guaranteed to be
151      * {@link NumericNode}, but just {@link ValueNode}.
152      */

153     @Override
154     public ValueNode numberNode(Short value) {
155         return (value == null) ? nullNode() : ShortNode.valueOf(value);
156     }
157
158     /**
159      * Factory method for getting an instance of JSON numeric value
160      * that expresses given 32-bit integer value
161      */

162     @Override
163     public NumericNode numberNode(int v) { return IntNode.valueOf(v); }
164
165     /**
166      * Alternate factory method that will handle wrapper value, which may
167      * be null.
168      * Due to possibility of null, returning type is not guaranteed to be
169      * {@link NumericNode}, but just {@link ValueNode}.
170      */

171     @Override
172     public ValueNode numberNode(Integer value) {
173         return (value == null) ? nullNode() : IntNode.valueOf(value.intValue());
174     }
175
176     /**
177      * Factory method for getting an instance of JSON numeric value
178      * that expresses given 64-bit integer value
179      */

180     @Override
181     public NumericNode numberNode(long v) {
182         return LongNode.valueOf(v);
183     }
184
185     /**
186      * Alternate factory method that will handle wrapper value, which may be null.
187      * Due to possibility of null, returning type is not guaranteed to be
188      * {@link NumericNode}, but just {@link ValueNode}.
189      */

190     @Override
191     public ValueNode numberNode(Long v) {
192         if (v == null) {
193             return nullNode();
194         }
195         return LongNode.valueOf(v.longValue());
196     }
197
198     /**
199      * Factory method for getting an instance of JSON numeric value
200      * that expresses given unlimited range integer value
201      */

202     @Override
203     public ValueNode numberNode(BigInteger v) {
204         if (v == null) {
205             return nullNode();
206         }
207         return BigIntegerNode.valueOf(v);
208     }
209
210     /**
211      * Factory method for getting an instance of JSON numeric value
212      * that expresses given 32-bit floating point value
213      */

214     @Override
215     public NumericNode numberNode(float v) { return FloatNode.valueOf((float) v); }
216
217     /**
218      * Alternate factory method that will handle wrapper value, which may
219      * be null.
220      * Due to possibility of null, returning type is not guaranteed to be
221      * {@link NumericNode}, but just {@link ValueNode}.
222      */

223     @Override
224     public ValueNode numberNode(Float value) {
225         return (value == null) ? nullNode() : FloatNode.valueOf(value.floatValue());
226     }
227
228     /**
229      * Factory method for getting an instance of JSON numeric value
230      * that expresses given 64-bit floating point value
231      */

232     @Override
233     public NumericNode numberNode(double v) { return DoubleNode.valueOf(v); }
234
235     /**
236      * Alternate factory method that will handle wrapper value, which may
237      * be null.
238      * Due to possibility of null, returning type is not guaranteed to be
239      * {@link NumericNode}, but just {@link ValueNode}.
240      */

241     @Override
242     public ValueNode numberNode(Double value) {
243         return (value == null) ? nullNode() : DoubleNode.valueOf(value.doubleValue());
244     }
245
246     /**
247      * Factory method for getting an instance of JSON numeric value
248      * that expresses given unlimited precision floating point value
249      *
250      * <p>In the event that the factory has been built to normalize decimal
251      * values, the BigDecimal argument will be stripped off its trailing zeroes,
252      * using {@link BigDecimal#stripTrailingZeros()}.</p>
253      *
254      * @see #JsonNodeFactory(boolean)
255      */

256     @Override
257     public ValueNode numberNode(BigDecimal v)
258     {
259         if (v == null) {
260             return nullNode();
261         }
262
263         /*
264          * If the user wants the exact representation of this big decimal,
265          * return the value directly
266          */

267         if (_cfgBigDecimalExact)
268             return DecimalNode.valueOf(v);
269
270         /*
271          * If the user has asked to strip trailing zeroes, however, there is
272          * this bug to account for:
273          *
274          * http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6480539
275          *
276          * In short: zeroes are never stripped out of 0! We therefore _have_
277          * to compare with BigDecimal.ZERO...
278          */

279         return v.compareTo(BigDecimal.ZERO) == 0 ? DecimalNode.ZERO
280             : DecimalNode.valueOf(v.stripTrailingZeros());
281     }
282
283     /*
284     /**********************************************************
285     /* Factory methods for textual values
286     /**********************************************************
287      */

288
289     /**
290      * Factory method for constructing a node that represents JSON
291      * String value
292      */

293     @Override
294     public TextNode textNode(String text) { return TextNode.valueOf(text); }
295
296     /**
297      * Factory method for constructing a node that represents given
298      * binary data, and will get serialized as equivalent base64-encoded
299      * String value
300      */

301     @Override
302     public BinaryNode binaryNode(byte[] data) { return BinaryNode.valueOf(data); }
303
304     /**
305      * Factory method for constructing a node that represents given
306      * binary data, and will get serialized as equivalent base64-encoded
307      * String value
308      */

309     @Override
310     public BinaryNode binaryNode(byte[] data, int offset, int length) {
311         return BinaryNode.valueOf(data, offset, length);
312     }
313
314     /*
315     /**********************************************************
316     /* Factory method for structured values
317     /**********************************************************
318      */

319
320     /**
321      * Factory method for constructing an empty JSON Array node
322      */

323     @Override
324     public ArrayNode arrayNode() { return new ArrayNode(this); }
325
326     /**
327      * Factory method for constructing a JSON Array node with an initial capacity
328      *
329      * @since 2.8
330      */

331     @Override
332     public ArrayNode arrayNode(int capacity) { return new ArrayNode(this, capacity); }
333
334     /**
335      * Factory method for constructing an empty JSON Object ("struct") node
336      */

337     @Override
338     public ObjectNode objectNode() { return new ObjectNode(this); }
339
340     /**
341      * Factory method for constructing a wrapper for POJO
342      * ("Plain Old Java Object") objects; these will get serialized
343      * using data binding, usually as JSON Objects, but in some
344      * cases as JSON Strings or other node types.
345      */

346     @Override
347     public ValueNode pojoNode(Object pojo) { return new POJONode(pojo); }
348
349     @Override
350     public ValueNode rawValueNode(RawValue value) {
351         return new POJONode(value);
352     }
353
354     /*
355     /**********************************************************
356     /* Helper methods
357     /**********************************************************
358      */

359
360     protected boolean _inIntRange(long l)
361     {
362         int i = (int) l;
363         long l2 = (long) i;
364         return (l2 == l);
365     }
366 }
367
368