7
7
using System ;
8
8
using System . Collections . Generic ;
9
9
using System . Linq ;
10
+ using System . Runtime . Serialization ;
10
11
11
12
namespace Hocon
12
13
{
@@ -16,8 +17,35 @@ namespace Hocon
16
17
/// the internal representation of a HOCON (Human-Optimized Config Object Notation)
17
18
/// configuration string.
18
19
/// </summary>
19
- public class Config : HoconRoot
20
+ [ Serializable ]
21
+ public class Config : HoconRoot , ISerializable
20
22
{
23
+ /// <summary>
24
+ /// INTERNAL API
25
+ ///
26
+ /// Special case for empty configurations. Immutable and can't be added as a fallback.
27
+ /// </summary>
28
+ internal sealed class EmptyConfig : Config
29
+ {
30
+ public static EmptyConfig Instance = new EmptyConfig ( ) ;
31
+
32
+ private EmptyConfig ( ) : base ( new HoconRoot ( new HoconEmptyValue ( null ) ) )
33
+ {
34
+ }
35
+
36
+ protected override Config Copy ( Config fallback = null )
37
+ {
38
+ return Instance ;
39
+ }
40
+
41
+ public override Config WithFallback ( Config fallback )
42
+ {
43
+ return fallback ;
44
+ }
45
+ }
46
+
47
+ public const string SerializedPropertyName = "_dump" ;
48
+
21
49
[ Obsolete ( "For json serialization/deserialization only" , true ) ]
22
50
private Config ( )
23
51
{
@@ -89,10 +117,10 @@ public string ToString(bool useFallbackValues)
89
117
/// Generates a deep clone of the current configuration.
90
118
/// </summary>
91
119
/// <returns>A deep clone of the current configuration</returns>
92
- protected Config Copy ( )
120
+ protected virtual Config Copy ( Config fallback = null )
93
121
{
94
122
//deep clone
95
- return new Config ( ( HoconValue ) Value . Clone ( null ) , Fallback ? . Copy ( ) ) ;
123
+ return new Config ( ( HoconValue ) Value . Clone ( null ) , fallback ? . Copy ( ) ?? Fallback ? . Copy ( ) ) ;
96
124
}
97
125
98
126
protected override HoconValue GetNode ( HoconPath path , bool throwIfNotFound = false )
@@ -137,10 +165,13 @@ public virtual Config WithFallback(Config fallback)
137
165
{
138
166
if ( fallback == this )
139
167
throw new ArgumentException ( "Config can not have itself as fallback" , nameof ( fallback ) ) ;
168
+
169
+ if ( fallback == Config . Empty )
170
+ return this ; // no-op
140
171
141
172
// If Fallback is not set - we will set it in new copy
142
173
// If Fallback was set - just use it, but with adding new fallback values
143
- return new Config ( ( HoconValue ) Value . Clone ( null ) , Fallback ? . WithFallback ( fallback ) ?? fallback ) ;
174
+ return Copy ( Fallback . SafeWithFallback ( fallback ) ) ;
144
175
}
145
176
146
177
/// <summary>
@@ -206,6 +237,23 @@ private HoconValue GetRootValue()
206
237
207
238
return aggregated ;
208
239
}
240
+
241
+ /// <inheritdoc />
242
+ public void GetObjectData ( SerializationInfo info , StreamingContext context )
243
+ {
244
+ info . AddValue ( SerializedPropertyName , this . ToString ( useFallbackValues : true ) , typeof ( string ) ) ;
245
+ }
246
+
247
+ [ Obsolete ( "Used for serialization only" , true ) ]
248
+ public Config ( SerializationInfo info , StreamingContext context )
249
+ {
250
+ var config = ConfigurationFactory . ParseString ( info . GetValue ( SerializedPropertyName , typeof ( string ) ) as string ) ;
251
+
252
+ Value = config . Value ;
253
+ Fallback = config . Fallback ;
254
+
255
+ Root = GetRootValue ( ) ;
256
+ }
209
257
}
210
258
211
259
/// <summary>
0 commit comments