github.com/swiftstack/ProxyFS@v0.0.0-20210203235616-4017c267d62f/conf/api_test.go (about) 1 // Copyright (c) 2015-2021, NVIDIA CORPORATION. 2 // SPDX-License-Identifier: Apache-2.0 3 4 package conf 5 6 import ( 7 "bytes" 8 "encoding/base64" 9 "io" 10 "io/ioutil" 11 "os" 12 "path/filepath" 13 "reflect" 14 "testing" 15 "time" 16 17 "github.com/stretchr/testify/assert" 18 ) 19 20 const errnoEACCES = int(13) 21 22 var tempFile1Name string 23 var tempFile2Name string 24 var tempFile3Name string 25 var tempFile4Name string 26 var tempFile5Name string 27 var tempFile6Name string 28 var tempFile7Name string 29 var confStringToTest1 string 30 var confStringToTest2 string 31 var confStringToTest3 string 32 33 func TestMain(m *testing.M) { 34 tempFile1, errorTempFile1 := ioutil.TempFile(os.TempDir(), "TestConfFile1_") 35 if nil != errorTempFile1 { 36 os.Exit(errnoEACCES) 37 } 38 39 tempFile1Name = tempFile1.Name() 40 41 io.WriteString(tempFile1, "# A comment on it's own line\n") 42 io.WriteString(tempFile1, "[TestNamespace:Test_-_Section]\n") 43 io.WriteString(tempFile1, "Test_-_Option : TestValue1,TestValue2 # A comment at the end of a line\n") 44 45 tempFile1.Close() 46 47 tempFile2, errorTempFile2 := ioutil.TempFile(os.TempDir(), "TestConfFile2_") 48 if nil != errorTempFile2 { 49 os.Remove(tempFile1Name) 50 os.Exit(errnoEACCES) 51 } 52 53 tempFile2Name = tempFile2.Name() 54 55 io.WriteString(tempFile2, "; A comment on it's own line\n") 56 io.WriteString(tempFile2, "[TestNamespace:Test_-_Section] ; A comment at the end of a line\n") 57 io.WriteString(tempFile2, "Test_-_Option =\n") 58 59 tempFile2.Close() 60 61 tempFile3, errorTempFile3 := ioutil.TempFile(os.TempDir(), "TestConfFile3_") 62 if nil != errorTempFile3 { 63 os.Remove(tempFile1Name) 64 os.Remove(tempFile2Name) 65 os.Exit(errnoEACCES) 66 } 67 68 tempFile3Name = tempFile3.Name() 69 70 io.WriteString(tempFile3, "[TestNamespace:Test_-_Section]\n") 71 io.WriteString(tempFile3, "Test_-_Option = http://Test.Value.3/ TestValue4$\tTestValue5$\n") 72 73 tempFile3.Close() 74 75 tempFile4, errorTempFile4 := ioutil.TempFile(os.TempDir(), "TestConfFile4_") 76 if nil != errorTempFile4 { 77 os.Remove(tempFile1Name) 78 os.Remove(tempFile2Name) 79 os.Remove(tempFile3Name) 80 os.Exit(errnoEACCES) 81 } 82 83 tempFile4Name = tempFile4.Name() 84 85 tempFile4.Close() 86 87 tempFile5, errorTempFile5 := ioutil.TempFile(os.TempDir(), "TestConfFile5_") 88 if nil != errorTempFile5 { 89 os.Remove(tempFile1Name) 90 os.Remove(tempFile2Name) 91 os.Remove(tempFile3Name) 92 os.Remove(tempFile4Name) 93 os.Exit(errnoEACCES) 94 } 95 96 tempFile5Name = tempFile5.Name() 97 98 io.WriteString(tempFile5, ".include ./"+filepath.Base(tempFile4Name)+"\n") 99 100 tempFile5.Close() 101 102 tempFile6, errorTempFile6 := ioutil.TempFile(os.TempDir(), "TestConfFile6_") 103 if nil != errorTempFile6 { 104 os.Remove(tempFile1Name) 105 os.Remove(tempFile2Name) 106 os.Remove(tempFile3Name) 107 os.Remove(tempFile4Name) 108 os.Remove(tempFile5Name) 109 os.Exit(errnoEACCES) 110 } 111 112 tempFile6Name = tempFile6.Name() 113 114 io.WriteString(tempFile6, "[TestNamespace:Test_-_Section_-_1]\n") 115 io.WriteString(tempFile6, "Option_-_1_-_No_-_Values :\n") 116 io.WriteString(tempFile6, "Option_-_2_-_One_-_Value : Value_-_1\n") 117 io.WriteString(tempFile6, "Option_-_3_-_Two_-_Values : Value_-_1, Value_-_2\n") 118 io.WriteString(tempFile6, "\n") 119 io.WriteString(tempFile6, "[TestNamespace:Test_-_Section_-_2]\n") 120 io.WriteString(tempFile6, "Option : Value\n") 121 122 tempFile6.Close() 123 124 tempFile7, errorTempFile7 := ioutil.TempFile(os.TempDir(), "TestConfFile7_") 125 if nil != errorTempFile7 { 126 os.Remove(tempFile1Name) 127 os.Remove(tempFile2Name) 128 os.Remove(tempFile3Name) 129 os.Remove(tempFile4Name) 130 os.Remove(tempFile5Name) 131 os.Remove(tempFile6Name) 132 os.Exit(errnoEACCES) 133 } 134 135 tempFile7Name = tempFile7.Name() 136 137 // Leave it empty... will be used as output file 138 139 tempFile7.Close() 140 141 confStringToTest1 = "TestNamespace:Test_-_Section.Test_-_Option = TestValue6,http://Test.Value_-_7/" 142 confStringToTest2 = "TestNamespace:Test_-_Section.Test_-_Option = TestValue8$,http://Test.Value_-_9/$" 143 confStringToTest3 = "TestNamespace:Test_-_Section.Test_-_Option =" 144 145 mRunReturn := m.Run() 146 147 os.Remove(tempFile1Name) 148 os.Remove(tempFile2Name) 149 os.Remove(tempFile3Name) 150 os.Remove(tempFile4Name) 151 os.Remove(tempFile5Name) 152 os.Remove(tempFile6Name) 153 os.Remove(tempFile7Name) 154 155 os.Exit(mRunReturn) 156 } 157 158 func TestUpdate(t *testing.T) { 159 var confMap = MakeConfMap() 160 161 err := confMap.UpdateFromFile(tempFile1Name) 162 if nil != err { 163 t.Fatalf("UpdateConfMapFromFile(\"%v\") returned: \"%v\"", tempFile1Name, err) 164 } 165 166 confMapSection, ok := confMap["TestNamespace:Test_-_Section"] 167 if !ok { 168 t.Fatalf("confMap[\"%v\"] missing", "TestNamespace:Test_-_Section") 169 } 170 171 confMapOption, ok := confMapSection["Test_-_Option"] 172 if !ok { 173 t.Fatalf("confMapSection[\"%v\"] missing", "Test_-_Option") 174 } 175 176 if 2 != len(confMapOption) { 177 t.Fatalf("confMapSection[\"%v\"] constains unexpected number of values (%v)", "Test_-_Option", len(confMapOption)) 178 } 179 180 if "TestValue1" != string(confMapOption[0]) { 181 t.Fatalf("confMapOption != \"%v\"", "TestValue1") 182 } 183 184 if "TestValue2" != string(confMapOption[1]) { 185 t.Fatalf("confMapOption != \"%v\"", "TestValue2") 186 } 187 188 err = confMap.UpdateFromFile(tempFile2Name) 189 if nil != err { 190 t.Fatalf("UpdateConfMapFromFile(\"%v\") returned: \"%v\"", tempFile2Name, err) 191 } 192 193 confMapSection, ok = confMap["TestNamespace:Test_-_Section"] 194 if !ok { 195 t.Fatalf("confMap[\"%v\"] missing", "Test_-_Section") 196 } 197 198 confMapOption, ok = confMapSection["Test_-_Option"] 199 if !ok { 200 t.Fatalf("confMapSection[\"%v\"] missing", "Test_-_Option") 201 } 202 203 if 0 != len(confMapOption) { 204 t.Fatalf("confMapSection[\"%v\"] constains unexpected number of values (%v)", "Test_-_Option", len(confMapOption)) 205 } 206 207 err = confMap.UpdateFromFile(tempFile3Name) 208 if nil != err { 209 t.Fatalf("UpdateConfMapFromFile(\"%v\") returned: \"%v\"", tempFile3Name, err) 210 } 211 212 confMapSection, ok = confMap["TestNamespace:Test_-_Section"] 213 if !ok { 214 t.Fatalf("confMap[\"%v\"] missing", "Test_-_Section") 215 } 216 217 confMapOption, ok = confMapSection["Test_-_Option"] 218 if !ok { 219 t.Fatalf("confMapSection[\"%v\"] missing", "Test_-_Option") 220 } 221 222 if 3 != len(confMapOption) { 223 t.Fatalf("confMapSection[\"%v\"] constains unexpected number of values (%v)", "Test_-_Option", len(confMapOption)) 224 } 225 226 if "http://Test.Value.3/" != string(confMapOption[0]) { 227 t.Fatalf("confMapOption != \"%v\"", "http://Test.Value.3/") 228 } 229 230 if "TestValue4$" != string(confMapOption[1]) { 231 t.Fatalf("confMapOption != \"%v\"", "TestValue4$") 232 } 233 234 if "TestValue5$" != string(confMapOption[2]) { 235 t.Fatalf("confMapOption != \"%v\"", "TestValue5$") 236 } 237 238 err = confMap.UpdateFromString(confStringToTest1) 239 240 if nil != err { 241 t.Fatalf("UpdateConfMapFromString(\"%v\") returned: \"%v\"", confStringToTest1, err) 242 } 243 244 confMapSection, ok = confMap["TestNamespace:Test_-_Section"] 245 if !ok { 246 t.Fatalf("confMap[\"%v\"] missing", "Test_-_Section") 247 } 248 249 confMapOption, ok = confMapSection["Test_-_Option"] 250 if !ok { 251 t.Fatalf("confMapSection[\"%v\"] missing", "Test_-_Option") 252 } 253 254 if 2 != len(confMapOption) { 255 t.Fatalf("confMapSection[\"%v\"] constains unexpected number of values (%v)", "Test_-_Option", len(confMapOption)) 256 } 257 258 if "TestValue6" != string(confMapOption[0]) { 259 t.Fatalf("confMapOption != \"%v\"", "TestValue6") 260 } 261 262 if "http://Test.Value_-_7/" != string(confMapOption[1]) { 263 t.Fatalf("confMapOption != \"%v\"", "http://Test.Value_-_7/") 264 } 265 266 err = confMap.UpdateFromString(confStringToTest2) 267 268 if nil != err { 269 t.Fatalf("UpdateConfMapFromString(\"%v\") returned: \"%v\"", confStringToTest2, err) 270 } 271 272 confMapSection, ok = confMap["TestNamespace:Test_-_Section"] 273 if !ok { 274 t.Fatalf("confMap[\"%v\"] missing", "Test_-_Section") 275 } 276 277 confMapOption, ok = confMapSection["Test_-_Option"] 278 if !ok { 279 t.Fatalf("confMapSection[\"%v\"] missing", "Test_-_Option") 280 } 281 282 if 2 != len(confMapOption) { 283 t.Fatalf("confMapSection[\"%v\"] constains unexpected number of values (%v)", "Test_-_Option", len(confMapOption)) 284 } 285 286 if "TestValue8$" != string(confMapOption[0]) { 287 t.Fatalf("confMapOption != \"%v\"", "TestValue8$") 288 } 289 290 if "http://Test.Value_-_9/$" != string(confMapOption[1]) { 291 t.Fatalf("confMapOption != \"%v\"", "http://Test.Value_-_9/$") 292 } 293 294 err = confMap.UpdateFromString(confStringToTest3) 295 296 if nil != err { 297 t.Fatalf("UpdateConfMapFromString(\"%v\") returned: \"%v\"", confStringToTest3, err) 298 } 299 300 confMapOption, ok = confMapSection["Test_-_Option"] 301 if !ok { 302 t.Fatalf("confMapSection[\"%v\"] missing", "Test_-_Option") 303 } 304 305 if 0 != len(confMapOption) { 306 t.Fatalf("confMapSection[\"%v\"] constains unexpected number of values (%v)", "Test_-_Option", len(confMapOption)) 307 } 308 } 309 310 func TestFromFileConstructor(t *testing.T) { 311 confMap, err := MakeConfMapFromFile(tempFile3Name) 312 if nil != err { 313 t.Fatalf("MakeConfMapFromFile(): expected err to be nil, got %#v", err) 314 } 315 316 values, err := confMap.FetchOptionValueStringSlice("TestNamespace:Test_-_Section", "Test_-_Option") 317 if err != nil { 318 t.Fatalf("FetchOptionValueStringSlice(): expected err to be nil, got %#v", err) 319 } 320 expected := "http://Test.Value.3/" 321 if values[0] != expected { 322 t.Fatalf("FetchOptionValueStringSlice(): expected %#v, got %#v", expected, values[0]) 323 } 324 } 325 326 func TestFromFileConstructorNonexistentFile(t *testing.T) { 327 _, err := MakeConfMapFromFile("/does/not/exist") 328 expectedErr := "open /does/not/exist: no such file or directory" 329 if err.Error() != expectedErr { 330 t.Fatalf("expected err to be %#v, got %#v", expectedErr, err.Error()) 331 } 332 } 333 334 func TestFetch(t *testing.T) { 335 const ( 336 base64DecodedString = "Now is the time" 337 base64DecodedStringSliceElement0 = "for all good men" 338 base64DecodedStringSliceElement1 = "to come to the aid of their country." 339 ) 340 var ( 341 base64EncodedString = base64.StdEncoding.EncodeToString([]byte(base64DecodedString)) 342 base64EncodedStringSliceElement0 = base64.StdEncoding.EncodeToString([]byte(base64DecodedStringSliceElement0)) 343 base64EncodedStringSliceElement1 = base64.StdEncoding.EncodeToString([]byte(base64DecodedStringSliceElement1)) 344 confMap = MakeConfMap() 345 err error 346 ) 347 348 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionStringSlice1=") 349 if nil != err { 350 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionStringSlice1=: %v", err) 351 } 352 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionStringSlice2=TestString1,TestString2") 353 if nil != err { 354 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionStringSlice2=TestString1,TestString2: %v", err) 355 } 356 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionString=TestString3") 357 if nil != err { 358 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionString=TestString3: %v", err) 359 } 360 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionBase64String=" + base64EncodedString) 361 if nil != err { 362 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionBase64String=" + base64EncodedString) 363 } 364 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionBase64StringSlice=" + base64EncodedStringSliceElement0 + "," + base64EncodedStringSliceElement1) 365 if nil != err { 366 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionBase64StringSlice=" + base64EncodedStringSliceElement0 + "," + base64EncodedStringSliceElement1) 367 } 368 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionBool=true") 369 if nil != err { 370 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionBool=true: %v", err) 371 } 372 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionUint8=91") 373 if nil != err { 374 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionUint8=91: %v", err) 375 } 376 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionUint16=12") 377 if nil != err { 378 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionUint16=12: %v", err) 379 } 380 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionUint32=345") 381 if nil != err { 382 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionUint32=345: %v", err) 383 } 384 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionUint64=6789") 385 if nil != err { 386 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionUint64=6789: %v", err) 387 } 388 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionMilliseconds32=0.123") 389 if nil != err { 390 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionMilliseconds32=0.123: %v", err) 391 } 392 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionMilliseconds64=0.456") 393 if nil != err { 394 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionMilliseconds64=0.456: %v", err) 395 } 396 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionDuration=1.2s") 397 if nil != err { 398 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionDuration=1.2s: %v", err) 399 } 400 err = confMap.UpdateFromString("TestNamespace:Test_-_Section.Test_-_OptionGUIDString=12345678-1234-1234-1234-123456789ABC") 401 if nil != err { 402 t.Fatalf("Couldn't add TestNamespace:Test_-_Section.Test_-_OptionGUIDString=12345678-1234-1234-1234-123456789ABC: %v", err) 403 } 404 405 err = confMap.VerifyOptionIsMissing("TestNamespace:Test_-_Section", "Test_-_OptionStringSlice0") 406 if nil != err { 407 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionStringSlice0 should have verified as missing") 408 } 409 err = confMap.VerifyOptionIsMissing("TestNamespace:Test_-_Section", "Test_-_OptionStringSlice1") 410 if nil == err { 411 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionStringSlice1 should have verified as not missing") 412 } 413 414 err = confMap.VerifyOptionValueIsEmpty("TestNamespace:Test_-_Section", "Test_-_OptionStringSlice1") 415 if nil != err { 416 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionStringSlice1 should have verified as empty") 417 } 418 err = confMap.VerifyOptionValueIsEmpty("TestNamespace:Test_-_Section", "Test_-_OptionStringSlice2") 419 if nil == err { 420 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionStringSlice2 should have verified as not empty") 421 } 422 423 testStringSlice1, err := confMap.FetchOptionValueStringSlice("TestNamespace:Test_-_Section", "Test_-_OptionStringSlice1") 424 if nil != err { 425 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionStringSlice1: %v", err) 426 } 427 testStringSlice2, err := confMap.FetchOptionValueStringSlice("TestNamespace:Test_-_Section", "Test_-_OptionStringSlice2") 428 if nil != err { 429 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionStringSlice2: %v", err) 430 } 431 testString, err := confMap.FetchOptionValueString("TestNamespace:Test_-_Section", "Test_-_OptionString") 432 if nil != err { 433 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionString: %v", err) 434 } 435 testBase64String, err := confMap.FetchOptionValueBase64String("TestNamespace:Test_-_Section", "Test_-_OptionBase64String") 436 if nil != err { 437 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionBase64String: %v", err) 438 } 439 testBase64StringSlice, err := confMap.FetchOptionValueBase64StringSlice("TestNamespace:Test_-_Section", "Test_-_OptionBase64StringSlice") 440 if nil != err { 441 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionBase64StringSlice: %v", err) 442 } 443 testBool, err := confMap.FetchOptionValueBool("TestNamespace:Test_-_Section", "Test_-_OptionBool") 444 if err != nil { 445 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionBool: %v", err) 446 } 447 testUint8, err := confMap.FetchOptionValueUint8("TestNamespace:Test_-_Section", "Test_-_OptionUint8") 448 if nil != err { 449 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionUint8: %v", err) 450 } 451 testUint16, err := confMap.FetchOptionValueUint16("TestNamespace:Test_-_Section", "Test_-_OptionUint16") 452 if nil != err { 453 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionUint16: %v", err) 454 } 455 testUint32, err := confMap.FetchOptionValueUint32("TestNamespace:Test_-_Section", "Test_-_OptionUint32") 456 if nil != err { 457 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionUint32: %v", err) 458 } 459 testUint64, err := confMap.FetchOptionValueUint64("TestNamespace:Test_-_Section", "Test_-_OptionUint64") 460 if nil != err { 461 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionUint64: %v", err) 462 } 463 testFloat32, err := confMap.FetchOptionValueFloat32("TestNamespace:Test_-_Section", "Test_-_OptionMilliseconds32") 464 if nil != err { 465 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionMilliseconds32 as float32: %v", err) 466 } 467 testFloat64, err := confMap.FetchOptionValueFloat64("TestNamespace:Test_-_Section", "Test_-_OptionMilliseconds64") 468 if nil != err { 469 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionMilliseconds64 as float64: %v", err) 470 } 471 testScaledUint32, err := confMap.FetchOptionValueFloatScaledToUint32("TestNamespace:Test_-_Section", "Test_-_OptionMilliseconds32", 1000) 472 if nil != err { 473 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionMilliseconds32 as uint32: %v", err) 474 } 475 testScaledUint64, err := confMap.FetchOptionValueFloatScaledToUint64("TestNamespace:Test_-_Section", "Test_-_OptionMilliseconds64", 1000) 476 if nil != err { 477 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionMilliseconds64 as uint64: %v", err) 478 } 479 testDuration, err := confMap.FetchOptionValueDuration("TestNamespace:Test_-_Section", "Test_-_OptionDuration") 480 if nil != err { 481 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.TestDuration: %v", err) 482 } 483 testGUID, err := confMap.FetchOptionValueUUID("TestNamespace:Test_-_Section", "Test_-_OptionGUIDString") 484 if nil != err { 485 t.Fatalf("Couldn't fetch TestNamespace:Test_-_Section.Test_-_OptionGUIDString: %v", err) 486 } 487 488 if 0 != len(testStringSlice1) { 489 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionStringSlice1 contained unexpected value(s)") 490 } 491 if (2 != len(testStringSlice2)) || ("TestString1" != testStringSlice2[0]) || ("TestString2" != testStringSlice2[1]) { 492 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionStringSlice2 contained unexpected value(s)") 493 } 494 if "TestString3" != testString { 495 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionString contained unexpected value") 496 } 497 if base64DecodedString != testBase64String { 498 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionBase64String contained unexpected value") 499 } 500 if (2 != len(testBase64StringSlice)) || (base64DecodedStringSliceElement0 != base64DecodedStringSliceElement0) || (base64DecodedStringSliceElement1 != base64DecodedStringSliceElement1) { 501 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionBase64StringSlice contained unexpected value(s)") 502 } 503 if testBool != true { 504 t.Fatalf("TestNamespace:Test_-_Section.TestBool contained unexpected value") 505 } 506 if uint8(91) != testUint8 { 507 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionUint8 contained unexpected value") 508 } 509 if uint16(12) != testUint16 { 510 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionUint16 contained unexpected value") 511 } 512 if uint32(345) != testUint32 { 513 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionUint32 contained unexpected value") 514 } 515 if uint64(6789) != testUint64 { 516 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionUint64 contained unexpected value") 517 } 518 if float32(0.123) != testFloat32 { 519 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionMilliseconds32 contained unexpected float32 value") 520 } 521 if float64(0.456) != testFloat64 { 522 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionMilliseconds64 contained unexpected float64 value") 523 } 524 if uint32(123) != testScaledUint32 { 525 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionMilliseconds32 contained unexpected uint32 value") 526 } 527 if uint64(456) != testScaledUint64 { 528 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionMilliseconds64 contained unexpected uint64 value") 529 } 530 timeBase := time.Time{} 531 timeBasePlusTestDuration := timeBase.Add(testDuration) 532 if (1 != timeBasePlusTestDuration.Second()) || (200000000 != timeBasePlusTestDuration.Nanosecond()) { 533 t.Fatalf("TestNamespace:Test_-_Section.TestDuration contained unexpected value") 534 } 535 if 0 != bytes.Compare([]byte{0x12, 0x34, 0x56, 0x78, 0x12, 0x34, 0x12, 0x34, 0x12, 0x34, 0x12, 0x34, 0x56, 0x78, 0x9A, 0xBC}, testGUID) { 536 t.Fatalf("TestNamespace:Test_-_Section.Test_-_OptionGUIDString contained unexpected value") 537 } 538 } 539 540 func TestInclude(t *testing.T) { 541 _, err := MakeConfMapFromFile(tempFile5Name) 542 if nil != err { 543 t.Fatalf("MakeConfMapFromFile() of <tempdir>/%v that includes <tempdir>/%v got %#v", filepath.Base(tempFile5Name), filepath.Base(tempFile4Name), err) 544 } 545 } 546 547 func TestDump(t *testing.T) { 548 var ( 549 confMap6 = MakeConfMap() 550 confMap7 = MakeConfMap() 551 ) 552 553 err := confMap6.UpdateFromFile(tempFile6Name) 554 if nil != err { 555 t.Fatalf("UpdateConfMapFromFile(\"%v\") returned: \"%v\"", tempFile6Name, err) 556 } 557 558 err = confMap6.DumpConfMapToFile(tempFile7Name, os.FileMode(0600)) 559 if nil != err { 560 t.Fatalf("DumpConfMapToFile() returned: \"%v\"", err) 561 } 562 563 err = confMap7.UpdateFromFile(tempFile7Name) 564 if nil != err { 565 t.Fatalf("UpdateConfMapFromFile(\"%v\") returned: \"%v\"", tempFile7Name, err) 566 } 567 568 if !reflect.DeepEqual(confMap6, confMap7) { 569 t.Fatalf("DumpConfMapToFile() failed to reproduce \"%v\" into \"%v\"", tempFile6Name, tempFile7Name) 570 } 571 } 572 573 // test SetOptionIfMissing and SetSectionIfMissing 574 func TestIfMissing(t *testing.T) { 575 576 assert := assert.New(t) 577 578 // create an empty confMap and populate it with one option (in one section) 579 confMap := MakeConfMap() 580 581 testSectionName0 := "TestSection0" 582 testSectionName1 := "TestSection1e" 583 testOptionName0 := "Test_-_Option0" 584 testOptionName1 := "Test_-_Option1" 585 testOptionString0 := "OptionValue0" 586 missingOptionString0 := "DefaultString0" 587 missingOptionString1 := "DefaultString1" 588 589 confStringToSection0Option0 := testSectionName0 + "." + testOptionName0 + " = " + testOptionString0 590 591 // populate testSectionName0.testOptionName0 592 err := confMap.UpdateFromString(confStringToSection0Option0) 593 assert.NoError(err, "UpdateFromString() should not fail with a valid option string") 594 595 // verify option was set 596 optionString, err := confMap.FetchOptionValueString(testSectionName0, testOptionName0) 597 assert.NoError(err, "FetchOptionValueString() cannot fail a valid request") 598 assert.Equal(testOptionString0, optionString, "FetchOptionValueString should return the option that was set") 599 600 missingOptionValue0 := ConfMapOption{missingOptionString0} 601 missingOptionValue1 := ConfMapOption{missingOptionString1} 602 603 // a new ConfMapOption should not overwrite the existing one 604 confMap.SetOptionIfMissing(testSectionName0, testOptionName0, missingOptionValue0) 605 606 optionString, err = confMap.FetchOptionValueString(testSectionName0, testOptionName0) 607 assert.NoError(err, "FetchOptionalValueString should not fail since the option exists") 608 assert.Equal(testOptionString0, optionString, "SetOptionIfMissing should not change existing optionValue") 609 610 // but a new ConfMapOption should replace a missing one 611 optionString, err = confMap.FetchOptionValueString(testSectionName0, testOptionName1) 612 assert.Error(err, "FetchOptionalValueString should fail since '%s' has not been set", testOptionName1) 613 614 confMap.SetOptionIfMissing(testSectionName0, testOptionName1, missingOptionValue1) 615 616 optionString, err = confMap.FetchOptionValueString(testSectionName0, testOptionName1) 617 assert.NoError(err, "FetchOptionalValueString should not fail since missing value was set") 618 assert.Equal(missingOptionString1, optionString, "SetOptionIfMissing should have set missing value") 619 620 // repeat a similar set of tests for sections 621 // 622 // verify option still exists 623 optionString, err = confMap.FetchOptionValueString(testSectionName0, testOptionName0) 624 assert.NoError(err, "FetchOptionValueString() cannot fail a valid request") 625 626 // a new ConfMapSection should not overwrite an existing one 627 missingSection0 := ConfMapSection{ 628 testOptionName0: ConfMapOption{missingOptionString0}, 629 testOptionName1: ConfMapOption{missingOptionString1}, 630 } 631 confMap.SetSectionIfMissing(testSectionName0, missingSection0) 632 633 optionString, err = confMap.FetchOptionValueString(testSectionName0, testOptionName0) 634 assert.NoError(err, "FetchOptionalValueString should not fail since the option exists") 635 assert.Equal(testOptionString0, optionString, "SetOptionIfMissing should not change existing optionValue") 636 637 optionString, err = confMap.FetchOptionValueString(testSectionName0, testOptionName1) 638 assert.NoError(err, "second option should have been added") 639 assert.Equal(missingOptionString1, optionString, "SetOptionIfMissing should not change existing optionValue") 640 641 // but a new ConfMapSection should replace a missing one 642 confMap.SetSectionIfMissing(testSectionName1, missingSection0) 643 644 optionString, err = confMap.FetchOptionValueString(testSectionName1, testOptionName0) 645 assert.NoError(err, "FetchOptionalValueString should not fail since section was added") 646 assert.Equal(missingOptionString0, optionString, "missing Option should have been set") 647 648 optionString, err = confMap.FetchOptionValueString(testSectionName1, testOptionName1) 649 assert.NoError(err, "FetchOptionalValueString should not fail since section was added") 650 assert.Equal(missingOptionString1, optionString, "missing Option should have been set") 651 }