-
Notifications
You must be signed in to change notification settings - Fork 7
Expand file tree
/
Copy pathAbstractSplitsCacheAsync.ts
More file actions
71 lines (61 loc) · 3.04 KB
/
AbstractSplitsCacheAsync.ts
File metadata and controls
71 lines (61 loc) · 3.04 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
import { ISplitsCacheAsync } from './types';
import { ISplit } from '../dtos/types';
import { objectAssign } from '../utils/lang/objectAssign';
/**
* This class provides a skeletal implementation of the ISplitsCacheAsync interface
* to minimize the effort required to implement this interface.
*/
export abstract class AbstractSplitsCacheAsync implements ISplitsCacheAsync {
protected abstract setChangeNumber(changeNumber: number): Promise<boolean | void>
protected abstract addSplit(split: ISplit): Promise<boolean>
protected abstract removeSplit(name: string): Promise<boolean>
update(addedFFs: ISplit[], removedFFs: ISplit[], changeNumber: number): Promise<boolean> {
return Promise.all([
this.setChangeNumber(changeNumber),
Promise.all(addedFFs.map(addedFF => this.addSplit(addedFF))),
Promise.all(removedFFs.map(removedFF => this.removeSplit(removedFF.name)))
]).then(([, added, removed]) => {
return added.some(result => result) || removed.some(result => result);
});
}
abstract getSplit(name: string): Promise<ISplit | null>
abstract getSplits(names: string[]): Promise<Record<string, ISplit | null>>
abstract getChangeNumber(): Promise<number>
abstract getAll(): Promise<ISplit[]>
abstract getSplitNames(): Promise<string[]>
abstract getNamesByFlagSets(flagSets: string[]): Promise<Set<string>[]>
abstract trafficTypeExists(trafficType: string): Promise<boolean>
abstract clear(): Promise<boolean | void>
// @TODO revisit segment-related methods ('usesSegments', 'getRegisteredSegments', 'registerSegments')
// noop, just keeping the interface. This is used by standalone client-side API only, and so only implemented by InMemory and InLocalStorage.
usesSegments(): Promise<boolean> {
return Promise.resolve(true);
}
/**
* Check if the splits information is already stored in cache.
* Noop, just keeping the interface. This is used by client-side implementations only.
*/
checkCache(): Promise<boolean> {
return Promise.resolve(false);
}
/**
* Kill `name` split and set `defaultTreatment` and `changeNumber`.
* Used for SPLIT_KILL push notifications.
*
* @returns a promise that is resolved once the split kill operation is performed. The fulfillment value is a boolean: `true` if the operation successed updating the split or `false` if no split is updated,
* for instance, if the `changeNumber` is old, or if the split is not found (e.g., `/splitchanges` hasn't been fetched yet), or if the storage fails to apply the update.
* The promise will never be rejected.
*/
killLocally(name: string, defaultTreatment: string, changeNumber: number): Promise<boolean> {
return this.getSplit(name).then(split => {
if (split && (!split.changeNumber || split.changeNumber < changeNumber)) {
const newSplit = objectAssign({}, split);
newSplit.killed = true;
newSplit.defaultTreatment = defaultTreatment;
newSplit.changeNumber = changeNumber;
return this.addSplit(newSplit);
}
return false;
}).catch(() => false);
}
}