• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 package kotlinx.serialization.json
2 
3 import kotlinx.serialization.*
4 import kotlinx.serialization.modules.*
5 import kotlinx.serialization.descriptors.*
6 
7 /**
8  * Configuration of the current [Json] instance available through [Json.configuration]
9  * and configured with [JsonBuilder] constructor.
10  *
11  * Can be used for debug purposes and for custom Json-specific serializers
12  * via [JsonEncoder] and [JsonDecoder].
13  *
14  * Standalone configuration object is meaningless and can nor be used outside the
15  * [Json], neither new [Json] instance can be created from it.
16  *
17  * Detailed description of each property is available in [JsonBuilder] class.
18  */
19 public class JsonConfiguration @OptIn(ExperimentalSerializationApi::class) internal constructor(
20     public val encodeDefaults: Boolean = false,
21     public val ignoreUnknownKeys: Boolean = false,
22     public val isLenient: Boolean = false,
23     public val allowStructuredMapKeys: Boolean = false,
24     public val prettyPrint: Boolean = false,
25     public val explicitNulls: Boolean = true,
26     @ExperimentalSerializationApi
27     public val prettyPrintIndent: String = "    ",
28     public val coerceInputValues: Boolean = false,
29     public val useArrayPolymorphism: Boolean = false,
30     public val classDiscriminator: String = "type",
31     public val allowSpecialFloatingPointValues: Boolean = false,
32     public val useAlternativeNames: Boolean = true,
33     @ExperimentalSerializationApi
34     public val namingStrategy: JsonNamingStrategy? = null,
35     @ExperimentalSerializationApi
36     public val decodeEnumsCaseInsensitive: Boolean = false,
37     @ExperimentalSerializationApi
38     public val allowTrailingComma: Boolean = false,
39     @ExperimentalSerializationApi
40     public val allowComments: Boolean = false,
41     @ExperimentalSerializationApi
42     @set:Deprecated(
43         "JsonConfiguration is not meant to be mutable, and will be made read-only in a future release. " +
44             "The `Json(from = ...) {}` copy builder should be used instead.",
45         level = DeprecationLevel.ERROR
46     )
47     public var classDiscriminatorMode: ClassDiscriminatorMode = ClassDiscriminatorMode.POLYMORPHIC,
48 ) {
49 
50     /** @suppress Dokka **/
51     @OptIn(ExperimentalSerializationApi::class)
toStringnull52     override fun toString(): String {
53         return "JsonConfiguration(encodeDefaults=$encodeDefaults, ignoreUnknownKeys=$ignoreUnknownKeys, isLenient=$isLenient, " +
54                 "allowStructuredMapKeys=$allowStructuredMapKeys, prettyPrint=$prettyPrint, explicitNulls=$explicitNulls, " +
55                 "prettyPrintIndent='$prettyPrintIndent', coerceInputValues=$coerceInputValues, useArrayPolymorphism=$useArrayPolymorphism, " +
56                 "classDiscriminator='$classDiscriminator', allowSpecialFloatingPointValues=$allowSpecialFloatingPointValues, " +
57                 "useAlternativeNames=$useAlternativeNames, namingStrategy=$namingStrategy, decodeEnumsCaseInsensitive=$decodeEnumsCaseInsensitive, " +
58                 "allowTrailingComma=$allowTrailingComma, allowComments=$allowComments, classDiscriminatorMode=$classDiscriminatorMode)"
59     }
60 }
61 
62 /**
63  * Defines which classes and objects should have their serial name included in the json as so-called class discriminator.
64  *
65  * Class discriminator is a JSON field added by kotlinx.serialization that has [JsonBuilder.classDiscriminator] as a key (`type` by default),
66  * and class' serial name as a value (fully qualified name by default, can be changed with [SerialName] annotation).
67  *
68  * Class discriminator is important for serializing and deserializing [polymorphic class hierarchies](https://github.com/Kotlin/kotlinx.serialization/blob/master/docs/polymorphism.md#sealed-classes).
69  * Default [ClassDiscriminatorMode.POLYMORPHIC] mode adds discriminator only to polymorphic classes.
70  * This behavior can be changed to match various JSON schemas.
71  *
72  * @see JsonBuilder.classDiscriminator
73  * @see JsonBuilder.classDiscriminatorMode
74  * @see Polymorphic
75  * @see PolymorphicSerializer
76  */
77 public enum class ClassDiscriminatorMode {
78     /**
79      * Never include class discriminator in the output.
80      *
81      * This mode is generally intended to produce JSON for consumption by third-party libraries.
82      * kotlinx.serialization is unable to deserialize [polymorphic classes][POLYMORPHIC] without class discriminators,
83      * so it is impossible to deserialize JSON produced in this mode if a data model has polymorphic classes.
84      */
85     NONE,
86 
87     /**
88      * Include class discriminators whenever possible.
89      *
90      * Given that class discriminator is added as a JSON field, adding class discriminator is possible
91      * when the resulting JSON is a json object — i.e., for Kotlin classes, `object`s, and interfaces.
92      * More specifically, discriminator is added to the output of serializers which descriptors
93      * have a [kind][SerialDescriptor.kind] of either [StructureKind.CLASS] or [StructureKind.OBJECT].
94      *
95      * This mode is generally intended to produce JSON for consumption by third-party libraries.
96      * Given that [JsonBuilder.classDiscriminatorMode] does not affect deserialization, kotlinx.serialization
97      * does not expect every object to have discriminator, which may trigger deserialization errors.
98      * If you experience such problems, refrain from using [ALL_JSON_OBJECTS] or use [JsonBuilder.ignoreUnknownKeys].
99      *
100      * In the example:
101      * ```
102      * @Serializable class Plain(val p: String)
103      * @Serializable sealed class Base
104      * @Serializable object Impl: Base()
105      *
106      * @Serializable class All(val p: Plain, val b: Base, val i: Impl)
107      * ```
108      * setting [JsonBuilder.classDiscriminatorMode] to [ClassDiscriminatorMode.ALL_JSON_OBJECTS] adds
109      * class discriminator to `All.p`, `All.b`, `All.i`, and to `All` object itself.
110      */
111     ALL_JSON_OBJECTS,
112 
113     /**
114      * Include class discriminators for polymorphic classes.
115      *
116      * Sealed classes, abstract classes, and interfaces are polymorphic classes by definition.
117      * Open classes can be polymorphic if they are serializable with [PolymorphicSerializer]
118      * and properly registered in the [SerializersModule].
119      * See [kotlinx.serialization polymorphism guide](https://github.com/Kotlin/kotlinx.serialization/blob/master/docs/polymorphism.md#sealed-classes) for details.
120      *
121      * Note that implementations of polymorphic classes (e.g., sealed class inheritors) are not polymorphic classes from kotlinx.serialization standpoint.
122      * This means that this mode adds class discriminators only if a statically known type of the property is a base class or interface.
123      *
124      * In the example:
125      * ```
126      * @Serializable class Plain(val p: String)
127      * @Serializable sealed class Base
128      * @Serializable object Impl: Base()
129      *
130      * @Serializable class All(val p: Plain, val b: Base, val i: Impl)
131      * ```
132      * setting [JsonBuilder.classDiscriminatorMode] to [ClassDiscriminatorMode.POLYMORPHIC] adds
133      * class discriminator to `All.b`, but leaves `All.p` and `All.i` intact.
134      *
135      * @see SerializersModule
136      * @see SerializersModuleBuilder
137      * @see PolymorphicModuleBuilder
138      */
139     POLYMORPHIC,
140 }
141