blob: 7af1177318d165534fde14324d63c1c52894eac9 [file] [log] [blame]
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001/* Jackson JSON-processor.
2 *
3 * Copyright (c) 2007- Tatu Saloranta, tatu.saloranta@iki.fi
4 *
5 * Licensed under the License specified in file LICENSE, included with
6 * the source code and binary code bundles.
7 * You may not use this file except in compliance with the License.
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15package com.fasterxml.jackson.core;
16
17import java.io.*;
18import java.lang.ref.SoftReference;
19import java.net.URL;
20
21import com.fasterxml.jackson.core.format.InputAccessor;
22import com.fasterxml.jackson.core.format.MatchStrength;
23import com.fasterxml.jackson.core.io.*;
Tatu07351902012-01-19 13:12:13 -080024import com.fasterxml.jackson.core.json.*;
Tatu Salorantaf15531c2011-12-22 23:00:40 -080025import com.fasterxml.jackson.core.sym.BytesToNameCanonicalizer;
26import com.fasterxml.jackson.core.sym.CharsToNameCanonicalizer;
27import com.fasterxml.jackson.core.util.BufferRecycler;
Tatu Salorantae6dfc692012-09-28 15:34:05 -070028import com.fasterxml.jackson.core.util.DefaultPrettyPrinter;
Tatu Salorantaf15531c2011-12-22 23:00:40 -080029
30/**
31 * The main factory class of Jackson package, used to configure and
32 * construct reader (aka parser, {@link JsonParser})
33 * and writer (aka generator, {@link JsonGenerator})
34 * instances.
35 *<p>
36 * Factory instances are thread-safe and reusable after configuration
37 * (if any). Typically applications and services use only a single
38 * globally shared factory instance, unless they need differently
39 * configured factories. Factory reuse is important if efficiency matters;
40 * most recycling of expensive construct is done on per-factory basis.
41 *<p>
42 * Creation of a factory instance is a light-weight operation,
43 * and since there is no need for pluggable alternative implementations
44 * (as there is no "standard" JSON processor API to implement),
45 * the default constructor is used for constructing factory
46 * instances.
47 *
48 * @author Tatu Saloranta
49 */
Tatu Saloranta95f76a42012-10-05 13:04:23 -070050public class JsonFactory
51 implements Versioned,
52 java.io.Serializable // since 2.1 (for Android, mostly)
Tatu Salorantaf15531c2011-12-22 23:00:40 -080053{
54 /**
Tatu Saloranta95f76a42012-10-05 13:04:23 -070055 * Computed for Jackson 2.1.0 release
56 */
Tatu Saloranta101820d2012-10-05 13:42:49 -070057 private static final long serialVersionUID = 8726401676402117450L;
Tatu Saloranta95f76a42012-10-05 13:04:23 -070058
59 /**
Tatu Salorantaf15531c2011-12-22 23:00:40 -080060 * Name used to identify JSON format
61 * (and returned by {@link #getFormatName()}
62 */
63 public final static String FORMAT_NAME_JSON = "JSON";
64
65 /**
Tatu07351902012-01-19 13:12:13 -080066 * Bitfield (set of flags) of all factory features that are enabled by default.
67 */
68 protected final static int DEFAULT_FACTORY_FEATURE_FLAGS = JsonFactory.Feature.collectDefaults();
69
70 /**
Tatu Salorantaf15531c2011-12-22 23:00:40 -080071 * Bitfield (set of flags) of all parser features that are enabled
72 * by default.
73 */
Tatu07351902012-01-19 13:12:13 -080074 protected final static int DEFAULT_PARSER_FEATURE_FLAGS = JsonParser.Feature.collectDefaults();
75
Tatu Salorantaf15531c2011-12-22 23:00:40 -080076 /**
77 * Bitfield (set of flags) of all generator features that are enabled
78 * by default.
79 */
Tatu07351902012-01-19 13:12:13 -080080 protected final static int DEFAULT_GENERATOR_FEATURE_FLAGS = JsonGenerator.Feature.collectDefaults();
Tatu Salorantaf15531c2011-12-22 23:00:40 -080081
Tatu Salorantae6dfc692012-09-28 15:34:05 -070082 private final static SerializableString DEFAULT_ROOT_VALUE_SEPARATOR = DefaultPrettyPrinter.DEFAULT_ROOT_VALUE_SEPARATOR;
83
Tatu07351902012-01-19 13:12:13 -080084 /**
85 * Enumeration that defines all on/off features that can only be
86 * changed for {@link JsonFactory}.
87 */
88 public enum Feature {
89
90 // // // Symbol handling (interning etc)
91
92 /**
93 * Feature that determines whether JSON object field names are
94 * to be canonicalized using {@link String#intern} or not:
95 * if enabled, all field names will be intern()ed (and caller
96 * can count on this being true for all such names); if disabled,
97 * no intern()ing is done. There may still be basic
98 * canonicalization (that is, same String will be used to represent
99 * all identical object property names for a single document).
100 *<p>
101 * Note: this setting only has effect if
102 * {@link #CANONICALIZE_FIELD_NAMES} is true -- otherwise no
103 * canonicalization of any sort is done.
104 *<p>
105 * This setting is enabled by default.
106 */
107 INTERN_FIELD_NAMES(true),
108
109 /**
110 * Feature that determines whether JSON object field names are
111 * to be canonicalized (details of how canonicalization is done
112 * then further specified by
113 * {@link #INTERN_FIELD_NAMES}).
114 *<p>
115 * This setting is enabled by default.
116 */
117 CANONICALIZE_FIELD_NAMES(true)
118
119 ;
120
121 /**
122 * Whether feature is enabled or disabled by default.
123 */
124 private final boolean _defaultState;
125
126 /**
127 * Method that calculates bit set (flags) of all features that
128 * are enabled by default.
129 */
130 public static int collectDefaults()
131 {
132 int flags = 0;
133 for (Feature f : values()) {
134 if (f.enabledByDefault()) {
135 flags |= f.getMask();
136 }
137 }
138 return flags;
139 }
140
141 private Feature(boolean defaultState)
142 {
143 _defaultState = defaultState;
144 }
145
146 public boolean enabledByDefault() { return _defaultState; }
147
148 public boolean enabledIn(int flags) { return (flags & getMask()) != 0; }
149
150 public int getMask() { return (1 << ordinal()); }
151 }
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800152 /*
153 /**********************************************************
154 /* Buffer, symbol table management
155 /**********************************************************
156 */
157
158 /**
Tatu Saloranta10c3ec82012-09-05 19:38:49 -0700159 * This <code>ThreadLocal</code> contains a {@link java.lang.ref.SoftReference}
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800160 * to a {@link BufferRecycler} used to provide a low-cost
161 * buffer recycling between reader and writer instances.
162 */
163 final protected static ThreadLocal<SoftReference<BufferRecycler>> _recyclerRef
164 = new ThreadLocal<SoftReference<BufferRecycler>>();
165
166 /**
167 * Each factory comes equipped with a shared root symbol table.
168 * It should not be linked back to the original blueprint, to
169 * avoid contents from leaking between factories.
170 */
Tatu Saloranta95f76a42012-10-05 13:04:23 -0700171 protected final transient CharsToNameCanonicalizer _rootCharSymbols = CharsToNameCanonicalizer.createRoot();
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800172
173 /**
174 * Alternative to the basic symbol table, some stream-based
175 * parsers use different name canonicalization method.
176 *<p>
177 * TODO: should clean up this; looks messy having 2 alternatives
178 * with not very clear differences.
179 */
Tatu Saloranta95f76a42012-10-05 13:04:23 -0700180 protected final transient BytesToNameCanonicalizer _rootByteSymbols = BytesToNameCanonicalizer.createRoot();
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800181
182 /*
183 /**********************************************************
184 /* Configuration
185 /**********************************************************
186 */
187
188 /**
189 * Object that implements conversion functionality between
190 * Java objects and JSON content. For base JsonFactory implementation
191 * usually not set by default, but can be explicitly set.
192 * Sub-classes (like @link org.codehaus.jackson.map.MappingJsonFactory}
193 * usually provide an implementation.
194 */
195 protected ObjectCodec _objectCodec;
196
197 /**
Tatu07351902012-01-19 13:12:13 -0800198 * Currently enabled factory features.
199 */
200 protected int _factoryFeatures = DEFAULT_FACTORY_FEATURE_FLAGS;
201
202 /**
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800203 * Currently enabled parser features.
204 */
205 protected int _parserFeatures = DEFAULT_PARSER_FEATURE_FLAGS;
206
207 /**
208 * Currently enabled generator features.
209 */
210 protected int _generatorFeatures = DEFAULT_GENERATOR_FEATURE_FLAGS;
211
212 /**
213 * Definition of custom character escapes to use for generators created
214 * by this factory, if any. If null, standard data format specific
215 * escapes are used.
216 */
217 protected CharacterEscapes _characterEscapes;
218
219 /**
220 * Optional helper object that may decorate input sources, to do
221 * additional processing on input during parsing.
222 */
223 protected InputDecorator _inputDecorator;
224
225 /**
226 * Optional helper object that may decorate output object, to do
227 * additional processing on output during content generation.
228 */
229 protected OutputDecorator _outputDecorator;
Tatu Salorantae6dfc692012-09-28 15:34:05 -0700230
231 /**
232 * Separator used between root-level values, if any; null indicates
233 * "do not add separator".
234 * Default separator is a single space character.
235 *
236 * @since 2.1
237 */
238 protected SerializableString _rootValueSeparator = DEFAULT_ROOT_VALUE_SEPARATOR;
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800239
240 /*
241 /**********************************************************
242 /* Construction
243 /**********************************************************
244 */
245
246 /**
247 * Default constructor used to create factory instances.
248 * Creation of a factory instance is a light-weight operation,
249 * but it is still a good idea to reuse limited number of
250 * factory instances (and quite often just a single instance):
251 * factories are used as context for storing some reused
252 * processing objects (such as symbol tables parsers use)
253 * and this reuse only works within context of a single
254 * factory instance.
255 */
256 public JsonFactory() { this(null); }
257
258 public JsonFactory(ObjectCodec oc) { _objectCodec = oc; }
259
Tatu Saloranta378ecdc2012-08-04 16:27:27 -0700260 /**
261 * Method for constructing a new {@link JsonFactory} that has
262 * the same settings as this instance, but is otherwise
263 * independent (i.e. nothing is actually shared, symbol tables
264 * are separate).
265 * Note that {@link ObjectCodec} reference is not copied but is
266 * set to null; caller typically needs to set it after calling
267 * this method.
268 *
269 * @since 2.1
270 */
271 public JsonFactory copy()
272 {
273 _checkInvalidCopy(JsonFactory.class);
274 return new JsonFactory(null);
275 }
276
277 /**
278 * @since 2.1
279 * @param exp
280 */
281 protected void _checkInvalidCopy(Class<?> exp)
282 {
283 if (getClass() != exp) {
284 throw new IllegalStateException("Failed copy(): "+getClass().getName()
285 +" (version: "+version()+") does not override copy(); it has to");
286 }
287 }
Tatu Saloranta95f76a42012-10-05 13:04:23 -0700288
289 /*
290 /**********************************************************
291 /* Serializable overrides
292 /**********************************************************
293 */
294
295 /**
296 * Method that we need to override to actually make restoration go
297 * through constructors etc.
298 * Also: must be overridden by sub-classes as well.
299 */
300 protected Object readResolve() {
301 return new JsonFactory(_objectCodec);
302 }
Tatu Saloranta378ecdc2012-08-04 16:27:27 -0700303
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800304 /*
305 /**********************************************************
306 /* Format detection functionality (since 1.8)
307 /**********************************************************
308 */
309
310 /**
Tatu Saloranta1bdf0262012-08-24 14:43:17 -0700311 * Method that can be used to quickly check whether given schema
312 * is something that parsers and/or generators constructed by this
313 * factory could use. Note that this means possible use, at the level
314 * of data format (i.e. schema is for same data format as parsers and
315 * generators this factory constructs); individual schema instances
316 * may have further usage restrictions.
317 *
318 * @since 2.1
319 */
320 public boolean canUseSchema(FormatSchema schema) {
321 String ourFormat = getFormatName();
322 return (ourFormat != null) && ourFormat.equals(schema.getSchemaType());
323 }
324
325 /**
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800326 * Method that returns short textual id identifying format
327 * this factory supports.
328 *<p>
329 * Note: sub-classes should override this method; default
330 * implementation will return null for all sub-classes
331 */
332 public String getFormatName()
333 {
334 /* Somewhat nasty check: since we can't make this abstract
335 * (due to backwards compatibility concerns), need to prevent
336 * format name "leakage"
337 */
338 if (getClass() == JsonFactory.class) {
339 return FORMAT_NAME_JSON;
340 }
341 return null;
342 }
343
344 public MatchStrength hasFormat(InputAccessor acc) throws IOException
345 {
346 // since we can't keep this abstract, only implement for "vanilla" instance
347 if (getClass() == JsonFactory.class) {
348 return hasJSONFormat(acc);
349 }
350 return null;
351 }
352
Tatu Salorantaad2df5f2012-08-22 20:55:49 -0700353 /**
354 * Method that can be called to determine if a custom
355 * {@link ObjectCodec} is needed for binding data parsed
356 * using {@link JsonParser} constructed by this factory
357 * (which typically also implies the same for serialization
358 * with {@link JsonGenerator}).
359 *
360 * @return True if custom codec is needed with parsers and
361 * generators created by this factory; false if a general
362 * {@link ObjectCodec} is enough
363 *
364 * @since 2.1
365 */
366 public boolean requiresCustomCodec() {
367 return false;
368 }
369
370 /**
371 * Helper method that can be called to determine if content accessed
372 * using given accessor seems to be JSON content.
373 */
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800374 protected MatchStrength hasJSONFormat(InputAccessor acc) throws IOException
375 {
376 return ByteSourceJsonBootstrapper.hasJSONFormat(acc);
Tatu Salorantaad2df5f2012-08-22 20:55:49 -0700377 }
378
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800379 /*
380 /**********************************************************
381 /* Versioned
382 /**********************************************************
383 */
384
Tatu Salorantae9b48512012-04-17 10:22:07 -0700385// @Override
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800386 public Version version() {
Tatu Saloranta5a1bd992011-12-28 23:18:23 -0800387 return CoreVersion.instance.version();
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800388 }
389
390 /*
391 /**********************************************************
Tatu07351902012-01-19 13:12:13 -0800392 /* Configuration, factory features
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800393 /**********************************************************
394 */
395
396 /**
397 * Method for enabling or disabling specified parser feature
398 * (check {@link JsonParser.Feature} for list of features)
399 */
Tatu07351902012-01-19 13:12:13 -0800400 public final JsonFactory configure(JsonFactory.Feature f, boolean state) {
401 return state ? enable(f) : disable(f);
402 }
403
404 /**
405 * Method for enabling specified parser feature
406 * (check {@link JsonFactory.Feature} for list of features)
407 */
408 public JsonFactory enable(JsonFactory.Feature f) {
409 _factoryFeatures |= f.getMask();
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800410 return this;
411 }
412
413 /**
Tatu07351902012-01-19 13:12:13 -0800414 * Method for disabling specified parser features
415 * (check {@link JsonFactory.Feature} for list of features)
416 */
417 public JsonFactory disable(JsonFactory.Feature f) {
418 _factoryFeatures &= ~f.getMask();
419 return this;
420 }
421
422 /**
423 * Checked whether specified parser feature is enabled.
424 */
425 public final boolean isEnabled(JsonFactory.Feature f) {
426 return (_factoryFeatures & f.getMask()) != 0;
427 }
428
429 /*
430 /**********************************************************
431 /* Configuration, parser configuration
432 /**********************************************************
433 */
434
435 /**
436 * Method for enabling or disabling specified parser feature
437 * (check {@link JsonParser.Feature} for list of features)
438 */
439 public final JsonFactory configure(JsonParser.Feature f, boolean state) {
440 return state ? enable(f) : disable(f);
441 }
442
443 /**
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800444 * Method for enabling specified parser feature
445 * (check {@link JsonParser.Feature} for list of features)
446 */
447 public JsonFactory enable(JsonParser.Feature f) {
448 _parserFeatures |= f.getMask();
449 return this;
450 }
451
452 /**
453 * Method for disabling specified parser features
454 * (check {@link JsonParser.Feature} for list of features)
455 */
456 public JsonFactory disable(JsonParser.Feature f) {
457 _parserFeatures &= ~f.getMask();
458 return this;
459 }
460
461 /**
462 * Checked whether specified parser feature is enabled.
463 */
464 public final boolean isEnabled(JsonParser.Feature f) {
465 return (_parserFeatures & f.getMask()) != 0;
466 }
467
468 /**
469 * Method for getting currently configured input decorator (if any;
470 * there is no default decorator).
471 */
472 public InputDecorator getInputDecorator() {
473 return _inputDecorator;
474 }
475
476 /**
477 * Method for overriding currently configured input decorator
478 */
479 public JsonFactory setInputDecorator(InputDecorator d) {
480 _inputDecorator = d;
481 return this;
482 }
483
484 /*
485 /**********************************************************
486 /* Configuration, generator settings
487 /**********************************************************
488 */
489
490 /**
491 * Method for enabling or disabling specified generator feature
492 * (check {@link JsonGenerator.Feature} for list of features)
493 */
494 public final JsonFactory configure(JsonGenerator.Feature f, boolean state) {
Tatu07351902012-01-19 13:12:13 -0800495 return state ? enable(f) : disable(f);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800496 }
497
498
499 /**
500 * Method for enabling specified generator features
501 * (check {@link JsonGenerator.Feature} for list of features)
502 */
503 public JsonFactory enable(JsonGenerator.Feature f) {
504 _generatorFeatures |= f.getMask();
505 return this;
506 }
507
508 /**
509 * Method for disabling specified generator feature
510 * (check {@link JsonGenerator.Feature} for list of features)
511 */
512 public JsonFactory disable(JsonGenerator.Feature f) {
513 _generatorFeatures &= ~f.getMask();
514 return this;
515 }
516
517 /**
518 * Check whether specified generator feature is enabled.
519 */
520 public final boolean isEnabled(JsonGenerator.Feature f) {
521 return (_generatorFeatures & f.getMask()) != 0;
522 }
523
524 /**
525 * Method for accessing custom escapes factory uses for {@link JsonGenerator}s
526 * it creates.
527 */
528 public CharacterEscapes getCharacterEscapes() {
529 return _characterEscapes;
530 }
531
532 /**
533 * Method for defining custom escapes factory uses for {@link JsonGenerator}s
534 * it creates.
535 */
536 public JsonFactory setCharacterEscapes(CharacterEscapes esc) {
537 _characterEscapes = esc;
538 return this;
539 }
540
541 /**
542 * Method for getting currently configured output decorator (if any;
543 * there is no default decorator).
544 */
545 public OutputDecorator getOutputDecorator() {
546 return _outputDecorator;
547 }
548
549 /**
550 * Method for overriding currently configured output decorator
551 */
552 public JsonFactory setOutputDecorator(OutputDecorator d) {
553 _outputDecorator = d;
554 return this;
555 }
Tatu Salorantae6dfc692012-09-28 15:34:05 -0700556
557 /**
558 * Method that allows overriding String used for separating root-level
559 * JSON values (default is single space character)
560 *
561 * @param sep Separator to use, if any; null means that no separator is
562 * automatically added
563 *
564 * @since 2.1
565 */
566 public JsonFactory setRootValueSeparator(String sep) {
567 _rootValueSeparator = (sep == null) ? null : new SerializedString(sep);
568 return this;
569 }
570
571 /**
572 * @since 2.1
573 */
574 public String getRootValueSeparator() {
575 return (_rootValueSeparator == null) ? null : _rootValueSeparator.getValue();
576 }
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800577
578 /*
579 /**********************************************************
580 /* Configuration, other
581 /**********************************************************
582 */
583
584 /**
585 * Method for associating a {@link ObjectCodec} (typically
Tatu Salorantad77350e2011-12-22 23:13:13 -0800586 * a <code>com.fasterxml.jackson.databind.ObjectMapper</code>)
587 * with this factory (and more importantly, parsers and generators
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800588 * it constructs). This is needed to use data-binding methods
589 * of {@link JsonParser} and {@link JsonGenerator} instances.
590 */
591 public JsonFactory setCodec(ObjectCodec oc) {
592 _objectCodec = oc;
593 return this;
594 }
595
596 public ObjectCodec getCodec() { return _objectCodec; }
597
598 /*
599 /**********************************************************
Tatu Salorantafeaabd12012-07-22 23:03:41 -0700600 /* Parser factories (new ones, as per [Issue-25])
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800601 /**********************************************************
602 */
603
604 /**
605 * Method for constructing JSON parser instance to parse
606 * contents of specified file. Encoding is auto-detected
607 * from contents according to JSON specification recommended
608 * mechanism.
609 *<p>
610 * Underlying input stream (needed for reading contents)
611 * will be <b>owned</b> (and managed, i.e. closed as need be) by
612 * the parser, since caller has no access to it.
613 *
614 * @param f File that contains JSON content to parse
Tatu Salorantafeaabd12012-07-22 23:03:41 -0700615 *
616 * @since 2.1
617 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800618 @SuppressWarnings("resource")
Tatu Salorantafeaabd12012-07-22 23:03:41 -0700619 public JsonParser createParser(File f)
620 throws IOException, JsonParseException
621 {
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800622 // true, since we create InputStream from File
623 IOContext ctxt = _createContext(f, true);
624 InputStream in = new FileInputStream(f);
625 // [JACKSON-512]: allow wrapping with InputDecorator
626 if (_inputDecorator != null) {
627 in = _inputDecorator.decorate(ctxt, in);
628 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -0700629 return _createParser(in, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800630 }
631
632 /**
633 * Method for constructing JSON parser instance to parse
634 * contents of resource reference by given URL.
635 * Encoding is auto-detected
636 * from contents according to JSON specification recommended
637 * mechanism.
638 *<p>
639 * Underlying input stream (needed for reading contents)
640 * will be <b>owned</b> (and managed, i.e. closed as need be) by
641 * the parser, since caller has no access to it.
642 *
643 * @param url URL pointing to resource that contains JSON content to parse
Tatu Saloranta68194922012-11-15 20:34:29 -0800644 *
645 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800646 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800647 public JsonParser createParser(URL url)
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800648 throws IOException, JsonParseException
649 {
650 // true, since we create InputStream from URL
651 IOContext ctxt = _createContext(url, true);
652 InputStream in = _optimizedStreamFromURL(url);
653 // [JACKSON-512]: allow wrapping with InputDecorator
654 if (_inputDecorator != null) {
655 in = _inputDecorator.decorate(ctxt, in);
656 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -0700657 return _createParser(in, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800658 }
659
660 /**
661 * Method for constructing JSON parser instance to parse
662 * the contents accessed via specified input stream.
663 *<p>
664 * The input stream will <b>not be owned</b> by
665 * the parser, it will still be managed (i.e. closed if
666 * end-of-stream is reacher, or parser close method called)
667 * if (and only if) {@link com.fasterxml.jackson.core.JsonParser.Feature#AUTO_CLOSE_SOURCE}
668 * is enabled.
669 *<p>
670 * Note: no encoding argument is taken since it can always be
Tatu Salorantafeaabd12012-07-22 23:03:41 -0700671 * auto-detected as suggested by JSON RFC.
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800672 *
673 * @param in InputStream to use for reading JSON content to parse
Tatu Saloranta68194922012-11-15 20:34:29 -0800674 *
675 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800676 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800677 public JsonParser createParser(InputStream in)
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800678 throws IOException, JsonParseException
679 {
680 IOContext ctxt = _createContext(in, false);
681 // [JACKSON-512]: allow wrapping with InputDecorator
682 if (_inputDecorator != null) {
683 in = _inputDecorator.decorate(ctxt, in);
684 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -0700685 return _createParser(in, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800686 }
687
688 /**
689 * Method for constructing parser for parsing
690 * the contents accessed via specified Reader.
691 <p>
692 * The read stream will <b>not be owned</b> by
693 * the parser, it will still be managed (i.e. closed if
694 * end-of-stream is reacher, or parser close method called)
695 * if (and only if) {@link com.fasterxml.jackson.core.JsonParser.Feature#AUTO_CLOSE_SOURCE}
696 * is enabled.
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800697 *
698 * @param r Reader to use for reading JSON content to parse
Tatu Saloranta68194922012-11-15 20:34:29 -0800699 *
700 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800701 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800702 public JsonParser createParser(Reader r)
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800703 throws IOException, JsonParseException
704 {
705 // false -> we do NOT own Reader (did not create it)
706 IOContext ctxt = _createContext(r, false);
707 // [JACKSON-512]: allow wrapping with InputDecorator
708 if (_inputDecorator != null) {
709 r = _inputDecorator.decorate(ctxt, r);
710 }
Tatu Saloranta3e5ff6d2012-06-27 18:46:43 -0700711 return _createParser(r, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800712 }
713
714 /**
715 * Method for constructing parser for parsing
716 * the contents of given byte array.
Tatu Saloranta68194922012-11-15 20:34:29 -0800717 *
718 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800719 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800720 public JsonParser createParser(byte[] data)
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800721 throws IOException, JsonParseException
722 {
723 IOContext ctxt = _createContext(data, true);
724 // [JACKSON-512]: allow wrapping with InputDecorator
725 if (_inputDecorator != null) {
726 InputStream in = _inputDecorator.decorate(ctxt, data, 0, data.length);
727 if (in != null) {
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -0700728 return _createParser(in, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800729 }
730 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -0700731 return _createParser(data, 0, data.length, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800732 }
733
734 /**
735 * Method for constructing parser for parsing
736 * the contents of given byte array.
737 *
738 * @param data Buffer that contains data to parse
739 * @param offset Offset of the first data byte within buffer
740 * @param len Length of contents to parse within buffer
Tatu Saloranta68194922012-11-15 20:34:29 -0800741 *
742 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800743 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800744 public JsonParser createParser(byte[] data, int offset, int len)
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800745 throws IOException, JsonParseException
746 {
747 IOContext ctxt = _createContext(data, true);
748 // [JACKSON-512]: allow wrapping with InputDecorator
749 if (_inputDecorator != null) {
750 InputStream in = _inputDecorator.decorate(ctxt, data, offset, len);
751 if (in != null) {
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -0700752 return _createParser(in, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800753 }
754 }
Tatu Saloranta68194922012-11-15 20:34:29 -0800755 return _createParser(data, offset, len, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800756 }
757
758 /**
759 * Method for constructing parser for parsing
760 * contents of given String.
Tatu Saloranta68194922012-11-15 20:34:29 -0800761 *
762 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800763 */
Tatu Saloranta68194922012-11-15 20:34:29 -0800764 public JsonParser createParser(String content)
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800765 throws IOException, JsonParseException
766 {
Tatu Saloranta3e5ff6d2012-06-27 18:46:43 -0700767 Reader r = new StringReader(content);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800768 // true -> we own the Reader (and must close); not a big deal
769 IOContext ctxt = _createContext(r, true);
770 // [JACKSON-512]: allow wrapping with InputDecorator
771 if (_inputDecorator != null) {
772 r = _inputDecorator.decorate(ctxt, r);
773 }
Tatu Saloranta3e5ff6d2012-06-27 18:46:43 -0700774 return _createParser(r, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800775 }
776
777 /*
778 /**********************************************************
Tatu Saloranta68194922012-11-15 20:34:29 -0800779 /* Parser factories (old ones, as per [Issue-25])
780 /**********************************************************
781 */
782
783 /**
784 * Method for constructing JSON parser instance to parse
785 * contents of specified file. Encoding is auto-detected
786 * from contents according to JSON specification recommended
787 * mechanism.
788 *<p>
789 * Underlying input stream (needed for reading contents)
790 * will be <b>owned</b> (and managed, i.e. closed as need be) by
791 * the parser, since caller has no access to it.
792 *<p>
793 * NOTE: as of 2.1, should not be used (will be deprecated in 2.2);
794 * instead, should call <code>createParser</code>.
795 *
796 * @param f File that contains JSON content to parse
797 *
798 * @deprecated Since 2.2, use {@link #createParser(File)} instead.
799 */
800 @Deprecated
801 public JsonParser createJsonParser(File f)
802 throws IOException, JsonParseException
803 {
804 return createParser(f);
805 }
806
807 /**
808 * Method for constructing JSON parser instance to parse
809 * contents of resource reference by given URL.
810 * Encoding is auto-detected
811 * from contents according to JSON specification recommended
812 * mechanism.
813 *<p>
814 * Underlying input stream (needed for reading contents)
815 * will be <b>owned</b> (and managed, i.e. closed as need be) by
816 * the parser, since caller has no access to it.
817 *<p>
818 * NOTE: as of 2.1, should not be used (will be deprecated in 2.2);
819 * instead, should call <code>createParser</code>.
820 *
821 * @param url URL pointing to resource that contains JSON content to parse
822 *
823 * @deprecated Since 2.2, use {@link #createParser(URL)} instead.
824 */
825 @Deprecated
826 public JsonParser createJsonParser(URL url)
827 throws IOException, JsonParseException
828 {
829 return createParser(url);
830 }
831
832 /**
833 * Method for constructing JSON parser instance to parse
834 * the contents accessed via specified input stream.
835 *<p>
836 * The input stream will <b>not be owned</b> by
837 * the parser, it will still be managed (i.e. closed if
838 * end-of-stream is reacher, or parser close method called)
839 * if (and only if) {@link com.fasterxml.jackson.core.JsonParser.Feature#AUTO_CLOSE_SOURCE}
840 * is enabled.
841 *<p>
842 * Note: no encoding argument is taken since it can always be
843 * auto-detected as suggested by JSON RFC.
844 *<p>
845 * NOTE: as of 2.1, should not be used (will be deprecated in 2.2);
846 * instead, should call <code>createParser</code>.
847 *
848 * @param in InputStream to use for reading JSON content to parse
849 *
850 * @deprecated Since 2.2, use {@link #createParser(InputStream)} instead.
851 */
852 @Deprecated
853 public JsonParser createJsonParser(InputStream in)
854 throws IOException, JsonParseException
855 {
856 return createParser(in);
857 }
858
859 /**
860 * Method for constructing parser for parsing
861 * the contents accessed via specified Reader.
862 <p>
863 * The read stream will <b>not be owned</b> by
864 * the parser, it will still be managed (i.e. closed if
865 * end-of-stream is reacher, or parser close method called)
866 * if (and only if) {@link com.fasterxml.jackson.core.JsonParser.Feature#AUTO_CLOSE_SOURCE}
867 * is enabled.
868 *<p>
869 * NOTE: as of 2.1, should not be used (will be deprecated in 2.2);
870 * instead, should call <code>createParser</code>.
871 *
872 * @param r Reader to use for reading JSON content to parse
873 *
874 * @deprecated Since 2.2, use {@link #createParser(Reader)} instead.
875 */
876 @Deprecated
877 public JsonParser createJsonParser(Reader r)
878 throws IOException, JsonParseException
879 {
880 return createParser(r);
881 }
882
883 /**
884 * Method for constructing parser for parsing
885 * the contents of given byte array.
886 *<p>
887 * NOTE: as of 2.1, should not be used (will be deprecated in 2.2);
888 * instead, should call <code>createParser</code>.
889 *
890 * @deprecated Since 2.2, use {@link #createParser(byte[])} instead.
891 */
892 @Deprecated
893 public JsonParser createJsonParser(byte[] data)
894 throws IOException, JsonParseException
895 {
896 return createParser(data);
897 }
898
899 /**
900 * Method for constructing parser for parsing
901 * the contents of given byte array.
902 *<p>
903 * NOTE: as of 2.1, should not be used (will be deprecated in 2.2);
904 * instead, should call <code>createParser</code>.
905 *
906 * @param data Buffer that contains data to parse
907 * @param offset Offset of the first data byte within buffer
908 * @param len Length of contents to parse within buffer
909 *
910 * @deprecated Since 2.2, use {@link #createParser(byte[],int,int)} instead.
911 */
912 @Deprecated
913 public JsonParser createJsonParser(byte[] data, int offset, int len)
914 throws IOException, JsonParseException
915 {
916 return createParser(data, offset, len);
917 }
918
919 /**
920 * Method for constructing parser for parsing
921 * contents of given String.
922 *
923 * @deprecated Since 2.2, use {@link #createParser(String)} instead.
924 */
925 @Deprecated
926 public JsonParser createJsonParser(String content)
927 throws IOException, JsonParseException
928 {
929 return createParser(content);
930 }
931
932 /*
933 /**********************************************************
Tatu Salorantafeaabd12012-07-22 23:03:41 -0700934 /* Generator factories, new (as per [Issue-25]
Tatu Salorantaf15531c2011-12-22 23:00:40 -0800935 /**********************************************************
936 */
937
938 /**
939 * Method for constructing JSON generator for writing JSON content
940 * using specified output stream.
941 * Encoding to use must be specified, and needs to be one of available
942 * types (as per JSON specification).
943 *<p>
944 * Underlying stream <b>is NOT owned</b> by the generator constructed,
945 * so that generator will NOT close the output stream when
946 * {@link JsonGenerator#close} is called (unless auto-closing
947 * feature,
948 * {@link com.fasterxml.jackson.core.JsonGenerator.Feature#AUTO_CLOSE_TARGET}
949 * is enabled).
950 * Using application needs to close it explicitly if this is the case.
951 *<p>
952 * Note: there are formats that use fixed encoding (like most binary data formats)
953 * and that ignore passed in encoding.
Tatu Salorantafeaabd12012-07-22 23:03:41 -0700954 *<p>
955 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
956 * instead, should call <code>createGenerator</code>.
957 *
958 * @since 2.1 Will eventually replace <code>createJsonGenerator</code> variant.
959 *
960 * @param out OutputStream to use for writing JSON content
961 * @param enc Character encoding to use
962 */
963 public JsonGenerator createGenerator(OutputStream out, JsonEncoding enc)
964 throws IOException
965 {
966 return createJsonGenerator(out, enc);
967 }
968
969 /**
970 * Method for constructing JSON generator for writing JSON content
971 * using specified Writer.
972 *<p>
973 * Underlying stream <b>is NOT owned</b> by the generator constructed,
974 * so that generator will NOT close the Reader when
975 * {@link JsonGenerator#close} is called (unless auto-closing
976 * feature,
977 * {@link com.fasterxml.jackson.core.JsonGenerator.Feature#AUTO_CLOSE_TARGET} is enabled).
978 * Using application needs to close it explicitly.
979 *<p>
980 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
981 * instead, should call <code>createGenerator</code>.
982 *
983 * @since 2.1 Will eventually replace <code>createJsonGenerator</code> variant.
984 *
985 * @param out Writer to use for writing JSON content
986 */
987 public JsonGenerator createGenerator(Writer out)
988 throws IOException
989 {
990 return createJsonGenerator(out);
991 }
992
993 /**
994 * Convenience method for constructing generator that uses default
995 * encoding of the format (UTF-8 for JSON and most other data formats).
996 *<p>
997 * Note: there are formats that use fixed encoding (like most binary data formats).
998 *<p>
999 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
1000 * instead, should call <code>createGenerator</code>.
1001 *
1002 * @since 2.1 Will eventually replace <code>createJsonGenerator</code> variant.
1003 */
1004 public JsonGenerator createGenerator(OutputStream out) throws IOException {
1005 return createJsonGenerator(out);
1006 }
1007
1008 /**
1009 * Method for constructing JSON generator for writing JSON content
1010 * to specified file, overwriting contents it might have (or creating
1011 * it if such file does not yet exist).
1012 * Encoding to use must be specified, and needs to be one of available
1013 * types (as per JSON specification).
1014 *<p>
1015 * Underlying stream <b>is owned</b> by the generator constructed,
1016 * i.e. generator will handle closing of file when
1017 * {@link JsonGenerator#close} is called.
1018 *<p>
1019 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
1020 * instead, should call <code>createGenerator</code>.
1021 *
1022 * @since 2.1 Will eventually replace <code>createJsonGenerator</code> variant.
1023 *
1024 * @param f File to write contents to
1025 * @param enc Character encoding to use
1026 */
1027 public JsonGenerator createGenerator(File f, JsonEncoding enc)
1028 throws IOException
1029 {
1030 return createJsonGenerator(f, enc);
1031 }
1032
1033 /*
1034 /**********************************************************
1035 /* Generator factories, old (as per [Issue-25]
1036 /**********************************************************
1037 */
1038
1039 /**
1040 * Method for constructing JSON generator for writing JSON content
1041 * using specified output stream.
1042 * Encoding to use must be specified, and needs to be one of available
1043 * types (as per JSON specification).
1044 *<p>
1045 * Underlying stream <b>is NOT owned</b> by the generator constructed,
1046 * so that generator will NOT close the output stream when
1047 * {@link JsonGenerator#close} is called (unless auto-closing
1048 * feature,
1049 * {@link com.fasterxml.jackson.core.JsonGenerator.Feature#AUTO_CLOSE_TARGET}
1050 * is enabled).
1051 * Using application needs to close it explicitly if this is the case.
1052 *<p>
1053 * Note: there are formats that use fixed encoding (like most binary data formats)
1054 * and that ignore passed in encoding.
1055 *<p>
1056 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
1057 * instead, should call <code>createGenerator</code>.
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001058 *
1059 * @param out OutputStream to use for writing JSON content
1060 * @param enc Character encoding to use
1061 */
1062 public JsonGenerator createJsonGenerator(OutputStream out, JsonEncoding enc)
1063 throws IOException
1064 {
1065 // false -> we won't manage the stream unless explicitly directed to
1066 IOContext ctxt = _createContext(out, false);
1067 ctxt.setEncoding(enc);
1068 if (enc == JsonEncoding.UTF8) {
1069 // [JACKSON-512]: allow wrapping with _outputDecorator
1070 if (_outputDecorator != null) {
1071 out = _outputDecorator.decorate(ctxt, out);
1072 }
1073 return _createUTF8JsonGenerator(out, ctxt);
1074 }
1075 Writer w = _createWriter(out, enc, ctxt);
1076 // [JACKSON-512]: allow wrapping with _outputDecorator
1077 if (_outputDecorator != null) {
1078 w = _outputDecorator.decorate(ctxt, w);
1079 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001080 return _createGenerator(w, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001081 }
1082
1083 /**
1084 * Method for constructing JSON generator for writing JSON content
1085 * using specified Writer.
1086 *<p>
1087 * Underlying stream <b>is NOT owned</b> by the generator constructed,
1088 * so that generator will NOT close the Reader when
1089 * {@link JsonGenerator#close} is called (unless auto-closing
1090 * feature,
1091 * {@link com.fasterxml.jackson.core.JsonGenerator.Feature#AUTO_CLOSE_TARGET} is enabled).
1092 * Using application needs to close it explicitly.
Tatu Salorantafeaabd12012-07-22 23:03:41 -07001093 *<p>
1094 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
1095 * instead, should call <code>createGenerator</code>.
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001096 *
1097 * @param out Writer to use for writing JSON content
1098 */
1099 public JsonGenerator createJsonGenerator(Writer out)
1100 throws IOException
1101 {
1102 IOContext ctxt = _createContext(out, false);
1103 // [JACKSON-512]: allow wrapping with _outputDecorator
1104 if (_outputDecorator != null) {
1105 out = _outputDecorator.decorate(ctxt, out);
1106 }
Tatu Saloranta68194922012-11-15 20:34:29 -08001107 return _createGenerator(out, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001108 }
1109
1110 /**
1111 * Convenience method for constructing generator that uses default
1112 * encoding of the format (UTF-8 for JSON and most other data formats).
1113 *<p>
1114 * Note: there are formats that use fixed encoding (like most binary data formats).
Tatu Salorantafeaabd12012-07-22 23:03:41 -07001115 *<p>
1116 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
1117 * instead, should call <code>createGenerator</code>.
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001118 */
1119 public JsonGenerator createJsonGenerator(OutputStream out) throws IOException {
1120 return createJsonGenerator(out, JsonEncoding.UTF8);
1121 }
1122
1123 /**
1124 * Method for constructing JSON generator for writing JSON content
1125 * to specified file, overwriting contents it might have (or creating
1126 * it if such file does not yet exist).
1127 * Encoding to use must be specified, and needs to be one of available
1128 * types (as per JSON specification).
1129 *<p>
1130 * Underlying stream <b>is owned</b> by the generator constructed,
1131 * i.e. generator will handle closing of file when
1132 * {@link JsonGenerator#close} is called.
Tatu Salorantafeaabd12012-07-22 23:03:41 -07001133 *<p>
1134 * NOTE: starting with 2.1, should not be used (will be deprecated in 2.2);
1135 * instead, should call <code>createGenerator</code>.
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001136 *
1137 * @param f File to write contents to
1138 * @param enc Character encoding to use
1139 */
1140 public JsonGenerator createJsonGenerator(File f, JsonEncoding enc)
1141 throws IOException
1142 {
Tatu Saloranta68194922012-11-15 20:34:29 -08001143 OutputStream out = new FileOutputStream(f);
1144 // true -> yes, we have to manage the stream since we created it
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001145 IOContext ctxt = _createContext(out, true);
1146 ctxt.setEncoding(enc);
1147 if (enc == JsonEncoding.UTF8) {
1148 // [JACKSON-512]: allow wrapping with _outputDecorator
1149 if (_outputDecorator != null) {
1150 out = _outputDecorator.decorate(ctxt, out);
1151 }
1152 return _createUTF8JsonGenerator(out, ctxt);
1153 }
1154 Writer w = _createWriter(out, enc, ctxt);
1155 // [JACKSON-512]: allow wrapping with _outputDecorator
1156 if (_outputDecorator != null) {
1157 w = _outputDecorator.decorate(ctxt, w);
1158 }
Tatu Saloranta68194922012-11-15 20:34:29 -08001159 return _createGenerator(w, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001160 }
1161
1162 /*
1163 /**********************************************************
1164 /* Factory methods used by factory for creating parser instances,
1165 /* overridable by sub-classes
1166 /**********************************************************
1167 */
1168
1169 /**
1170 * Overridable factory method that actually instantiates desired parser
1171 * given {@link InputStream} and context object.
1172 *<p>
1173 * This method is specifically designed to remain
1174 * compatible between minor versions so that sub-classes can count
1175 * on it being called as expected. That is, it is part of official
1176 * interface from sub-class perspective, although not a public
1177 * method available to users of factory implementations.
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001178 *
1179 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001180 */
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001181 protected JsonParser _createParser(InputStream in, IOContext ctxt)
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001182 throws IOException, JsonParseException
1183 {
Tatu Saloranta68194922012-11-15 20:34:29 -08001184 // As per [JACKSON-259], may want to fully disable canonicalization:
1185 return new ByteSourceJsonBootstrapper(ctxt, in).constructParser(_parserFeatures,
1186 _objectCodec, _rootByteSymbols, _rootCharSymbols,
1187 isEnabled(JsonFactory.Feature.CANONICALIZE_FIELD_NAMES),
1188 isEnabled(JsonFactory.Feature.INTERN_FIELD_NAMES));
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001189 }
1190
1191 /**
1192 * @deprecated since 2.1 -- use {@link #_createParser(InputStream, IOContext)} instead
1193 */
1194 @Deprecated
1195 protected JsonParser _createJsonParser(InputStream in, IOContext ctxt) throws IOException, JsonParseException {
Tatu Saloranta68194922012-11-15 20:34:29 -08001196 return _createParser(in, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001197 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001198
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001199 /**
1200 * Overridable factory method that actually instantiates parser
1201 * using given {@link Reader} object for reading content.
1202 *<p>
1203 * This method is specifically designed to remain
1204 * compatible between minor versions so that sub-classes can count
1205 * on it being called as expected. That is, it is part of official
1206 * interface from sub-class perspective, although not a public
1207 * method available to users of factory implementations.
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001208 *
1209 * @since 2.1
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001210 */
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001211 protected JsonParser _createParser(Reader r, IOContext ctxt)
1212 throws IOException, JsonParseException
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001213 {
Tatu Saloranta68194922012-11-15 20:34:29 -08001214 return new ReaderBasedJsonParser(ctxt, _parserFeatures, r, _objectCodec,
1215 _rootCharSymbols.makeChild(isEnabled(JsonFactory.Feature.CANONICALIZE_FIELD_NAMES),
1216 isEnabled(JsonFactory.Feature.INTERN_FIELD_NAMES)));
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001217 }
1218
1219 /**
1220 * @deprecated since 2.1 -- use {@link #_createParser(Reader, IOContext)} instead
1221 */
1222 @Deprecated
1223 protected JsonParser _createJsonParser(Reader r, IOContext ctxt) throws IOException, JsonParseException {
Tatu Saloranta68194922012-11-15 20:34:29 -08001224 return _createParser(r, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001225 }
1226
1227 /**
1228 * Overridable factory method that actually instantiates parser
1229 * using given {@link Reader} object for reading content
1230 * passed as raw byte array.
1231 *<p>
1232 * This method is specifically designed to remain
1233 * compatible between minor versions so that sub-classes can count
1234 * on it being called as expected. That is, it is part of official
1235 * interface from sub-class perspective, although not a public
1236 * method available to users of factory implementations.
1237 */
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001238 protected JsonParser _createParser(byte[] data, int offset, int len, IOContext ctxt)
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001239 throws IOException, JsonParseException
1240 {
Tatu Saloranta68194922012-11-15 20:34:29 -08001241 return new ByteSourceJsonBootstrapper(ctxt, data, offset, len).constructParser(_parserFeatures,
1242 _objectCodec, _rootByteSymbols, _rootCharSymbols,
1243 isEnabled(JsonFactory.Feature.CANONICALIZE_FIELD_NAMES),
1244 isEnabled(JsonFactory.Feature.INTERN_FIELD_NAMES));
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001245 }
1246
1247 /**
1248 * @deprecated since 2.1 -- use {@link #_createParser(byte[], int, int, IOContext)} instead
1249 */
1250 @Deprecated
1251 protected JsonParser _createJsonParser(byte[] data, int offset, int len, IOContext ctxt) throws IOException, JsonParseException {
Tatu Saloranta68194922012-11-15 20:34:29 -08001252 return _createParser(data, offset, len, ctxt);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001253 }
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001254
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001255 /*
1256 /**********************************************************
1257 /* Factory methods used by factory for creating generator instances,
1258 /* overridable by sub-classes
1259 /**********************************************************
1260 */
1261
1262 /**
1263 * Overridable factory method that actually instantiates generator for
1264 * given {@link Writer} and context object.
1265 *<p>
1266 * This method is specifically designed to remain
1267 * compatible between minor versions so that sub-classes can count
1268 * on it being called as expected. That is, it is part of official
1269 * interface from sub-class perspective, although not a public
1270 * method available to users of factory implementations.
1271 */
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001272 protected JsonGenerator _createGenerator(Writer out, IOContext ctxt)
1273 throws IOException
1274 {
Tatu Salorantae6dfc692012-09-28 15:34:05 -07001275 WriterBasedJsonGenerator gen = new WriterBasedJsonGenerator(ctxt,
1276 _generatorFeatures, _objectCodec, out);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001277 if (_characterEscapes != null) {
1278 gen.setCharacterEscapes(_characterEscapes);
1279 }
Tatu Salorantae6dfc692012-09-28 15:34:05 -07001280 SerializableString rootSep = _rootValueSeparator;
1281 if (rootSep != DEFAULT_ROOT_VALUE_SEPARATOR) {
1282 gen.setRootValueSeparator(rootSep);
1283 }
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001284 return gen;
1285 }
1286
1287 /**
Tatu Saloranta68194922012-11-15 20:34:29 -08001288 * @deprecated since 2.1 -- use {@link #_createGenerator(Writer, IOContext)} instead
1289 */
1290 @Deprecated
1291 protected JsonGenerator _createJsonGenerator(Writer out, IOContext ctxt)
1292 throws IOException
1293 {
1294 /* NOTE: MUST call the deprecated method until it is deleted, just so
1295 * that override still works as expected, for now.
1296 */
1297 return _createGenerator(out, ctxt);
1298 }
1299
1300 /**
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001301 * Overridable factory method that actually instantiates generator for
1302 * given {@link OutputStream} and context object, using UTF-8 encoding.
1303 *<p>
1304 * This method is specifically designed to remain
1305 * compatible between minor versions so that sub-classes can count
1306 * on it being called as expected. That is, it is part of official
1307 * interface from sub-class perspective, although not a public
1308 * method available to users of factory implementations.
1309 */
Tatu Salorantaeeb2fbd2012-05-28 22:00:08 -07001310 protected JsonGenerator _createUTF8Generator(OutputStream out, IOContext ctxt) throws IOException {
Tatu Salorantae6dfc692012-09-28 15:34:05 -07001311 UTF8JsonGenerator gen = new UTF8JsonGenerator(ctxt,
1312 _generatorFeatures, _objectCodec, out);
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001313 if (_characterEscapes != null) {
1314 gen.setCharacterEscapes(_characterEscapes);
1315 }
Tatu Salorantae6dfc692012-09-28 15:34:05 -07001316 SerializableString rootSep = _rootValueSeparator;
1317 if (rootSep != DEFAULT_ROOT_VALUE_SEPARATOR) {
1318 gen.setRootValueSeparator(rootSep);
1319 }
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001320 return gen;
1321 }
1322
Tatu Saloranta68194922012-11-15 20:34:29 -08001323 /**
1324 * @deprecated since 2.1
1325 */
1326 @Deprecated
1327 protected JsonGenerator _createUTF8JsonGenerator(OutputStream out, IOContext ctxt)
1328 throws IOException
1329 {
1330 return _createUTF8Generator(out, ctxt);
1331 }
1332
Tatu Salorantaf15531c2011-12-22 23:00:40 -08001333 protected Writer _createWriter(OutputStream out, JsonEncoding enc, IOContext ctxt) throws IOException
1334 {
1335 // note: this should not get called any more (caller checks, dispatches)
1336 if (enc == JsonEncoding.UTF8) { // We have optimized writer for UTF-8
1337 return new UTF8Writer(ctxt, out);
1338 }
1339 // not optimal, but should do unless we really care about UTF-16/32 encoding speed
1340 return new OutputStreamWriter(out, enc.getJavaName());
1341 }
1342
1343 /*
1344 /**********************************************************
1345 /* Internal factory methods, other
1346 /**********************************************************
1347 */
1348
1349 /**
1350 * Overridable factory method that actually instantiates desired
1351 * context object.
1352 */
1353 protected IOContext _createContext(Object srcRef, boolean resourceManaged)
1354 {
1355 return new IOContext(_getBufferRecycler(), srcRef, resourceManaged);
1356 }
1357
1358 /**
1359 * Method used by factory to create buffer recycler instances
1360 * for parsers and generators.
1361 *<p>
1362 * Note: only public to give access for <code>ObjectMapper</code>
1363 */
1364 public BufferRecycler _getBufferRecycler()
1365 {
1366 SoftReference<BufferRecycler> ref = _recyclerRef.get();
1367 BufferRecycler br = (ref == null) ? null : ref.get();
1368
1369 if (br == null) {
1370 br = new BufferRecycler();
1371 _recyclerRef.set(new SoftReference<BufferRecycler>(br));
1372 }
1373 return br;
1374 }
1375
1376 /**
1377 * Helper methods used for constructing an optimal stream for
1378 * parsers to use, when input is to be read from an URL.
1379 * This helps when reading file content via URL.
1380 */
1381 protected InputStream _optimizedStreamFromURL(URL url)
1382 throws IOException
1383 {
1384 if ("file".equals(url.getProtocol())) {
1385 /* Can not do this if the path refers
1386 * to a network drive on windows. This fixes the problem;
1387 * might not be needed on all platforms (NFS?), but should not
1388 * matter a lot: performance penalty of extra wrapping is more
1389 * relevant when accessing local file system.
1390 */
1391 String host = url.getHost();
1392 if (host == null || host.length() == 0) {
1393 return new FileInputStream(url.getPath());
1394 }
1395 }
1396 return url.openStream();
1397 }
1398}