@featurevisor/sdk 0.34.0 → 0.35.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +11 -0
- package/coverage/clover.xml +333 -322
- package/coverage/coverage-final.json +2 -2
- package/coverage/lcov-report/bucket.ts.html +1 -1
- package/coverage/lcov-report/conditions.ts.html +1 -1
- package/coverage/lcov-report/datafileReader.ts.html +1 -1
- package/coverage/lcov-report/emitter.ts.html +1 -1
- package/coverage/lcov-report/feature.ts.html +13 -805
- package/coverage/lcov-report/index.html +28 -28
- package/coverage/lcov-report/instance.ts.html +1018 -109
- package/coverage/lcov-report/logger.ts.html +1 -1
- package/coverage/lcov-report/segments.ts.html +1 -1
- package/coverage/lcov.info +603 -578
- package/dist/index.js +1 -1
- package/dist/index.js.gz +0 -0
- package/dist/index.js.map +1 -1
- package/lib/feature.d.ts +2 -9
- package/lib/feature.js +1 -169
- package/lib/feature.js.map +1 -1
- package/lib/instance.d.ts +26 -1
- package/lib/instance.js +313 -81
- package/lib/instance.js.map +1 -1
- package/package.json +3 -3
- package/src/feature.ts +2 -266
- package/src/instance.ts +398 -95
package/lib/feature.js
CHANGED
|
@@ -1,8 +1,5 @@
|
|
|
1
1
|
import { allGroupSegmentsAreMatched } from "./segments";
|
|
2
2
|
import { allConditionsAreMatched } from "./conditions";
|
|
3
|
-
/**
|
|
4
|
-
* Traffic
|
|
5
|
-
*/
|
|
6
3
|
export function getMatchedAllocation(traffic, bucketValue) {
|
|
7
4
|
for (var _i = 0, _a = traffic.allocation; _i < _a.length; _i++) {
|
|
8
5
|
var allocation = _a[_i];
|
|
@@ -30,10 +27,7 @@ export function getMatchedTrafficAndAllocation(traffic, attributes, bucketValue,
|
|
|
30
27
|
matchedAllocation: matchedAllocation,
|
|
31
28
|
};
|
|
32
29
|
}
|
|
33
|
-
|
|
34
|
-
* Variations and variables
|
|
35
|
-
*/
|
|
36
|
-
function findForceFromFeature(feature, attributes, datafileReader) {
|
|
30
|
+
export function findForceFromFeature(feature, attributes, datafileReader) {
|
|
37
31
|
if (!feature.force) {
|
|
38
32
|
return undefined;
|
|
39
33
|
}
|
|
@@ -47,166 +41,4 @@ function findForceFromFeature(feature, attributes, datafileReader) {
|
|
|
47
41
|
return false;
|
|
48
42
|
});
|
|
49
43
|
}
|
|
50
|
-
export function getForcedVariation(feature, attributes, datafileReader) {
|
|
51
|
-
var force = findForceFromFeature(feature, attributes, datafileReader);
|
|
52
|
-
if (!force || !force.variation) {
|
|
53
|
-
return undefined;
|
|
54
|
-
}
|
|
55
|
-
return feature.variations.find(function (v) { return v.value === force.variation; });
|
|
56
|
-
}
|
|
57
|
-
export function getBucketedVariation(feature, attributes, bucketValue, datafileReader, logger) {
|
|
58
|
-
var _a = getMatchedTrafficAndAllocation(feature.traffic, attributes, bucketValue, datafileReader, logger), matchedTraffic = _a.matchedTraffic, matchedAllocation = _a.matchedAllocation;
|
|
59
|
-
if (!matchedTraffic) {
|
|
60
|
-
logger.debug("no matched rule found", {
|
|
61
|
-
featureKey: feature.key,
|
|
62
|
-
bucketValue: bucketValue,
|
|
63
|
-
});
|
|
64
|
-
return undefined;
|
|
65
|
-
}
|
|
66
|
-
if (matchedTraffic.variation) {
|
|
67
|
-
var variation_1 = feature.variations.find(function (v) {
|
|
68
|
-
return v.value === matchedTraffic.variation;
|
|
69
|
-
});
|
|
70
|
-
if (variation_1) {
|
|
71
|
-
logger.debug("using variation from rule", {
|
|
72
|
-
featureKey: feature.key,
|
|
73
|
-
variation: variation_1.value,
|
|
74
|
-
ruleKey: matchedTraffic.key,
|
|
75
|
-
});
|
|
76
|
-
return variation_1;
|
|
77
|
-
}
|
|
78
|
-
}
|
|
79
|
-
if (!matchedAllocation) {
|
|
80
|
-
logger.debug("no matched allocation found", {
|
|
81
|
-
featureKey: feature.key,
|
|
82
|
-
bucketValue: bucketValue,
|
|
83
|
-
});
|
|
84
|
-
return undefined;
|
|
85
|
-
}
|
|
86
|
-
var variationValue = matchedAllocation.variation;
|
|
87
|
-
var variation = feature.variations.find(function (v) {
|
|
88
|
-
return v.value === variationValue;
|
|
89
|
-
});
|
|
90
|
-
if (!variation) {
|
|
91
|
-
// this should never happen
|
|
92
|
-
logger.debug("no matched variation found", {
|
|
93
|
-
featureKey: feature.key,
|
|
94
|
-
variation: variationValue,
|
|
95
|
-
bucketValue: bucketValue,
|
|
96
|
-
});
|
|
97
|
-
return undefined;
|
|
98
|
-
}
|
|
99
|
-
logger.debug("matched variation", {
|
|
100
|
-
featureKey: feature.key,
|
|
101
|
-
variation: variation.value,
|
|
102
|
-
bucketValue: bucketValue,
|
|
103
|
-
});
|
|
104
|
-
return variation;
|
|
105
|
-
}
|
|
106
|
-
export function getForcedVariableValue(feature, variableSchema, attributes, datafileReader) {
|
|
107
|
-
var force = findForceFromFeature(feature, attributes, datafileReader);
|
|
108
|
-
if (!force || !force.variables) {
|
|
109
|
-
return undefined;
|
|
110
|
-
}
|
|
111
|
-
var value = force.variables[variableSchema.key];
|
|
112
|
-
if (typeof value === "string" && variableSchema.type === "json") {
|
|
113
|
-
return JSON.parse(value);
|
|
114
|
-
}
|
|
115
|
-
return value;
|
|
116
|
-
}
|
|
117
|
-
export function getBucketedVariableValue(feature, variableSchema, attributes, bucketValue, datafileReader, logger) {
|
|
118
|
-
var _a;
|
|
119
|
-
// get traffic
|
|
120
|
-
var _b = getMatchedTrafficAndAllocation(feature.traffic, attributes, bucketValue, datafileReader, logger), matchedTraffic = _b.matchedTraffic, matchedAllocation = _b.matchedAllocation;
|
|
121
|
-
if (!matchedTraffic) {
|
|
122
|
-
logger.debug("no matched rule found", {
|
|
123
|
-
featureKey: feature.key,
|
|
124
|
-
variableKey: variableSchema.key,
|
|
125
|
-
bucketValue: bucketValue,
|
|
126
|
-
});
|
|
127
|
-
return undefined;
|
|
128
|
-
}
|
|
129
|
-
var variableKey = variableSchema.key;
|
|
130
|
-
// see if variable is set at traffic/rule level
|
|
131
|
-
if (matchedTraffic.variables && typeof matchedTraffic.variables[variableKey] !== "undefined") {
|
|
132
|
-
logger.debug("using variable from rule", {
|
|
133
|
-
featureKey: feature.key,
|
|
134
|
-
variableKey: variableKey,
|
|
135
|
-
bucketValue: bucketValue,
|
|
136
|
-
});
|
|
137
|
-
return matchedTraffic.variables[variableKey];
|
|
138
|
-
}
|
|
139
|
-
if (!matchedAllocation) {
|
|
140
|
-
logger.debug("no matched allocation found", {
|
|
141
|
-
featureKey: feature.key,
|
|
142
|
-
variableKey: variableKey,
|
|
143
|
-
bucketValue: bucketValue,
|
|
144
|
-
});
|
|
145
|
-
return undefined;
|
|
146
|
-
}
|
|
147
|
-
var variationValue = matchedAllocation.variation;
|
|
148
|
-
var variation = feature.variations.find(function (v) {
|
|
149
|
-
return v.value === variationValue;
|
|
150
|
-
});
|
|
151
|
-
if (!variation) {
|
|
152
|
-
// this should never happen
|
|
153
|
-
logger.debug("no matched variation found", {
|
|
154
|
-
feature: feature.key,
|
|
155
|
-
variableKey: variableKey,
|
|
156
|
-
variation: variationValue,
|
|
157
|
-
bucketValue: bucketValue,
|
|
158
|
-
});
|
|
159
|
-
return undefined;
|
|
160
|
-
}
|
|
161
|
-
var variableFromVariation = (_a = variation.variables) === null || _a === void 0 ? void 0 : _a.find(function (v) {
|
|
162
|
-
return v.key === variableKey;
|
|
163
|
-
});
|
|
164
|
-
if (!variableFromVariation) {
|
|
165
|
-
logger.debug("using default value as variation has no variable", {
|
|
166
|
-
featureKey: feature.key,
|
|
167
|
-
variableKey: variableKey,
|
|
168
|
-
variation: variationValue,
|
|
169
|
-
bucketValue: bucketValue,
|
|
170
|
-
});
|
|
171
|
-
if (variableSchema.type === "json") {
|
|
172
|
-
return JSON.parse(variableSchema.defaultValue);
|
|
173
|
-
}
|
|
174
|
-
return variableSchema.defaultValue;
|
|
175
|
-
}
|
|
176
|
-
if (variableFromVariation.overrides) {
|
|
177
|
-
var override = variableFromVariation.overrides.find(function (o) {
|
|
178
|
-
if (o.conditions) {
|
|
179
|
-
return allConditionsAreMatched(typeof o.conditions === "string" ? JSON.parse(o.conditions) : o.conditions, attributes);
|
|
180
|
-
}
|
|
181
|
-
if (o.segments) {
|
|
182
|
-
return allGroupSegmentsAreMatched(typeof o.segments === "string" && o.segments !== "*"
|
|
183
|
-
? JSON.parse(o.segments)
|
|
184
|
-
: o.segments, attributes, datafileReader);
|
|
185
|
-
}
|
|
186
|
-
return false;
|
|
187
|
-
});
|
|
188
|
-
if (override) {
|
|
189
|
-
logger.debug("using override value from variation", {
|
|
190
|
-
feature: feature.key,
|
|
191
|
-
variableKey: variableKey,
|
|
192
|
-
variation: variationValue,
|
|
193
|
-
bucketValue: bucketValue,
|
|
194
|
-
});
|
|
195
|
-
if (variableSchema.type === "json") {
|
|
196
|
-
return JSON.parse(override.value);
|
|
197
|
-
}
|
|
198
|
-
return override.value;
|
|
199
|
-
}
|
|
200
|
-
}
|
|
201
|
-
logger.debug("using value from variation", {
|
|
202
|
-
feature: feature.key,
|
|
203
|
-
variableKey: variableKey,
|
|
204
|
-
variation: variationValue,
|
|
205
|
-
bucketValue: bucketValue,
|
|
206
|
-
});
|
|
207
|
-
if (variableSchema.type === "json") {
|
|
208
|
-
return JSON.parse(variableFromVariation.value);
|
|
209
|
-
}
|
|
210
|
-
return variableFromVariation.value;
|
|
211
|
-
}
|
|
212
44
|
//# sourceMappingURL=feature.js.map
|
package/lib/feature.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"feature.js","sourceRoot":"","sources":["../src/feature.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"feature.js","sourceRoot":"","sources":["../src/feature.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,0BAA0B,EAAE,MAAM,YAAY,CAAC;AACxD,OAAO,EAAE,uBAAuB,EAAE,MAAM,cAAc,CAAC;AAGvD,MAAM,UAAU,oBAAoB,CAClC,OAAgB,EAChB,WAAmB;IAEnB,KAAyB,UAAkB,EAAlB,KAAA,OAAO,CAAC,UAAU,EAAlB,cAAkB,EAAlB,IAAkB,EAAE;QAAxC,IAAM,UAAU,SAAA;QACb,IAAA,KAAe,UAAU,CAAC,KAAK,EAA9B,KAAK,QAAA,EAAE,GAAG,QAAoB,CAAC;QAEtC,IAAI,UAAU,CAAC,KAAK,IAAI,KAAK,IAAI,WAAW,IAAI,GAAG,IAAI,WAAW,EAAE;YAClE,OAAO,UAAU,CAAC;SACnB;KACF;IAED,OAAO,SAAS,CAAC;AACnB,CAAC;AAOD,MAAM,UAAU,8BAA8B,CAC5C,OAAkB,EAClB,UAAsB,EACtB,WAAmB,EACnB,cAA8B,EAC9B,MAAc;IAEd,IAAI,iBAAyC,CAAC;IAE9C,IAAM,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC,UAAC,CAAC;QACpC,IACE,CAAC,0BAA0B,CACzB,OAAO,CAAC,CAAC,QAAQ,KAAK,QAAQ,IAAI,CAAC,CAAC,QAAQ,KAAK,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,QAAQ,EAC1F,UAAU,EACV,cAAc,CACf,EACD;YACA,OAAO,KAAK,CAAC;SACd;QAED,iBAAiB,GAAG,oBAAoB,CAAC,CAAC,EAAE,WAAW,CAAC,CAAC;QAEzD,IAAI,iBAAiB,EAAE;YACrB,OAAO,IAAI,CAAC;SACb;QAED,OAAO,KAAK,CAAC;IACf,CAAC,CAAC,CAAC;IAEH,OAAO;QACL,cAAc,gBAAA;QACd,iBAAiB,mBAAA;KAClB,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,oBAAoB,CAClC,OAAgB,EAChB,UAAsB,EACtB,cAA8B;IAE9B,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE;QAClB,OAAO,SAAS,CAAC;KAClB;IAED,OAAO,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,UAAC,CAAQ;QACjC,IAAI,CAAC,CAAC,UAAU,EAAE;YAChB,OAAO,uBAAuB,CAAC,CAAC,CAAC,UAAU,EAAE,UAAU,CAAC,CAAC;SAC1D;QAED,IAAI,CAAC,CAAC,QAAQ,EAAE;YACd,OAAO,0BAA0B,CAAC,CAAC,CAAC,QAAQ,EAAE,UAAU,EAAE,cAAc,CAAC,CAAC;SAC3E;QAED,OAAO,KAAK,CAAC;IACf,CAAC,CAAC,CAAC;AACL,CAAC"}
|
package/lib/instance.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { Attributes, BucketKey, BucketValue, DatafileContent, Feature, FeatureKey, InitialFeatures, StickyFeatures, VariableType, VariableValue, VariationType, VariationValue } from "@featurevisor/types";
|
|
1
|
+
import { Attributes, BucketKey, BucketValue, DatafileContent, Feature, FeatureKey, InitialFeatures, StickyFeatures, VariableType, VariableValue, VariationType, VariationValue, Variation, RuleKey, VariableKey, VariableSchema } from "@featurevisor/types";
|
|
2
2
|
import { Logger } from "./logger";
|
|
3
3
|
import { Emitter } from "./emitter";
|
|
4
4
|
export type ReadyCallback = () => void;
|
|
@@ -27,6 +27,29 @@ export interface InstanceOptions {
|
|
|
27
27
|
stickyFeatures?: StickyFeatures;
|
|
28
28
|
}
|
|
29
29
|
export type DatafileFetchHandler = (datafileUrl: string) => Promise<DatafileContent>;
|
|
30
|
+
export declare enum EvaluationReason {
|
|
31
|
+
NOT_FOUND = "not_found",
|
|
32
|
+
FORCED = "forced",
|
|
33
|
+
INITIAL = "initial",
|
|
34
|
+
STICKY = "sticky",
|
|
35
|
+
RULE = "rule",
|
|
36
|
+
ALLOCATED = "allocated",
|
|
37
|
+
DEFAULTED = "defaulted",
|
|
38
|
+
OVERRIDE = "override",
|
|
39
|
+
ERROR = "error"
|
|
40
|
+
}
|
|
41
|
+
export interface Evaluation {
|
|
42
|
+
featureKey: FeatureKey;
|
|
43
|
+
reason: EvaluationReason;
|
|
44
|
+
bucketValue?: BucketValue;
|
|
45
|
+
ruleKey?: RuleKey;
|
|
46
|
+
error?: Error;
|
|
47
|
+
variation?: Variation;
|
|
48
|
+
variationValue?: VariationValue;
|
|
49
|
+
variableKey?: VariableKey;
|
|
50
|
+
variableValue?: VariableValue;
|
|
51
|
+
variableSchema?: VariableSchema;
|
|
52
|
+
}
|
|
30
53
|
type FieldType = VariationType | VariableType;
|
|
31
54
|
type ValueType = VariableValue;
|
|
32
55
|
export declare function getValueByType(value: ValueType, fieldType: FieldType): ValueType;
|
|
@@ -73,6 +96,7 @@ export declare class FeaturevisorInstance {
|
|
|
73
96
|
/**
|
|
74
97
|
* Variation
|
|
75
98
|
*/
|
|
99
|
+
evaluateVariation(featureKey: FeatureKey | Feature, attributes?: Attributes): Evaluation;
|
|
76
100
|
getVariation(featureKey: FeatureKey | Feature, attributes?: Attributes): VariationValue | undefined;
|
|
77
101
|
getVariationBoolean(featureKey: FeatureKey | Feature, attributes?: Attributes): boolean | undefined;
|
|
78
102
|
getVariationString(featureKey: FeatureKey | Feature, attributes?: Attributes): string | undefined;
|
|
@@ -89,6 +113,7 @@ export declare class FeaturevisorInstance {
|
|
|
89
113
|
/**
|
|
90
114
|
* Variable
|
|
91
115
|
*/
|
|
116
|
+
evaluateVariable(featureKey: FeatureKey | Feature, variableKey: VariableKey, attributes?: Attributes): Evaluation;
|
|
92
117
|
getVariable(featureKey: FeatureKey | Feature, variableKey: string, attributes?: Attributes): VariableValue | undefined;
|
|
93
118
|
getVariableBoolean(featureKey: FeatureKey | Feature, variableKey: string, attributes?: Attributes): boolean | undefined;
|
|
94
119
|
getVariableString(featureKey: FeatureKey | Feature, variableKey: string, attributes?: Attributes): string | undefined;
|