@splitsoftware/splitio-commons 2.12.0 → 3.0.0-rc.1

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.
Files changed (395) hide show
  1. package/CHANGES.txt +19 -1
  2. package/cjs/evaluator/condition/engineUtils.js +2 -2
  3. package/cjs/evaluator/fallbackConfigsCalculator/fallbackSanitizer/index.js +70 -0
  4. package/cjs/evaluator/fallbackConfigsCalculator/index.js +25 -0
  5. package/cjs/evaluator/fallbackTreatmentsCalculator/fallbackSanitizer/index.js +5 -8
  6. package/cjs/evaluator/fallbackTreatmentsCalculator/index.js +21 -32
  7. package/cjs/evaluator/index.js +73 -48
  8. package/cjs/evaluator/matchers/whitelist.js +1 -1
  9. package/cjs/integrations/pluggable.js +1 -1
  10. package/cjs/listeners/browser.js +4 -3
  11. package/cjs/listeners/node.js +4 -4
  12. package/cjs/logger/constants.js +15 -21
  13. package/cjs/logger/index.js +1 -1
  14. package/cjs/logger/messages/debug.js +6 -7
  15. package/cjs/logger/messages/error.js +4 -4
  16. package/cjs/logger/messages/info.js +2 -4
  17. package/cjs/logger/messages/warn.js +9 -10
  18. package/cjs/platform/browser.js +15 -0
  19. package/cjs/platform/getEventSource/browser.js +8 -0
  20. package/cjs/platform/getEventSource/eventsource.js +480 -0
  21. package/cjs/platform/getEventSource/node.js +26 -0
  22. package/cjs/platform/getFetch/browser.js +9 -0
  23. package/cjs/platform/getFetch/node.js +27 -0
  24. package/cjs/platform/getOptions/node.js +25 -0
  25. package/cjs/platform/node.js +17 -0
  26. package/cjs/readiness/constants.js +5 -4
  27. package/cjs/readiness/readinessManager.js +22 -22
  28. package/cjs/readiness/sdkReadinessManager.js +0 -16
  29. package/cjs/sdkClient/client.js +9 -35
  30. package/cjs/sdkClient/clientAttributesDecoration.js +3 -3
  31. package/cjs/sdkClient/clientInputValidation.js +38 -81
  32. package/cjs/sdkClient/identity.js +1 -1
  33. package/cjs/sdkClient/sdkClient.js +4 -49
  34. package/cjs/sdkClient/sdkLifecycle.js +71 -0
  35. package/cjs/sdkClient/trackMethod.js +56 -0
  36. package/cjs/sdkFactory/index.js +13 -50
  37. package/cjs/sdkManager/index.js +5 -5
  38. package/cjs/services/authProvider.js +67 -0
  39. package/cjs/services/secureSplitHttpClient.js +39 -0
  40. package/cjs/services/splitApi.js +24 -14
  41. package/cjs/services/splitHttpClient.js +1 -1
  42. package/cjs/storages/AbstractDefinitionsCacheAsync.js +51 -0
  43. package/cjs/storages/AbstractDefinitionsCacheSync.js +76 -0
  44. package/cjs/storages/KeyBuilder.js +16 -16
  45. package/cjs/storages/KeyBuilderCS.js +17 -17
  46. package/cjs/storages/KeyBuilderSS.js +16 -16
  47. package/cjs/storages/getRolloutPlan.js +4 -4
  48. package/cjs/storages/inLocalStorage/DefinitionsCacheInLocal.js +194 -0
  49. package/cjs/storages/inLocalStorage/MySegmentsCacheInLocal.js +1 -1
  50. package/cjs/storages/inLocalStorage/RBSegmentsCacheInLocal.js +10 -10
  51. package/cjs/storages/inLocalStorage/index.js +6 -6
  52. package/cjs/storages/inLocalStorage/validateCache.js +3 -3
  53. package/cjs/storages/inMemory/DefinitionsCacheInMemory.js +121 -0
  54. package/cjs/storages/inMemory/ImpressionCountsCacheInMemory.js +1 -1
  55. package/cjs/storages/inMemory/InMemoryStorage.js +4 -4
  56. package/cjs/storages/inMemory/InMemoryStorageCS.js +5 -5
  57. package/cjs/storages/inMemory/MySegmentsCacheInMemory.js +1 -1
  58. package/cjs/storages/inMemory/RBSegmentsCacheInMemory.js +5 -5
  59. package/cjs/storages/inMemory/SegmentsCacheInMemory.js +1 -1
  60. package/cjs/storages/inMemory/TelemetryCacheInMemory.js +5 -5
  61. package/cjs/storages/inRedis/DefinitionsCacheInRedis.js +243 -0
  62. package/cjs/storages/inRedis/EventsCacheInRedis.js +1 -1
  63. package/cjs/storages/inRedis/ImpressionCountsCacheInRedis.js +5 -5
  64. package/cjs/storages/inRedis/ImpressionsCacheInRedis.js +1 -1
  65. package/cjs/storages/inRedis/RBSegmentsCacheInRedis.js +1 -1
  66. package/cjs/storages/inRedis/RedisAdapter.js +8 -8
  67. package/cjs/storages/inRedis/TelemetryCacheInRedis.js +7 -7
  68. package/cjs/storages/inRedis/UniqueKeysCacheInRedis.js +3 -3
  69. package/cjs/storages/inRedis/index.js +2 -2
  70. package/cjs/storages/pluggable/DefinitionsCachePluggable.js +212 -0
  71. package/cjs/storages/pluggable/EventsCachePluggable.js +1 -1
  72. package/cjs/storages/pluggable/ImpressionCountsCachePluggable.js +6 -6
  73. package/cjs/storages/pluggable/RBSegmentsCachePluggable.js +1 -1
  74. package/cjs/storages/pluggable/TelemetryCachePluggable.js +7 -7
  75. package/cjs/storages/pluggable/UniqueKeysCachePluggable.js +2 -2
  76. package/cjs/storages/pluggable/index.js +5 -5
  77. package/cjs/storages/pluggable/wrapperAdapter.js +1 -1
  78. package/cjs/storages/setRolloutPlan.js +6 -6
  79. package/cjs/storages/utils.js +6 -6
  80. package/cjs/sync/offline/splitsParser/parseCondition.js +1 -1
  81. package/cjs/sync/offline/syncTasks/fromObjectSyncTask.js +5 -5
  82. package/cjs/sync/polling/fetchers/segmentChangesFetcher.js +1 -1
  83. package/cjs/sync/polling/fetchers/splitChangesFetcher.js +24 -15
  84. package/cjs/sync/polling/pollingManagerCS.js +18 -18
  85. package/cjs/sync/polling/pollingManagerSS.js +13 -13
  86. package/cjs/sync/polling/syncTasks/definitionsSyncTask.js +12 -0
  87. package/cjs/sync/polling/updaters/{splitChangesUpdater.js → definitionChangesUpdater.js} +72 -64
  88. package/cjs/sync/polling/updaters/mySegmentsUpdater.js +3 -3
  89. package/cjs/sync/polling/updaters/segmentChangesUpdater.js +6 -6
  90. package/cjs/sync/streaming/SSEClient/index.js +2 -2
  91. package/cjs/sync/streaming/SSEHandler/NotificationKeeper.js +1 -1
  92. package/cjs/sync/streaming/SSEHandler/index.js +1 -1
  93. package/cjs/sync/streaming/UpdateWorkers/{SplitsUpdateWorker.js → DefinitionsUpdateWorker.js} +18 -18
  94. package/cjs/sync/streaming/UpdateWorkers/MySegmentsUpdateWorker.js +2 -2
  95. package/cjs/sync/streaming/UpdateWorkers/SegmentsUpdateWorker.js +2 -2
  96. package/cjs/sync/streaming/constants.js +3 -3
  97. package/cjs/sync/streaming/parseUtils.js +12 -12
  98. package/cjs/sync/streaming/pushManager.js +14 -14
  99. package/cjs/sync/submitters/impressionsSubmitter.js +6 -6
  100. package/cjs/sync/submitters/submitter.js +1 -1
  101. package/cjs/sync/submitters/telemetrySubmitter.js +1 -2
  102. package/cjs/sync/syncManagerOnline.js +9 -6
  103. package/cjs/trackers/eventTracker.js +10 -12
  104. package/cjs/trackers/impressionObserver/buildKey.js +1 -1
  105. package/cjs/trackers/impressionsTracker.js +37 -20
  106. package/cjs/trackers/uniqueKeysTracker.js +1 -1
  107. package/cjs/utils/Backoff.js +20 -0
  108. package/cjs/utils/EventEmitter.js +391 -0
  109. package/cjs/utils/filter/bloomFilter.js +37 -0
  110. package/cjs/utils/inputValidation/apiKey.js +1 -1
  111. package/cjs/utils/inputValidation/attribute.js +2 -2
  112. package/cjs/utils/inputValidation/{split.js → definition.js} +10 -10
  113. package/cjs/utils/inputValidation/{splitExistence.js → definitionExistence.js} +6 -6
  114. package/cjs/utils/inputValidation/definitions.js +25 -0
  115. package/cjs/utils/inputValidation/eventProperties.js +1 -1
  116. package/cjs/utils/inputValidation/index.js +7 -7
  117. package/cjs/utils/inputValidation/isOperational.js +4 -4
  118. package/cjs/utils/inputValidation/target.js +22 -0
  119. package/cjs/utils/labels/index.js +3 -3
  120. package/cjs/utils/lang/index.js +1 -1
  121. package/cjs/utils/lang/sets.js +4 -4
  122. package/cjs/utils/promise/timeout.js +1 -1
  123. package/cjs/utils/settingsValidation/splitFilters.js +4 -4
  124. package/cjs/utils/settingsValidation/url.js +6 -6
  125. package/esm/evaluator/condition/engineUtils.js +2 -2
  126. package/esm/evaluator/fallbackConfigsCalculator/fallbackSanitizer/index.js +64 -0
  127. package/esm/evaluator/fallbackConfigsCalculator/index.js +21 -0
  128. package/esm/evaluator/fallbackTreatmentsCalculator/fallbackSanitizer/index.js +5 -8
  129. package/esm/evaluator/fallbackTreatmentsCalculator/index.js +21 -33
  130. package/esm/evaluator/index.js +72 -48
  131. package/esm/evaluator/matchers/whitelist.js +1 -1
  132. package/esm/integrations/pluggable.js +1 -1
  133. package/esm/listeners/browser.js +4 -3
  134. package/esm/listeners/node.js +4 -4
  135. package/esm/logger/constants.js +12 -18
  136. package/esm/logger/index.js +1 -1
  137. package/esm/logger/messages/debug.js +5 -6
  138. package/esm/logger/messages/error.js +3 -3
  139. package/esm/logger/messages/info.js +1 -3
  140. package/esm/logger/messages/warn.js +8 -9
  141. package/esm/platform/browser.js +12 -0
  142. package/esm/platform/getEventSource/browser.js +4 -0
  143. package/esm/platform/getEventSource/eventsource.js +480 -0
  144. package/esm/platform/getEventSource/node.js +20 -0
  145. package/esm/platform/getFetch/browser.js +5 -0
  146. package/esm/platform/getFetch/node.js +22 -0
  147. package/esm/platform/getOptions/node.js +20 -0
  148. package/esm/platform/node.js +14 -0
  149. package/esm/readiness/constants.js +4 -3
  150. package/esm/readiness/readinessManager.js +23 -23
  151. package/esm/readiness/sdkReadinessManager.js +1 -17
  152. package/esm/sdkClient/client.js +10 -37
  153. package/esm/sdkClient/clientAttributesDecoration.js +3 -3
  154. package/esm/sdkClient/clientInputValidation.js +40 -83
  155. package/esm/sdkClient/identity.js +1 -1
  156. package/esm/sdkClient/sdkClient.js +4 -49
  157. package/esm/sdkClient/sdkLifecycle.js +67 -0
  158. package/esm/sdkClient/trackMethod.js +52 -0
  159. package/esm/sdkFactory/index.js +14 -51
  160. package/esm/sdkManager/index.js +6 -6
  161. package/esm/services/authProvider.js +63 -0
  162. package/esm/services/secureSplitHttpClient.js +35 -0
  163. package/esm/services/splitApi.js +24 -14
  164. package/esm/services/splitHttpClient.js +1 -1
  165. package/esm/storages/AbstractDefinitionsCacheAsync.js +48 -0
  166. package/esm/storages/AbstractDefinitionsCacheSync.js +71 -0
  167. package/esm/storages/KeyBuilder.js +16 -16
  168. package/esm/storages/KeyBuilderCS.js +16 -16
  169. package/esm/storages/KeyBuilderSS.js +15 -15
  170. package/esm/storages/getRolloutPlan.js +4 -4
  171. package/esm/storages/inLocalStorage/DefinitionsCacheInLocal.js +191 -0
  172. package/esm/storages/inLocalStorage/RBSegmentsCacheInLocal.js +7 -7
  173. package/esm/storages/inLocalStorage/index.js +6 -6
  174. package/esm/storages/inLocalStorage/validateCache.js +3 -3
  175. package/esm/storages/inMemory/DefinitionsCacheInMemory.js +118 -0
  176. package/esm/storages/inMemory/ImpressionCountsCacheInMemory.js +1 -1
  177. package/esm/storages/inMemory/InMemoryStorage.js +4 -4
  178. package/esm/storages/inMemory/InMemoryStorageCS.js +5 -5
  179. package/esm/storages/inMemory/RBSegmentsCacheInMemory.js +2 -2
  180. package/esm/storages/inMemory/SegmentsCacheInMemory.js +1 -1
  181. package/esm/storages/inMemory/TelemetryCacheInMemory.js +5 -5
  182. package/esm/storages/inRedis/DefinitionsCacheInRedis.js +240 -0
  183. package/esm/storages/inRedis/EventsCacheInRedis.js +1 -1
  184. package/esm/storages/inRedis/ImpressionCountsCacheInRedis.js +4 -4
  185. package/esm/storages/inRedis/RBSegmentsCacheInRedis.js +1 -1
  186. package/esm/storages/inRedis/RedisAdapter.js +7 -7
  187. package/esm/storages/inRedis/TelemetryCacheInRedis.js +7 -7
  188. package/esm/storages/inRedis/UniqueKeysCacheInRedis.js +1 -1
  189. package/esm/storages/inRedis/index.js +2 -2
  190. package/esm/storages/pluggable/DefinitionsCachePluggable.js +209 -0
  191. package/esm/storages/pluggable/EventsCachePluggable.js +1 -1
  192. package/esm/storages/pluggable/ImpressionCountsCachePluggable.js +5 -5
  193. package/esm/storages/pluggable/RBSegmentsCachePluggable.js +1 -1
  194. package/esm/storages/pluggable/TelemetryCachePluggable.js +7 -7
  195. package/esm/storages/pluggable/UniqueKeysCachePluggable.js +1 -1
  196. package/esm/storages/pluggable/index.js +4 -4
  197. package/esm/storages/pluggable/wrapperAdapter.js +1 -1
  198. package/esm/storages/setRolloutPlan.js +6 -6
  199. package/esm/storages/utils.js +6 -6
  200. package/esm/sync/offline/splitsParser/parseCondition.js +1 -1
  201. package/esm/sync/offline/syncTasks/fromObjectSyncTask.js +6 -6
  202. package/esm/sync/polling/fetchers/splitChangesFetcher.js +25 -16
  203. package/esm/sync/polling/pollingManagerCS.js +15 -15
  204. package/esm/sync/polling/pollingManagerSS.js +13 -13
  205. package/esm/sync/polling/syncTasks/definitionsSyncTask.js +8 -0
  206. package/esm/sync/polling/updaters/definitionChangesUpdater.js +200 -0
  207. package/esm/sync/polling/updaters/mySegmentsUpdater.js +3 -3
  208. package/esm/sync/polling/updaters/segmentChangesUpdater.js +7 -7
  209. package/esm/sync/streaming/SSEClient/index.js +2 -2
  210. package/esm/sync/streaming/SSEHandler/NotificationKeeper.js +2 -2
  211. package/esm/sync/streaming/SSEHandler/index.js +2 -2
  212. package/esm/sync/streaming/UpdateWorkers/{SplitsUpdateWorker.js → DefinitionsUpdateWorker.js} +17 -17
  213. package/esm/sync/streaming/UpdateWorkers/MySegmentsUpdateWorker.js +2 -2
  214. package/esm/sync/streaming/UpdateWorkers/SegmentsUpdateWorker.js +2 -2
  215. package/esm/sync/streaming/constants.js +2 -2
  216. package/esm/sync/streaming/parseUtils.js +10 -10
  217. package/esm/sync/streaming/pushManager.js +16 -16
  218. package/esm/sync/submitters/impressionsSubmitter.js +6 -6
  219. package/esm/sync/submitters/submitter.js +1 -1
  220. package/esm/sync/submitters/telemetrySubmitter.js +1 -2
  221. package/esm/sync/syncManagerOnline.js +8 -5
  222. package/esm/trackers/eventTracker.js +10 -12
  223. package/esm/trackers/impressionObserver/buildKey.js +1 -1
  224. package/esm/trackers/impressionsTracker.js +38 -21
  225. package/esm/trackers/uniqueKeysTracker.js +1 -1
  226. package/esm/utils/Backoff.js +20 -0
  227. package/esm/utils/EventEmitter.js +387 -0
  228. package/esm/utils/filter/bloomFilter.js +33 -0
  229. package/esm/utils/inputValidation/apiKey.js +1 -1
  230. package/esm/utils/inputValidation/attribute.js +2 -2
  231. package/esm/utils/inputValidation/{split.js → definition.js} +8 -8
  232. package/esm/utils/inputValidation/definitionExistence.js +15 -0
  233. package/esm/utils/inputValidation/definitions.js +21 -0
  234. package/esm/utils/inputValidation/index.js +3 -3
  235. package/esm/utils/inputValidation/isOperational.js +4 -4
  236. package/esm/utils/inputValidation/target.js +18 -0
  237. package/esm/utils/labels/index.js +2 -2
  238. package/esm/utils/lang/sets.js +4 -4
  239. package/esm/utils/promise/timeout.js +1 -1
  240. package/esm/utils/settingsValidation/splitFilters.js +4 -4
  241. package/esm/utils/settingsValidation/url.js +6 -6
  242. package/package.json +15 -6
  243. package/src/dtos/types.ts +65 -70
  244. package/src/evaluator/Engine.ts +4 -4
  245. package/src/evaluator/combiners/and.ts +3 -3
  246. package/src/evaluator/combiners/ifelseif.ts +2 -2
  247. package/src/evaluator/condition/engineUtils.ts +2 -2
  248. package/src/evaluator/condition/index.ts +3 -3
  249. package/src/evaluator/fallbackConfigsCalculator/fallbackSanitizer/index.ts +76 -0
  250. package/src/evaluator/fallbackConfigsCalculator/index.ts +24 -0
  251. package/src/evaluator/fallbackTreatmentsCalculator/fallbackSanitizer/index.ts +5 -7
  252. package/src/evaluator/fallbackTreatmentsCalculator/index.ts +27 -41
  253. package/src/evaluator/index.ts +86 -51
  254. package/src/evaluator/matchers/dependency.ts +2 -2
  255. package/src/evaluator/matchers/matcherTypes.ts +2 -2
  256. package/src/evaluator/matchers/prerequisites.ts +4 -4
  257. package/src/evaluator/matchers/rbsegment.ts +2 -2
  258. package/src/evaluator/matchers/whitelist.ts +2 -2
  259. package/src/evaluator/matchersTransform/index.ts +2 -2
  260. package/src/evaluator/matchersTransform/whitelist.ts +2 -2
  261. package/src/evaluator/parser/index.ts +4 -4
  262. package/src/evaluator/treatments/index.ts +2 -2
  263. package/src/evaluator/types.ts +6 -6
  264. package/src/evaluator/value/index.ts +1 -1
  265. package/src/integrations/pluggable.ts +1 -1
  266. package/src/listeners/browser.ts +11 -8
  267. package/src/listeners/node.ts +2 -5
  268. package/src/logger/constants.ts +12 -18
  269. package/src/logger/messages/debug.ts +5 -6
  270. package/src/logger/messages/error.ts +3 -3
  271. package/src/logger/messages/info.ts +1 -3
  272. package/src/logger/messages/warn.ts +8 -9
  273. package/src/platform/browser.ts +14 -0
  274. package/src/platform/getEventSource/browser.ts +4 -0
  275. package/src/platform/getEventSource/eventsource.js +519 -0
  276. package/src/platform/getEventSource/node.ts +23 -0
  277. package/src/platform/getFetch/browser.ts +5 -0
  278. package/src/platform/getFetch/node.ts +27 -0
  279. package/src/platform/getOptions/node.ts +24 -0
  280. package/src/platform/node.ts +16 -0
  281. package/src/readiness/constants.ts +4 -3
  282. package/src/readiness/readinessManager.ts +22 -22
  283. package/src/readiness/sdkReadinessManager.ts +1 -16
  284. package/src/readiness/types.ts +10 -16
  285. package/src/sdkClient/client.ts +11 -41
  286. package/src/sdkClient/clientInputValidation.ts +44 -84
  287. package/src/sdkClient/sdkClient.ts +5 -54
  288. package/src/sdkClient/sdkLifecycle.ts +79 -0
  289. package/src/sdkClient/trackMethod.ts +59 -0
  290. package/src/sdkFactory/index.ts +15 -59
  291. package/src/sdkFactory/types.ts +19 -16
  292. package/src/sdkManager/index.ts +15 -15
  293. package/src/services/authProvider.ts +86 -0
  294. package/src/services/secureSplitHttpClient.ts +44 -0
  295. package/src/services/splitApi.ts +14 -2
  296. package/src/services/types.ts +7 -2
  297. package/src/storages/AbstractDefinitionsCacheAsync.ts +63 -0
  298. package/src/storages/AbstractDefinitionsCacheSync.ts +95 -0
  299. package/src/storages/KeyBuilder.ts +6 -6
  300. package/src/storages/KeyBuilderCS.ts +6 -6
  301. package/src/storages/KeyBuilderSS.ts +2 -2
  302. package/src/storages/getRolloutPlan.ts +3 -3
  303. package/src/storages/inLocalStorage/DefinitionsCacheInLocal.ts +234 -0
  304. package/src/storages/inLocalStorage/RBSegmentsCacheInLocal.ts +8 -8
  305. package/src/storages/inLocalStorage/index.ts +6 -6
  306. package/src/storages/inLocalStorage/validateCache.ts +4 -4
  307. package/src/storages/inMemory/DefinitionsCacheInMemory.ts +130 -0
  308. package/src/storages/inMemory/InMemoryStorage.ts +4 -4
  309. package/src/storages/inMemory/InMemoryStorageCS.ts +5 -5
  310. package/src/storages/inMemory/RBSegmentsCacheInMemory.ts +3 -3
  311. package/src/storages/inMemory/SegmentsCacheInMemory.ts +1 -1
  312. package/src/storages/inMemory/TelemetryCacheInMemory.ts +5 -5
  313. package/src/storages/inRedis/{SplitsCacheInRedis.ts → DefinitionsCacheInRedis.ts} +69 -69
  314. package/src/storages/inRedis/RBSegmentsCacheInRedis.ts +2 -2
  315. package/src/storages/inRedis/index.ts +2 -2
  316. package/src/storages/pluggable/DefinitionsCachePluggable.ts +230 -0
  317. package/src/storages/pluggable/RBSegmentsCachePluggable.ts +2 -2
  318. package/src/storages/pluggable/index.ts +2 -2
  319. package/src/storages/setRolloutPlan.ts +7 -7
  320. package/src/storages/types.ts +34 -29
  321. package/src/sync/offline/splitsParser/parseCondition.ts +2 -2
  322. package/src/sync/offline/splitsParser/splitsParserFromSettings.ts +3 -3
  323. package/src/sync/offline/splitsParser/types.ts +6 -3
  324. package/src/sync/offline/syncManagerOffline.ts +2 -2
  325. package/src/sync/offline/syncTasks/fromObjectSyncTask.ts +14 -14
  326. package/src/sync/polling/fetchers/splitChangesFetcher.ts +58 -23
  327. package/src/sync/polling/fetchers/types.ts +5 -3
  328. package/src/sync/polling/pollingManagerCS.ts +16 -14
  329. package/src/sync/polling/pollingManagerSS.ts +15 -13
  330. package/src/sync/polling/syncTasks/{splitsSyncTask.ts → definitionsSyncTask.ts} +11 -12
  331. package/src/sync/polling/types.ts +3 -3
  332. package/src/sync/polling/updaters/definitionChangesUpdater.ts +239 -0
  333. package/src/sync/polling/updaters/mySegmentsUpdater.ts +3 -3
  334. package/src/sync/polling/updaters/segmentChangesUpdater.ts +7 -7
  335. package/src/sync/streaming/AuthClient/index.ts +2 -2
  336. package/src/sync/streaming/AuthClient/types.ts +14 -11
  337. package/src/sync/streaming/SSEClient/index.ts +2 -2
  338. package/src/sync/streaming/SSEClient/types.ts +2 -2
  339. package/src/sync/streaming/SSEHandler/NotificationKeeper.ts +2 -2
  340. package/src/sync/streaming/SSEHandler/index.ts +2 -2
  341. package/src/sync/streaming/UpdateWorkers/{SplitsUpdateWorker.ts → DefinitionsUpdateWorker.ts} +21 -21
  342. package/src/sync/streaming/constants.ts +2 -2
  343. package/src/sync/streaming/parseUtils.ts +12 -12
  344. package/src/sync/streaming/pushManager.ts +18 -18
  345. package/src/sync/streaming/types.ts +2 -2
  346. package/src/sync/submitters/impressionsSubmitter.ts +9 -9
  347. package/src/sync/submitters/telemetrySubmitter.ts +1 -2
  348. package/src/sync/submitters/types.ts +3 -0
  349. package/src/sync/syncManagerOnline.ts +9 -5
  350. package/src/trackers/eventTracker.ts +7 -10
  351. package/src/trackers/impressionsTracker.ts +42 -26
  352. package/src/trackers/types.ts +3 -1
  353. package/src/utils/Backoff.ts +21 -0
  354. package/src/utils/EventEmitter.js +444 -0
  355. package/src/utils/filter/bloomFilter.ts +38 -0
  356. package/src/utils/inputValidation/definition.ts +27 -0
  357. package/src/utils/inputValidation/definitionExistence.ts +19 -0
  358. package/src/utils/inputValidation/definitions.ts +21 -0
  359. package/src/utils/inputValidation/index.ts +3 -3
  360. package/src/utils/inputValidation/isOperational.ts +4 -4
  361. package/src/utils/inputValidation/target.ts +21 -0
  362. package/src/utils/inputValidation/trafficTypeExistence.ts +2 -2
  363. package/src/utils/jwt/types.ts +1 -1
  364. package/src/utils/labels/index.ts +2 -2
  365. package/src/utils/lang/sets.ts +4 -2
  366. package/src/utils/settingsValidation/splitFilters.ts +3 -3
  367. package/src/utils/settingsValidation/url.ts +1 -1
  368. package/types/splitio.d.ts +222 -11
  369. package/cjs/storages/AbstractSplitsCacheAsync.js +0 -51
  370. package/cjs/storages/AbstractSplitsCacheSync.js +0 -76
  371. package/cjs/storages/inLocalStorage/SplitsCacheInLocal.js +0 -194
  372. package/cjs/storages/inMemory/SplitsCacheInMemory.js +0 -121
  373. package/cjs/storages/inRedis/SplitsCacheInRedis.js +0 -243
  374. package/cjs/storages/pluggable/SplitsCachePluggable.js +0 -212
  375. package/cjs/sync/polling/syncTasks/splitsSyncTask.js +0 -13
  376. package/cjs/utils/inputValidation/splits.js +0 -25
  377. package/esm/storages/AbstractSplitsCacheAsync.js +0 -48
  378. package/esm/storages/AbstractSplitsCacheSync.js +0 -71
  379. package/esm/storages/inLocalStorage/SplitsCacheInLocal.js +0 -191
  380. package/esm/storages/inMemory/SplitsCacheInMemory.js +0 -118
  381. package/esm/storages/inRedis/SplitsCacheInRedis.js +0 -240
  382. package/esm/storages/pluggable/SplitsCachePluggable.js +0 -209
  383. package/esm/sync/polling/syncTasks/splitsSyncTask.js +0 -9
  384. package/esm/sync/polling/updaters/splitChangesUpdater.js +0 -192
  385. package/esm/utils/inputValidation/splitExistence.js +0 -15
  386. package/esm/utils/inputValidation/splits.js +0 -21
  387. package/src/storages/AbstractSplitsCacheAsync.ts +0 -63
  388. package/src/storages/AbstractSplitsCacheSync.ts +0 -95
  389. package/src/storages/inLocalStorage/SplitsCacheInLocal.ts +0 -234
  390. package/src/storages/inMemory/SplitsCacheInMemory.ts +0 -130
  391. package/src/storages/pluggable/SplitsCachePluggable.ts +0 -230
  392. package/src/sync/polling/updaters/splitChangesUpdater.ts +0 -230
  393. package/src/utils/inputValidation/split.ts +0 -27
  394. package/src/utils/inputValidation/splitExistence.ts +0 -19
  395. package/src/utils/inputValidation/splits.ts +0 -21
@@ -0,0 +1,63 @@
1
+ import { IDefinitionsCacheAsync } from './types';
2
+ import { IDefinition } from '../dtos/types';
3
+ import { objectAssign } from '../utils/lang/objectAssign';
4
+
5
+ /**
6
+ * This class provides a skeletal implementation of the IDefinitionsCacheAsync interface
7
+ * to minimize the effort required to implement this interface.
8
+ */
9
+ export abstract class AbstractDefinitionsCacheAsync implements IDefinitionsCacheAsync {
10
+
11
+ protected abstract add(definition: IDefinition): Promise<boolean>
12
+ protected abstract remove(name: string): Promise<boolean>
13
+ protected abstract setChangeNumber(changeNumber: number): Promise<boolean | void>
14
+
15
+ update(toAdd: IDefinition[], toRemove: string[], changeNumber: number): Promise<boolean> {
16
+ return Promise.all([
17
+ this.setChangeNumber(changeNumber),
18
+ Promise.all(toAdd.map(addedFF => this.add(addedFF))),
19
+ Promise.all(toRemove.map(removedFF => this.remove(removedFF)))
20
+ ]).then(([, added, removed]) => {
21
+ return added.some(result => result) || removed.some(result => result);
22
+ });
23
+ }
24
+
25
+ abstract get(name: string): Promise<IDefinition | null>
26
+ abstract getMany(names: string[]): Promise<Record<string, IDefinition | null>>
27
+ abstract getChangeNumber(): Promise<number>
28
+ abstract getAll(): Promise<IDefinition[]>
29
+ abstract getNames(): Promise<string[]>
30
+ abstract getNamesBySets(sets: string[]): Promise<Set<string>[]>
31
+ abstract trafficTypeExists(trafficType: string): Promise<boolean>
32
+ abstract clear(): Promise<boolean | void>
33
+
34
+ // @TODO revisit segment-related methods ('usesSegments', 'getRegisteredSegments', 'registerSegments')
35
+ // noop, just keeping the interface. This is used by standalone client-side API only, and so only implemented by InMemory and InLocalStorage.
36
+ usesSegments(): Promise<boolean> {
37
+ return Promise.resolve(true);
38
+ }
39
+
40
+ /**
41
+ * Kill `name` definition and set `defaultTreatment` and `changeNumber`.
42
+ * Used for SPLIT_KILL push notifications.
43
+ *
44
+ * @returns a promise that is resolved once the definition kill operation is performed. The fulfillment value is a boolean: `true` if the operation succeeded updating the definition or `false` if no definition is updated,
45
+ * for instance, if the `changeNumber` is old, or if the definition is not found (e.g., `/splitchanges` hasn't been fetched yet), or if the storage fails to apply the update.
46
+ * The promise will never be rejected.
47
+ */
48
+ killLocally(name: string, defaultTreatment: string, changeNumber: number): Promise<boolean> {
49
+ return this.get(name).then(definition => {
50
+
51
+ if (definition && (!definition.changeNumber || definition.changeNumber < changeNumber)) {
52
+ const newDefinition = objectAssign({}, definition);
53
+ newDefinition.killed = true;
54
+ newDefinition.defaultTreatment = defaultTreatment;
55
+ newDefinition.changeNumber = changeNumber;
56
+
57
+ return this.add(newDefinition);
58
+ }
59
+ return false;
60
+ }).catch(() => false);
61
+ }
62
+
63
+ }
@@ -0,0 +1,95 @@
1
+ import { IDefinitionsCacheSync, IStorageSync } from './types';
2
+ import { IRBSegment, IDefinition } from '../dtos/types';
3
+ import { objectAssign } from '../utils/lang/objectAssign';
4
+ import { IN_SEGMENT, IN_LARGE_SEGMENT } from '../utils/constants';
5
+
6
+ /**
7
+ * This class provides a skeletal implementation of the IDefinitionsCacheSync interface
8
+ * to minimize the effort required to implement this interface.
9
+ */
10
+ export abstract class AbstractDefinitionsCacheSync implements IDefinitionsCacheSync {
11
+
12
+ protected abstract add(definition: IDefinition): boolean
13
+ protected abstract remove(name: string): boolean
14
+ protected abstract setChangeNumber(changeNumber: number): boolean | void
15
+
16
+ update(toAdd: IDefinition[], toRemove: string[], changeNumber: number): boolean {
17
+ let updated = toAdd.map(addedFF => this.add(addedFF)).some(result => result);
18
+ updated = toRemove.map(removedFF => this.remove(removedFF)).some(result => result) || updated;
19
+ this.setChangeNumber(changeNumber);
20
+ return updated;
21
+ }
22
+
23
+ abstract get(name: string): IDefinition | null
24
+
25
+ getMany(names: string[]): Record<string, IDefinition | null> {
26
+ const definitions: Record<string, IDefinition | null> = {};
27
+ names.forEach(name => {
28
+ definitions[name] = this.get(name);
29
+ });
30
+ return definitions;
31
+ }
32
+
33
+ abstract getChangeNumber(): number
34
+
35
+ getAll(): IDefinition[] {
36
+ return this.getNames().map(key => this.get(key) as IDefinition);
37
+ }
38
+
39
+ abstract getNames(): string[]
40
+
41
+ abstract trafficTypeExists(trafficType: string): boolean
42
+
43
+ abstract usesSegments(): boolean
44
+
45
+ abstract clear(): void
46
+
47
+ /**
48
+ * Kill `name` definition and set `defaultTreatment` and `changeNumber`.
49
+ * Used for SPLIT_KILL push notifications.
50
+ *
51
+ * @returns `true` if the operation successed updating the definition, or `false` if no definition is updated,
52
+ * for instance, if the `changeNumber` is old, or if the definition is not found (e.g., `/splitchanges` hasn't been fetched yet), or if the storage fails to apply the update.
53
+ */
54
+ killLocally(name: string, defaultTreatment: string, changeNumber: number): boolean {
55
+ const definition = this.get(name);
56
+
57
+ if (definition && (!definition.changeNumber || definition.changeNumber < changeNumber)) {
58
+ const newDefinition = objectAssign({}, definition);
59
+ newDefinition.killed = true;
60
+ newDefinition.defaultTreatment = defaultTreatment;
61
+ newDefinition.changeNumber = changeNumber;
62
+
63
+ return this.add(newDefinition);
64
+ }
65
+ return false;
66
+ }
67
+
68
+ abstract getNamesBySets(sets: string[]): Set<string>[]
69
+
70
+ }
71
+
72
+ /**
73
+ * Given a parsed definition, it returns a boolean flagging if its conditions use segments matchers (rules & whitelists).
74
+ * This util is intended to simplify the implementation of `definitionsCache::usesSegments` method
75
+ */
76
+ export function usesSegments(ruleEntity: IDefinition | IRBSegment) {
77
+ const conditions = ruleEntity.conditions || [];
78
+ for (let i = 0; i < conditions.length; i++) {
79
+ const matchers = conditions[i].matcherGroup.matchers;
80
+
81
+ for (let j = 0; j < matchers.length; j++) {
82
+ const matcher = matchers[j].matcherType;
83
+ if (matcher === IN_SEGMENT || matcher === IN_LARGE_SEGMENT) return true;
84
+ }
85
+ }
86
+
87
+ const excluded = (ruleEntity as IRBSegment).excluded;
88
+ if (excluded && excluded.segments && excluded.segments.length > 0) return true;
89
+
90
+ return false;
91
+ }
92
+
93
+ export function usesSegmentsSync(storage: Pick<IStorageSync, 'definitions' | 'rbSegments'>) {
94
+ return storage.definitions.usesSegments() || storage.rbSegments.usesSegments();
95
+ }
@@ -21,19 +21,19 @@ export class KeyBuilder {
21
21
  return `${this.prefix}.trafficType.${trafficType}`;
22
22
  }
23
23
 
24
- buildFlagSetKey(flagSet: string) {
25
- return `${this.prefix}.flagSet.${flagSet}`;
24
+ buildSetKey(set: string) {
25
+ return `${this.prefix}.flagSet.${set}`;
26
26
  }
27
27
 
28
- buildSplitKey(splitName: string) {
29
- return `${this.prefix}.split.${splitName}`;
28
+ buildDefinitionKey(definitionName: string) {
29
+ return `${this.prefix}.split.${definitionName}`;
30
30
  }
31
31
 
32
- buildSplitsTillKey() {
32
+ buildDefinitionsTillKey() {
33
33
  return `${this.prefix}.splits.till`;
34
34
  }
35
35
 
36
- buildSplitKeyPrefix() {
36
+ buildDefinitionKeyPrefix() {
37
37
  return `${this.prefix}.split.`;
38
38
  }
39
39
 
@@ -9,13 +9,13 @@ export interface MySegmentsKeyBuilder {
9
9
 
10
10
  export class KeyBuilderCS extends KeyBuilder implements MySegmentsKeyBuilder {
11
11
 
12
- protected readonly regexSplitsCacheKey: RegExp;
12
+ protected readonly regexDefinitionsCacheKey: RegExp;
13
13
  protected readonly matchingKey: string;
14
14
 
15
15
  constructor(prefix: string, matchingKey: string) {
16
16
  super(prefix);
17
17
  this.matchingKey = matchingKey;
18
- this.regexSplitsCacheKey = new RegExp(`^${prefix}\\.(splits?|trafficType|flagSet)\\.`);
18
+ this.regexDefinitionsCacheKey = new RegExp(`^${prefix}\\.(splits?|trafficType|flagSet)\\.`);
19
19
  }
20
20
 
21
21
  /**
@@ -35,15 +35,15 @@ export class KeyBuilderCS extends KeyBuilder implements MySegmentsKeyBuilder {
35
35
  return `${this.prefix}.splits.lastUpdated`;
36
36
  }
37
37
 
38
- isSplitsCacheKey(key: string) {
39
- return this.regexSplitsCacheKey.test(key);
38
+ isDefinitionsCacheKey(key: string) {
39
+ return this.regexDefinitionsCacheKey.test(key);
40
40
  }
41
41
 
42
42
  buildTillKey() {
43
43
  return `${this.prefix}.${this.matchingKey}.segments.till`;
44
44
  }
45
45
 
46
- isSplitKey(key: string) {
46
+ isDefinitionKey(key: string) {
47
47
  return startsWith(key, `${this.prefix}.split.`);
48
48
  }
49
49
 
@@ -51,7 +51,7 @@ export class KeyBuilderCS extends KeyBuilder implements MySegmentsKeyBuilder {
51
51
  return startsWith(key, `${this.prefix}.rbsegment.`);
52
52
  }
53
53
 
54
- buildSplitsWithSegmentCountKey() {
54
+ buildDefinitionsWithSegmentCountKey() {
55
55
  return `${this.prefix}.splits.usingSegments`;
56
56
  }
57
57
 
@@ -49,8 +49,8 @@ export class KeyBuilderSS extends KeyBuilder {
49
49
  return `${this.prefix}.events`;
50
50
  }
51
51
 
52
- searchPatternForSplitKeys() {
53
- return `${this.buildSplitKeyPrefix()}*`;
52
+ searchPatternForDefinitionKeys() {
53
+ return `${this.buildDefinitionKeyPrefix()}*`;
54
54
  }
55
55
 
56
56
  searchPatternForRBSegmentKeys() {
@@ -12,16 +12,16 @@ import { IMembershipsResponse, IMySegmentsResponse } from '../dtos/types';
12
12
  export function getRolloutPlan(log: ILogger, storage: IStorageSync, options: SplitIO.RolloutPlanOptions = {}): RolloutPlan {
13
13
 
14
14
  const { keys, exposeSegments } = options;
15
- const { splits, segments, rbSegments } = storage;
15
+ const { definitions, segments, rbSegments } = storage;
16
16
 
17
17
  log.debug(`storage: get feature flags${keys ? `, and memberships for keys: ${keys}` : ''}${exposeSegments ? ', and segments' : ''}`);
18
18
 
19
19
  return {
20
20
  splitChanges: {
21
21
  ff: {
22
- t: splits.getChangeNumber(),
22
+ t: definitions.getChangeNumber(),
23
23
  s: -1,
24
- d: splits.getAll(),
24
+ d: definitions.getAll(),
25
25
  },
26
26
  rbs: {
27
27
  t: rbSegments.getChangeNumber(),
@@ -0,0 +1,234 @@
1
+ import { IDefinition } from '../../dtos/types';
2
+ import { AbstractDefinitionsCacheSync, usesSegments } from '../AbstractDefinitionsCacheSync';
3
+ import { isFiniteNumber, toNumber, isNaNNumber } from '../../utils/lang';
4
+ import { KeyBuilderCS } from '../KeyBuilderCS';
5
+ import { ILogger } from '../../logger/types';
6
+ import { LOG_PREFIX } from './constants';
7
+ import { ISettings } from '../../types';
8
+ import { setToArray } from '../../utils/lang/sets';
9
+ import { StorageAdapter } from '../types';
10
+
11
+ export class DefinitionsCacheInLocal extends AbstractDefinitionsCacheSync {
12
+
13
+ private readonly keys: KeyBuilderCS;
14
+ private readonly log: ILogger;
15
+ private readonly setsFilter: string[];
16
+ private hasSync?: boolean;
17
+ private readonly storage: StorageAdapter;
18
+
19
+ constructor(settings: ISettings, keys: KeyBuilderCS, storage: StorageAdapter) {
20
+ super();
21
+ this.keys = keys;
22
+ this.log = settings.log;
23
+ this.setsFilter = settings.sync.__splitFiltersValidation.groupedFilters.bySet;
24
+ this.storage = storage;
25
+ }
26
+
27
+ private _decrementCount(key: string) {
28
+ const count = toNumber(this.storage.getItem(key)) - 1;
29
+ if (count > 0) this.storage.setItem(key, count + '');
30
+ else this.storage.removeItem(key);
31
+ }
32
+
33
+ private _decrementCounts(definition: IDefinition) {
34
+ try {
35
+ const ttKey = this.keys.buildTrafficTypeKey(definition.trafficTypeName);
36
+ this._decrementCount(ttKey);
37
+
38
+ if (usesSegments(definition)) {
39
+ const segmentsCountKey = this.keys.buildDefinitionsWithSegmentCountKey();
40
+ this._decrementCount(segmentsCountKey);
41
+ }
42
+ } catch (e) {
43
+ this.log.error(LOG_PREFIX + e);
44
+ }
45
+ }
46
+
47
+ private _incrementCounts(definition: IDefinition) {
48
+ try {
49
+ const ttKey = this.keys.buildTrafficTypeKey(definition.trafficTypeName);
50
+ this.storage.setItem(ttKey, (toNumber(this.storage.getItem(ttKey)) + 1) + '');
51
+
52
+ if (usesSegments(definition)) {
53
+ const segmentsCountKey = this.keys.buildDefinitionsWithSegmentCountKey();
54
+ this.storage.setItem(segmentsCountKey, (toNumber(this.storage.getItem(segmentsCountKey)) + 1) + '');
55
+ }
56
+ } catch (e) {
57
+ this.log.error(LOG_PREFIX + e);
58
+ }
59
+ }
60
+
61
+
62
+ /**
63
+ * Removes all definitions related data from localStorage (splits, counters, changeNumber and lastUpdated).
64
+ * We cannot simply call `localStorage.clear()` since that implies removing user items from the storage.
65
+ */
66
+ clear() {
67
+ // collect item keys
68
+ const len = this.storage.length;
69
+ const accum = [];
70
+ for (let cur = 0; cur < len; cur++) {
71
+ const key = this.storage.key(cur);
72
+ if (key != null && this.keys.isDefinitionsCacheKey(key)) accum.push(key);
73
+ }
74
+ // remove items
75
+ accum.forEach(key => {
76
+ this.storage.removeItem(key);
77
+ });
78
+
79
+ this.hasSync = false;
80
+ }
81
+
82
+ add(definition: IDefinition) {
83
+ const name = definition.name;
84
+ const definitionKey = this.keys.buildDefinitionKey(name);
85
+ const definitionFromStorage = this.storage.getItem(definitionKey);
86
+ const previousDefinition = definitionFromStorage ? JSON.parse(definitionFromStorage) : null;
87
+
88
+ if (previousDefinition) {
89
+ this._decrementCounts(previousDefinition);
90
+ this.removeFromSets(previousDefinition.name, previousDefinition.sets);
91
+ }
92
+
93
+ this.storage.setItem(definitionKey, JSON.stringify(definition));
94
+
95
+ this._incrementCounts(definition);
96
+ this.addToSets(definition);
97
+
98
+ return true;
99
+ }
100
+
101
+ remove(name: string): boolean {
102
+ const definition = this.get(name);
103
+ if (!definition) return false;
104
+
105
+ this.storage.removeItem(this.keys.buildDefinitionKey(name));
106
+
107
+ this._decrementCounts(definition);
108
+ this.removeFromSets(definition.name, definition.sets);
109
+
110
+ return true;
111
+ }
112
+
113
+ get(name: string): IDefinition | null {
114
+ const item = this.storage.getItem(this.keys.buildDefinitionKey(name));
115
+ return item && JSON.parse(item);
116
+ }
117
+
118
+ setChangeNumber(changeNumber: number): boolean {
119
+ try {
120
+ this.storage.setItem(this.keys.buildDefinitionsTillKey(), changeNumber + '');
121
+ // update "last updated" timestamp with current time
122
+ this.storage.setItem(this.keys.buildLastUpdatedKey(), Date.now() + '');
123
+ this.hasSync = true;
124
+ return true;
125
+ } catch (e) {
126
+ this.log.error(LOG_PREFIX + e);
127
+ return false;
128
+ }
129
+ }
130
+
131
+ getChangeNumber(): number {
132
+ const n = -1;
133
+ let value: string | number | null = this.storage.getItem(this.keys.buildDefinitionsTillKey());
134
+
135
+ if (value !== null) {
136
+ value = parseInt(value, 10);
137
+
138
+ return isNaNNumber(value) ? n : value;
139
+ }
140
+
141
+ return n;
142
+ }
143
+
144
+ getNames(): string[] {
145
+ const len = this.storage.length;
146
+ const accum = [];
147
+
148
+ let cur = 0;
149
+
150
+ while (cur < len) {
151
+ const key = this.storage.key(cur);
152
+
153
+ if (key != null && this.keys.isDefinitionKey(key)) accum.push(this.keys.extractKey(key));
154
+
155
+ cur++;
156
+ }
157
+
158
+ return accum;
159
+ }
160
+
161
+ trafficTypeExists(trafficType: string): boolean {
162
+ const ttCount = toNumber(this.storage.getItem(this.keys.buildTrafficTypeKey(trafficType)));
163
+ return isFiniteNumber(ttCount) && ttCount > 0;
164
+ }
165
+
166
+ usesSegments() {
167
+ // If cache hasn't been synchronized with the cloud, assume we need them.
168
+ if (!this.hasSync) return true;
169
+
170
+ const storedCount = this.storage.getItem(this.keys.buildDefinitionsWithSegmentCountKey());
171
+ const definitionsWithSegmentsCount = storedCount === null ? 0 : toNumber(storedCount);
172
+
173
+ return isFiniteNumber(definitionsWithSegmentsCount) ?
174
+ definitionsWithSegmentsCount > 0 :
175
+ true;
176
+ }
177
+
178
+ getNamesBySets(sets: string[]): Set<string>[] {
179
+ return sets.map(set => {
180
+ const setKey = this.keys.buildSetKey(set);
181
+ const setFromStorage = this.storage.getItem(setKey);
182
+
183
+ return new Set(setFromStorage ? JSON.parse(setFromStorage) : []);
184
+ });
185
+ }
186
+
187
+ private addToSets(definition: IDefinition) {
188
+ if (!definition.sets) return;
189
+
190
+ definition.sets.forEach(set => {
191
+
192
+ if (this.setsFilter.length > 0 && !this.setsFilter.some(filterSet => filterSet === set)) return;
193
+
194
+ const setKey = this.keys.buildSetKey(set);
195
+
196
+ const setFromStorage = this.storage.getItem(setKey);
197
+
198
+ const setCache = new Set(setFromStorage ? JSON.parse(setFromStorage) : []);
199
+
200
+ if (setCache.has(definition.name)) return;
201
+
202
+ setCache.add(definition.name);
203
+
204
+ this.storage.setItem(setKey, JSON.stringify(setToArray(setCache)));
205
+ });
206
+ }
207
+
208
+ private removeFromSets(definitionName: string, sets?: string[] | null) {
209
+ if (!sets) return;
210
+
211
+ sets.forEach(set => {
212
+ this.removeNames(set, definitionName);
213
+ });
214
+ }
215
+
216
+ private removeNames(setName: string, definitionName: string) {
217
+ const setKey = this.keys.buildSetKey(setName);
218
+
219
+ const setFromStorage = this.storage.getItem(setKey);
220
+
221
+ if (!setFromStorage) return;
222
+
223
+ const setCache = new Set(JSON.parse(setFromStorage));
224
+ setCache.delete(definitionName);
225
+
226
+ if (setCache.size === 0) {
227
+ this.storage.removeItem(setKey);
228
+ return;
229
+ }
230
+
231
+ this.storage.setItem(setKey, JSON.stringify(setToArray(setCache)));
232
+ }
233
+
234
+ }
@@ -3,7 +3,7 @@ import { ILogger } from '../../logger/types';
3
3
  import { ISettings } from '../../types';
4
4
  import { isFiniteNumber, isNaNNumber, toNumber } from '../../utils/lang';
5
5
  import { setToArray } from '../../utils/lang/sets';
6
- import { usesSegments } from '../AbstractSplitsCacheSync';
6
+ import { usesSegments } from '../AbstractDefinitionsCacheSync';
7
7
  import { KeyBuilderCS } from '../KeyBuilderCS';
8
8
  import { IRBSegmentsCacheSync, StorageAdapter } from '../types';
9
9
  import { LOG_PREFIX } from './constants';
@@ -25,9 +25,9 @@ export class RBSegmentsCacheInLocal implements IRBSegmentsCacheSync {
25
25
  this.storage.removeItem(this.keys.buildRBSegmentsTillKey());
26
26
  }
27
27
 
28
- update(toAdd: IRBSegment[], toRemove: IRBSegment[], changeNumber: number): boolean {
28
+ update(toAdd: IRBSegment[], toRemove: string[], changeNumber: number): boolean {
29
29
  let updated = toAdd.map(toAdd => this.add(toAdd)).some(result => result);
30
- updated = toRemove.map(toRemove => this.remove(toRemove.name)).some(result => result) || updated;
30
+ updated = toRemove.map(toRemove => this.remove(toRemove)).some(result => result) || updated;
31
31
  this.setChangeNumber(changeNumber);
32
32
  return updated;
33
33
  }
@@ -42,7 +42,7 @@ export class RBSegmentsCacheInLocal implements IRBSegmentsCacheSync {
42
42
  }
43
43
 
44
44
  private updateSegmentCount(diff: number) {
45
- const segmentsCountKey = this.keys.buildSplitsWithSegmentCountKey();
45
+ const segmentsCountKey = this.keys.buildDefinitionsWithSegmentCountKey();
46
46
  const count = toNumber(this.storage.getItem(segmentsCountKey)) + diff;
47
47
  if (count > 0) this.storage.setItem(segmentsCountKey, count + '');
48
48
  else this.storage.removeItem(segmentsCountKey);
@@ -121,11 +121,11 @@ export class RBSegmentsCacheInLocal implements IRBSegmentsCacheSync {
121
121
  }
122
122
 
123
123
  usesSegments(): boolean {
124
- const storedCount = this.storage.getItem(this.keys.buildSplitsWithSegmentCountKey());
125
- const splitsWithSegmentsCount = storedCount === null ? 0 : toNumber(storedCount);
124
+ const storedCount = this.storage.getItem(this.keys.buildDefinitionsWithSegmentCountKey());
125
+ const definitionsWithSegmentsCount = storedCount === null ? 0 : toNumber(storedCount);
126
126
 
127
- return isFiniteNumber(splitsWithSegmentsCount) ?
128
- splitsWithSegmentsCount > 0 :
127
+ return isFiniteNumber(definitionsWithSegmentsCount) ?
128
+ definitionsWithSegmentsCount > 0 :
129
129
  true;
130
130
  }
131
131
 
@@ -5,7 +5,7 @@ import { IStorageFactoryParams, IStorageSync, IStorageSyncFactory, StorageAdapte
5
5
  import { validatePrefix } from '../KeyBuilder';
6
6
  import { KeyBuilderCS, myLargeSegmentsKeyBuilder } from '../KeyBuilderCS';
7
7
  import { isLocalStorageAvailable, isValidStorageWrapper, isWebStorage } from '../../utils/env/isLocalStorageAvailable';
8
- import { SplitsCacheInLocal } from './SplitsCacheInLocal';
8
+ import { DefinitionsCacheInLocal } from './DefinitionsCacheInLocal';
9
9
  import { RBSegmentsCacheInLocal } from './RBSegmentsCacheInLocal';
10
10
  import { MySegmentsCacheInLocal } from './MySegmentsCacheInLocal';
11
11
  import { InMemoryStorageCSFactory } from '../inMemory/InMemoryStorageCS';
@@ -50,26 +50,26 @@ export function InLocalStorage(options: SplitIO.InLocalStorageOptions = {}): ISt
50
50
  const matchingKey = getMatching(settings.core.key);
51
51
  const keys = new KeyBuilderCS(prefix, matchingKey);
52
52
 
53
- const splits = new SplitsCacheInLocal(settings, keys, storage);
53
+ const definitions = new DefinitionsCacheInLocal(settings, keys, storage);
54
54
  const rbSegments = new RBSegmentsCacheInLocal(settings, keys, storage);
55
55
  const segments = new MySegmentsCacheInLocal(log, keys, storage);
56
56
  const largeSegments = new MySegmentsCacheInLocal(log, myLargeSegmentsKeyBuilder(prefix, matchingKey), storage);
57
57
  let validateCachePromise: Promise<SplitIO.SdkReadyMetadata> | undefined;
58
58
 
59
59
  return {
60
- splits,
60
+ definitions,
61
61
  rbSegments,
62
62
  segments,
63
63
  largeSegments,
64
64
  impressions: new ImpressionsCacheInMemory(impressionsQueueSize),
65
65
  impressionCounts: new ImpressionCountsCacheInMemory(),
66
66
  events: new EventsCacheInMemory(eventsQueueSize),
67
- telemetry: shouldRecordTelemetry(params) ? new TelemetryCacheInMemory(splits, segments) : undefined,
67
+ telemetry: shouldRecordTelemetry(params) ? new TelemetryCacheInMemory(definitions, segments) : undefined,
68
68
  uniqueKeys: new UniqueKeysCacheInMemoryCS(),
69
69
 
70
70
  validateCache() {
71
71
  if (!validateCachePromise) {
72
- validateCachePromise = validateCache(options, storage, settings, keys, splits, rbSegments, segments, largeSegments);
72
+ validateCachePromise = validateCache(options, storage, settings, keys, definitions, rbSegments, segments, largeSegments);
73
73
  }
74
74
  return validateCachePromise;
75
75
  },
@@ -86,7 +86,7 @@ export function InLocalStorage(options: SplitIO.InLocalStorageOptions = {}): ISt
86
86
  shared(matchingKey: string) {
87
87
 
88
88
  return {
89
- splits: this.splits,
89
+ definitions: this.definitions,
90
90
  rbSegments: this.rbSegments,
91
91
  segments: new MySegmentsCacheInLocal(log, new KeyBuilderCS(prefix, matchingKey), storage),
92
92
  largeSegments: new MySegmentsCacheInLocal(log, myLargeSegmentsKeyBuilder(prefix, matchingKey), storage),
@@ -2,7 +2,7 @@ import { ISettings } from '../../types';
2
2
  import { isFiniteNumber, isNaNNumber } from '../../utils/lang';
3
3
  import { getStorageHash } from '../KeyBuilder';
4
4
  import { LOG_PREFIX } from './constants';
5
- import type { SplitsCacheInLocal } from './SplitsCacheInLocal';
5
+ import type { DefinitionsCacheInLocal } from './DefinitionsCacheInLocal';
6
6
  import type { RBSegmentsCacheInLocal } from './RBSegmentsCacheInLocal';
7
7
  import type { MySegmentsCacheInLocal } from './MySegmentsCacheInLocal';
8
8
  import { KeyBuilderCS } from '../KeyBuilderCS';
@@ -68,11 +68,11 @@ function validateExpiration(options: SplitIO.InLocalStorageOptions, storage: Sto
68
68
  *
69
69
  * @returns Metadata object with `initialCacheLoad` (true if is fresh install, false if is ready from cache) and `lastUpdateTimestamp` (timestamp of last cache update or undefined)
70
70
  */
71
- export function validateCache(options: SplitIO.InLocalStorageOptions, storage: StorageAdapter, settings: ISettings, keys: KeyBuilderCS, splits: SplitsCacheInLocal, rbSegments: RBSegmentsCacheInLocal, segments: MySegmentsCacheInLocal, largeSegments: MySegmentsCacheInLocal): Promise<SplitIO.SdkReadyMetadata> {
71
+ export function validateCache(options: SplitIO.InLocalStorageOptions, storage: StorageAdapter, settings: ISettings, keys: KeyBuilderCS, definitions: DefinitionsCacheInLocal, rbSegments: RBSegmentsCacheInLocal, segments: MySegmentsCacheInLocal, largeSegments: MySegmentsCacheInLocal): Promise<SplitIO.SdkReadyMetadata> {
72
72
 
73
73
  return Promise.resolve(storage.load && storage.load()).then(() => {
74
74
  const currentTimestamp = Date.now();
75
- const isThereCache = splits.getChangeNumber() > -1;
75
+ const isThereCache = definitions.getChangeNumber() > -1;
76
76
 
77
77
  // Get lastUpdateTimestamp from storage
78
78
  const lastUpdatedTimestampStr = storage.getItem(keys.buildLastUpdatedKey());
@@ -80,7 +80,7 @@ export function validateCache(options: SplitIO.InLocalStorageOptions, storage: S
80
80
  const lastUpdateTimestamp = (!isNaNNumber(lastUpdatedTimestamp) && lastUpdatedTimestamp !== undefined) ? lastUpdatedTimestamp : undefined;
81
81
 
82
82
  if (validateExpiration(options, storage, settings, keys, currentTimestamp, isThereCache)) {
83
- splits.clear();
83
+ definitions.clear();
84
84
  rbSegments.clear();
85
85
  segments.clear();
86
86
  largeSegments.clear();