001// ***************************************************************************************************************************
002// * Licensed to the Apache Software Foundation (ASF) under one or more contributor license agreements.  See the NOTICE file *
003// * distributed with this work for additional information regarding copyright ownership.  The ASF licenses this file        *
004// * to you under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance            *
005// * with the License.  You may obtain a copy of the License at                                                              *
006// *                                                                                                                         *
007// *  http://www.apache.org/licenses/LICENSE-2.0                                                                             *
008// *                                                                                                                         *
009// * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an  *
010// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the License for the        *
011// * specific language governing permissions and limitations under the License.                                              *
012// ***************************************************************************************************************************
013package org.apache.juneau.json;
014
015import static org.apache.juneau.collections.JsonMap.*;
016
017import java.lang.annotation.*;
018import java.lang.reflect.*;
019import java.nio.charset.*;
020import java.util.*;
021import java.util.concurrent.*;
022
023import org.apache.juneau.*;
024import org.apache.juneau.annotation.*;
025import org.apache.juneau.collections.*;
026import org.apache.juneau.internal.*;
027import org.apache.juneau.jsonschema.*;
028import org.apache.juneau.utils.*;
029
030/**
031 * Serializes POJO metadata to HTTP responses as JSON-Schema.
032 *
033 * <h5 class='topic'>Media types</h5>
034 *
035 * Handles <c>Accept</c> types:  <bc>application/json+schema, text/json+schema</bc>
036 * <p>
037 * Produces <c>Content-Type</c> types:  <bc>application/json</bc>
038 *
039 * <h5 class='topic'>Description</h5>
040 *
041 * Produces the JSON-schema for the JSON produced by the {@link JsonSerializer} class with the same properties.
042 *
043 * <h5 class='section'>Notes:</h5><ul>
044 *    <li class='note'>This class is thread safe and reusable.
045 * </ul>
046 *
047 * <h5 class='section'>See Also:</h5><ul>
048 *    <li class='link'><a class="doclink" href="../../../../index.html#jm.JsonDetails">JSON Details</a>
049
050 * </ul>
051 */
052public class JsonSchemaSerializer extends JsonSerializer implements JsonSchemaMetaProvider {
053
054   //-------------------------------------------------------------------------------------------------------------------
055   // Static
056   //-------------------------------------------------------------------------------------------------------------------
057
058   /** Default serializer, all default settings.*/
059   public static final JsonSchemaSerializer DEFAULT = new JsonSchemaSerializer(create());
060
061   /** Default serializer, all default settings.*/
062   public static final JsonSchemaSerializer DEFAULT_READABLE = new Readable(create());
063
064   /** Default serializer, single quotes, simple mode. */
065   public static final JsonSchemaSerializer DEFAULT_SIMPLE = new Simple(create());
066
067   /** Default serializer, single quotes, simple mode, with whitespace. */
068   public static final JsonSchemaSerializer DEFAULT_SIMPLE_READABLE = new SimpleReadable(create());
069
070   /**
071    * Creates a new builder for this object.
072    *
073    * @return A new builder.
074    */
075   public static Builder create() {
076      return new Builder();
077   }
078
079   //-------------------------------------------------------------------------------------------------------------------
080   // Static subclasses
081   //-------------------------------------------------------------------------------------------------------------------
082
083   /** Default serializer, with whitespace. */
084   public static class Readable extends JsonSchemaSerializer {
085
086      /**
087       * Constructor.
088       *
089       * @param builder The builder for this object.
090       */
091      public Readable(Builder builder) {
092         super(builder.useWhitespace());
093      }
094   }
095
096   /** Default serializer, single quotes, simple mode. */
097   public static class Simple extends JsonSchemaSerializer {
098
099      /**
100       * Constructor.
101       *
102       * @param builder The builder for this object.
103       */
104      public Simple(Builder builder) {
105         super(builder.simpleAttrs().quoteChar('\''));
106      }
107   }
108
109   /** Default serializer, single quotes, simple mode, with whitespace. */
110   public static class SimpleReadable extends JsonSchemaSerializer {
111
112      /**
113       * Constructor.
114       *
115       * @param builder The builder for this object.
116       */
117      public SimpleReadable(Builder builder) {
118         super(builder.simpleAttrs().quoteChar('\'').useWhitespace());
119      }
120   }
121
122   //-------------------------------------------------------------------------------------------------------------------
123   // Builder
124   //-------------------------------------------------------------------------------------------------------------------
125
126   /**
127    * Builder class.
128    */
129   @FluentSetters
130   public static class Builder extends JsonSerializer.Builder {
131
132      private static final Cache<HashKey,JsonSchemaSerializer> CACHE = Cache.of(HashKey.class, JsonSchemaSerializer.class).build();
133
134      JsonSchemaGenerator.Builder generatorBuilder;
135
136      /**
137       * Constructor, default settings.
138       */
139      protected Builder() {
140         produces("application/json");
141         accept("application/json+schema,text/json+schema");
142         generatorBuilder = JsonSchemaGenerator.create().beanContext(beanContext());
143      }
144
145      /**
146       * Copy constructor.
147       *
148       * @param copyFrom The bean to copy from.
149       */
150      protected Builder(JsonSchemaSerializer copyFrom) {
151         super(copyFrom);
152         generatorBuilder = copyFrom.generator.copy().beanContext(beanContext());
153      }
154
155      /**
156       * Copy constructor.
157       *
158       * @param copyFrom The builder to copy from.
159       */
160      protected Builder(Builder copyFrom) {
161         super(copyFrom);
162         generatorBuilder = copyFrom.generatorBuilder.copy().beanContext(beanContext());
163      }
164
165      @Override /* Context.Builder */
166      public Builder copy() {
167         return new Builder(this);
168      }
169
170      @Override /* Context.Builder */
171      public JsonSchemaSerializer build() {
172         return cache(CACHE).build(JsonSchemaSerializer.class);
173      }
174
175      @Override /* Context.Builder */
176      public HashKey hashKey() {
177         return HashKey.of(
178            super.hashKey(),
179            generatorBuilder.hashKey()
180         );
181      }
182
183      //-----------------------------------------------------------------------------------------------------------------
184      // Properties
185      //-----------------------------------------------------------------------------------------------------------------
186
187      /**
188       * <i><l>JsonSchemaSerializer</l> configuration property:&emsp;</i>  Add descriptions.
189       *
190       * <p>
191       * Identifies which categories of types that descriptions should be automatically added to generated schemas.
192       * <p>
193       * The description is the result of calling {@link ClassMeta#getFullName()}.
194       *
195       * <h5 class='section'>See Also:</h5><ul>
196       *    <li class='jm'>{@link org.apache.juneau.jsonschema.JsonSchemaGenerator.Builder#addDescriptionsTo(TypeCategory...)}
197       * </ul>
198       *
199       * @param values
200       *    The values to add to this setting.
201       *    <br>The default is an empty string.
202       * @return This object.
203       */
204      @FluentSetter
205      public Builder addDescriptionsTo(TypeCategory...values) {
206         generatorBuilder.addDescriptionsTo(values);
207         return this;
208      }
209
210      /**
211       * <i><l>JsonSchemaSerializer</l> configuration property:&emsp;</i>  Add examples.
212       *
213       * <p>
214       * Identifies which categories of types that examples should be automatically added to generated schemas.
215       * <p>
216       * The examples come from calling {@link ClassMeta#getExample(BeanSession,JsonParserSession)} which in turn gets examples
217       * from the following:
218       * <ul class='javatree'>
219       *    <li class='ja'>{@link Example}
220       *    <li class='ja'>{@link Marshalled#example() Marshalled(example)}
221       * </ul>
222       *
223       * <h5 class='section'>See Also:</h5><ul>
224       *    <li class='jm'>{@link org.apache.juneau.jsonschema.JsonSchemaGenerator.Builder#addExamplesTo(TypeCategory...)}
225       * </ul>
226       *
227       * @param values
228       *    The values to add to this setting.
229       *    <br>The default is an empty string.
230       * @return This object.
231       */
232      @FluentSetter
233      public Builder addExamplesTo(TypeCategory...values) {
234         generatorBuilder.addExamplesTo(values);
235         return this;
236      }
237
238      /**
239       * <i><l>JsonSchemaSerializer</l> configuration property:&emsp;</i>  Allow nested descriptions.
240       *
241       * <p>
242       * Identifies whether nested descriptions are allowed in schema definitions.
243       *
244       * <h5 class='section'>See Also:</h5><ul>
245       *    <li class='jm'>{@link org.apache.juneau.jsonschema.JsonSchemaGenerator.Builder#allowNestedDescriptions()}
246       * </ul>
247       *
248       * @return This object.
249       */
250      @FluentSetter
251      public Builder allowNestedDescriptions() {
252         generatorBuilder.allowNestedDescriptions();
253         return this;
254      }
255
256      /**
257       * <i><l>JsonSchemaSerializer</l> configuration property:&emsp;</i>  Allow nested examples.
258       *
259       * <p>
260       * Identifies whether nested examples are allowed in schema definitions.
261       *
262       * <h5 class='section'>See Also:</h5><ul>
263       *    <li class='jm'>{@link org.apache.juneau.jsonschema.JsonSchemaGenerator.Builder#allowNestedExamples()}
264       * </ul>
265       *
266       * @return This object.
267       */
268      @FluentSetter
269      public Builder allowNestedExamples() {
270         generatorBuilder.allowNestedExamples();
271         return this;
272      }
273
274      /**
275       * <i><l>JsonSchemaSerializer</l> configuration property:&emsp;</i>  Schema definition mapper.
276       *
277       * <p>
278       * Interface to use for converting Bean classes to definition IDs and URIs.
279       * <p>
280       * Used primarily for defining common definition sections for beans in Swagger JSON.
281       * <p>
282       * This setting is ignored if {@link org.apache.juneau.jsonschema.JsonSchemaGenerator.Builder#useBeanDefs()} is not enabled.
283       *
284       * <h5 class='section'>See Also:</h5><ul>
285       *    <li class='jm'>{@link org.apache.juneau.jsonschema.JsonSchemaGenerator.Builder#beanDefMapper(Class)}
286       * </ul>
287       *
288       * @param value
289       *    The new value for this property.
290       *    <br>The default is {@link org.apache.juneau.jsonschema.BasicBeanDefMapper}.
291       * @return This object.
292       */
293      @FluentSetter
294      public Builder beanDefMapper(Class<? extends BeanDefMapper> value) {
295         generatorBuilder.beanDefMapper(value);
296         return this;
297      }
298
299      /**
300       * <i><l>JsonSchemaSerializer</l> configuration property:&emsp;</i>  Use bean definitions.
301       *
302       * <p>
303       * When enabled, schemas on beans will be serialized as the following:
304       * <p class='bjson'>
305       *    {
306       *       type: <js>'object'</js>,
307       *       <js>'$ref'</js>: <js>'#/definitions/TypeId'</js>
308       *    }
309       * </p>
310       *
311       * @return This object.
312       */
313      @FluentSetter
314      public Builder useBeanDefs() {
315         generatorBuilder.useBeanDefs();
316         return this;
317      }
318
319      // <FluentSetters>
320
321      @Override /* GENERATED - org.apache.juneau.Context.Builder */
322      public Builder annotations(Annotation...values) {
323         super.annotations(values);
324         return this;
325      }
326
327      @Override /* GENERATED - org.apache.juneau.Context.Builder */
328      public Builder apply(AnnotationWorkList work) {
329         super.apply(work);
330         return this;
331      }
332
333      @Override /* GENERATED - org.apache.juneau.Context.Builder */
334      public Builder applyAnnotations(java.lang.Class<?>...fromClasses) {
335         super.applyAnnotations(fromClasses);
336         return this;
337      }
338
339      @Override /* GENERATED - org.apache.juneau.Context.Builder */
340      public Builder applyAnnotations(Method...fromMethods) {
341         super.applyAnnotations(fromMethods);
342         return this;
343      }
344
345      @Override /* GENERATED - org.apache.juneau.Context.Builder */
346      public Builder cache(Cache<HashKey,? extends org.apache.juneau.Context> value) {
347         super.cache(value);
348         return this;
349      }
350
351      @Override /* GENERATED - org.apache.juneau.Context.Builder */
352      public Builder debug() {
353         super.debug();
354         return this;
355      }
356
357      @Override /* GENERATED - org.apache.juneau.Context.Builder */
358      public Builder debug(boolean value) {
359         super.debug(value);
360         return this;
361      }
362
363      @Override /* GENERATED - org.apache.juneau.Context.Builder */
364      public Builder impl(Context value) {
365         super.impl(value);
366         return this;
367      }
368
369      @Override /* GENERATED - org.apache.juneau.Context.Builder */
370      public Builder type(Class<? extends org.apache.juneau.Context> value) {
371         super.type(value);
372         return this;
373      }
374
375      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
376      public Builder beanClassVisibility(Visibility value) {
377         super.beanClassVisibility(value);
378         return this;
379      }
380
381      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
382      public Builder beanConstructorVisibility(Visibility value) {
383         super.beanConstructorVisibility(value);
384         return this;
385      }
386
387      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
388      public Builder beanContext(BeanContext value) {
389         super.beanContext(value);
390         return this;
391      }
392
393      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
394      public Builder beanContext(BeanContext.Builder value) {
395         super.beanContext(value);
396         return this;
397      }
398
399      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
400      public Builder beanDictionary(java.lang.Class<?>...values) {
401         super.beanDictionary(values);
402         return this;
403      }
404
405      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
406      public Builder beanFieldVisibility(Visibility value) {
407         super.beanFieldVisibility(value);
408         return this;
409      }
410
411      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
412      public Builder beanInterceptor(Class<?> on, Class<? extends org.apache.juneau.swap.BeanInterceptor<?>> value) {
413         super.beanInterceptor(on, value);
414         return this;
415      }
416
417      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
418      public Builder beanMapPutReturnsOldValue() {
419         super.beanMapPutReturnsOldValue();
420         return this;
421      }
422
423      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
424      public Builder beanMethodVisibility(Visibility value) {
425         super.beanMethodVisibility(value);
426         return this;
427      }
428
429      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
430      public Builder beanProperties(Map<String,Object> values) {
431         super.beanProperties(values);
432         return this;
433      }
434
435      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
436      public Builder beanProperties(Class<?> beanClass, String properties) {
437         super.beanProperties(beanClass, properties);
438         return this;
439      }
440
441      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
442      public Builder beanProperties(String beanClassName, String properties) {
443         super.beanProperties(beanClassName, properties);
444         return this;
445      }
446
447      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
448      public Builder beanPropertiesExcludes(Map<String,Object> values) {
449         super.beanPropertiesExcludes(values);
450         return this;
451      }
452
453      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
454      public Builder beanPropertiesExcludes(Class<?> beanClass, String properties) {
455         super.beanPropertiesExcludes(beanClass, properties);
456         return this;
457      }
458
459      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
460      public Builder beanPropertiesExcludes(String beanClassName, String properties) {
461         super.beanPropertiesExcludes(beanClassName, properties);
462         return this;
463      }
464
465      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
466      public Builder beanPropertiesReadOnly(Map<String,Object> values) {
467         super.beanPropertiesReadOnly(values);
468         return this;
469      }
470
471      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
472      public Builder beanPropertiesReadOnly(Class<?> beanClass, String properties) {
473         super.beanPropertiesReadOnly(beanClass, properties);
474         return this;
475      }
476
477      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
478      public Builder beanPropertiesReadOnly(String beanClassName, String properties) {
479         super.beanPropertiesReadOnly(beanClassName, properties);
480         return this;
481      }
482
483      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
484      public Builder beanPropertiesWriteOnly(Map<String,Object> values) {
485         super.beanPropertiesWriteOnly(values);
486         return this;
487      }
488
489      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
490      public Builder beanPropertiesWriteOnly(Class<?> beanClass, String properties) {
491         super.beanPropertiesWriteOnly(beanClass, properties);
492         return this;
493      }
494
495      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
496      public Builder beanPropertiesWriteOnly(String beanClassName, String properties) {
497         super.beanPropertiesWriteOnly(beanClassName, properties);
498         return this;
499      }
500
501      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
502      public Builder beansRequireDefaultConstructor() {
503         super.beansRequireDefaultConstructor();
504         return this;
505      }
506
507      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
508      public Builder beansRequireSerializable() {
509         super.beansRequireSerializable();
510         return this;
511      }
512
513      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
514      public Builder beansRequireSettersForGetters() {
515         super.beansRequireSettersForGetters();
516         return this;
517      }
518
519      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
520      public Builder dictionaryOn(Class<?> on, java.lang.Class<?>...values) {
521         super.dictionaryOn(on, values);
522         return this;
523      }
524
525      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
526      public Builder disableBeansRequireSomeProperties() {
527         super.disableBeansRequireSomeProperties();
528         return this;
529      }
530
531      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
532      public Builder disableIgnoreMissingSetters() {
533         super.disableIgnoreMissingSetters();
534         return this;
535      }
536
537      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
538      public Builder disableIgnoreTransientFields() {
539         super.disableIgnoreTransientFields();
540         return this;
541      }
542
543      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
544      public Builder disableIgnoreUnknownNullBeanProperties() {
545         super.disableIgnoreUnknownNullBeanProperties();
546         return this;
547      }
548
549      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
550      public Builder disableInterfaceProxies() {
551         super.disableInterfaceProxies();
552         return this;
553      }
554
555      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
556      public <T> Builder example(Class<T> pojoClass, T o) {
557         super.example(pojoClass, o);
558         return this;
559      }
560
561      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
562      public <T> Builder example(Class<T> pojoClass, String json) {
563         super.example(pojoClass, json);
564         return this;
565      }
566
567      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
568      public Builder findFluentSetters() {
569         super.findFluentSetters();
570         return this;
571      }
572
573      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
574      public Builder findFluentSetters(Class<?> on) {
575         super.findFluentSetters(on);
576         return this;
577      }
578
579      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
580      public Builder ignoreInvocationExceptionsOnGetters() {
581         super.ignoreInvocationExceptionsOnGetters();
582         return this;
583      }
584
585      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
586      public Builder ignoreInvocationExceptionsOnSetters() {
587         super.ignoreInvocationExceptionsOnSetters();
588         return this;
589      }
590
591      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
592      public Builder ignoreUnknownBeanProperties() {
593         super.ignoreUnknownBeanProperties();
594         return this;
595      }
596
597      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
598      public Builder ignoreUnknownEnumValues() {
599         super.ignoreUnknownEnumValues();
600         return this;
601      }
602
603      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
604      public Builder implClass(Class<?> interfaceClass, Class<?> implClass) {
605         super.implClass(interfaceClass, implClass);
606         return this;
607      }
608
609      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
610      public Builder implClasses(Map<Class<?>,Class<?>> values) {
611         super.implClasses(values);
612         return this;
613      }
614
615      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
616      public Builder interfaceClass(Class<?> on, Class<?> value) {
617         super.interfaceClass(on, value);
618         return this;
619      }
620
621      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
622      public Builder interfaces(java.lang.Class<?>...value) {
623         super.interfaces(value);
624         return this;
625      }
626
627      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
628      public Builder locale(Locale value) {
629         super.locale(value);
630         return this;
631      }
632
633      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
634      public Builder mediaType(MediaType value) {
635         super.mediaType(value);
636         return this;
637      }
638
639      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
640      public Builder notBeanClasses(java.lang.Class<?>...values) {
641         super.notBeanClasses(values);
642         return this;
643      }
644
645      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
646      public Builder notBeanPackages(String...values) {
647         super.notBeanPackages(values);
648         return this;
649      }
650
651      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
652      public Builder propertyNamer(Class<? extends org.apache.juneau.PropertyNamer> value) {
653         super.propertyNamer(value);
654         return this;
655      }
656
657      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
658      public Builder propertyNamer(Class<?> on, Class<? extends org.apache.juneau.PropertyNamer> value) {
659         super.propertyNamer(on, value);
660         return this;
661      }
662
663      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
664      public Builder sortProperties() {
665         super.sortProperties();
666         return this;
667      }
668
669      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
670      public Builder sortProperties(java.lang.Class<?>...on) {
671         super.sortProperties(on);
672         return this;
673      }
674
675      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
676      public Builder stopClass(Class<?> on, Class<?> value) {
677         super.stopClass(on, value);
678         return this;
679      }
680
681      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
682      public <T, S> Builder swap(Class<T> normalClass, Class<S> swappedClass, ThrowingFunction<T,S> swapFunction) {
683         super.swap(normalClass, swappedClass, swapFunction);
684         return this;
685      }
686
687      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
688      public <T, S> Builder swap(Class<T> normalClass, Class<S> swappedClass, ThrowingFunction<T,S> swapFunction, ThrowingFunction<S,T> unswapFunction) {
689         super.swap(normalClass, swappedClass, swapFunction, unswapFunction);
690         return this;
691      }
692
693      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
694      public Builder swaps(java.lang.Class<?>...values) {
695         super.swaps(values);
696         return this;
697      }
698
699      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
700      public Builder timeZone(TimeZone value) {
701         super.timeZone(value);
702         return this;
703      }
704
705      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
706      public Builder typeName(Class<?> on, String value) {
707         super.typeName(on, value);
708         return this;
709      }
710
711      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
712      public Builder typePropertyName(String value) {
713         super.typePropertyName(value);
714         return this;
715      }
716
717      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
718      public Builder typePropertyName(Class<?> on, String value) {
719         super.typePropertyName(on, value);
720         return this;
721      }
722
723      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
724      public Builder useEnumNames() {
725         super.useEnumNames();
726         return this;
727      }
728
729      @Override /* GENERATED - org.apache.juneau.BeanContextable.Builder */
730      public Builder useJavaBeanIntrospector() {
731         super.useJavaBeanIntrospector();
732         return this;
733      }
734
735      @Override /* GENERATED - org.apache.juneau.BeanTraverseContext.Builder */
736      public Builder detectRecursions() {
737         super.detectRecursions();
738         return this;
739      }
740
741      @Override /* GENERATED - org.apache.juneau.BeanTraverseContext.Builder */
742      public Builder detectRecursions(boolean value) {
743         super.detectRecursions(value);
744         return this;
745      }
746
747      @Override /* GENERATED - org.apache.juneau.BeanTraverseContext.Builder */
748      public Builder ignoreRecursions() {
749         super.ignoreRecursions();
750         return this;
751      }
752
753      @Override /* GENERATED - org.apache.juneau.BeanTraverseContext.Builder */
754      public Builder ignoreRecursions(boolean value) {
755         super.ignoreRecursions(value);
756         return this;
757      }
758
759      @Override /* GENERATED - org.apache.juneau.BeanTraverseContext.Builder */
760      public Builder initialDepth(int value) {
761         super.initialDepth(value);
762         return this;
763      }
764
765      @Override /* GENERATED - org.apache.juneau.BeanTraverseContext.Builder */
766      public Builder maxDepth(int value) {
767         super.maxDepth(value);
768         return this;
769      }
770
771      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
772      public Builder accept(String value) {
773         super.accept(value);
774         return this;
775      }
776
777      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
778      public Builder addBeanTypes() {
779         super.addBeanTypes();
780         return this;
781      }
782
783      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
784      public Builder addBeanTypes(boolean value) {
785         super.addBeanTypes(value);
786         return this;
787      }
788
789      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
790      public Builder addRootType() {
791         super.addRootType();
792         return this;
793      }
794
795      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
796      public Builder addRootType(boolean value) {
797         super.addRootType(value);
798         return this;
799      }
800
801      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
802      public Builder keepNullProperties() {
803         super.keepNullProperties();
804         return this;
805      }
806
807      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
808      public Builder keepNullProperties(boolean value) {
809         super.keepNullProperties(value);
810         return this;
811      }
812
813      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
814      public Builder listener(Class<? extends org.apache.juneau.serializer.SerializerListener> value) {
815         super.listener(value);
816         return this;
817      }
818
819      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
820      public Builder produces(String value) {
821         super.produces(value);
822         return this;
823      }
824
825      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
826      public Builder sortCollections() {
827         super.sortCollections();
828         return this;
829      }
830
831      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
832      public Builder sortCollections(boolean value) {
833         super.sortCollections(value);
834         return this;
835      }
836
837      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
838      public Builder sortMaps() {
839         super.sortMaps();
840         return this;
841      }
842
843      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
844      public Builder sortMaps(boolean value) {
845         super.sortMaps(value);
846         return this;
847      }
848
849      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
850      public Builder trimEmptyCollections() {
851         super.trimEmptyCollections();
852         return this;
853      }
854
855      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
856      public Builder trimEmptyCollections(boolean value) {
857         super.trimEmptyCollections(value);
858         return this;
859      }
860
861      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
862      public Builder trimEmptyMaps() {
863         super.trimEmptyMaps();
864         return this;
865      }
866
867      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
868      public Builder trimEmptyMaps(boolean value) {
869         super.trimEmptyMaps(value);
870         return this;
871      }
872
873      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
874      public Builder trimStrings() {
875         super.trimStrings();
876         return this;
877      }
878
879      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
880      public Builder trimStrings(boolean value) {
881         super.trimStrings(value);
882         return this;
883      }
884
885      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
886      public Builder uriContext(UriContext value) {
887         super.uriContext(value);
888         return this;
889      }
890
891      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
892      public Builder uriRelativity(UriRelativity value) {
893         super.uriRelativity(value);
894         return this;
895      }
896
897      @Override /* GENERATED - org.apache.juneau.serializer.Serializer.Builder */
898      public Builder uriResolution(UriResolution value) {
899         super.uriResolution(value);
900         return this;
901      }
902
903      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
904      public Builder fileCharset(Charset value) {
905         super.fileCharset(value);
906         return this;
907      }
908
909      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
910      public Builder maxIndent(int value) {
911         super.maxIndent(value);
912         return this;
913      }
914
915      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
916      public Builder quoteChar(char value) {
917         super.quoteChar(value);
918         return this;
919      }
920
921      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
922      public Builder quoteCharOverride(char value) {
923         super.quoteCharOverride(value);
924         return this;
925      }
926
927      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
928      public Builder sq() {
929         super.sq();
930         return this;
931      }
932
933      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
934      public Builder streamCharset(Charset value) {
935         super.streamCharset(value);
936         return this;
937      }
938
939      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
940      public Builder useWhitespace() {
941         super.useWhitespace();
942         return this;
943      }
944
945      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
946      public Builder useWhitespace(boolean value) {
947         super.useWhitespace(value);
948         return this;
949      }
950
951      @Override /* GENERATED - org.apache.juneau.serializer.WriterSerializer.Builder */
952      public Builder ws() {
953         super.ws();
954         return this;
955      }
956
957      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
958      public Builder addBeanTypesJson() {
959         super.addBeanTypesJson();
960         return this;
961      }
962
963      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
964      public Builder addBeanTypesJson(boolean value) {
965         super.addBeanTypesJson(value);
966         return this;
967      }
968
969      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
970      public Builder escapeSolidus() {
971         super.escapeSolidus();
972         return this;
973      }
974
975      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
976      public Builder escapeSolidus(boolean value) {
977         super.escapeSolidus(value);
978         return this;
979      }
980
981      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
982      public Builder simpleAttrs() {
983         super.simpleAttrs();
984         return this;
985      }
986
987      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
988      public Builder simpleAttrs(boolean value) {
989         super.simpleAttrs(value);
990         return this;
991      }
992
993      @Override /* GENERATED - org.apache.juneau.json.JsonSerializer.Builder */
994      public Builder json5() {
995         super.json5();
996         return this;
997      }
998
999      // </FluentSetters>
1000   }
1001
1002   //-------------------------------------------------------------------------------------------------------------------
1003   // Instance
1004   //-------------------------------------------------------------------------------------------------------------------
1005
1006   final JsonSchemaGenerator generator;
1007
1008   private final Map<ClassMeta<?>,JsonSchemaClassMeta> jsonSchemaClassMetas = new ConcurrentHashMap<>();
1009   private final Map<BeanPropertyMeta,JsonSchemaBeanPropertyMeta> jsonSchemaBeanPropertyMetas = new ConcurrentHashMap<>();
1010
1011   /**
1012    * Constructor.
1013    *
1014    * @param builder The builder for this object.
1015    */
1016   public JsonSchemaSerializer(Builder builder) {
1017      super(builder.detectRecursions().ignoreRecursions());
1018
1019      generator = builder.generatorBuilder.build();
1020   }
1021
1022   @Override /* Context */
1023   public Builder copy() {
1024      return new Builder(this);
1025   }
1026
1027   @Override /* Context */
1028   public JsonSchemaSerializerSession.Builder createSession() {
1029      return JsonSchemaSerializerSession.create(this);
1030   }
1031
1032   @Override /* Context */
1033   public JsonSchemaSerializerSession getSession() {
1034      return createSession().build();
1035   }
1036
1037   JsonSchemaGenerator getGenerator() {
1038      return generator;
1039   }
1040
1041   //-----------------------------------------------------------------------------------------------------------------
1042   // Extended metadata
1043   //-----------------------------------------------------------------------------------------------------------------
1044
1045   @Override /* JsonSchemaMetaProvider */
1046   public JsonSchemaClassMeta getJsonSchemaClassMeta(ClassMeta<?> cm) {
1047      JsonSchemaClassMeta m = jsonSchemaClassMetas.get(cm);
1048      if (m == null) {
1049         m = new JsonSchemaClassMeta(cm, this);
1050         jsonSchemaClassMetas.put(cm, m);
1051      }
1052      return m;
1053   }
1054
1055   @Override /* JsonSchemaMetaProvider */
1056   public JsonSchemaBeanPropertyMeta getJsonSchemaBeanPropertyMeta(BeanPropertyMeta bpm) {
1057      JsonSchemaBeanPropertyMeta m = jsonSchemaBeanPropertyMetas.get(bpm);
1058      if (m == null) {
1059         m = new JsonSchemaBeanPropertyMeta(bpm.getDelegateFor(), this);
1060         jsonSchemaBeanPropertyMetas.put(bpm, m);
1061      }
1062      return m;
1063   }
1064
1065   //-----------------------------------------------------------------------------------------------------------------
1066   // Other methods
1067   //-----------------------------------------------------------------------------------------------------------------
1068
1069   @Override /* Context */
1070   protected JsonMap properties() {
1071      return filteredMap("generator", generator);
1072   }
1073}