Repository: open-feature/go-sdk
Pull request #77 (2022-09-23 12:09:09)

feat!: replaced EvaluationOptions with variadic option setter in client functions
Signed-off-by: Skye Gill <gill.skye95@gmail.com>

codecov-commenter: # [Codecov](https://codecov.io/gh/open-feature/go-sdk/pull/77?src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature) Report
> Merging [#77](https://codecov.io/gh/open-feature/go-sdk/pull/77?src=pr&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature) (4ff8491) into [main](https://codecov.io/gh/open-feature/go-sdk/commit/aa59b35d7be363736a29b4101b5c85e00baed919?el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature) (aa59b35) will **decrease** coverage by `4.16%`.
> The diff coverage is `64.70%`.

```diff
@@            Coverage Diff             @@
##             main      #77      +/-   ##
==========================================
- Coverage   84.30%   80.14%   -4.17%     
==========================================
  Files           6        6              
  Lines         376      418      +42     
==========================================
+ Hits          317      335      +18     
- Misses         54       70      +16     
- Partials        5       13       +8     
```


| [Impacted Files](https://codecov.io/gh/open-feature/go-sdk/pull/77?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature) | Coverage Δ | |
|---|---|---|
| [pkg/openfeature/openfeature.go](https://codecov.io/gh/open-feature/go-sdk/pull/77/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature#diff-cGtnL29wZW5mZWF0dXJlL29wZW5mZWF0dXJlLmdv) | `90.69% <ø> (-0.97%)` | :arrow_down: |
| [pkg/openfeature/client.go](https://codecov.io/gh/open-feature/go-sdk/pull/77/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature#diff-cGtnL29wZW5mZWF0dXJlL2NsaWVudC5nbw==) | `78.52% <64.70%> (-5.55%)` | :arrow_down: |

:mega: We’re building smart automated test selection to slash your CI/CD build times. [Learn more](https://about.codecov.io/iterative-testing/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=open-feature)


Patch:
diff --git a/pkg/openfeature/client.go b/pkg/openfeature/client.go
index 1e3dd57..99b79ea 100644
--- a/pkg/openfeature/client.go
+++ b/pkg/openfeature/client.go
@@ -14,16 +14,16 @@ type IClient interface {
 	AddHooks(hooks ...Hook)
 	SetEvaluationContext(evalCtx EvaluationContext)
 	EvaluationContext() EvaluationContext
-	BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (bool, error)
-	StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (string, error)
-	FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (float64, error)
-	IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (int64, error)
-	ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (interface{}, error)
-	BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-	StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-	FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-	IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-	ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
+	BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (bool, error)
+	StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (string, error)
+	FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (float64, error)
+	IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (int64, error)
+	ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (interface{}, error)
+	BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+	StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+	FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+	IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+	ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
 }
 
 // ClientMetadata provides a client's metadata
@@ -113,6 +113,23 @@ type EvaluationDetails struct {
 	InterfaceResolutionDetail
 }
 
+// Option applies a change to EvaluationOptions
+type Option func(*EvaluationOptions)
+
+// WithHooks applies provided hooks.
+func WithHooks(hooks ...Hook) Option {
+	return func(options *EvaluationOptions) {
+		options.hooks = hooks
+	}
+}
+
+// WithHookHints applies provided hook hints.
+func WithHookHints(hookHints HookHints) Option {
+	return func(options *EvaluationOptions) {
+		options.hookHints = hookHints
+	}
+}
+
 // BooleanValue performs a flag evaluation that returns a boolean.
 //
 // Parameters:
@@ -120,9 +137,14 @@ type EvaluationDetails struct {
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (bool, error) {
-	evalDetails, err := c.evaluate(ctx, flag, Boolean, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (bool, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	evalDetails, err := c.evaluate(ctx, flag, Boolean, defaultValue, evalCtx, *evalOptions)
 	if err != nil {
 		return defaultValue, err
 	}
@@ -147,9 +169,14 @@ func (c Client) BooleanValue(ctx context.Context, flag string, defaultValue bool
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (string, error) {
-	evalDetails, err := c.evaluate(ctx, flag, String, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (string, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	evalDetails, err := c.evaluate(ctx, flag, String, defaultValue, evalCtx, *evalOptions)
 	if err != nil {
 		return defaultValue, err
 	}
@@ -174,9 +201,14 @@ func (c Client) StringValue(ctx context.Context, flag string, defaultValue strin
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (float64, error) {
-	evalDetails, err := c.evaluate(ctx, flag, Float, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (float64, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	evalDetails, err := c.evaluate(ctx, flag, Float, defaultValue, evalCtx, *evalOptions)
 	if err != nil {
 		return defaultValue, err
 	}
@@ -201,9 +233,14 @@ func (c Client) FloatValue(ctx context.Context, flag string, defaultValue float6
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (int64, error) {
-	evalDetails, err := c.evaluate(ctx, flag, Int, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (int64, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	evalDetails, err := c.evaluate(ctx, flag, Int, defaultValue, evalCtx, *evalOptions)
 	if err != nil {
 		return defaultValue, err
 	}
@@ -228,9 +265,14 @@ func (c Client) IntValue(ctx context.Context, flag string, defaultValue int64, e
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (interface{}, error) {
-	evalDetails, err := c.evaluate(ctx, flag, Object, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (interface{}, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	evalDetails, err := c.evaluate(ctx, flag, Object, defaultValue, evalCtx, *evalOptions)
 	return evalDetails.Value, err
 }
 
@@ -241,9 +283,14 @@ func (c Client) ObjectValue(ctx context.Context, flag string, defaultValue inter
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error) {
-	return c.evaluate(ctx, flag, Boolean, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	return c.evaluate(ctx, flag, Boolean, defaultValue, evalCtx, *evalOptions)
 }
 
 // StringValueDetails performs a flag evaluation that returns an evaluation details struct.
@@ -253,9 +300,14 @@ func (c Client) BooleanValueDetails(ctx context.Context, flag string, defaultVal
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error) {
-	return c.evaluate(ctx, flag, String, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	return c.evaluate(ctx, flag, String, defaultValue, evalCtx, *evalOptions)
 }
 
 // FloatValueDetails performs a flag evaluation that returns an evaluation details struct.
@@ -265,9 +317,14 @@ func (c Client) StringValueDetails(ctx context.Context, flag string, defaultValu
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error) {
-	return c.evaluate(ctx, flag, Float, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	return c.evaluate(ctx, flag, Float, defaultValue, evalCtx, *evalOptions)
 }
 
 // IntValueDetails performs a flag evaluation that returns an evaluation details struct.
@@ -277,9 +334,14 @@ func (c Client) FloatValueDetails(ctx context.Context, flag string, defaultValue
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error) {
-	return c.evaluate(ctx, flag, Int, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	return c.evaluate(ctx, flag, Int, defaultValue, evalCtx, *evalOptions)
 }
 
 // ObjectValueDetails performs a flag evaluation that returns an evaluation details struct.
@@ -289,9 +351,14 @@ func (c Client) IntValueDetails(ctx context.Context, flag string, defaultValue i
 // - flag is the key that uniquely identifies a particular flag
 // - defaultValue is returned if an error occurs
 // - evalCtx is the evaluation context used in a flag evaluation (not to be confused with ctx)
-// - options are optional additional evaluation options
-func (c Client) ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error) {
-	return c.evaluate(ctx, flag, Object, defaultValue, evalCtx, options)
+// - options are optional additional evaluation options e.g. WithHooks & WithHookHints
+func (c Client) ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error) {
+	evalOptions := &EvaluationOptions{}
+	for _, option := range options {
+		option(evalOptions)
+	}
+
+	return c.evaluate(ctx, flag, Object, defaultValue, evalCtx, *evalOptions)
 }
 
 func (c Client) evaluate(
diff --git a/pkg/openfeature/openfeature.go b/pkg/openfeature/openfeature.go
index d1ff121..265f644 100644
--- a/pkg/openfeature/openfeature.go
+++ b/pkg/openfeature/openfeature.go
@@ -37,14 +37,6 @@ type EvaluationOptions struct {
 	hookHints HookHints
 }
 
-// NewEvaluationOptions constructs an EvaluationOptions
-func NewEvaluationOptions(hooks []Hook, hookHints HookHints) EvaluationOptions {
-	return EvaluationOptions{
-		hooks:     hooks,
-		hookHints: hookHints,
-	}
-}
-
 // HookHints returns evaluation options' hook hints
 func (e EvaluationOptions) HookHints() HookHints {
 	return e.hookHints


Test patch:
diff --git a/pkg/openfeature/client_example_test.go b/pkg/openfeature/client_example_test.go
index fba2dd0..0fddc28 100644
--- a/pkg/openfeature/client_example_test.go
+++ b/pkg/openfeature/client_example_test.go
@@ -18,7 +18,7 @@ func ExampleNewClient() {
 func ExampleClient_BooleanValue() {
 	client := openfeature.NewClient("example-client")
 	value, err := client.BooleanValue(
-		context.Background(), "test-flag", true, openfeature.EvaluationContext{}, openfeature.EvaluationOptions{},
+		context.Background(), "test-flag", true, openfeature.EvaluationContext{},
 	)
 	if err != nil {
 		log.Fatal("error while getting boolean value : ", err)
@@ -31,7 +31,7 @@ func ExampleClient_BooleanValue() {
 func ExampleClient_StringValue() {
 	client := openfeature.NewClient("example-client")
 	value, err := client.StringValue(
-		context.Background(), "test-flag", "openfeature", openfeature.EvaluationContext{}, openfeature.EvaluationOptions{},
+		context.Background(), "test-flag", "openfeature", openfeature.EvaluationContext{},
 	)
 	if err != nil {
 		log.Fatal("error while getting string value : ", err)
@@ -44,7 +44,7 @@ func ExampleClient_StringValue() {
 func ExampleClient_FloatValue() {
 	client := openfeature.NewClient("example-client")
 	value, err := client.FloatValue(
-		context.Background(), "test-flag", 0.55, openfeature.EvaluationContext{}, openfeature.EvaluationOptions{},
+		context.Background(), "test-flag", 0.55, openfeature.EvaluationContext{},
 	)
 	if err != nil {
 		log.Fatalf("error while getting float value: %v", err)
@@ -57,7 +57,7 @@ func ExampleClient_FloatValue() {
 func ExampleClient_IntValue() {
 	client := openfeature.NewClient("example-client")
 	value, err := client.IntValue(
-		context.Background(), "test-flag", 3, openfeature.EvaluationContext{}, openfeature.EvaluationOptions{},
+		context.Background(), "test-flag", 3, openfeature.EvaluationContext{},
 	)
 	if err != nil {
 		log.Fatalf("error while getting int value: %v", err)
@@ -70,7 +70,7 @@ func ExampleClient_IntValue() {
 func ExampleClient_ObjectValue() {
 	client := openfeature.NewClient("example-client")
 	value, err := client.ObjectValue(
-		context.Background(), "test-flag", map[string]string{"foo": "bar"}, openfeature.EvaluationContext{}, openfeature.EvaluationOptions{},
+		context.Background(), "test-flag", map[string]string{"foo": "bar"}, openfeature.EvaluationContext{},
 	)
 	if err != nil {
 		log.Fatal("error while getting object value : ", err)
diff --git a/pkg/openfeature/client_test.go b/pkg/openfeature/client_test.go
index e6c8a0c..7bd49da 100644
--- a/pkg/openfeature/client_test.go
+++ b/pkg/openfeature/client_test.go
@@ -61,11 +61,11 @@ func TestRequirements_1_3(t *testing.T) {
 	client := NewClient("test-client")
 
 	type requirements interface {
-		BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (bool, error)
-		StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (string, error)
-		FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (float64, error)
-		IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (int64, error)
-		ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (interface{}, error)
+		BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (bool, error)
+		StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (string, error)
+		FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (float64, error)
+		IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (int64, error)
+		ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (interface{}, error)
 	}
 
 	var clientI interface{} = client
@@ -82,11 +82,11 @@ func TestRequirement_1_4_1(t *testing.T) {
 	client := NewClient("test-client")
 
 	type requirements interface {
-		BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-		StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-		FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-		IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-		ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
+		BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+		StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+		FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+		IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+		ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
 	}
 
 	var clientI interface{} = client
@@ -111,7 +111,7 @@ func TestRequirement_1_4_4(t *testing.T) {
 	flagKey := "foo"
 
 	t.Run("BooleanValueDetails", func(t *testing.T) {
-		evDetails, err := client.BooleanValueDetails(context.Background(), flagKey, true, EvaluationContext{}, EvaluationOptions{})
+		evDetails, err := client.BooleanValueDetails(context.Background(), flagKey, true, EvaluationContext{})
 		if err != nil {
 			t.Error(err)
 		}
@@ -124,7 +124,7 @@ func TestRequirement_1_4_4(t *testing.T) {
 	})
 
 	t.Run("StringValueDetails", func(t *testing.T) {
-		evDetails, err := client.StringValueDetails(context.Background(), flagKey, "", EvaluationContext{}, EvaluationOptions{})
+		evDetails, err := client.StringValueDetails(context.Background(), flagKey, "", EvaluationContext{})
 		if err != nil {
 			t.Error(err)
 		}
@@ -137,7 +137,7 @@ func TestRequirement_1_4_4(t *testing.T) {
 	})
 
 	t.Run("FloatValueDetails", func(t *testing.T) {
-		evDetails, err := client.FloatValueDetails(context.Background(), flagKey, 1, EvaluationContext{}, EvaluationOptions{})
+		evDetails, err := client.FloatValueDetails(context.Background(), flagKey, 1, EvaluationContext{})
 		if err != nil {
 			t.Error(err)
 		}
@@ -150,7 +150,7 @@ func TestRequirement_1_4_4(t *testing.T) {
 	})
 
 	t.Run("IntValueDetails", func(t *testing.T) {
-		evDetails, err := client.IntValueDetails(context.Background(), flagKey, 1, EvaluationContext{}, EvaluationOptions{})
+		evDetails, err := client.IntValueDetails(context.Background(), flagKey, 1, EvaluationContext{})
 		if err != nil {
 			t.Error(err)
 		}
@@ -163,7 +163,7 @@ func TestRequirement_1_4_4(t *testing.T) {
 	})
 
 	t.Run("ObjectValueDetails", func(t *testing.T) {
-		evDetails, err := client.ObjectValueDetails(context.Background(), flagKey, 1, EvaluationContext{}, EvaluationOptions{})
+		evDetails, err := client.ObjectValueDetails(context.Background(), flagKey, 1, EvaluationContext{})
 		if err != nil {
 			t.Error(err)
 		}
@@ -233,7 +233,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			}).Times(2)
 		SetProvider(mockProvider)
 
-		value, err := client.BooleanValue(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		value, err := client.BooleanValue(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected BooleanValue to return an error, got nil")
 		}
@@ -242,7 +242,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			t.Errorf("expected default value from BooleanValue, got %v", value)
 		}
 
-		valueDetails, err := client.BooleanValueDetails(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		valueDetails, err := client.BooleanValueDetails(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected BooleanValueDetails to return an error, got nil")
 		}
@@ -268,7 +268,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			}).Times(2)
 		SetProvider(mockProvider)
 
-		value, err := client.StringValue(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		value, err := client.StringValue(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected StringValue to return an error, got nil")
 		}
@@ -277,7 +277,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			t.Errorf("expected default value from StringValue, got %v", value)
 		}
 
-		valueDetails, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		valueDetails, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected StringValueDetails to return an error, got nil")
 		}
@@ -303,7 +303,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			}).Times(2)
 		SetProvider(mockProvider)
 
-		value, err := client.FloatValue(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		value, err := client.FloatValue(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected FloatValue to return an error, got nil")
 		}
@@ -312,7 +312,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			t.Errorf("expected default value from FloatValue, got %v", value)
 		}
 
-		valueDetails, err := client.FloatValueDetails(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		valueDetails, err := client.FloatValueDetails(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected FloatValueDetails to return an error, got nil")
 		}
@@ -338,7 +338,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			}).Times(2)
 		SetProvider(mockProvider)
 
-		value, err := client.IntValue(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		value, err := client.IntValue(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected IntValue to return an error, got nil")
 		}
@@ -347,7 +347,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			t.Errorf("expected default value from IntValue, got %v", value)
 		}
 
-		valueDetails, err := client.IntValueDetails(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		valueDetails, err := client.IntValueDetails(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected FloatValueDetails to return an error, got nil")
 		}
@@ -375,7 +375,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			}).Times(2)
 		SetProvider(mockProvider)
 
-		value, err := client.ObjectValue(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		value, err := client.ObjectValue(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected ObjectValue to return an error, got nil")
 		}
@@ -384,7 +384,7 @@ func TestRequirement_1_4_9(t *testing.T) {
 			t.Errorf("expected default value from ObjectValue, got %v", value)
 		}
 
-		valueDetails, err := client.ObjectValueDetails(context.Background(), flagKey, defaultValue, evalCtx, EvaluationOptions{})
+		valueDetails, err := client.ObjectValueDetails(context.Background(), flagKey, defaultValue, evalCtx)
 		if err == nil {
 			t.Error("expected ObjectValueDetails to return an error, got nil")
 		}
@@ -509,7 +509,7 @@ func TestBeforeHookNilContext(t *testing.T) {
 	mockProvider.EXPECT().BooleanEvaluation(gomock.Any(), gomock.Any(), gomock.Any(), attributes)
 
 	_, err := client.BooleanValue(
-		context.Background(), "foo", false, evalCtx, NewEvaluationOptions([]Hook{hookNilContext}, HookHints{}),
+		context.Background(), "foo", false, evalCtx, WithHooks(hookNilContext),
 	)
 	if err != nil {
 		t.Fatal(err)
@@ -535,7 +535,7 @@ func TestClientLoggerUsesLatestGlobalLogger(t *testing.T) {
 
 	client := NewClient("test")
 	SetLogger(logr.New(l))
-	_, err := client.BooleanValue(context.Background(), "foo", false, EvaluationContext{}, EvaluationOptions{})
+	_, err := client.BooleanValue(context.Background(), "foo", false, EvaluationContext{})
 	if err != nil {
 		t.Fatal(err)
 	}
diff --git a/pkg/openfeature/evaluation_context_test.go b/pkg/openfeature/evaluation_context_test.go
index d349357..af6a3b8 100644
--- a/pkg/openfeature/evaluation_context_test.go
+++ b/pkg/openfeature/evaluation_context_test.go
@@ -64,16 +64,16 @@ func TestRequirement_3_2_1(t *testing.T) {
 		client := NewClient("test")
 
 		type requirement interface {
-			BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (bool, error)
-			StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (string, error)
-			FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (float64, error)
-			IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (int64, error)
-			ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (interface{}, error)
-			BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
+			BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (bool, error)
+			StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (string, error)
+			FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (float64, error)
+			IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (int64, error)
+			ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (interface{}, error)
+			BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
 		}
 
 		var clientI interface{} = client
@@ -136,7 +136,7 @@ func TestRequirement_3_2_2(t *testing.T) {
 	flatCtx := flattenContext(expectedMergedEvalCtx)
 	mockProvider.EXPECT().StringEvaluation(gomock.Any(), gomock.Any(), gomock.Any(), flatCtx)
 
-	_, err := client.StringValue(context.Background(), "foo", "bar", invocationEvalCtx, EvaluationOptions{})
+	_, err := client.StringValue(context.Background(), "foo", "bar", invocationEvalCtx)
 	if err != nil {
 		t.Error(err)
 	}
diff --git a/pkg/openfeature/hooks_test.go b/pkg/openfeature/hooks_test.go
index d72de6f..b268bea 100644
--- a/pkg/openfeature/hooks_test.go
+++ b/pkg/openfeature/hooks_test.go
@@ -163,7 +163,6 @@ func TestRequirement_4_3_2(t *testing.T) {
 		defaultValue := "bar"
 		evalCtx := EvaluationContext{}
 		flatCtx := flattenContext(evalCtx)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -173,7 +172,7 @@ func TestRequirement_4_3_2(t *testing.T) {
 		mockHook.EXPECT().After(gomock.Any(), gomock.Any(), gomock.Any())
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err != nil {
 			t.Errorf("unexpected err: %v", err)
 		}
@@ -208,7 +207,6 @@ func TestRequirement_4_3_3(t *testing.T) {
 	flagKey := "foo"
 	defaultValue := "bar"
 	evalCtx := EvaluationContext{}
-	evalOptions := NewEvaluationOptions([]Hook{mockHook1, mockHook2}, HookHints{})
 
 	mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -235,7 +233,7 @@ func TestRequirement_4_3_3(t *testing.T) {
 	mockHook2.EXPECT().After(gomock.Any(), gomock.Any(), gomock.Any())
 	mockHook2.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-	_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+	_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook1, mockHook2))
 	if err != nil {
 		t.Errorf("unexpected err: %v", err)
 	}
@@ -280,7 +278,6 @@ func TestRequirement_4_3_4(t *testing.T) {
 			"beatsClient": true,
 		},
 	}
-	evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 	mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -306,7 +303,7 @@ func TestRequirement_4_3_4(t *testing.T) {
 	mockHook.EXPECT().After(gomock.Any(), gomock.Any(), gomock.Any())
 	mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-	_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, invEvalCtx, evalOptions)
+	_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, invEvalCtx, WithHooks(mockHook))
 	if err != nil {
 		t.Errorf("unexpected err: %v", err)
 	}
@@ -329,7 +326,6 @@ func TestRequirement_4_3_5(t *testing.T) {
 		defaultValue := "bar"
 		evalCtx := EvaluationContext{}
 		flatCtx := flattenContext(evalCtx)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -339,7 +335,7 @@ func TestRequirement_4_3_5(t *testing.T) {
 			After(mockProvider.EXPECT().StringEvaluation(gomock.Any(), flagKey, defaultValue, flatCtx))
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err != nil {
 			t.Errorf("unexpected err: %v", err)
 		}
@@ -377,7 +373,6 @@ func TestRequirement_4_3_6(t *testing.T) {
 		mockProvider := NewMockFeatureProvider(ctrl)
 		mockProvider.EXPECT().Metadata().AnyTimes()
 		SetProvider(mockProvider)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -386,7 +381,7 @@ func TestRequirement_4_3_6(t *testing.T) {
 			After(mockHook.EXPECT().Before(gomock.Any(), gomock.Any()).Return(nil, errors.New("forced")))
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err == nil {
 			t.Error("expected error, got nil")
 		}
@@ -398,7 +393,6 @@ func TestRequirement_4_3_6(t *testing.T) {
 		mockProvider := NewMockFeatureProvider(ctrl)
 		mockProvider.EXPECT().Metadata().AnyTimes()
 		SetProvider(mockProvider)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -411,7 +405,7 @@ func TestRequirement_4_3_6(t *testing.T) {
 			)
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err == nil {
 			t.Error("expected error, got nil")
 		}
@@ -423,7 +417,6 @@ func TestRequirement_4_3_6(t *testing.T) {
 		mockProvider := NewMockFeatureProvider(ctrl)
 		mockProvider.EXPECT().Metadata().AnyTimes()
 		SetProvider(mockProvider)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -434,7 +427,7 @@ func TestRequirement_4_3_6(t *testing.T) {
 			After(mockHook.EXPECT().After(gomock.Any(), gomock.Any(), gomock.Any()).Return(errors.New("forced")))
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err == nil {
 			t.Error("expected error, got nil")
 		}
@@ -471,7 +464,6 @@ func TestRequirement_4_3_7(t *testing.T) {
 		mockProvider := NewMockFeatureProvider(ctrl)
 		mockProvider.EXPECT().Metadata().AnyTimes()
 		SetProvider(mockProvider)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -481,7 +473,7 @@ func TestRequirement_4_3_7(t *testing.T) {
 			After(mockHook.EXPECT().Before(gomock.Any(), gomock.Any()))
 		mockProvider.EXPECT().StringEvaluation(context.Background(), flagKey, defaultValue, flatCtx)
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err != nil {
 			t.Errorf("unexpected err: %v", err)
 		}
@@ -493,7 +485,6 @@ func TestRequirement_4_3_7(t *testing.T) {
 		mockProvider := NewMockFeatureProvider(ctrl)
 		mockProvider.EXPECT().Metadata().AnyTimes()
 		SetProvider(mockProvider)
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -502,7 +493,7 @@ func TestRequirement_4_3_7(t *testing.T) {
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any()).
 			After(mockHook.EXPECT().Error(gomock.Any(), gomock.Any(), gomock.Any()))
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 		if err == nil {
 			t.Error("expected error, got nil")
 		}
@@ -566,16 +557,16 @@ func TestRequirement_4_4_1(t *testing.T) {
 
 		// EvaluationOptions contains the hooks registered at invocation
 		type requirement interface {
-			BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (bool, error)
-			StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (string, error)
-			FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (float64, error)
-			IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (int64, error)
-			ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (interface{}, error)
-			BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
-			ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options EvaluationOptions) (EvaluationDetails, error)
+			BooleanValue(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (bool, error)
+			StringValue(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (string, error)
+			FloatValue(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (float64, error)
+			IntValue(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (int64, error)
+			ObjectValue(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (interface{}, error)
+			BooleanValueDetails(ctx context.Context, flag string, defaultValue bool, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			StringValueDetails(ctx context.Context, flag string, defaultValue string, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			FloatValueDetails(ctx context.Context, flag string, defaultValue float64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			IntValueDetails(ctx context.Context, flag string, defaultValue int64, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
+			ObjectValueDetails(ctx context.Context, flag string, defaultValue interface{}, evalCtx EvaluationContext, options ...Option) (EvaluationDetails, error)
 		}
 
 		var clientI interface{} = client
@@ -604,7 +595,6 @@ func TestRequirement_4_4_2(t *testing.T) {
 		client := NewClient("test")
 		client.AddHooks(mockClientHook)
 		mockInvocationHook := NewMockHook(ctrl)
-		evalOptions := NewEvaluationOptions([]Hook{mockInvocationHook}, HookHints{})
 		mockProviderHook := NewMockHook(ctrl)
 
 		mockProvider := NewMockFeatureProvider(ctrl)
@@ -632,7 +622,7 @@ func TestRequirement_4_4_2(t *testing.T) {
 
 		mockProvider.EXPECT().StringEvaluation(context.Background(), flagKey, defaultValue, flatCtx)
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockInvocationHook))
 		if err != nil {
 			t.Errorf("unexpected err: %v", err)
 		}
@@ -647,7 +637,6 @@ func TestRequirement_4_4_2(t *testing.T) {
 		client := NewClient("test")
 		client.AddHooks(mockClientHook)
 		mockInvocationHook := NewMockHook(ctrl)
-		evalOptions := NewEvaluationOptions([]Hook{mockInvocationHook}, HookHints{})
 		mockProviderHook := NewMockHook(ctrl)
 
 		mockProvider := NewMockFeatureProvider(ctrl)
@@ -668,7 +657,7 @@ func TestRequirement_4_4_2(t *testing.T) {
 		mockClientHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 		mockAPIHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockInvocationHook))
 		if err == nil {
 			t.Error("expected error, got nil")
 		}
@@ -712,7 +701,6 @@ func TestRequirement_4_4_6(t *testing.T) {
 			mockProvider := NewMockFeatureProvider(ctrl)
 			mockProvider.EXPECT().Metadata().AnyTimes()
 			SetProvider(mockProvider)
-			evalOptions := NewEvaluationOptions([]Hook{mockHook1, mockHook2}, HookHints{})
 
 			mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -723,7 +711,7 @@ func TestRequirement_4_4_6(t *testing.T) {
 			mockHook2.EXPECT().Error(gomock.Any(), gomock.Any(), gomock.Any())
 			mockHook2.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-			_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+			_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook1, mockHook2))
 			if err == nil {
 				t.Error("expected error, got nil")
 			}
@@ -739,7 +727,6 @@ func TestRequirement_4_4_6(t *testing.T) {
 			mockProvider := NewMockFeatureProvider(ctrl)
 			mockProvider.EXPECT().Metadata().AnyTimes()
 			SetProvider(mockProvider)
-			evalOptions := NewEvaluationOptions([]Hook{mockHook1, mockHook2}, HookHints{})
 
 			mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -754,7 +741,7 @@ func TestRequirement_4_4_6(t *testing.T) {
 
 			mockProvider.EXPECT().StringEvaluation(context.Background(), flagKey, defaultValue, flatCtx)
 
-			_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+			_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook1, mockHook2))
 			if err == nil {
 				t.Error("expected error, got nil")
 			}
@@ -776,7 +763,6 @@ func TestRequirement_4_4_7(t *testing.T) {
 	mockProvider := NewMockFeatureProvider(ctrl)
 	mockProvider.EXPECT().Metadata().AnyTimes()
 	SetProvider(mockProvider)
-	evalOptions := NewEvaluationOptions([]Hook{mockHook}, HookHints{})
 
 	mockProvider.EXPECT().Hooks().AnyTimes()
 
@@ -784,7 +770,7 @@ func TestRequirement_4_4_7(t *testing.T) {
 	mockHook.EXPECT().Error(gomock.Any(), gomock.Any(), gomock.Any())
 	mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-	res, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+	res, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook))
 	if err == nil {
 		t.Error("expected error, got nil")
 	}
@@ -797,7 +783,12 @@ func TestRequirement_4_4_7(t *testing.T) {
 
 // `Flag evaluation options` MAY contain `hook hints`, a map of data to be provided to hook invocations.
 func TestRequirement_4_5_1(t *testing.T) {
-	NewEvaluationOptions(nil, NewHookHints(map[string]interface{}{"foo": "bar"}))
+	evalOptions := &EvaluationOptions{}
+	option := WithHookHints(NewHookHints(map[string]interface{}{"foo": "bar"}))
+	option(evalOptions)
+	if evalOptions.hookHints.Value("foo") != "bar" {
+		t.Error("hook hints not set to EvaluationOptions")
+	}
 }
 
 // `hook hints` MUST be passed to each hook.
@@ -819,7 +810,6 @@ func TestRequirement_4_5_2(t *testing.T) {
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
 		hookHints := NewHookHints(map[string]interface{}{"foo": "bar"})
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, hookHints)
 
 		mockHook.EXPECT().Before(gomock.Any(), hookHints)
 		mockHook.EXPECT().After(gomock.Any(), gomock.Any(), hookHints)
@@ -827,7 +817,7 @@ func TestRequirement_4_5_2(t *testing.T) {
 
 		mockProvider.EXPECT().StringEvaluation(context.Background(), flagKey, defaultValue, flatCtx)
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook), WithHookHints(hookHints))
 		if err != nil {
 			t.Errorf("unexpected error: %v", err)
 		}
@@ -843,13 +833,12 @@ func TestRequirement_4_5_2(t *testing.T) {
 		mockProvider.EXPECT().Hooks().AnyTimes()
 
 		hookHints := NewHookHints(map[string]interface{}{"foo": "bar"})
-		evalOptions := NewEvaluationOptions([]Hook{mockHook}, hookHints)
 
 		mockHook.EXPECT().Before(gomock.Any(), gomock.Any()).Return(nil, errors.New("forced"))
 		mockHook.EXPECT().Error(gomock.Any(), gomock.Any(), hookHints)
 		mockHook.EXPECT().Finally(gomock.Any(), gomock.Any())
 
-		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, evalOptions)
+		_, err := client.StringValueDetails(context.Background(), flagKey, defaultValue, evalCtx, WithHooks(mockHook), WithHookHints(hookHints))
 		if err == nil {
 			t.Error("expected error, got nil")
 		}