Skip to content

Commit

Permalink
fixup: single test suite
Browse files Browse the repository at this point in the history
Signed-off-by: Todd Baert <todd.baert@dynatrace.com>
  • Loading branch information
toddbaert committed Sep 18, 2023
1 parent 34e8980 commit 90bd8bc
Show file tree
Hide file tree
Showing 7 changed files with 117 additions and 472 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
@IncludeEngines("cucumber")
@SelectClasspathResource("features")
@ConfigurationParameter(key = PLUGIN_PROPERTY_NAME, value = "pretty")
@ConfigurationParameter(key = GLUE_PROPERTY_NAME, value = "dev.openfeature.contrib.providers.flagd.e2e.process")
@ConfigurationParameter(key = GLUE_PROPERTY_NAME, value = "dev.openfeature.contrib.providers.flagd.e2e.process,dev.openfeature.contrib.providers.flagd.e2e")
public class RunFlagdInProcessCucumberTest {

}
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
@IncludeEngines("cucumber")
@SelectClasspathResource("features")
@ConfigurationParameter(key = PLUGIN_PROPERTY_NAME, value = "pretty")
@ConfigurationParameter(key = GLUE_PROPERTY_NAME, value = "dev.openfeature.contrib.providers.flagd.e2e.rpc")
@ConfigurationParameter(key = GLUE_PROPERTY_NAME, value = "dev.openfeature.contrib.providers.flagd.e2e.rpc,dev.openfeature.contrib.providers.flagd.e2e")
public class RunFlagdRpcCucumberTest {

}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.locks.ReentrantReadWriteLock;

import dev.openfeature.sdk.Client;
import dev.openfeature.sdk.EvaluationContext;
Expand All @@ -12,10 +13,19 @@
import dev.openfeature.sdk.Reason;
import dev.openfeature.sdk.Structure;
import dev.openfeature.sdk.Value;
import io.cucumber.java.AfterAll;
import io.cucumber.java.BeforeAll;
import io.cucumber.java.en.Given;
import io.cucumber.java.en.Then;
import io.cucumber.java.en.When;

public abstract class BaseStepDefinitions {
/**
* Common test suite used by both RPC and in-process flagd.
*/
public class StepDefinitions {

protected static Client client;
private static final ReentrantReadWriteLock sync = new ReentrantReadWriteLock();
private static Client client;

private boolean booleanFlagValue;
private String stringFlagValue;
Expand All @@ -41,52 +51,84 @@ public abstract class BaseStepDefinitions {
private int typeErrorDefaultValue;
private FlagEvaluationDetails<Integer> typeErrorDetails;

/**
* Injects the client to use for this test.
* Tests run one at a time, but just in case, a lock is used to make sure the client is not updated mid-test.
*
* @param client client to inject into test.
*/
public static void setClient(Client client) {
StepDefinitions.client = client;
sync.writeLock().lock();
}

@AfterAll()
public static void cleanUp() {
sync.writeLock().unlock();
}

@BeforeAll()
@Given("a provider is registered")
public static void setup() {
// this is handled by the "Setup" files
}

/*
* Basic evaluation
*/

// boolean value
@When("a boolean flag with key {string} is evaluated with default value {string}")
public void a_boolean_flag_with_key_boolean_flag_is_evaluated_with_default_value_false(String flagKey,
String defaultValue) {
this.booleanFlagValue = client.getBooleanValue(flagKey, Boolean.valueOf(defaultValue));
}

@Then("the resolved boolean value should be {string}")
public void the_resolved_boolean_value_should_be_true(String expected) {
assertEquals(Boolean.valueOf(expected), this.booleanFlagValue);
}

// string value
@When("a string flag with key {string} is evaluated with default value {string}")
public void a_string_flag_with_key_is_evaluated_with_default_value(String flagKey, String defaultValue) {
this.stringFlagValue = client.getStringValue(flagKey, defaultValue);
}

@Then("the resolved string value should be {string}")
public void the_resolved_string_value_should_be(String expected) {
assertEquals(expected, this.stringFlagValue);
}

// integer value
@When("an integer flag with key {string} is evaluated with default value {int}")
public void an_integer_flag_with_key_is_evaluated_with_default_value(String flagKey, Integer defaultValue) {
this.intFlagValue = client.getIntegerValue(flagKey, defaultValue);
}

@Then("the resolved integer value should be {int}")
public void the_resolved_integer_value_should_be(int expected) {
assertEquals(expected, this.intFlagValue);
}

// float/double value
@When("a float flag with key {string} is evaluated with default value {double}")
public void a_float_flag_with_key_is_evaluated_with_default_value(String flagKey, double defaultValue) {
this.doubleFlagValue = client.getDoubleValue(flagKey, defaultValue);
}

@Then("the resolved float value should be {double}")
public void the_resolved_float_value_should_be(double expected) {
assertEquals(expected, this.doubleFlagValue);
}

// object value
@When("an object flag with key {string} is evaluated with a null default value")
public void an_object_flag_with_key_is_evaluated_with_a_null_default_value(String flagKey) {
this.objectFlagValue = client.getObjectValue(flagKey, new Value());
}

@Then("the resolved object value should be contain fields {string}, {string}, and {string}, with values {string}, {string} and {int}, respectively")
public void the_resolved_object_value_should_be_contain_fields_and_with_values_and_respectively(String boolField,
String stringField, String numberField, String boolValue, String stringValue, int numberValue) {
Structure structure = this.objectFlagValue.asStructure();
Expand All @@ -101,11 +143,13 @@ public void the_resolved_object_value_should_be_contain_fields_and_with_values_a
*/

// boolean details
@When("a boolean flag with key {string} is evaluated with details and default value {string}")
public void a_boolean_flag_with_key_is_evaluated_with_details_and_default_value(String flagKey,
String defaultValue) {
this.booleanFlagDetails = client.getBooleanDetails(flagKey, Boolean.valueOf(defaultValue));
}

@Then("the resolved boolean details value should be {string}, the variant should be {string}, and the reason should be {string}")
public void the_resolved_boolean_value_should_be_the_variant_should_be_and_the_reason_should_be(
String expectedValue,
String expectedVariant, String expectedReason) {
Expand All @@ -115,11 +159,13 @@ public void the_resolved_boolean_value_should_be_the_variant_should_be_and_the_r
}

// string details
@When("a string flag with key {string} is evaluated with details and default value {string}")
public void a_string_flag_with_key_is_evaluated_with_details_and_default_value(String flagKey,
String defaultValue) {
this.stringFlagDetails = client.getStringDetails(flagKey, defaultValue);
}

@Then("the resolved string details value should be {string}, the variant should be {string}, and the reason should be {string}")
public void the_resolved_string_value_should_be_the_variant_should_be_and_the_reason_should_be(String expectedValue,
String expectedVariant, String expectedReason) {
assertEquals(expectedValue, this.stringFlagDetails.getValue());
Expand All @@ -128,10 +174,12 @@ public void the_resolved_string_value_should_be_the_variant_should_be_and_the_re
}

// integer details
@When("an integer flag with key {string} is evaluated with details and default value {int}")
public void an_integer_flag_with_key_is_evaluated_with_details_and_default_value(String flagKey, int defaultValue) {
this.intFlagDetails = client.getIntegerDetails(flagKey, defaultValue);
}

@Then("the resolved integer details value should be {int}, the variant should be {string}, and the reason should be {string}")
public void the_resolved_integer_value_should_be_the_variant_should_be_and_the_reason_should_be(int expectedValue,
String expectedVariant, String expectedReason) {
assertEquals(expectedValue, this.intFlagDetails.getValue());
Expand All @@ -140,10 +188,12 @@ public void the_resolved_integer_value_should_be_the_variant_should_be_and_the_r
}

// float/double details
@When("a float flag with key {string} is evaluated with details and default value {double}")
public void a_float_flag_with_key_is_evaluated_with_details_and_default_value(String flagKey, double defaultValue) {
this.doubleFlagDetails = client.getDoubleDetails(flagKey, defaultValue);
}

@Then("the resolved float details value should be {double}, the variant should be {string}, and the reason should be {string}")
public void the_resolved_float_value_should_be_the_variant_should_be_and_the_reason_should_be(double expectedValue,
String expectedVariant, String expectedReason) {
assertEquals(expectedValue, this.doubleFlagDetails.getValue());
Expand All @@ -152,10 +202,12 @@ public void the_resolved_float_value_should_be_the_variant_should_be_and_the_rea
}

// object details
@When("an object flag with key {string} is evaluated with details and a null default value")
public void an_object_flag_with_key_is_evaluated_with_details_and_a_null_default_value(String flagKey) {
this.objectFlagDetails = client.getObjectDetails(flagKey, new Value());
}

@Then("the resolved object details value should be contain fields {string}, {string}, and {string}, with values {string}, {string} and {int}, respectively")
public void the_resolved_object_value_should_be_contain_fields_and_with_values_and_respectively_again(
String boolField,
String stringField, String numberField, String boolValue, String stringValue, int numberValue) {
Expand All @@ -166,6 +218,7 @@ public void the_resolved_object_value_should_be_contain_fields_and_with_values_a
assertEquals(numberValue, structure.asMap().get(numberField).asInteger());
}

@Then("the variant should be {string}, and the reason should be {string}")
public void the_variant_should_be_and_the_reason_should_be(String expectedVariant, String expectedReason) {
assertEquals(expectedVariant, this.objectFlagDetails.getVariant());
assertEquals(expectedReason, this.objectFlagDetails.getReason());
Expand All @@ -175,6 +228,7 @@ public void the_variant_should_be_and_the_reason_should_be(String expectedVarian
* Context-aware evaluation
*/

@When("context contains keys {string}, {string}, {string}, {string} with values {string}, {string}, {int}, {string}")
public void context_contains_keys_with_values(String field1, String field2, String field3, String field4,
String value1, String value2, Integer value3, String value4) {
Map<String, Value> attributes = new HashMap<>();
Expand All @@ -185,17 +239,20 @@ public void context_contains_keys_with_values(String field1, String field2, Stri
this.context = new ImmutableContext(attributes);
}

@When("a flag with key {string} is evaluated with default value {string}")
public void an_a_flag_with_key_is_evaluated(String flagKey, String defaultValue) {
contextAwareFlagKey = flagKey;
contextAwareDefaultValue = defaultValue;
contextAwareValue = client.getStringValue(flagKey, contextAwareDefaultValue, context);

}

@Then("the resolved string response should be {string}")
public void the_resolved_string_response_should_be(String expected) {
assertEquals(expected, this.contextAwareValue);
}

@Then("the resolved flag value is {string} when the context is empty")
public void the_resolved_flag_value_is_when_the_context_is_empty(String expected) {
String emptyContextValue = client.getStringValue(contextAwareFlagKey, contextAwareDefaultValue,
new ImmutableContext());
Expand All @@ -207,38 +264,43 @@ public void the_resolved_flag_value_is_when_the_context_is_empty(String expected
*/

// not found
@When("a non-existent string flag with key {string} is evaluated with details and a default value {string}")
public void a_non_existent_string_flag_with_key_is_evaluated_with_details_and_a_default_value(String flagKey,
String defaultValue) {
notFoundFlagKey = flagKey;
notFoundDefaultValue = defaultValue;
notFoundDetails = client.getStringDetails(notFoundFlagKey, notFoundDefaultValue);
}

@Then("the default string value should be returned")
public void then_the_default_string_value_should_be_returned() {
assertEquals(notFoundDefaultValue, notFoundDetails.getValue());
}

@Then("the reason should indicate an error and the error code should indicate a missing flag with {string}")
public void the_reason_should_indicate_an_error_and_the_error_code_should_be_flag_not_found(String errorCode) {
assertEquals(Reason.ERROR.toString(), notFoundDetails.getReason());
assertEquals(errorCode, notFoundDetails.getErrorCode().toString());
// TODO: add errorCode assertion once flagd provider is updated.
}

// type mismatch
@When("a string flag with key {string} is evaluated as an integer, with details and a default value {int}")
public void a_string_flag_with_key_is_evaluated_as_an_integer_with_details_and_a_default_value(String flagKey,
int defaultValue) {
typeErrorFlagKey = flagKey;
typeErrorDefaultValue = defaultValue;
typeErrorDetails = client.getIntegerDetails(typeErrorFlagKey, typeErrorDefaultValue);
}

@Then("the default integer value should be returned")
public void then_the_default_integer_value_should_be_returned() {
assertEquals(typeErrorDefaultValue, typeErrorDetails.getValue());
}

@Then("the reason should indicate an error and the error code should indicate a type mismatch with {string}")
public void the_reason_should_indicate_an_error_and_the_error_code_should_be_type_mismatch(String errorCode) {
assertEquals(Reason.ERROR.toString(), typeErrorDetails.getReason());
assertEquals(errorCode, typeErrorDetails.getErrorCode().toString());
}

}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package dev.openfeature.contrib.providers.flagd.e2e.process;

import dev.openfeature.contrib.providers.flagd.Config;
import dev.openfeature.contrib.providers.flagd.FlagdOptions;
import dev.openfeature.contrib.providers.flagd.FlagdProvider;
import dev.openfeature.contrib.providers.flagd.e2e.StepDefinitions;
import dev.openfeature.sdk.Client;
import dev.openfeature.sdk.OpenFeatureAPI;
import io.cucumber.java.BeforeAll;

public class FlagdInProcessSetup {

@BeforeAll()
public static void setup() throws InterruptedException {
FlagdProvider provider = new FlagdProvider(FlagdOptions.builder()
.resolverType(Config.Evaluator.IN_PROCESS)
.host("localhost")
.port(9090)
.build());
OpenFeatureAPI.getInstance().setProviderAndWait("process", provider);
Client client = OpenFeatureAPI.getInstance().getClient("process");
StepDefinitions.setClient(client);
}
}
Loading

0 comments on commit 90bd8bc

Please sign in to comment.