aboutsummaryrefslogtreecommitdiffstats
path: root/flags/src/test
diff options
context:
space:
mode:
authorHåkon Hallingstad <hakon@oath.com>2018-11-23 17:30:13 +0100
committerHåkon Hallingstad <hakon@oath.com>2018-11-23 17:30:13 +0100
commitcadcac9a8c0501f86372eb05d107d7b089643d0a (patch)
tree9593cc78763cba8e790e49c21f28a19182002765 /flags/src/test
parentf67aa7bfa1553d8cc19ce4eef96f42ff8c31a320 (diff)
Add flags module
FileFlagSource reads flags from files in /etc/vespa/flags and is a component that can be injected in host admin, config server, etc. A flag named foo corresponds to filename foo. In general a FlagSource manages: - Feature flags: A feature is either set (true/enabled) or otherwise false. Touching a file foo means the feature flag foo is set (true). - Value flags: Either a String or empty if not set. The String corresponds to the file content. The plan is to make the config server another source of flags. A unified FlagSource can merge the two sources with some priority and used in e.g. parts of node-admin. In other parts one would only have access to the file source. Defines various flag facades: - FeatureFlag: Used to test whether a feature has been enabled or not. - IntFlag - JacksonFlag: Deserializes JSON to Jackson class, or return default if unset. - LongFlag - OptionalJacksonFlag: Deserializes JSON to Jackson class, or empty if unset. - OptionalStringFlag - StringFlag This is part of removing some of the last Chef recipes. Some minor tweaks have been necessary as part of this and are included in this PR (test whether a systemd service exists, task-friendly file deletion, allow capitalized letters in YUM package name).
Diffstat (limited to 'flags/src/test')
-rw-r--r--flags/src/test/java/com/yahoo/vespa/flags/FileFlagSourceTest.java49
-rw-r--r--flags/src/test/java/com/yahoo/vespa/flags/JacksonFlagTest.java72
2 files changed, 121 insertions, 0 deletions
diff --git a/flags/src/test/java/com/yahoo/vespa/flags/FileFlagSourceTest.java b/flags/src/test/java/com/yahoo/vespa/flags/FileFlagSourceTest.java
new file mode 100644
index 00000000000..e422057f5fe
--- /dev/null
+++ b/flags/src/test/java/com/yahoo/vespa/flags/FileFlagSourceTest.java
@@ -0,0 +1,49 @@
+// Copyright 2018 Yahoo Holdings. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root.
+package com.yahoo.vespa.flags;
+
+import com.yahoo.vespa.test.file.TestFileSystem;
+import org.junit.Test;
+
+import java.io.IOException;
+import java.nio.file.FileSystem;
+import java.nio.file.Files;
+import java.nio.file.Path;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+
+public class FileFlagSourceTest {
+ private final FileSystem fileSystem = TestFileSystem.create();
+ private final FileFlagSource source = new FileFlagSource(fileSystem);
+
+ @Test
+ public void absentThenSet() throws IOException {
+ FlagId id = new FlagId("foo");
+ FeatureFlag featureFlag = new FeatureFlag(id, source);
+ StringFlag stringFlag = new StringFlag(id, "default", source);
+ OptionalStringFlag optionalStringFlag = new OptionalStringFlag(id, source);
+ IntFlag intFlag = new IntFlag(id, -1, source);
+ LongFlag longFlag = new LongFlag(id, -2L, source);
+
+ assertFalse(source.hasFeature(id));
+ assertFalse(source.getString(id).isPresent());
+ assertFalse(featureFlag.isSet());
+ assertEquals("default", stringFlag.value());
+ assertFalse(optionalStringFlag.value().isPresent());
+ assertEquals(-1, intFlag.value());
+ assertEquals(-2L, longFlag.value());
+
+ Path featurePath = fileSystem.getPath(FileFlagSource.FLAGS_DIRECTORY).resolve(id.toString());
+ Files.createDirectories(featurePath.getParent());
+ Files.write(featurePath, "1\n".getBytes());
+
+ assertTrue(source.hasFeature(id));
+ assertTrue(source.getString(id).isPresent());
+ assertTrue(featureFlag.isSet());
+ assertEquals("1\n", stringFlag.value());
+ assertEquals("1\n", optionalStringFlag.value().get());
+ assertEquals(1, intFlag.value());
+ assertEquals(1L, longFlag.value());
+ }
+} \ No newline at end of file
diff --git a/flags/src/test/java/com/yahoo/vespa/flags/JacksonFlagTest.java b/flags/src/test/java/com/yahoo/vespa/flags/JacksonFlagTest.java
new file mode 100644
index 00000000000..e4424d9886a
--- /dev/null
+++ b/flags/src/test/java/com/yahoo/vespa/flags/JacksonFlagTest.java
@@ -0,0 +1,72 @@
+// Copyright 2018 Yahoo Holdings. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root.
+package com.yahoo.vespa.flags;
+
+import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
+import com.fasterxml.jackson.annotation.JsonProperty;
+import org.junit.Test;
+
+import java.util.Objects;
+import java.util.Optional;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+public class JacksonFlagTest {
+ private final FlagId id = new FlagId("id");
+ private final ExampleJacksonClass defaultValue = new ExampleJacksonClass();
+ private final FlagSource source = mock(FlagSource.class);
+ private final JacksonFlag<ExampleJacksonClass> jacksonFlag = new JacksonFlag<>(id.toString(), ExampleJacksonClass.class, defaultValue, source);
+ private final OptionalJacksonFlag<ExampleJacksonClass> optionalJacksonFlag = new OptionalJacksonFlag<>(id, ExampleJacksonClass.class, source);
+
+ @Test
+ public void unsetThenSet() {
+ when(source.getString(id)).thenReturn(Optional.empty());
+ ExampleJacksonClass value = jacksonFlag.value();
+ assertEquals(1, value.integer);
+ assertEquals("2", value.string);
+ assertEquals("3", value.dummy);
+ assertFalse(optionalJacksonFlag.value().isPresent());
+
+ when(source.getString(id)).thenReturn(Optional.of("{\"integer\": 4, \"string\": \"foo\", \"stray\": 6}"));
+ value = jacksonFlag.value();
+ assertEquals(4, value.integer);
+ assertEquals("foo", value.string);
+ assertEquals("3", value.dummy);
+
+ assertTrue(optionalJacksonFlag.value().isPresent());
+ value = optionalJacksonFlag.value().get();
+ assertEquals(4, value.integer);
+ assertEquals("foo", value.string);
+ assertEquals("3", value.dummy);
+ }
+
+ @JsonIgnoreProperties(ignoreUnknown = true)
+ private static class ExampleJacksonClass {
+ @JsonProperty("integer")
+ public int integer = 1;
+
+ @JsonProperty("string")
+ public String string = "2";
+
+ @JsonProperty("dummy")
+ public String dummy = "3";
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+ ExampleJacksonClass that = (ExampleJacksonClass) o;
+ return integer == that.integer &&
+ Objects.equals(string, that.string) &&
+ Objects.equals(dummy, that.dummy);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(integer, string, dummy);
+ }
+ }
+} \ No newline at end of file