From dbf7980021c3731c13c8d7054e7ac98a10b00f40 Mon Sep 17 00:00:00 2001 From: "Derrick J. Wippler" Date: Tue, 3 Jul 2018 12:00:59 -0500 Subject: [PATCH] added variadic defaults to SetDefault --- README.md | 4 ++++ set_default.go | 29 +++++++++++++++++++++-------- set_default_test.go | 21 ++++++++++++++++++++- version | 2 +- 4 files changed, 46 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 7b2641e0..043af73b 100644 --- a/README.md +++ b/README.md @@ -274,6 +274,10 @@ var config struct { } holster.SetDefault(&config.Foo, "default") holster.SetDefault(&config.Bar, 200) + +// Supply additional default values and SetDefault will +// choose the first default that is not of zero value +// holster.SetDefault(&config.Foo, os.Getenv("FOO"), "default") ``` ## GetEnv diff --git a/set_default.go b/set_default.go index 5e2c056b..032d8f70 100644 --- a/set_default.go +++ b/set_default.go @@ -15,7 +15,9 @@ limitations under the License. */ package holster -import "reflect" +import ( + "reflect" +) // If 'value' is empty or of zero value, assign the default value. // This panics if the value is not a pointer or if value and @@ -27,14 +29,25 @@ import "reflect" // } // holster.SetDefault(&config.Foo, "default") // holster.SetDefault(&config.Bar, 200) -func SetDefault(value, defaultValue interface{}) { - v := reflect.ValueOf(value) - if v.Kind() != reflect.Ptr { - panic("holster.IfEmpty: Expected first argument to be of type reflect.Ptr") +// +// Supply additional default values and SetDefault will +// choose the first default that is not of zero value +// holster.SetDefault(&config.Foo, os.Getenv("FOO"), "default") +func SetDefault(dest interface{}, defaultValue ...interface{}) { + d := reflect.ValueOf(dest) + if d.Kind() != reflect.Ptr { + panic("holster.SetDefault: Expected first argument to be of type reflect.Ptr") } - v = reflect.Indirect(v) - if IsZeroValue(v) { - v.Set(reflect.ValueOf(defaultValue)) + d = reflect.Indirect(d) + if IsZeroValue(d) { + // Use the first non zero default value we find + for _, value := range defaultValue { + v := reflect.ValueOf(value) + if !IsZeroValue(v) { + d.Set(reflect.ValueOf(value)) + return + } + } } } diff --git a/set_default_test.go b/set_default_test.go index 8afb09ff..cbf95d14 100644 --- a/set_default_test.go +++ b/set_default_test.go @@ -53,6 +53,25 @@ func (s *SetDefaultTestSuite) TestIfEmpty(c *C) { c.Assert(conf.Bar, Equals, 500) } +func (s *SetDefaultTestSuite) TestIfDefaultPrecedence(c *C) { + var conf struct { + Foo string + Bar string + } + c.Assert(conf.Foo, Equals, "") + c.Assert(conf.Bar, Equals, "") + + // Should use the final default value + envValue := "" + holster.SetDefault(&conf.Foo, envValue, "default") + c.Assert(conf.Foo, Equals, "default") + + // Should use envValue + envValue = "bar" + holster.SetDefault(&conf.Bar, envValue, "default") + c.Assert(conf.Bar, Equals, "bar") +} + func (s *SetDefaultTestSuite) TestIsEmpty(c *C) { var count64 int64 var thing string @@ -83,7 +102,7 @@ func (s *SetDefaultTestSuite) TestIfEmptyTypePanic(c *C) { func (s *SetDefaultTestSuite) TestIfEmptyNonPtrPanic(c *C) { defer func() { if r := recover(); r != nil { - c.Assert(r, Equals, "holster.IfEmpty: Expected first argument to be of type reflect.Ptr") + c.Assert(r, Equals, "holster.SetDefault: Expected first argument to be of type reflect.Ptr") } }() diff --git a/version b/version index bd8bf882..943f9cbc 100644 --- a/version +++ b/version @@ -1 +1 @@ -1.7.0 +1.7.1