Skip to content

Commit 5071797

Browse files
authored
add features to project config (#120)
* add version 4 to the Project Config. Add features to the Project Config * add helper methods to ProjectConfigTestUtils to create a list or map of elements * alphabetize mappings and parameters in ProjectConfig. add feature key mapping * update v4 test datafile with launched experiment * refactor feature to featureFlag
1 parent f232f4b commit 5071797

File tree

6 files changed

+114
-23
lines changed

6 files changed

+114
-23
lines changed

core-api/src/main/java/com/optimizely/ab/Optimizely.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -416,7 +416,7 @@ Double getVariableDouble(@Nonnull String variableKey,
416416
return null;
417417
}
418418

419-
//======== Feature APIs ========//
419+
//======== FeatureFlag APIs ========//
420420

421421
/**
422422
* Determine whether a boolean feature is enabled.

core-api/src/main/java/com/optimizely/ab/config/Feature.java renamed to core-api/src/main/java/com/optimizely/ab/config/FeatureFlag.java

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,10 @@
2323
import java.util.List;
2424

2525
/**
26-
* Represents a Feature definition at the project level
26+
* Represents a FeatureFlag definition at the project level
2727
*/
2828
@JsonIgnoreProperties(ignoreUnknown = true)
29-
public class Feature implements IdKeyMapped{
29+
public class FeatureFlag implements IdKeyMapped{
3030

3131
private final String id;
3232
private final String key;
@@ -35,11 +35,11 @@ public class Feature implements IdKeyMapped{
3535
private final List<LiveVariable> variables;
3636

3737
@JsonCreator
38-
public Feature(@JsonProperty("id") String id,
39-
@JsonProperty("key") String key,
40-
@JsonProperty("layerId") String layerId,
41-
@JsonProperty("experimentIds") List<String> experimentIds,
42-
@JsonProperty("variables") List<LiveVariable> variables) {
38+
public FeatureFlag(@JsonProperty("id") String id,
39+
@JsonProperty("key") String key,
40+
@JsonProperty("layerId") String layerId,
41+
@JsonProperty("experimentIds") List<String> experimentIds,
42+
@JsonProperty("variables") List<LiveVariable> variables) {
4343
this.id = id;
4444
this.key = key;
4545
this.layerId = layerId;
@@ -69,7 +69,7 @@ public List<LiveVariable> getVariables() {
6969

7070
@Override
7171
public String toString() {
72-
return "Feature{" +
72+
return "FeatureFlag{" +
7373
"id='" + id + '\'' +
7474
", key='" + key + '\'' +
7575
", layerId='" + layerId + '\'' +

core-api/src/main/java/com/optimizely/ab/config/ProjectConfig.java

Lines changed: 59 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,8 @@ public class ProjectConfig {
3737

3838
public enum Version {
3939
V2 ("2"),
40-
V3 ("3");
40+
V3 ("3"),
41+
V4 ("4");
4142

4243
private final String version;
4344

@@ -56,54 +57,100 @@ public String toString() {
5657
private final String revision;
5758
private final String version;
5859
private final boolean anonymizeIP;
59-
private final List<Group> groups;
60-
private final List<Experiment> experiments;
6160
private final List<Attribute> attributes;
62-
private final List<EventType> events;
6361
private final List<Audience> audiences;
62+
private final List<EventType> events;
63+
private final List<Experiment> experiments;
64+
private final List<FeatureFlag> featureFlags;
65+
private final List<Group> groups;
6466
private final List<LiveVariable> liveVariables;
6567

66-
// convenience mappings for efficient lookup
67-
private final Map<String, Experiment> experimentKeyMapping;
68+
// key to entity mappings
6869
private final Map<String, Attribute> attributeKeyMapping;
69-
private final Map<String, LiveVariable> liveVariableKeyMapping;
7070
private final Map<String, EventType> eventNameMapping;
71+
private final Map<String, Experiment> experimentKeyMapping;
72+
private final Map<String, FeatureFlag> featureKeyMapping;
73+
private final Map<String, LiveVariable> liveVariableKeyMapping;
74+
75+
// id to entity mappings
7176
private final Map<String, Audience> audienceIdMapping;
7277
private final Map<String, Experiment> experimentIdMapping;
7378
private final Map<String, Group> groupIdMapping;
79+
80+
// other mappings
7481
private final Map<String, List<Experiment>> liveVariableIdToExperimentsMapping;
7582
private final Map<String, Map<String, LiveVariableUsageInstance>> variationToLiveVariableUsageInstanceMapping;
7683

84+
// v2 constructor
7785
public ProjectConfig(String accountId, String projectId, String version, String revision, List<Group> groups,
7886
List<Experiment> experiments, List<Attribute> attributes, List<EventType> eventType,
7987
List<Audience> audiences) {
8088
this(accountId, projectId, version, revision, groups, experiments, attributes, eventType, audiences, false,
8189
null);
8290
}
8391

92+
// v3 constructor
8493
public ProjectConfig(String accountId, String projectId, String version, String revision, List<Group> groups,
8594
List<Experiment> experiments, List<Attribute> attributes, List<EventType> eventType,
8695
List<Audience> audiences, boolean anonymizeIP, List<LiveVariable> liveVariables) {
96+
this(
97+
accountId,
98+
anonymizeIP,
99+
projectId,
100+
revision,
101+
version,
102+
attributes,
103+
audiences,
104+
eventType,
105+
experiments,
106+
null,
107+
groups,
108+
liveVariables
109+
);
110+
}
111+
112+
// v4 constructor
113+
public ProjectConfig(String accountId,
114+
boolean anonymizeIP,
115+
String projectId,
116+
String revision,
117+
String version,
118+
List<Attribute> attributes,
119+
List<Audience> audiences,
120+
List<EventType> events,
121+
List<Experiment> experiments,
122+
List<FeatureFlag> featureFlags,
123+
List<Group> groups,
124+
List<LiveVariable> liveVariables) {
87125

88126
this.accountId = accountId;
89127
this.projectId = projectId;
90128
this.version = version;
91129
this.revision = revision;
92130
this.anonymizeIP = anonymizeIP;
93131

132+
this.attributes = Collections.unmodifiableList(attributes);
133+
this.audiences = Collections.unmodifiableList(audiences);
134+
this.events = Collections.unmodifiableList(events);
135+
if (featureFlags == null) {
136+
this.featureFlags = Collections.emptyList();
137+
}
138+
else {
139+
this.featureFlags = Collections.unmodifiableList(featureFlags);
140+
}
141+
94142
this.groups = Collections.unmodifiableList(groups);
143+
95144
List<Experiment> allExperiments = new ArrayList<Experiment>();
96145
allExperiments.addAll(experiments);
97146
allExperiments.addAll(aggregateGroupExperiments(groups));
98147
this.experiments = Collections.unmodifiableList(allExperiments);
99-
this.attributes = Collections.unmodifiableList(attributes);
100-
this.events = Collections.unmodifiableList(eventType);
101-
this.audiences = Collections.unmodifiableList(audiences);
102148

103149
// generate the name mappers
104-
this.experimentKeyMapping = ProjectConfigUtils.generateNameMapping(this.experiments);
105150
this.attributeKeyMapping = ProjectConfigUtils.generateNameMapping(attributes);
106-
this.eventNameMapping = ProjectConfigUtils.generateNameMapping(events);
151+
this.eventNameMapping = ProjectConfigUtils.generateNameMapping(this.events);
152+
this.experimentKeyMapping = ProjectConfigUtils.generateNameMapping(this.experiments);
153+
this.featureKeyMapping = ProjectConfigUtils.generateNameMapping(this.featureFlags);
107154

108155
// generate audience id to audience mapping
109156
this.audienceIdMapping = ProjectConfigUtils.generateIdMapping(audiences);

core-api/src/main/java/com/optimizely/ab/event/internal/payload/Feature.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@ public int hashCode() {
103103

104104
@Override
105105
public String toString() {
106-
return "Feature{" +
106+
return "FeatureFlag{" +
107107
"id='" + id + '\'' +
108108
", name='" + name + '\'' +
109109
", type='" + type + '\'' +

core-api/src/test/java/com/optimizely/ab/config/ProjectConfigTestUtils.java

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
import java.util.Arrays;
3333
import java.util.Collections;
3434
import java.util.HashMap;
35+
import java.util.Iterator;
3536
import java.util.List;
3637
import java.util.Map;
3738

@@ -618,4 +619,26 @@ private static void verifyLiveVariableInstances(List<LiveVariableUsageInstance>
618619
}
619620
}
620621
}
622+
623+
public static <T> List<T> createListOfObjects(T ... elements) {
624+
ArrayList<T> list = new ArrayList<T>(elements.length);
625+
for (T element : elements) {
626+
list.add(element);
627+
}
628+
return list;
629+
}
630+
631+
public static <K, V> Map<K, V> createMapOfObjects(List<K>keys, List<V>values) {
632+
HashMap<K, V> map = new HashMap<K, V>(keys.size());
633+
if (keys.size() == values.size()) {
634+
Iterator<K> keysIterator = keys.iterator();
635+
Iterator<V> valuesIterator = values.iterator();
636+
while (keysIterator.hasNext() && valuesIterator.hasNext()) {
637+
K key = keysIterator.next();
638+
V value = valuesIterator.next();
639+
map.put(key, value);
640+
}
641+
}
642+
return map;
643+
}
621644
}

core-api/src/test/resources/config/valid-project-config-v4.json

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -191,6 +191,27 @@
191191
"forcedVariations": {
192192
"Harry Potter": "Control"
193193
}
194+
},
195+
{
196+
"id": "3072915611",
197+
"key": "launched_experiment",
198+
"layerId": "3587821424",
199+
"status": "Launched",
200+
"variations": [
201+
{
202+
"id": "1647582435",
203+
"key": "launch_control",
204+
"variables": []
205+
}
206+
],
207+
"trafficAllocation": [
208+
{
209+
"entityId": "1647582435",
210+
"endOfRang": 8000
211+
}
212+
],
213+
"audienceIds": [],
214+
"forcedVariations": {}
194215
}
195216
],
196217
"groups": [
@@ -281,7 +302,7 @@
281302
]
282303
}
283304
],
284-
"features": [
305+
"featureFlags": [
285306
{
286307
"id": "4195505407",
287308
"key": "boolean_feature",

0 commit comments

Comments
 (0)