@@ -193,6 +193,97 @@ public async Task Success_SimpleTest_TokenAuth()
193
193
}
194
194
}
195
195
196
+ [ Fact ]
197
+ public async Task Success_SimpleTestWithKeyPrefix_TokenAuth ( )
198
+ {
199
+ // arrange
200
+ var values =
201
+ new Dictionary < string , IEnumerable < KeyValuePair < string , object > > >
202
+ {
203
+ {
204
+ "test" , new [ ]
205
+ {
206
+ new KeyValuePair < string , object > ( "option1" , "value1" ) ,
207
+ new KeyValuePair < string , object > ( "option3" , 5 ) ,
208
+ new KeyValuePair < string , object > ( "option4" , true ) ,
209
+ new KeyValuePair < string , object > ( "option5" , new [ ] { "v1" , "v2" , "v3" } ) ,
210
+ new KeyValuePair < string , object > (
211
+ "option6" ,
212
+ new [ ]
213
+ {
214
+ new TestConfigObject ( ) { OptionA = "a1" , OptionB = "b1" } ,
215
+ new TestConfigObject ( ) { OptionA = "a2" , OptionB = "b2" } ,
216
+ } ) ,
217
+ }
218
+ } ,
219
+ {
220
+ "test/subsection" , new [ ]
221
+ {
222
+ new KeyValuePair < string , object > ( "option2" , "value2" ) ,
223
+ }
224
+ } ,
225
+ {
226
+ "test/otherSubsection.otherSubsection2/otherSubsection3.otherSubsection4.otherSubsection5" , new [ ]
227
+ {
228
+ new KeyValuePair < string , object > ( "option7" , "value7" ) ,
229
+ }
230
+ } ,
231
+ {
232
+ "test/subsection/testsection" , new [ ]
233
+ {
234
+ new KeyValuePair < string , object > ( "option8" , "value8" ) ,
235
+ }
236
+ } ,
237
+ } ;
238
+
239
+ var container = this . PrepareVaultContainer ( ) ;
240
+ try
241
+ {
242
+ await container . StartAsync ( ) . ConfigureAwait ( false ) ;
243
+ await this . LoadDataAsync ( "http://localhost:8200" , values ) . ConfigureAwait ( false ) ;
244
+
245
+ // act
246
+ var builder = new ConfigurationBuilder ( ) ;
247
+
248
+ var keyPrefix = "MyConfig" ;
249
+ builder . AddVaultConfiguration (
250
+ ( ) => new VaultOptions ( "http://localhost:8200" , "root" , additionalCharactersForConfigurationPath : new [ ] { '.' } , keyPrefix : keyPrefix ) ,
251
+ "test" ,
252
+ "secret" ,
253
+ this . logger ) ;
254
+ var configurationRoot = builder . Build ( ) ;
255
+
256
+ // assert
257
+ configurationRoot . GetValue < string > ( $ "{ keyPrefix } :option1") . Should ( ) . Be ( "value1" ) ;
258
+ configurationRoot . GetValue < int > ( $ "{ keyPrefix } :option3") . Should ( ) . Be ( 5 ) ;
259
+ configurationRoot . GetValue < bool > ( $ "{ keyPrefix } :option4") . Should ( ) . Be ( true ) ;
260
+ configurationRoot . GetValue < string > ( $ "{ keyPrefix } :option5:0") . Should ( ) . Be ( "v1" ) ;
261
+ configurationRoot . GetValue < string > ( $ "{ keyPrefix } :option5:1") . Should ( ) . Be ( "v2" ) ;
262
+ configurationRoot . GetValue < string > ( $ "{ keyPrefix } :option5:2") . Should ( ) . Be ( "v3" ) ;
263
+ var t1 = new TestConfigObject ( ) ;
264
+ configurationRoot . Bind ( $ "{ keyPrefix } :option6:0", t1 ) ;
265
+ t1 . OptionA . Should ( ) . Be ( "a1" ) ;
266
+ t1 . OptionB . Should ( ) . Be ( "b1" ) ;
267
+ var t2 = new TestConfigObject ( ) ;
268
+ configurationRoot . Bind ( $ "{ keyPrefix } :option6:1", t2 ) ;
269
+ t2 . OptionA . Should ( ) . Be ( "a2" ) ;
270
+ t2 . OptionB . Should ( ) . Be ( "b2" ) ;
271
+ configurationRoot . GetSection ( $ "{ keyPrefix } :subsection") . GetValue < string > ( "option2" ) . Should ( ) . Be ( "value2" ) ;
272
+ configurationRoot . GetSection ( $ "{ keyPrefix } :otherSubsection")
273
+ . GetSection ( $ "otherSubsection2")
274
+ . GetSection ( "otherSubsection3" )
275
+ . GetSection ( "otherSubsection4" )
276
+ . GetSection ( "otherSubsection5" )
277
+ . GetValue < string > ( "option7" ) . Should ( ) . Be ( "value7" ) ;
278
+ configurationRoot . GetSection ( $ "{ keyPrefix } :subsection") . GetSection ( "testsection" ) . GetValue < string > ( "option8" ) . Should ( ) . Be ( "value8" ) ;
279
+ }
280
+ finally
281
+ {
282
+ await container . DisposeAsync ( ) . ConfigureAwait ( false ) ;
283
+ }
284
+ }
285
+
286
+
196
287
[ Fact ]
197
288
public async Task Success_SimpleTestOmitVaultKey_TokenAuth ( )
198
289
{
@@ -296,6 +387,70 @@ public async Task Success_WatcherTest_TokenAuth()
296
387
}
297
388
}
298
389
390
+ [ Fact ]
391
+ public async Task Success_WatcherTestWithPrefix_TokenAuth ( )
392
+ {
393
+ // arrange
394
+ using var cts = new CancellationTokenSource ( ) ;
395
+
396
+ var values =
397
+ new Dictionary < string , IEnumerable < KeyValuePair < string , object > > >
398
+ {
399
+ { "test" , new [ ] { new KeyValuePair < string , object > ( "option1" , "value1" ) } } ,
400
+ { "test/subsection" , new [ ] { new KeyValuePair < string , object > ( "option2" , "value2" ) } } ,
401
+ } ;
402
+
403
+ var container = this . PrepareVaultContainer ( ) ;
404
+ try
405
+ {
406
+ await container . StartAsync ( ) . ConfigureAwait ( false ) ;
407
+ await this . LoadDataAsync ( "http://localhost:8200" , values ) . ConfigureAwait ( false ) ;
408
+
409
+ var testPrefix = "MyConfig" ;
410
+
411
+ // act
412
+ var builder = new ConfigurationBuilder ( ) ;
413
+ builder . AddVaultConfiguration (
414
+ ( ) => new VaultOptions ( "http://localhost:8200" , "root" , reloadOnChange : true , reloadCheckIntervalSeconds : 10 , keyPrefix : testPrefix ) ,
415
+ "test" ,
416
+ "secret" ,
417
+ this . logger ) ;
418
+ var configurationRoot = builder . Build ( ) ;
419
+ var changeWatcher = new VaultChangeWatcher ( configurationRoot , this . logger ) ;
420
+ await changeWatcher . StartAsync ( cts . Token ) . ConfigureAwait ( false ) ;
421
+ var reloadToken = configurationRoot . GetReloadToken ( ) ;
422
+
423
+ // assert
424
+ configurationRoot . GetValue < string > ( $ "{ testPrefix } :option1") . Should ( ) . Be ( "value1" ) ;
425
+ configurationRoot . GetSection ( $ "{ testPrefix } :subsection") . GetValue < string > ( "option2" ) . Should ( ) . Be ( "value2" ) ;
426
+ reloadToken . HasChanged . Should ( ) . BeFalse ( ) ;
427
+
428
+ // load new data and wait for reload
429
+ values = new Dictionary < string , IEnumerable < KeyValuePair < string , object > > >
430
+ {
431
+ { "test" , new [ ] { new KeyValuePair < string , object > ( "option1" , "value1_new" ) } } ,
432
+ { "test/subsection" , new [ ] { new KeyValuePair < string , object > ( "option2" , "value2_new" ) } } ,
433
+ { "test/subsection3" , new [ ] { new KeyValuePair < string , object > ( "option3" , "value3_new" ) } } ,
434
+ { "test/testsection" , new [ ] { new KeyValuePair < string , object > ( "option4" , "value4_new" ) } } ,
435
+ } ;
436
+ await this . LoadDataAsync ( "http://localhost:8200" , values ) . ConfigureAwait ( false ) ;
437
+ await Task . Delay ( TimeSpan . FromSeconds ( 15 ) , cts . Token ) . ConfigureAwait ( true ) ;
438
+
439
+ reloadToken . HasChanged . Should ( ) . BeTrue ( ) ;
440
+ configurationRoot . GetValue < string > ( $ "{ testPrefix } :option1") . Should ( ) . Be ( "value1_new" ) ;
441
+ configurationRoot . GetSection ( $ "{ testPrefix } :subsection") . GetValue < string > ( "option2" ) . Should ( ) . Be ( "value2_new" ) ;
442
+ configurationRoot . GetSection ( $ "{ testPrefix } :subsection3") . GetValue < string > ( "option3" ) . Should ( ) . Be ( "value3_new" ) ;
443
+ configurationRoot . GetSection ( $ "{ testPrefix } :testsection") . GetValue < string > ( "option4" ) . Should ( ) . Be ( "value4_new" ) ;
444
+
445
+ changeWatcher . Dispose ( ) ;
446
+ }
447
+ finally
448
+ {
449
+ await cts . CancelAsync ( ) ;
450
+ await container . DisposeAsync ( ) . ConfigureAwait ( false ) ;
451
+ }
452
+ }
453
+
299
454
[ Fact ]
300
455
public async Task Success_WatcherTest_NoChanges ( )
301
456
{
0 commit comments