From dbcb39412edf64b824d7e65bbbf76dbdf8c0005e Mon Sep 17 00:00:00 2001 From: cosmos-explorer Date: Sun, 19 May 2024 08:46:56 +0200 Subject: [PATCH] bump version --- examples/web-app/umd/featbit-js-client-sdk-3.0.3.js | 2 ++ examples/web-app/umd/featbit-js-client-sdk-3.0.3.js.map | 1 + examples/web-app/umd/featbit-js-client-sdk.js | 2 +- examples/web-app/umd/featbit-js-client-sdk.js.map | 2 +- package.json | 2 +- src/FbClientBuilder.ts | 2 +- src/version.ts | 2 +- 7 files changed, 8 insertions(+), 5 deletions(-) create mode 100644 examples/web-app/umd/featbit-js-client-sdk-3.0.3.js create mode 100644 examples/web-app/umd/featbit-js-client-sdk-3.0.3.js.map diff --git a/examples/web-app/umd/featbit-js-client-sdk-3.0.3.js b/examples/web-app/umd/featbit-js-client-sdk-3.0.3.js new file mode 100644 index 0000000..12b07d2 --- /dev/null +++ b/examples/web-app/umd/featbit-js-client-sdk-3.0.3.js @@ -0,0 +1,2 @@ +!function(e,t){if("object"==typeof exports&&"object"==typeof module)module.exports=t();else if("function"==typeof define&&define.amd)define([],t);else{var i=t();for(var r in i)("object"==typeof exports?exports:e)[r]=i[r]}}(this,(()=>(()=>{"use strict";var e={1058:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.defaultValues=void 0;const n=i(5862),s=r(i(9176)),o=r(i(7783)),a=i(5562),l=i(1624),u=i(665),c=i(7837),d=i(607),h=i(8317),f={startWaitTime:n.TypeValidators.Number,sdkKey:n.TypeValidators.String,pollingUri:n.TypeValidators.String,streamingUri:n.TypeValidators.String,eventsUri:n.TypeValidators.String,webSocketPingInterval:n.TypeValidators.Number,logger:n.TypeValidators.Object,store:n.TypeValidators.ObjectOrFactory,dataSynchronizer:n.TypeValidators.ObjectOrFactory,flushInterval:n.TypeValidators.Number,maxEventsInQueue:n.TypeValidators.Number,pollingInterval:n.TypeValidators.Number,offline:n.TypeValidators.Boolean,dataSyncMode:n.TypeValidators.String,bootstrap:n.TypeValidators.Bootstrap,user:n.TypeValidators.User};t.defaultValues={startWaitTime:5e3,sdkKey:"",pollingUri:"",streamingUri:"",eventsUri:"",dataSyncMode:d.DataSyncModeEnum.STREAMING,sendEvents:!0,webSocketPingInterval:18e3,flushInterval:2e3,maxEventsInQueue:1e4,pollingInterval:3e4,offline:!1,store:e=>new o.default,bootstrap:void 0,user:void 0},t.default=class{constructor(e={}){var i,r;this.bootstrapProvider=new u.NullBootstrapProvider,e=e||{},this.logger=e.logger;const{errors:o,validatedOptions:v}=function(e){let i=[];const r=Object.assign({},t.defaultValues);return Object.keys(e).forEach((o=>{var a;const l=e[o],u=f[o];if(u)if(u.is(l))r[o]=l;else if("boolean"===u.getType())i.push(s.default.wrongOptionTypeBoolean(o,typeof l)),r[o]=!!l;else if(u instanceof n.NumberWithMinimum&&n.TypeValidators.Number.is(l)){const{min:e}=u;i.push(s.default.optionBelowMinimum(o,l,e)),r[o]=e}else u instanceof n.UserValidator?(i=[...i,...u.messages],r[o]=t.defaultValues[o]):(i.push(s.default.wrongOptionType(o,u.getType(),typeof l)),r[o]=t.defaultValues[o]);else null===(a=e.logger)||void 0===a||a.warn(s.default.unknownOption(o))})),{errors:i,validatedOptions:r}}(e);if(o.forEach((e=>{var t;null===(t=this.logger)||void 0===t||t.warn(e)})),this.user=e.user,function(e,t){var i,r,n;const{streamingUri:o,pollingUri:l,eventsUri:u}=e,h=(0,a.isNullOrUndefined)(o)||o===c.EmptyString,f=(0,a.isNullOrUndefined)(l)||l===c.EmptyString,v=(0,a.isNullOrUndefined)(u)||u===c.EmptyString;!t.offline&&(v||h&&f)&&(v&&(null===(i=t.logger)||void 0===i||i.error(s.default.partialEndpoint("eventsUri"))),t.dataSyncMode===d.DataSyncModeEnum.STREAMING&&h&&(null===(r=t.logger)||void 0===r||r.error(s.default.partialEndpoint("streamingUri"))),t.dataSyncMode===d.DataSyncModeEnum.POLLING&&f&&(null===(n=t.logger)||void 0===n||n.error(s.default.partialEndpoint("pollingUri"))))}(e,v),this.streamingUri=`${(0,l.canonicalizeUri)(v.streamingUri)}/streaming`,this.pollingUri=`${(0,l.canonicalizeUri)(v.pollingUri)}/api/public/sdk/client/latest-all`,this.eventsUri=`${(0,l.canonicalizeUri)(v.eventsUri)}/api/public/insight/track`,this.startWaitTime=v.startWaitTime,this.sdkKey=v.sdkKey,this.webSocketPingInterval=v.webSocketPingInterval,this.flushInterval=v.flushInterval,this.maxEventsInQueue=v.maxEventsInQueue,this.pollingInterval=v.pollingInterval,this.offline=v.offline,v.bootstrap&&v.bootstrap.length>0)try{this.bootstrapProvider=new h.JsonBootstrapProvider(v.bootstrap)}catch(e){null===(i=this.logger)||void 0===i||i.error("Failed to parse bootstrap JSON, use NullBootstrapProvider.")}this.offline&&(null===(r=this.logger)||void 0===r||r.info("Offline mode enabled. No data synchronization with the FeatBit server will occur.")),this.dataSyncMode=v.dataSyncMode,n.TypeValidators.Function.is(v.dataSynchronizer)?this.dataSynchronizerFactory=v.dataSynchronizer:this.dataSynchronizerFactory=()=>v.dataSynchronizer,n.TypeValidators.Function.is(v.store)?this.storeFactory=v.store:this.storeFactory=()=>v.store}}},1731:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0});class i{constructor(e,t){this.valid=e,this.message=t}static fromUser(e){if(!e)return i.contextForError("No user specified");const{keyId:t,name:r}=e;if(null==t||""===t.trim())return i.contextForError("key is mandatory");const n=new i(!0);return n._user=e,n}get user(){return this._user}get keyId(){return this._user.keyId}value(e){var t,i,r,n,s;return"keyId"===e?null===(t=this._user)||void 0===t?void 0:t.keyId:"name"===e?null===(i=this._user)||void 0===i?void 0:i.name:null===(s=null===(n=null===(r=this._user)||void 0===r?void 0:r.customizedProperties)||void 0===n?void 0:n.find((t=>t.name===e)))||void 0===s?void 0:s.value}static contextForError(e){return new i(!1,e)}}t.default=i},70:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.FbClientBuilder=void 0;const n=r(i(8322));t.FbClientBuilder=class{constructor(e){this._options=null!=e?e:{}}build(){return new n.default(this._options)}platform(e){return this._platform=e,this}startWaitTime(e){return this._options.startWaitTime=e,this}sdkKey(e){return this._options.sdkKey=e,this}user(e){return this._options.user=e,this}streamingUri(e){return this._options.streamingUri=e,this}pollingUri(e){return this._options.pollingUri=e,this}eventsUri(e){return this._options.eventsUri=e,this}dataSyncMode(e){return this._options.dataSyncMode=e,this}pollingInterval(e){return this._options.pollingInterval=e,this}flushInterval(e){return this._options.flushInterval=e,this}maxEventsInQueue(e){return this._options.maxEventsInQueue=e,this}logger(e){return this._options.logger=e,this}offline(e){return this._options.offline=e,this}bootstrap(e){return this._options.bootstrap=e,this}dataSynchronizer(e){return this._options.dataSynchronizer=e,this}}},4129:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.FbClientCore=void 0;const s=n(i(1058)),o=n(i(8311)),a=n(i(4659)),l=i(7539),u=n(i(6100)),c=n(i(3148)),d=n(i(4943)),h=n(i(2093)),f=n(i(8874)),v=i(5192),p=i(7449),g=n(i(1731)),y=i(1142),m=i(8722),_=i(407),b=i(2305),O=i(7584),w=i(607),P=i(5862);var S;!function(e){e[e.Initializing=0]="Initializing",e[e.Initialized=1]="Initialized",e[e.Failed=2]="Failed"}(S||(S={})),t.FbClientCore=class{constructor(e,t,i){this.options=e,this.platform=t,this.state=S.Initializing,this.onError=i.onError,this.onFailed=i.onFailed,this.onReady=i.onReady;const{onUpdate:r,hasEventListeners:n}=i,o=new s.default(e);if(!o.sdkKey&&!o.offline)throw new Error("You must configure the client with an SDK key");if(!o.user)throw new Error("You must configure the client with a user");this.config=o,this.logger=o.logger,this.init(t,r,n)}init(e,t,i){var n,s,h;return r(this,void 0,void 0,(function*(){const r=new o.default(this.config.sdkKey,this.config,e);if(this.store=this.config.storeFactory(r),yield this.store.identify(this.config.user),this.dataSourceUpdates=new a.default(this.store,i,t),this.evaluator=new f.default(this.store),yield this.config.bootstrapProvider.populate(this.config.user.keyId,this.dataSourceUpdates),this.config.offline)this.eventProcessor=new _.NullEventProcessor,this.dataSynchronizer=new m.NullDataSynchronizer,this.initSuccess();else{this.eventProcessor=new b.DefaultEventProcessor(r);const t=(0,l.createStreamListeners)(this.dataSourceUpdates,this.logger,{put:()=>this.initSuccess(),patch:()=>this.initSuccess()}),i=this.config.dataSyncMode===w.DataSyncModeEnum.STREAMING?new u.default(this.config.sdkKey,this.config.user,r,e.webSocket,(()=>this.store.version),t,this.config.webSocketPingInterval):new c.default(this.config,new d.default(this.config.sdkKey,this.config,this.platform.info,this.platform.requests),(()=>this.store.version),t,(e=>this.dataSourceErrorHandler(e)));this.dataSynchronizer=null!==(h=null===(s=(n=this.config).dataSynchronizerFactory)||void 0===s?void 0:s.call(n,r,this.store,this.dataSourceUpdates,(()=>this.initSuccess()),(e=>this.dataSourceErrorHandler(e))))&&void 0!==h?h:i}this.start()}))}identify(e){return r(this,void 0,void 0,(function*(){const t=new P.UserValidator;if(!t.is(e))return void t.messages.forEach((e=>{var t;null===(t=this.logger)||void 0===t||t.warn(e)}));this.store.identify(e),this.dataSynchronizer.identify(e);const[i]=this.store.all(h.default.Flags);0===Object.keys(i).length&&(yield this.config.bootstrapProvider.populate(e.keyId,this.dataSourceUpdates))}))}start(){this.config.offline||(this.dataSynchronizer.start(),setTimeout((()=>{var e,t;if(!this.initialized()){const i=`FbClient failed to start successfully within ${this.config.startWaitTime} milliseconds. This error usually indicates a connection issue with FeatBit or an invalid sdkKey.Please double-check your sdkKey and streamingUri/pollingUri configuration. We will continue to initialize the FbClient, it still have a chance to get to work if it's a temporary network issue`,r=new Error(i);return this.state=S.Failed,this.rejectionReason=r,null===(e=this.initReject)||void 0===e||e.call(this,r),null===(t=this.logger)||void 0===t?void 0:t.warn(i)}}),this.config.startWaitTime))}initialized(){return this.state===S.Initialized}waitForInitialization(){return this.initializedPromise?this.initializedPromise:this.state===S.Initialized?(this.initializedPromise=Promise.resolve(this),this.initializedPromise):this.state===S.Failed?(this.initializedPromise=Promise.reject(this.rejectionReason),this.initializedPromise):(this.initializedPromise||(this.initializedPromise=new Promise(((e,t)=>{this.initResolve=e,this.initReject=t}))),this.initializedPromise)}boolVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.bool).value}boolVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.bool)}jsonVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.json).value}jsonVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.json)}numberVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.number).value}numberVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.number)}stringVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.string).value}stringVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.string)}variation(e,t){return this.evaluateCore(e,t,y.ValueConverters.string).value}variationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.string)}getAllVariations(){var e;const t=g.default.fromUser(this.config.user);if(!t.valid){const i=new p.ClientError(`${null!==(e=t.message)&&void 0!==e?e:"User not valid;"} returning default value.`);return this.onError(i),Promise.resolve([])}const[i,r]=this.store.all(h.default.Flags),n=Object.keys(i).map((e=>{var t;const i=this.evaluator.evaluate(e);return{flagKey:e,kind:i.kind,reason:i.reason,value:null===(t=i.value)||void 0===t?void 0:t.variation}}));return Promise.resolve(n)}close(){var e;return r(this,void 0,void 0,(function*(){yield this.eventProcessor.close(),null===(e=this.dataSynchronizer)||void 0===e||e.close(),this.store.close()}))}track(e,t){const i=new O.MetricEvent(this.config.user,e,this.platform.info.appType,null!=t?t:1);this.eventProcessor.record(i)}flush(e){return r(this,void 0,void 0,(function*(){try{return yield this.eventProcessor.flush(),null==e||e(!0),!0}catch(t){return null==e||e(!1),!1}}))}evaluateCore(e,t,i){var r,n,s;const o=g.default.fromUser(this.config.user);if(!o.valid){const i=new p.ClientError(`${null!==(r=o.message)&&void 0!==r?r:"User not valid;"} returning default value.`);return this.onError(i),{flagKey:e,kind:v.ReasonKinds.Error,reason:i.message,value:t}}const a=this.evaluator.evaluate(e);if(a.kind===v.ReasonKinds.FlagNotFound){const i=new p.ClientError(a.reason);return this.onError(i),{flagKey:e,kind:a.kind,reason:a.reason,value:t}}this.initialized()?this.eventProcessor.record(a.toEvalEvent(this.config.user)):null===(n=this.logger)||void 0===n||n.warn("Variation called before FeatBit client initialization completed (did you wait for the'ready' event?)");const{isSucceeded:l,value:u}=i(null===(s=a.value)||void 0===s?void 0:s.variation);return l?{flagKey:e,kind:a.kind,reason:a.reason,value:u}:{flagKey:e,kind:v.ReasonKinds.WrongType,reason:"type mismatch",value:t}}dataSourceErrorHandler(e){var t;const i=401===e.code?new Error("Authentication failed. Double check your SDK key."):e;this.onError(i),this.onFailed(i),this.initialized()||(this.state=S.Failed,this.rejectionReason=i,null===(t=this.initReject)||void 0===t||t.call(this,i))}initSuccess(){var e,t;this.initialized()||(this.state=S.Initialized,null===(e=this.logger)||void 0===e||e.info("FbClient started successfully."),null===(t=this.initResolve)||void 0===t||t.call(this,this),this.onReady())}}},5717:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},4881:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},292:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},226:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6399:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},700:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.JsonBootstrapProvider=void 0;const r=i(4426),n=i(5562);t.JsonBootstrapProvider=class{constructor(e){const t=(e||[]).map((e=>Object.assign(Object.assign({},e),{variationOptions:e.variationOptions||[{id:null,variation:e.variation}]}))),i=(0,r.deserializeAll)(t);this.dataSet={flags:i.flags,version:0}}populate(e,t,i){return new Promise(((r,s)=>{if((0,n.isNullOrUndefined)(this.dataSet))return r();t.init(e,this.dataSet,(()=>{r(),null==i||i()}))}))}}},665:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullBootstrapProvider=void 0,t.NullBootstrapProvider=class{constructor(){this.dataSet={flags:{},version:0}}populate(e,t,i){return new Promise(((e,t)=>{e(),null==i||i()}))}}},8317:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(6399),t),n(i(700),t),n(i(665),t)},7837:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.MinInt=t.EmptyString=void 0,t.EmptyString="",t.MinInt=2147483648},4659:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const s=n(i(2093));t.default=class{constructor(e,t,i){this.store=e,this.hasEventListeners=t,this.onChange=i}init(e,t,i){if(e!==this.store.user.keyId)return void(null==i||i());const n=this.hasEventListeners(),o=e=>r(this,void 0,void 0,(function*(){yield this.store.init(t),Promise.resolve().then((()=>{if(n){const i=Object.keys(t).flatMap((i=>{const r=(null==e?void 0:e[i])||{},n=t[i],s=Object.assign(Object.assign({},r),n);return Object.keys(s).filter((e=>this.isUpdated(r&&r[e],n&&n[e])))}));i.length>0&&this.onChange(i)}})),null==i||i()}));if(n){const[e,t]=this.store.all(s.default.Flags);o({flags:e,version:t})}else o()}upsert(e,t,i,n){if(e!==this.store.user.keyId)return void(null==n||n());const{key:s}=i,o=this.hasEventListeners(),a=e=>r(this,void 0,void 0,(function*(){yield this.store.upsert(t,i),Promise.resolve().then((()=>{o&&this.isUpdated(e,i[s])&&this.onChange([s])})),null==n||n()}));o?a(this.store.get(t,s)||void 0):a()}isUpdated(e,t){return!e||!t||t.version>e.version}}},7539:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.createStreamListeners=t.createPatchListener=t.createPutListener=void 0;const n=i(4426);t.createPutListener=(e,t,i=(()=>{}))=>({deserializeData:n.deserializeAll,processJson:(n,{flags:s})=>r(void 0,void 0,void 0,(function*(){const r={flags:s,version:0};null==t||t.debug("Initializing all data"),e.init(n,r,i)}))}),t.createPatchListener=(e,t,i=(()=>{}))=>({deserializeData:n.deserializePatch,processJson:(n,s)=>r(void 0,void 0,void 0,(function*(){0!==(null==s?void 0:s.length)?null==s||s.forEach((r=>{null==t||t.debug(`Updating ${r.data.key} in ${r.kind.namespace}`),e.upsert(n,r.kind,r.data,i)})):null==i||i()}))}),t.createStreamListeners=(e,i,r)=>{const n=new Map;return n.set("put",(0,t.createPutListener)(e,i,null==r?void 0:r.put)),n.set("patch",(0,t.createPatchListener)(e,i,null==r?void 0:r.patch)),n}},3758:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(7539),t),n(i(4659),t)},607:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.DataSyncModeEnum=void 0,function(e){e.POLLING="polling",e.STREAMING="streaming"}(i||(t.DataSyncModeEnum=i={}))},304:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},450:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8722:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullDataSynchronizer=void 0,t.NullDataSynchronizer=class{close(){}start(){}stop(){}identify(){}}},3148:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(7449),n=i(1962),s=i(8688);t.default=class{constructor(e,t,i,r,n){this.requestor=t,this.getStoreTimestamp=i,this.listeners=r,this.errorHandler=n,this.stopped=!1,this.logger=e.logger,this.pollingInterval=e.pollingInterval,this.user=e.user}poll(){var e;if(this.stopped)return;const t=Date.now();null===(e=this.logger)||void 0===e||e.debug("Polling for feature flag and segments updates"),this.requestor.requestData(this.getStoreTimestamp(),this.user,((e,i)=>{var o,a,l,u,c,d,h;const f=Date.now()-t,v=Math.max(this.pollingInterval-f,0);if(null===(o=this.logger)||void 0===o||o.debug("Elapsed: %d ms, sleeping for %d ms",f,v),e){const{status:t}=e;if(t&&!(0,r.isHttpRecoverable)(t)){const i=(0,s.httpErrorMessage)(e,"polling request");return null===(a=this.logger)||void 0===a||a.error(i),void(null===(l=this.errorHandler)||void 0===l||l.call(this,new r.PollingError(i,t)))}null===(u=this.logger)||void 0===u||u.warn((0,s.httpErrorMessage)(e,"polling request","will retry"))}else{let e=[],t=null===(c=this.user)||void 0===c?void 0:c.keyId,r=this.listeners.get("patch");if(i){const s=JSON.parse(i);if("data-sync"===s.messageType){switch(s.data.eventType){case n.StreamResponseEventType.patch:r=this.listeners.get("patch");break;case n.StreamResponseEventType.full:r=this.listeners.get("put")}({featureFlags:e,userKeyId:t}=s.data)}}const s=null===(d=null==r?void 0:r.deserializeData)||void 0===d?void 0:d.call(r,e);null===(h=null==r?void 0:r.processJson)||void 0===h||h.call(r,t,s)}this.timeoutHandle=setTimeout((()=>{this.poll()}),v)}))}identify(e){this.user=Object.assign({},e)}close(){this.stop()}start(){this.poll()}stop(){this.timeoutHandle&&(clearTimeout(this.timeoutHandle),this.timeoutHandle=void 0),this.stopped=!0}}},4943:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(7449),s=i(8688);t.default=class{constructor(e,t,i,r){this.requests=r,this.headers=(0,s.defaultHeaders)(e,i),this.uri=t.pollingUri}request(e,t){return r(this,void 0,void 0,(function*(){const i=yield this.requests.fetch(e,t),r=yield i.text();return{res:i,body:r}}))}requestData(e,t,i){return r(this,void 0,void 0,(function*(){const r={method:"POST",headers:this.headers,body:JSON.stringify(t)};try{const{res:t,body:s}=yield this.request(`${this.uri}?timestamp=${null!=e?e:0}`,r);if(200!==t.status&&304!==t.status){const e=new n.StreamingError(`Unexpected status code: ${t.status}`,t.status);return i(e,void 0)}return i(void 0,304===t.status?null:s)}catch(e){return i(e,void 0)}}))}}},6100:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{constructor(e,t,i,r,n,s,o){this.getStoreTimestamp=n,this.listeners=s;const{logger:a,streamingUri:l}=i;this.logger=a,this.socket=r,this.socket.config({sdkKey:e,streamingUri:l,pingInterval:o,user:t,logger:a,getStoreTimestamp:n}),this.listeners.forEach((({deserializeData:e,processJson:t},i)=>{var r;null===(r=this.socket)||void 0===r||r.addListener(i,(r=>{var n;if(null===(n=this.logger)||void 0===n||n.debug(`Received ${i} event`),null==r?void 0:r.data){const{featureFlags:i,userKeyId:n}=r.data,s=e(i);t(n,s)}}))}))}identify(e){var t;null===(t=this.socket)||void 0===t||t.identify(e)}start(){var e;this.logConnectionStarted(),null===(e=this.socket)||void 0===e||e.connect()}logConnectionStarted(){var e;this.connectionAttemptStartTime=Date.now(),null===(e=this.logger)||void 0===e||e.info(`Stream connection attempt StartTime ${this.connectionAttemptStartTime}`)}close(){this.stop()}stop(){var e;null===(e=this.socket)||void 0===e||e.close(),this.socket=void 0}}},9999:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(607),t),n(i(304),t),n(i(450),t),n(i(8722),t),n(i(3148),t),n(i(4943),t),n(i(1962),t),n(i(6870),t),n(i(6100),t)},1962:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.StreamResponseEventType=void 0,function(e){e.full="full",e.patch="patch"}(i||(t.StreamResponseEventType=i={}))},6870:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.generateConnectionToken=void 0;const i={0:"Q",1:"B",2:"W",3:"S",4:"P",5:"H",6:"D",7:"X",8:"Z",9:"U"};function r(e,t){var r="000000000000"+e;return r.slice(r.length-t).split("").map((e=>i[e])).join("")}t.generateConnectionToken=function(e){e=e.replace(/=*$/,"");const t=Date.now(),i=r(t,t.toString().length),n=Math.max(Math.floor(Math.random()*e.length),2);return`${r(n,3)}${r(i.length,2)}${e.slice(0,n)}${i}${e.slice(n)}`}},7449:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.isHttpRecoverable=t.ClientError=t.UnexpectedResponseError=t.StreamingError=t.PollingError=void 0;class i extends Error{constructor(e,t){super(e),this.status=t,this.name="FbPollingError"}}t.PollingError=i;class r extends Error{constructor(e,t){super(e),this.code=t,this.name="FbStreamingError"}}t.StreamingError=r;class n extends Error{constructor(e){super(e),this.name="FbUnexpectedResponseError"}}t.UnexpectedResponseError=n;class s extends Error{constructor(e){super(e),this.name="FbClientError"}}t.ClientError=s,t.isHttpRecoverable=function(e){return!(e>=400&&e<500)||400===e||408===e||429===e}},3100:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5192),n=i(7584);class s{constructor(e,t,i){this.kind=e,this.value=t,this.reason=i}static flagNotFound(e){return new s(r.ReasonKinds.FlagNotFound,null,`flag not found: ${e}`)}static matched(e){return new s(r.ReasonKinds.Match,e,"target match")}toEvalEvent(e){var t,i,s;if(this.kind!==r.ReasonKinds.Match)return null;const o=null===(t=this.value)||void 0===t?void 0:t.variations.find((e=>{var t;return e.value===(null===(t=this.value)||void 0===t?void 0:t.variation)}));return new n.EvalEvent(e,null===(i=this.value)||void 0===i?void 0:i.id,o,null===(s=this.value)||void 0===s?void 0:s.sendToExperiment)}}t.default=s},8874:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=r(i(3100)),s=r(i(2093));t.default=class{constructor(e){this.store=e}evaluate(e){const t=this.store.get(s.default.Flags,e);return t?n.default.matched(t):n.default.flagNotFound(e)}}},3675:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5192:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.ReasonKinds=void 0,function(e){e.ClientNotReady="ClientNotReady",e.Match="Match",e.WrongType="WrongType",e.FlagNotFound="FlagNotFound",e.Error="Error"}(i||(t.ReasonKinds=i={}))},9653:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.VariationDataType=void 0,function(e){e.string="string",e.boolean="boolean",e.number="number",e.json="json",e.empty=""}(i||(t.VariationDataType=i={}))},4228:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(9653),t)},9823:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(4228),t),n(i(3100),t),n(i(8874),t),n(i(3675),t),n(i(5192),t)},2305:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventProcessor=void 0;const n=i(5381),s=i(7584),o=i(5562),a=i(1218);t.DefaultEventProcessor=class{constructor(e){this.closed=!1;const{logger:t,flushInterval:i,maxEventsInQueue:r}=e;this.logger=t,this.flushInterval=i,this.eventQueue=new a.DefaultEventQueue(r,this.logger),this.eventDispatcher=new n.EventDispatcher(e,this.eventQueue),this.flushLoop()}flushLoop(){this.closed||setTimeout((()=>r(this,void 0,void 0,(function*(){try{yield this.flush()}catch(e){this.logger.error("Unexpected error while flushing events in event processor.",e)}this.flushLoop()}))),this.flushInterval)}flush(){const e=new s.FlushEvent;return this.record(e),e.waitForCompletion()}close(){return r(this,void 0,void 0,(function*(){if(this.closed)return;const e=new s.ShutdownEvent;this.record(e);try{yield e.waitForCompletion()}catch(e){this.logger.error("Event processor shutdown but not complete.")}this.eventQueue.close(),this.closed=!0}))}record(e){return!((0,o.isNullOrUndefined)(e)||!this.eventQueue.addEvent(e)&&(e instanceof s.FlushEvent&&e.complete(),1))}}},1218:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventQueue=void 0,t.DefaultEventQueue=class{constructor(e,t){this.capacity=e,this.logger=t,this.closed=!1,this.events=[]}addEvent(e){return!this.closed&&(this.events.length>=this.capacity?(this.logger.warn("Events are being produced faster than they can be processed. We shouldn't see this."),!1):(this.events.push(e),!0))}clear(){this.events=[]}shift(){return this.events.shift()}close(){this.closed=!0}get eventsSnapshot(){return[...this.events]}get length(){return this.events.length}get isEmpty(){return 0===this.length}}},2580:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventSender=void 0;const s=i(8174),o=i(8688),a=i(7449),l=n(i(1773));t.DefaultEventSender=class{constructor(e){const{sdkKey:t,eventsUri:i,platform:r}=e,{info:n,requests:s}=r;this.defaultHeaders=(0,o.defaultHeaders)(t,n),this.eventsUri=i,this.requests=s}send(e,t){return r(this,void 0,void 0,(function*(){const i={status:s.DeliveryStatus.Succeeded},r=Object.assign(Object.assign({},this.defaultHeaders),{"content-type":"application/json"});let n;try{const{status:t}=yield this.requests.fetch(this.eventsUri,{headers:r,body:e,method:"POST"});if(t>=200&&t<=299)return i;if(n=new a.UnexpectedResponseError((0,o.httpErrorMessage)({status:t,message:"some events were dropped"},"event posting")),!(0,a.isHttpRecoverable)(t))return i.status=s.DeliveryStatus.FailedAndMustShutDown,i.error=n,i}catch(e){n=e}return n&&!t?(i.status=s.DeliveryStatus.Failed,i.error=n,i):(yield(0,l.default)(),this.send(e,!1))}))}}},9657:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventSerializer=void 0;const r=i(7584);t.DefaultEventSerializer=class{serialize(e){const t=e.map((e=>e instanceof r.EvalEvent||e instanceof r.MetricEvent?e.toPayload():null)).filter((e=>null!==e));return JSON.stringify(t)}}},5381:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.EventDispatcher=void 0;const s=i(8174),o=i(1218),a=i(2580),l=i(7584),u=i(9657),c=n(i(1773));t.EventDispatcher=class{constructor(e,t){this.maxEventPerRequest=50,this.stopped=!1;const{logger:i,maxEventsInQueue:r}=e;this.logger=i,this.buffer=new o.DefaultEventQueue(r,this.logger),this.sender=new a.DefaultEventSender(e),this.serializer=new u.DefaultEventSerializer,this.dispatchLoop(t).then()}dispatchLoop(e){return r(this,void 0,void 0,(function*(){this.logger.debug("Start dispatch loop.");let t=!0;for(;t;)try{const i=e.shift();if(void 0===i){yield(0,c.default)(1e3);continue}i instanceof l.PayloadEvent?this.addEventToBuffer(i):i instanceof l.FlushEvent?yield this.triggerFlush(i):i instanceof l.ShutdownEvent&&(yield this.triggerFlush(i),this.stopped=!0,t=!1)}catch(e){this.logger.error("Unexpected error in event dispatcher.",e)}this.logger.debug("Finish dispatch loop.")}))}addEventToBuffer(e){this.stopped||(this.buffer.addEvent(e)?this.logger.debug("Added event to buffer."):this.logger.warn("Exceeded event queue capacity, event will be dropped. Increase capacity to avoid dropping events."))}triggerFlush(e){return r(this,void 0,void 0,(function*(){if(this.stopped)return void e.complete();if(this.buffer.isEmpty)return e.complete(),void this.logger.debug("Flush empty buffer.");const t=this.buffer.eventsSnapshot;this.buffer.clear();try{yield this.flushEvents(t),this.logger.debug(`${t.length} events has been flushed.`)}catch(e){this.logger.warn("Exception happened when flushing events",e)}e.complete()}))}flushEvents(e){return r(this,void 0,void 0,(function*(){const t=(e=this.getUniqueEvents(e)).length;for(let i=0;i{Object.defineProperty(t,"__esModule",{value:!0})},6735:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},1564:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8174:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.DeliveryStatus=void 0,function(e){e[e.Succeeded=0]="Succeeded",e[e.Failed=1]="Failed",e[e.FailedAndMustShutDown=2]="FailedAndMustShutDown"}(i||(t.DeliveryStatus=i={}))},407:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullEventProcessor=void 0,t.NullEventProcessor=class{flush(){return Promise.resolve()}close(){return Promise.resolve()}record(e){return!1}}},7584:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.EvalEvent=t.MetricEvent=t.PayloadEvent=t.ShutdownEvent=t.FlushEvent=t.AsyncEvent=void 0;class i{get hash(){return this.timestamp.toString()}constructor(){this.timestamp=(new Date).getTime(),this.isCompletedPromise=new Promise((e=>{this.resolveFn=e}))}waitForCompletion(){return this.isCompletedPromise}complete(){var e;null===(e=this.resolveFn)||void 0===e||e.call(this,this)}}t.AsyncEvent=i,t.FlushEvent=class extends i{},t.ShutdownEvent=class extends i{};class r{constructor(){this.timestamp=(new Date).getTime()}get hash(){return this.timestamp.toString()}toPayload(){}}t.PayloadEvent=r,t.MetricEvent=class extends r{constructor(e,t,i,r){super(),this.user=e,this.eventName=t,this.appType=i,this.metricValue=r}userPayload(){return{keyId:this.user.keyId,name:this.user.name,customizedProperties:this.user.customizedProperties}}toPayload(){return{user:this.userPayload(),metrics:[{route:"index/metric",timestamp:this.timestamp,numericValue:this.metricValue,appType:this.appType,eventName:this.eventName,type:"CustomEvent"}]}}get hash(){const e=this.toPayload(),t={user:e.user,metrics:e.metrics.map((e=>Object.assign(Object.assign({},e),{timestamp:void 0})))};return JSON.stringify(t)}},t.EvalEvent=class extends r{constructor(e,t,i,r){super(),this.user=e,this.flagKey=t,this.variation=i,this.sendToExperiment=r}userPayload(){return{keyId:this.user.keyId,name:this.user.name,customizedProperties:this.user.customizedProperties}}toPayload(){return{user:this.userPayload(),variations:[{featureFlagKey:this.flagKey,sendToExperiment:this.sendToExperiment,timestamp:this.timestamp,variation:this.variation}]}}get hash(){const e=this.toPayload(),t={user:e.user,variations:e.variations.map((e=>Object.assign(Object.assign({},e),{timestamp:void 0})))};return JSON.stringify(t)}}},4008:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(2305),t),n(i(1218),t),n(i(2580),t),n(i(9657),t),n(i(7584),t),n(i(5381),t),n(i(8284),t),n(i(6735),t),n(i(1564),t),n(i(8174),t),n(i(407),t)},9872:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(8317),t),n(i(3758),t),n(i(9823),t),n(i(4008),t),n(i(7302),t),n(i(1045),t),n(i(9718),t),n(i(8598),t),n(i(9999),t),n(i(2710),t),n(i(1058),t),n(i(7837),t),n(i(1731),t),n(i(7449),t),n(i(70),t),n(i(5717),t),n(i(4881),t),n(i(292),t),n(i(226),t),n(i(4129),t)},5768:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.BasicLogger=void 0;const n=r(i(3919)),s={debug:0,info:1,warn:2,error:3,none:4},o=["debug","info","warn","error","none"];class a{static get(){return new a({})}constructor(e){var t,i,r;this.logLevel=null!==(i=s[null!==(t=e.level)&&void 0!==t?t:"info"])&&void 0!==i?i:s.info,this.name=null!==(r=e.name)&&void 0!==r?r:"FeatBit",this.destination=e.destination,this.formatter=e.formatter}tryFormat(...e){var t;try{return this.formatter?null===(t=this.formatter)||void 0===t?void 0:t.call(this,...e):(0,n.default)(...e)}catch(t){return(0,n.default)(...e)}}tryWrite(e){try{this.destination(e)}catch(t){console.error(e)}}log(e,t){if(e>=this.logLevel){const i=`${o[e]}: [${this.name}]`;try{this.destination?this.tryWrite(`${i} ${this.tryFormat(...t)}`):console.error(...t)}catch(e){console.error(...t)}}}error(...e){this.log(s.error,e)}warn(...e){this.log(s.warn,e)}info(...e){this.log(s.info,e)}debug(...e){this.log(s.debug,e)}}t.BasicLogger=a},7973:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5781:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7076:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7689:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.SafeLogger=void 0;const r=i(5862),n={error:r.TypeValidators.Function,warn:r.TypeValidators.Function,info:r.TypeValidators.Function,debug:r.TypeValidators.Function};t.SafeLogger=class{constructor(e,t){Object.entries(n).forEach((([t,i])=>{if(!i.is(e[t]))throw new Error(`Provided logger instance must support logger.${t}(...) method`)})),this.logger=e,this.fallback=t}log(e,t){try{this.logger[e](...t)}catch(i){this.fallback[e](...t)}}error(...e){this.log("error",e)}warn(...e){this.log("warn",e)}info(...e){this.log("info",e)}debug(...e){this.log("debug",e)}}},3919:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5862);function n(e){if("string"==typeof e)return e;if(void 0===e)return"undefined";if(null===e)return"null";if(Object.prototype.hasOwnProperty.call(e,"toString"))try{return e.toString()}catch(e){}if("bigint"==typeof e)return`${e}n`;try{return JSON.stringify(e)}catch(e){return e instanceof TypeError&&e.message.indexOf("circular")>=0?"[Circular]":"[Not Stringifiable]"}}const s={s:e=>n(e),d:e=>function(e){return"symbol"==typeof e?"NaN":"bigint"==typeof e?`${e}n`:String(Number(e))}(e),i:e=>function(e){return"symbol"==typeof e?"NaN":"bigint"==typeof e?`${e}n`:String(parseInt(e,10))}(e),f:e=>function(e){return"symbol"==typeof e?"NaN":String(parseFloat(e))}(e),j:e=>n(e),o:e=>n(e),O:e=>n(e),c:()=>""};t.default=function(...e){var t;const i=e.shift();if(r.TypeValidators.String.is(i)){let r="",o=0;for(;o{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{constructor(e,t,i){this.sdkKey=e,this.platform=i,this.logger=t.logger,this.offline=t.offline,this.flushInterval=t.flushInterval,this.maxEventsInQueue=t.maxEventsInQueue,this.streamingUri=t.streamingUri,this.pollingUri=t.pollingUri,this.eventsUri=t.eventsUri}}},8222:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},4670:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6273:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8758:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},9176:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{static optionBelowMinimum(e,t,i){return`Config option "${e}" had invalid value of ${t}, using minimum of ${i} instead`}static unknownOption(e){return`Ignoring unknown config option "${e}"`}static wrongOptionType(e,t,i){return`Config option "${e}" should be of type ${t}, got ${i}, using default value`}static wrongOptionTypeBoolean(e,t){return`Config option "${e}" should be a boolean, got ${t}, converting to boolean`}static partialEndpoint(e){return`You have set custom uris without specifying the ${e} URI; connections may not work properly`}static mandatory(e){return`${e} is mandatory`}static invalidOptionValue(e){return`Invalid option value: ${e}`}static missingKeyInBootstrapValue(e){return`Missing key "${e}" in bootstrap value`}}},595:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.UserBuilder=void 0,t.UserBuilder=class{constructor(e){this._keyId="",this._name="",this._custom=[],this._keyId=e}name(e){return this._name=e,this}custom(e,t){var i;return null===(i=this._custom)||void 0===i||i.push({name:e,value:t}),this}build(){return{name:this._name,keyId:this._keyId,customizedProperties:this._custom}}}},5862:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.TypeValidators=t.KindValidator=t.DateValidator=t.UserValidator=t.BootstrapValidator=t.NullableBoolean=t.Function=t.StringMatchingRegex=t.NumberWithMinimum=t.TypeArray=t.Type=t.FactoryOrInstance=void 0;const n=r(i(9176));class s{is(e){if(Array.isArray(e))return!1;const t=typeof e;return"function"===t||"object"===t}getType(){return"factory method or object"}}t.FactoryOrInstance=s;class o{constructor(e,t){this.typeName=e,this.typeOf=typeof t}is(e){return!Array.isArray(e)&&typeof e===this.typeOf}getType(){return this.typeName}}t.Type=o;class a{constructor(e,t){this.typeName=e,this.typeOf=typeof t}is(e){return!!Array.isArray(e)&&(!(e.length>0)||e.every((e=>typeof e===this.typeOf)))}getType(){return this.typeName}}t.TypeArray=a;class l extends o{constructor(e){super(`number with minimum value of ${e}`,0),this.min=e}is(e){return typeof e===this.typeOf&&e>=this.min}}t.NumberWithMinimum=l;class u extends o{constructor(e){super(`string matching ${e}`,""),this.expression=e}is(e){return!!e.match(this.expression)}}t.StringMatchingRegex=u;class c{is(e){return"function"==typeof e}getType(){return"function"}}t.Function=c;class d{is(e){return"boolean"==typeof e||null==e}getType(){return"boolean | undefined | null"}}t.NullableBoolean=d,t.BootstrapValidator=class{constructor(){this.messages=[]}is(e){if("object"!=typeof e||null===e)return this.messages.push(n.default.invalidOptionValue("bootstrap")),!1;try{const t=e;for(let e of t){["id","variation"].every((t=>Object.keys(e).includes(t)));const t=Object.keys(e);if(t.includes("id")&&this.messages.push(n.default.missingKeyInBootstrapValue("id")),t.includes("variation")&&this.messages.push(n.default.missingKeyInBootstrapValue("variation")),this.messages.length>0)return!1}}catch(t){return this.messages.push(n.default.wrongOptionType("bootstrap",this.getType(),typeof e)),!1}return!0}getType(){return"IFlagBase[]"}},t.UserValidator=class{constructor(){this.messages=[]}is(e){if("object"!=typeof e||null===e)return this.messages.push(n.default.mandatory("user")),!1;const t=e;return"string"!=typeof t.keyId||""===t.keyId.trim()?(this.messages.push(n.default.mandatory("user.keyId")),!1):"string"==typeof t.name&&""!==t.name.trim()||(this.messages.push(n.default.mandatory("user.name")),!1)}getType(){return"user"}};const h=/^\d\d\d\d-\d\d-\d\dT\d\d:\d\d:\d\d(\.\d\d*)?(Z|[-+]\d\d(:\d\d)?)/;class f{is(e){return"number"==typeof e||"string"==typeof e&&h.test(e)}getType(){return"date"}}t.DateValidator=f;class v extends u{constructor(){super(/^(\w|\.|-)+$/)}is(e){return super.is(e)&&"kind"!==e}}t.KindValidator=v;class p{static createTypeArray(e,t){return new a(e,t)}static numberWithMin(e){return new l(e)}static stringMatchingRegex(e){return new u(e)}}t.TypeValidators=p,p.String=new o("string",""),p.Number=new o("number",0),p.ObjectOrFactory=new s,p.Object=new o("object",{}),p.StringArray=new a("string[]",""),p.Boolean=new o("boolean",!0),p.User=new o("object",{}),p.Bootstrap=new o("object",{}),p.Function=new c,p.Date=new f,p.Kind=new v,p.NullableBoolean=new d},1045:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(8311),t),n(i(8222),t),n(i(4670),t),n(i(6273),t),n(i(8758),t),n(i(9176),t),n(i(595),t),n(i(5862),t)},5309:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},9938:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5800:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6510:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},2833:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5972);t.default=class{get appType(){return"Browser-Client-SDK"}platformData(){return{os:{},name:"Browser",additional:{}}}sdkData(){return{name:r.name,version:r.version,userAgentBase:this.appType}}}},9174:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=r(i(2833)),s=i(891),o=r(i(9018));t.default=class{constructor(e){this.info=new n.default,this.requests=new s.BrowserRequests,this.webSocket=new o.default}}},891:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.BrowserRequests=void 0,t.BrowserRequests=class{fetch(e,t={}){return fetch(e,t)}}},9018:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(3046),n=i(6842),s=i(6870),o=i(1962),a=[1e3,3e3,5e3,7e3,11e3,13e3,3e4,6e4];t.default=(0,r.Emits)(class{constructor(){this.retryCounter=0,this.closed=!1,this._config={},this.emitter=new n.EventEmitter}identify(e){this._config.user=e,this.doDataSync()}connect(){var e,t,i,r;let n=this;const a=Date.now(),l=this._config.streamingUri.replace(/^http/,"ws")+`?type=client&token=${(0,s.generateConnectionToken)(this._config.sdkKey)}`;this.ws=new WebSocket(l),null===(e=n.ws)||void 0===e||e.addEventListener("open",(function(e){n._config.logger.info(`WebSocket connection succeeded, connection time: ${Date.now()-a} ms`),n.doDataSync(),n.sendPingMessage()})),null===(t=n.ws)||void 0===t||t.addEventListener("close",(function(e){n._config.logger.warn("WebSocket closed"),4003!==e.code&&n.reconnect()})),null===(i=n.ws)||void 0===i||i.addEventListener("error",(function(e){n._config.logger.debug("error")})),null===(r=n.ws)||void 0===r||r.addEventListener("message",(function(e){const t=JSON.parse(e.data);if("data-sync"===t.messageType)switch(t.data.eventType){case o.StreamResponseEventType.patch:n.emitter.emit("patch",t);break;case o.StreamResponseEventType.full:n.emitter.emit("put",t)}}))}close(){var e;this.closed=!0,null===(e=this.ws)||void 0===e||e.close(4003,"The client is closed by user"),this.ws=void 0}config(e){e.emitter&&(this.emitter=e.emitter),this._config=Object.assign({},e)}sendPingMessage(){const e={messageType:"ping",data:null};setTimeout((()=>{var t;try{(null===(t=this.ws)||void 0===t?void 0:t.readyState)===WebSocket.OPEN?(this._config.logger.debug("sending ping"),this.ws.send(JSON.stringify(e)),this.sendPingMessage()):this._config.logger.debug(`socket closed at ${new Date}`)}catch(e){this._config.logger.debug(e)}}),this._config.pingInterval)}doDataSync(){var e,t;const i={messageType:"data-sync",data:{timestamp:this._config.getStoreTimestamp(),user:this._config.user}};try{(null===(e=this.ws)||void 0===e?void 0:e.readyState)===WebSocket.OPEN?(this._config.logger.debug("requesting data"),null===(t=this.ws)||void 0===t||t.send(JSON.stringify(i))):this._config.logger.error("not requesting data because socket not open")}catch(e){this._config.logger.debug(e)}}reconnect(){if(!this.closed){this.ws=void 0;const e=a[Math.min(this.retryCounter++,a.length-1)];this._config.logger.info(`The client will try to reconnect in ${e} milliseconds.`),setTimeout((()=>{this._config.logger.info(`The client is trying to reconnect, flag evaluation results may be stale until reconnected, waited for: ${e} milliseconds`),this.connect()}),e)}}})},8322:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=i(4129),s=i(5768),o=i(6842),a=i(7689),l=i(3046),u=r(i(9174)),c=r(i(6940));class d extends n.FbClientCore{constructor(e,t=void 0){const i=new s.BasicLogger({level:"none",destination:console.log}),r=e.logger?new a.SafeLogger(e.logger,i):i,n=new o.EventEmitter(r);let{store:l}=e;l||(l=new c.default(e)),super(Object.assign(Object.assign({},e),{logger:r,store:l}),null!=t?t:new u.default(Object.assign(Object.assign({},e),{logger:r})),{onError:e=>{n.listenerCount("error")&&n.emit("error",e)},onFailed:e=>{n.emit("failed",e)},onReady:()=>{n.emit("ready")},onUpdate:e=>{n.emit("update",[e]),e.forEach((e=>n.emit(`update:${e}`,e)))},hasEventListeners:()=>n.eventNames().some((e=>"update"===e||"string"==typeof e&&e.startsWith("update:")))}),this.emitter=n}}t.default=(0,l.Emits)(d)},6940:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(443),s=i(6860),o=i(5067);class a extends s.BaseStore{constructor(e){super(),this.logger=e.logger}close(){}get description(){return"local-storage-store"}saveUser(){return r(this,void 0,void 0,(function*(){localStorage.setItem(n.CurrentUserStorageKey,(0,o.serializeUser)(this._user))}))}dumpStoreToStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`;localStorage.setItem(e,JSON.stringify(this.store))}))}loadStoreFromStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`,t=localStorage.getItem(e);let i=null;try{t&&t.trim().length>0&&(i=JSON.parse(t))}catch(t){this.logger.error(`error while loading local data store: ${e}`,t)}this.store=i||{flags:{},version:0}}))}}t.default=a},9718:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)},s=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.BrowserWebSocket=void 0,n(i(5309),t),n(i(5800),t),n(i(9938),t),n(i(6510),t),n(i(2894),t),n(i(891),t);const o=s(i(9018));t.BrowserWebSocket=o.default},2894:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6860:function(e,t){var i=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.BaseStore=void 0,t.BaseStore=class{constructor(){this.store={},this.initCalled=!1,this._user={}}identify(e){return i(this,void 0,void 0,(function*(){this._user=Object.assign({},e),yield this.saveUser(),yield this.loadStoreFromStorage()}))}get user(){return this._user}addItem(e,t,r){return i(this,void 0,void 0,(function*(){let i=this.store[e.namespace];if(i||(i={},this.store[e.namespace]=i),Object.hasOwnProperty.call(i,t)){const e=i[t];(!e||e.versionthis.store.version&&(this.store.version=r.version),yield this.dumpStoreToStorage()}))}get(e,t){const i=this.store[e.namespace];if(i&&Object.prototype.hasOwnProperty.call(i,t)){const e=i[t];if(e)return e}return null}all(e){var t;const i={},r=null!==(t=this.store[e.namespace])&&void 0!==t?t:{};return Object.entries(r).forEach((([e,t])=>{t&&(i[e]=t)})),[i,this.store.version]}init(e){return i(this,void 0,void 0,(function*(){this.store=e,Object.keys(e).map((t=>{Object.entries(e[t]).forEach((([e,t])=>{const i=t;i.version>this.store.version&&(this.store.version=i.version)}))})),yield this.dumpStoreToStorage(),this.initCalled=!0}))}upsert(e,t){return i(this,void 0,void 0,(function*(){yield this.addItem(e,t.key,t)}))}initialized(){return this.initCalled}close(){}get version(){return this.store.version}get description(){return""}saveUser(){return i(this,void 0,void 0,(function*(){}))}loadStoreFromStorage(){return i(this,void 0,void 0,(function*(){}))}dumpStoreToStorage(){return i(this,void 0,void 0,(function*(){}))}}},2093:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0});class i{}i.Flags={namespace:"flags"},t.default=i},356:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7783:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(443),s=i(6860);class o extends s.BaseStore{constructor(){super(),this.allStores={}}close(){}get description(){return"in-memory-store"}saveUser(){return r(this,void 0,void 0,(function*(){}))}dumpStoreToStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`;this.allStores[e]=Object.assign({},this.store)}))}loadStoreFromStorage(){var e;return r(this,void 0,void 0,(function*(){const t=`${n.StoreStorageKey}-${this._user.keyId}`;this.store=null!==(e=this.allStores[t])&&void 0!==e?e:{flags:{},version:0}}))}}t.default=o},8598:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(2093),t),n(i(356),t),n(i(7783),t),n(i(4426),t),n(i(443),t),n(i(6860),t)},4426:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.deserializePatch=t.deserializeAll=void 0;const n=r(i(2093));t.deserializeAll=function(e){const t={[n.default.Flags.namespace]:{}};return(null==e?void 0:e.length)&&(t[n.default.Flags.namespace]=e.reduce(((e,t)=>(e[t.id]=Object.assign(Object.assign({},t),{version:t.timestamp||0,key:t.id,variations:t.variationOptions}),e)),{})),t},t.deserializePatch=function(e){return[...(null==e?void 0:e.map((e=>({data:Object.assign(Object.assign({},e),{version:e.timestamp,key:e.id,variations:e.variationOptions}),kind:n.default.Flags}))))||[]]}},443:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.CurrentUserStorageKey=t.StoreStorageKey=void 0,t.StoreStorageKey="fb-datastore",t.CurrentUserStorageKey="fb-user"},3046:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.Emits=void 0,t.Emits=function(e){return class extends e{on(e,t,i){return this.emitter.on(e,t,i),this}addListener(e,t,i){return this.emitter.addListener(e,t,i),this}once(e,t,i){return this.emitter.once(e,t,i),this}removeListener(e,t,i){return this.emitter.removeListener(e,t,i),this}off(e,t,i){return this.emitter.off(e,t,i),this}removeAllListeners(e){return this.emitter.removeAllListeners(e),this}listeners(e){return this.emitter.listeners(e)}emit(e,...t){return this.emitter.emit(e,t),this}listenerCount(e){return this.emitter.listenerCount(e)}prependListener(e,t,i){return this.emitter.prependListener(e,t,i),this}prependOnceListener(e,t,i){return this.emitter.prependOnceListener(e,t,i),this}eventNames(){return this.emitter.eventNames()}maybeReportError(e){return this.emitter.maybeReportError(e),this}}}},6842:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.EventEmitter=void 0,t.EventEmitter=class{constructor(e){this.logger=e,this.events={}}listeningTo(e){return!!this.events[e]}on(e,t,i){return this.events[e]=this.events[e]||[],this.events[e]=this.events[e].concat({handler:t,context:i}),this}addListener(e,t,i){return this.on(e,t,i)}once(e,t,i){const r=(...n)=>{this.off(e,r,i),t.apply(i,n)};return this.on(e,r,i)}off(e,t,i){if(!this.events[e])return this;for(let r=0;re.handler)):[]}emit(e,...t){if(!this.events[e])return this;const i=[...this.events[e]];for(let e=0;e{this.off(e,r,i),t.apply(i,n)};return this.prependListener(e,r,i)}eventNames(){return Object.keys(this.events)}maybeReportError(e){var t;return e?(this.listeningTo("error")?this.emit("error",e):null===(t=this.logger)||void 0===t||t.error(e),this):this}}},1142:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.ValueConverters=void 0;class i{static bool(e){return"TRUE"===(null==e?void 0:e.toUpperCase())?i.success(!0):"FALSE"===(null==e?void 0:e.toUpperCase())?i.success(!1):i.error()}static number(e){const t=Number(e);return Number.isNaN(t)?i.error():i.success(t)}static string(e){return i.success(e)}static json(e){try{const t=JSON.parse(e);return i.success(t)}catch(e){return i.error()}}static success(e){return{isSucceeded:!0,value:e}}static error(){return{isSucceeded:!1}}}t.ValueConverters=i},7266:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},1624:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.canonicalizeUri=void 0,t.canonicalizeUri=function(e){return e.replace(/\/+$/,"")}},9183:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.debounce=void 0,t.debounce=(e,t=5e3)=>{let i;return(...r)=>{clearTimeout(i),i=setTimeout((()=>{e(...r)}),t)}}},8688:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.httpErrorMessage=t.defaultHeaders=void 0,t.defaultHeaders=function(e,t){const{userAgentBase:i,version:r}=t.sdkData();return{"Content-Type":"application/json","User-Agent":`${null!=i?i:t.appType}/${r}`,Authorization:e}},t.httpErrorMessage=function(e,t,i){let r;return r=e.status?`error ${e.status}${401===e.status?" (invalid SDK key)":""}`:`I/O error (${e.message||e})`,`Received ${r} for ${t} - ${null!=i?i:"giving up permanently"}`}},2710:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(5562),t),n(i(1773),t),n(i(1142),t),n(i(7266),t),n(i(5067),t),n(i(9183),t)},5562:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.isNullOrUndefined=void 0,t.isNullOrUndefined=function(e){return null==e}},5067:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.serializeUser=void 0,t.serializeUser=function(e){var t;return e?`${e.keyId},${e.name},${null===(t=e.customizedProperties)||void 0===t?void 0:t.sort(((e,t)=>{const i=e.name.toLowerCase(),r=t.name.toLowerCase();return ir?1:0})).map((e=>`${e.name}:${e.value}`)).join(",")}`:""}},1773:function(e,t){var i=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.default=(e=1e3)=>i(void 0,void 0,void 0,(function*(){return new Promise((t=>{setTimeout(t,e)}))}))},5972:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.name=t.version=void 0,t.version="3.0.3",t.name="@featbit/js-client-sdk"}},t={};return function i(r){var n=t[r];if(void 0!==n)return n.exports;var s=t[r]={exports:{}};return e[r].call(s.exports,s,s.exports,i),s.exports}(9872)})())); +//# sourceMappingURL=featbit-js-client-sdk-3.0.3.js.map \ No newline at end of file diff --git a/examples/web-app/umd/featbit-js-client-sdk-3.0.3.js.map b/examples/web-app/umd/featbit-js-client-sdk-3.0.3.js.map new file mode 100644 index 0000000..3e803a8 --- /dev/null +++ b/examples/web-app/umd/featbit-js-client-sdk-3.0.3.js.map @@ -0,0 +1 @@ +{"version":3,"file":"featbit-js-client-sdk-3.0.3.js","mappings":"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","sources":["webpack://@featbit/js-client-sdk/webpack/universalModuleDefinition","webpack://@featbit/js-client-sdk/./src/Configuration.ts","webpack://@featbit/js-client-sdk/./src/Context.ts","webpack://@featbit/js-client-sdk/./src/FbClientBuilder.ts","webpack://@featbit/js-client-sdk/./src/FbClientCore.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/JsonBootstrapProvider.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/NullBootstrapProvider.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/index.ts","webpack://@featbit/js-client-sdk/./src/constants.ts","webpack://@featbit/js-client-sdk/./src/data-sources/DataSourceUpdates.ts","webpack://@featbit/js-client-sdk/./src/data-sources/createStreamListeners.ts","webpack://@featbit/js-client-sdk/./src/data-sources/index.ts","webpack://@featbit/js-client-sdk/./src/data-sync/DataSyncMode.ts","webpack://@featbit/js-client-sdk/./src/data-sync/NullDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/PollingDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/Requestor.ts","webpack://@featbit/js-client-sdk/./src/data-sync/WebSocketDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/index.ts","webpack://@featbit/js-client-sdk/./src/data-sync/types.ts","webpack://@featbit/js-client-sdk/./src/data-sync/utils.ts","webpack://@featbit/js-client-sdk/./src/errors.ts","webpack://@featbit/js-client-sdk/./src/evaluation/EvalResult.ts","webpack://@featbit/js-client-sdk/./src/evaluation/Evaluator.ts","webpack://@featbit/js-client-sdk/./src/evaluation/ReasonKinds.ts","webpack://@featbit/js-client-sdk/./src/evaluation/data/IFlag.ts","webpack://@featbit/js-client-sdk/./src/evaluation/data/index.ts","webpack://@featbit/js-client-sdk/./src/evaluation/index.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventProcessor.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventQueue.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventSender.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventSerializer.ts","webpack://@featbit/js-client-sdk/./src/events/EventDispatcher.ts","webpack://@featbit/js-client-sdk/./src/events/IEventSender.ts","webpack://@featbit/js-client-sdk/./src/events/NullEventProcessor.ts","webpack://@featbit/js-client-sdk/./src/events/event.ts","webpack://@featbit/js-client-sdk/./src/events/index.ts","webpack://@featbit/js-client-sdk/./src/index.ts","webpack://@featbit/js-client-sdk/./src/logging/BasicLogger.ts","webpack://@featbit/js-client-sdk/./src/logging/SafeLogger.ts","webpack://@featbit/js-client-sdk/./src/logging/format.ts","webpack://@featbit/js-client-sdk/./src/logging/index.ts","webpack://@featbit/js-client-sdk/./src/options/ClientContext.ts","webpack://@featbit/js-client-sdk/./src/options/OptionMessages.ts","webpack://@featbit/js-client-sdk/./src/options/UserBuilder.ts","webpack://@featbit/js-client-sdk/./src/options/Validators.ts","webpack://@featbit/js-client-sdk/./src/options/index.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserInfo.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserPlatform.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserRequests.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserWebSocket.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/FbClient.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/LocalStorageStore.ts","webpack://@featbit/js-client-sdk/./src/platform/index.ts","webpack://@featbit/js-client-sdk/./src/store/BaseStore.ts","webpack://@featbit/js-client-sdk/./src/store/DataKinds.ts","webpack://@featbit/js-client-sdk/./src/store/InMemoryStore.ts","webpack://@featbit/js-client-sdk/./src/store/index.ts","webpack://@featbit/js-client-sdk/./src/store/serialization.ts","webpack://@featbit/js-client-sdk/./src/store/store.ts","webpack://@featbit/js-client-sdk/./src/utils/Emits.ts","webpack://@featbit/js-client-sdk/./src/utils/EventEmitter.ts","webpack://@featbit/js-client-sdk/./src/utils/ValueConverters.ts","webpack://@featbit/js-client-sdk/./src/utils/canonicalizeUri.ts","webpack://@featbit/js-client-sdk/./src/utils/debounce.ts","webpack://@featbit/js-client-sdk/./src/utils/http.ts","webpack://@featbit/js-client-sdk/./src/utils/index.ts","webpack://@featbit/js-client-sdk/./src/utils/isNullOrUndefined.ts","webpack://@featbit/js-client-sdk/./src/utils/serializeUser.ts","webpack://@featbit/js-client-sdk/./src/utils/sleep.ts","webpack://@featbit/js-client-sdk/./src/version.ts","webpack://@featbit/js-client-sdk/webpack/bootstrap","webpack://@featbit/js-client-sdk/webpack/startup"],"sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse {\n\t\tvar a = factory();\n\t\tfor(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i];\n\t}\n})(this, () => {\nreturn ","import { IOptions } from \"./options/IOptions\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport { IValidatedOptions } from \"./options/IValidatedOptions\";\r\nimport { NumberWithMinimum, TypeValidator, TypeValidators, UserValidator } from \"./options/Validators\";\r\nimport OptionMessages from \"./options/OptionMessages\";\r\nimport { IStore } from \"./platform/IStore\";\r\nimport { IClientContext } from \"./options/IClientContext\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport { IDataSourceUpdates } from \"./store/IDataSourceUpdates\";\r\nimport InMemoryStore from \"./store/InMemoryStore\";\r\nimport { VoidFunction } from \"./utils/VoidFunction\";\r\nimport { isNullOrUndefined } from \"./utils/isNullOrUndefined\";\r\nimport { canonicalizeUri } from \"./utils/canonicalizeUri\";\r\nimport { IBootstrapProvider } from \"./bootstrap/IBootstrapProvider\";\r\nimport { NullBootstrapProvider } from \"./bootstrap/NullBootstrapProvider\";\r\nimport { EmptyString } from \"./constants\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { JsonBootstrapProvider } from \"./bootstrap\";\r\n\r\n// Once things are internal to the implementation of the SDK we can depend on\r\n// types. Calls to the SDK could contain anything without any regard to typing.\r\n// So, data we take from external sources must be normalized into something\r\n// that can be trusted.\r\n\r\n/**\r\n * These perform cursory validations. Complex objects are implemented with classes\r\n * and these should allow for conditional construction.\r\n */\r\nconst validations: Record = {\r\n startWaitTime: TypeValidators.Number,\r\n sdkKey: TypeValidators.String,\r\n pollingUri: TypeValidators.String,\r\n streamingUri: TypeValidators.String,\r\n eventsUri: TypeValidators.String,\r\n webSocketPingInterval: TypeValidators.Number,\r\n logger: TypeValidators.Object,\r\n store: TypeValidators.ObjectOrFactory,\r\n dataSynchronizer: TypeValidators.ObjectOrFactory,\r\n flushInterval: TypeValidators.Number,\r\n maxEventsInQueue: TypeValidators.Number,\r\n pollingInterval: TypeValidators.Number,\r\n offline: TypeValidators.Boolean,\r\n dataSyncMode: TypeValidators.String,\r\n bootstrap: TypeValidators.Bootstrap,\r\n user: TypeValidators.User\r\n};\r\n\r\n/**\r\n * @internal\r\n */\r\nexport const defaultValues: IValidatedOptions = {\r\n startWaitTime: 5000,\r\n sdkKey: '',\r\n pollingUri: '',\r\n streamingUri: '',\r\n eventsUri: '',\r\n dataSyncMode: DataSyncModeEnum.STREAMING,\r\n sendEvents: true,\r\n webSocketPingInterval: 18 * 1000,\r\n flushInterval: 2000,\r\n maxEventsInQueue: 10000,\r\n pollingInterval: 30000,\r\n offline: false,\r\n store: (options: IOptions) => new InMemoryStore(),\r\n bootstrap: undefined,\r\n user: undefined,\r\n};\r\n\r\nfunction validateTypesAndNames(options: IOptions): {\r\n errors: string[];\r\n validatedOptions: IValidatedOptions;\r\n} {\r\n let errors: string[] = [];\r\n const validatedOptions: IValidatedOptions = {...defaultValues};\r\n Object.keys(options).forEach((optionName) => {\r\n // We need to tell typescript it doesn't actually know what options are.\r\n // If we don't then it complains we are doing crazy things with it.\r\n const optionValue = (options as unknown as any)[optionName];\r\n const validator = validations[optionName];\r\n if (validator) {\r\n if (!validator.is(optionValue)) {\r\n if (validator.getType() === 'boolean') {\r\n errors.push(OptionMessages.wrongOptionTypeBoolean(optionName, typeof optionValue));\r\n validatedOptions[optionName] = !!optionValue;\r\n } else if (\r\n validator instanceof NumberWithMinimum &&\r\n TypeValidators.Number.is(optionValue)\r\n ) {\r\n const {min} = validator as NumberWithMinimum;\r\n errors.push(OptionMessages.optionBelowMinimum(optionName, optionValue, min));\r\n validatedOptions[optionName] = min;\r\n } else if (validator instanceof UserValidator) {\r\n errors = [...errors, ...validator.messages];\r\n validatedOptions[optionName] = defaultValues[optionName];\r\n } else {\r\n errors.push(\r\n OptionMessages.wrongOptionType(optionName, validator.getType(), typeof optionValue),\r\n );\r\n validatedOptions[optionName] = defaultValues[optionName];\r\n }\r\n } else {\r\n validatedOptions[optionName] = optionValue;\r\n }\r\n } else {\r\n options.logger?.warn(OptionMessages.unknownOption(optionName));\r\n }\r\n });\r\n return {errors, validatedOptions};\r\n}\r\n\r\nfunction validateEndpoints(options: IOptions, validatedOptions: IValidatedOptions) {\r\n const {streamingUri, pollingUri, eventsUri} = options;\r\n const streamingUriMissing = isNullOrUndefined(streamingUri) || streamingUri === EmptyString;\r\n const pollingUriMissing = isNullOrUndefined(pollingUri) || pollingUri === EmptyString;\r\n const eventsUriMissing = isNullOrUndefined(eventsUri) || eventsUri === EmptyString;\r\n\r\n if (!validatedOptions.offline && (eventsUriMissing || (streamingUriMissing && pollingUriMissing))) {\r\n if (eventsUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('eventsUri'));\r\n }\r\n\r\n if (validatedOptions.dataSyncMode === DataSyncModeEnum.STREAMING && streamingUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('streamingUri'));\r\n }\r\n\r\n if (validatedOptions.dataSyncMode === DataSyncModeEnum.POLLING && pollingUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('pollingUri'));\r\n }\r\n }\r\n}\r\n\r\nexport default class Configuration {\r\n public readonly startWaitTime: number;\r\n\r\n public readonly sdkKey: string;\r\n\r\n public readonly streamingUri: string;\r\n\r\n public readonly pollingUri: string;\r\n\r\n public readonly eventsUri: string;\r\n\r\n public readonly webSocketPingInterval: number;\r\n\r\n public readonly logger?: ILogger;\r\n\r\n public readonly flushInterval: number;\r\n\r\n public readonly maxEventsInQueue: number;\r\n\r\n public readonly pollingInterval: number;\r\n\r\n public readonly offline: boolean;\r\n\r\n public readonly dataSyncMode: DataSyncModeEnum;\r\n\r\n public readonly bootstrapProvider: IBootstrapProvider = new NullBootstrapProvider();\r\n\r\n public readonly user: IUser;\r\n\r\n public readonly storeFactory: (clientContext: IClientContext) => IStore;\r\n\r\n public readonly dataSynchronizerFactory?: (\r\n clientContext: IClientContext,\r\n store: IStore,\r\n dataSourceUpdates: IDataSourceUpdates,\r\n initSuccessHandler: VoidFunction,\r\n errorHandler?: (e: Error) => void,\r\n ) => IDataSynchronizer;\r\n\r\n constructor(options: IOptions = {}) {\r\n // The default will handle undefined, but not null.\r\n // Because we can be called from JS we need to be extra defensive.\r\n options = options || {};\r\n // If there isn't a valid logger from the platform, then logs would go nowhere.\r\n this.logger = options.logger;\r\n\r\n const {errors, validatedOptions} = validateTypesAndNames(options);\r\n errors.forEach((error) => {\r\n this.logger?.warn(error);\r\n });\r\n\r\n this.user = options.user!;\r\n\r\n validateEndpoints(options, validatedOptions);\r\n this.streamingUri = `${ canonicalizeUri(validatedOptions.streamingUri) }/streaming`;\r\n this.pollingUri = `${ canonicalizeUri(validatedOptions.pollingUri) }/api/public/sdk/client/latest-all`;\r\n this.eventsUri = `${ canonicalizeUri(validatedOptions.eventsUri) }/api/public/insight/track`;\r\n\r\n this.startWaitTime = validatedOptions.startWaitTime;\r\n\r\n this.sdkKey = validatedOptions.sdkKey;\r\n this.webSocketPingInterval = validatedOptions.webSocketPingInterval!;\r\n\r\n this.flushInterval = validatedOptions.flushInterval;\r\n this.maxEventsInQueue = validatedOptions.maxEventsInQueue;\r\n this.pollingInterval = validatedOptions.pollingInterval;\r\n\r\n this.offline = validatedOptions.offline;\r\n if (validatedOptions.bootstrap && validatedOptions.bootstrap.length > 0) {\r\n try {\r\n this.bootstrapProvider = new JsonBootstrapProvider(validatedOptions.bootstrap);\r\n } catch (_) {\r\n this.logger?.error('Failed to parse bootstrap JSON, use NullBootstrapProvider.');\r\n }\r\n }\r\n\r\n if (this.offline) {\r\n this.logger?.info('Offline mode enabled. No data synchronization with the FeatBit server will occur.');\r\n }\r\n\r\n this.dataSyncMode = validatedOptions.dataSyncMode;\r\n\r\n if (TypeValidators.Function.is(validatedOptions.dataSynchronizer)) {\r\n // @ts-ignore\r\n this.dataSynchronizerFactory = validatedOptions.dataSynchronizer;\r\n } else {\r\n // The processor is already created, just have the method return it.\r\n // @ts-ignore\r\n this.dataSynchronizerFactory = () => validatedOptions.dataSynchronizer;\r\n }\r\n\r\n if (TypeValidators.Function.is(validatedOptions.store)) {\r\n // @ts-ignore\r\n this.storeFactory = validatedOptions.store;\r\n } else {\r\n // The store is already created, just have the method return it.\r\n // @ts-ignore\r\n this.storeFactory = () => validatedOptions.store;\r\n }\r\n }\r\n}","import { IUser } from \"./options/IUser\";\r\n\r\nexport default class Context {\r\n private _user?: IUser;\r\n /**\r\n * Is this a valid context. If a valid context cannot be created, then this flag will be true.\r\n * The validity of a context should be tested before it is used.\r\n */\r\n public readonly valid: boolean;\r\n\r\n public readonly message?: string;\r\n\r\n /**\r\n * Contexts should be created using the static factory method {@link Context.fromUser}.\r\n *\r\n * The factory methods are static functions within the class because they access private\r\n * implementation details, so they cannot be free functions.\r\n */\r\n private constructor(valid: boolean, message?: string) {\r\n this.valid = valid;\r\n this.message = message;\r\n }\r\n\r\n public static fromUser(user: IUser): Context {\r\n if (!user) {\r\n return Context.contextForError('No user specified');\r\n }\r\n\r\n const {keyId, name} = user;\r\n\r\n if (keyId === undefined || keyId === null || keyId.trim() === '') {\r\n return Context.contextForError('key is mandatory');\r\n }\r\n\r\n const context = new Context(true);\r\n context._user = user;\r\n\r\n return context;\r\n }\r\n\r\n get user(): IUser {\r\n return this._user!;\r\n }\r\n\r\n get keyId(): string {\r\n return this._user!.keyId;\r\n }\r\n\r\n value(property: string): any {\r\n if (property === 'keyId') {\r\n return this._user?.keyId;\r\n } else if (property === 'name') {\r\n return this._user?.name;\r\n } else {\r\n return this._user?.customizedProperties?.find(x => x.name === property)?.value;\r\n }\r\n }\r\n\r\n private static contextForError(message: string) {\r\n return new Context(false, message);\r\n }\r\n}","import { IFbClient } from \"./IFbClient\";\r\nimport { IOptions } from \"./options/IOptions\";\r\nimport FbClient from \"./platform/browser/FbClient\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport { IClientContext } from \"./options/IClientContext\";\r\nimport { IDataSourceUpdates } from \"./store/IDataSourceUpdates\";\r\nimport { VoidFunction } from \"./utils/VoidFunction\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { IFlagBase } from \"./evaluation\";\r\nimport { IPlatform } from \"./platform\";\r\n\r\n/**\r\n * Creates an instance of the FeatBit client.\r\n *\r\n * Applications should instantiate a single instance for the lifetime of the application.\r\n * The client will begin attempting to connect to FeatBit as soon as it is created. To\r\n * determine when it is ready to use, call {@link IFbClient.waitForInitialization}, or register an\r\n * event listener for the `\"ready\"` event using {@link IFbClient.on}.\r\n *\r\n * **Important:** Do **not** try to instantiate `FbClient` with its constructor\r\n * (`new FbClientNode()`); the SDK does not currently support\r\n * this.\r\n *\r\n * @return\r\n * The new {@link IFbClient} instance.\r\n */\r\nexport class FbClientBuilder {\r\n private _options: IOptions;\r\n private _platform: IPlatform | undefined;\r\n\r\n constructor(options?: IOptions) {\r\n this._options = options ?? {};\r\n }\r\n\r\n /**\r\n * Creates a new instance of the FeatBit client.\r\n */\r\n build(): IFbClient {\r\n return new FbClient(this._options);\r\n }\r\n\r\n platform(platform: IPlatform | undefined): FbClientBuilder {\r\n this._platform = platform;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.startWaitTime}.\r\n */\r\n startWaitTime(startWaitTime: number): FbClientBuilder {\r\n this._options.startWaitTime = startWaitTime;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.sdkKey}.\r\n */\r\n sdkKey(sdkKey: string): FbClientBuilder {\r\n this._options.sdkKey = sdkKey;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.user}.\r\n */\r\n user(user: IUser): FbClientBuilder {\r\n this._options.user = user;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.streamingUri}.\r\n */\r\n streamingUri(streamingUri: string): FbClientBuilder {\r\n this._options.streamingUri = streamingUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.pollingUri}.\r\n */\r\n pollingUri(pollingUri: string): FbClientBuilder {\r\n this._options.pollingUri = pollingUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.eventsUri}.\r\n */\r\n eventsUri(eventsUri: string): FbClientBuilder {\r\n this._options.eventsUri = eventsUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.dataSyncMode}.\r\n */\r\n dataSyncMode(mode: DataSyncModeEnum): FbClientBuilder {\r\n this._options.dataSyncMode = mode;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.pollingInterval}.\r\n */\r\n pollingInterval(pollingInterval: number): FbClientBuilder {\r\n this._options.pollingInterval = pollingInterval;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.flushInterval}.\r\n */\r\n flushInterval(flushInterval: number): FbClientBuilder {\r\n this._options.flushInterval = flushInterval;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.maxEventsInQueue}.\r\n */\r\n maxEventsInQueue(maxEventsInQueue: number): FbClientBuilder {\r\n this._options.maxEventsInQueue = maxEventsInQueue;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.logger}.\r\n */\r\n logger(logger: ILogger): FbClientBuilder {\r\n this._options.logger = logger;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.offline}.\r\n */\r\n offline(offline: boolean): FbClientBuilder {\r\n this._options.offline = offline;\r\n return this;\r\n }\r\n\r\n /**\r\n * Use the JsonBootstrapProvider.\r\n */\r\n bootstrap(flags: IFlagBase[]): FbClientBuilder {\r\n this._options.bootstrap = flags;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.dataSynchronizer}.\r\n */\r\n dataSynchronizer(\r\n dataSynchronizer: IDataSynchronizer |\r\n ((\r\n clientContext: IClientContext,\r\n dataSourceUpdates: IDataSourceUpdates,\r\n initSuccessHandler: VoidFunction,\r\n errorHandler?: (e: Error) => void,\r\n ) => IDataSynchronizer)\r\n ): FbClientBuilder {\r\n this._options.dataSynchronizer = dataSynchronizer;\r\n return this;\r\n }\r\n}","import { IFbClientCore } from \"./IFbClientCore\";\r\nimport { IPlatform } from \"./platform/IPlatform\";\r\nimport Configuration from \"./Configuration\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport ClientContext from \"./options/ClientContext\";\r\nimport DataSourceUpdates from \"./data-sources/DataSourceUpdates\";\r\nimport { createStreamListeners } from \"./data-sources/createStreamListeners\";\r\nimport { IEvalDetail } from \"./evaluation/IEvalDetail\";\r\nimport WebSocketDataSynchronizer from \"./data-sync/WebSocketDataSynchronizer\";\r\nimport PollingDataSynchronizer from \"./data-sync/PollingDataSynchronizer\";\r\nimport Requestor from \"./data-sync/Requestor\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport DataKinds from \"./store/DataKinds\";\r\nimport Evaluator from \"./evaluation/Evaluator\";\r\nimport { ReasonKinds } from \"./evaluation/ReasonKinds\";\r\nimport { ClientError } from \"./errors\";\r\nimport Context from \"./Context\";\r\nimport { IConvertResult, ValueConverters } from \"./utils/ValueConverters\";\r\nimport { NullDataSynchronizer } from \"./data-sync/NullDataSynchronizer\";\r\nimport { IEventProcessor } from \"./events/IEventProcessor\";\r\nimport { NullEventProcessor } from \"./events/NullEventProcessor\";\r\nimport { DefaultEventProcessor } from \"./events/DefaultEventProcessor\";\r\nimport { IStore } from \"./platform/IStore\";\r\nimport { IOptions } from \"./options/IOptions\";\r\nimport { MetricEvent } from \"./events/event\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { UserValidator } from \"./options/Validators\";\r\n\r\nenum ClientState {\r\n Initializing,\r\n Initialized,\r\n Failed,\r\n}\r\n\r\nexport interface IClientCallbacks {\r\n onError: (err: Error) => void;\r\n onFailed: (err: Error) => void;\r\n onReady: () => void;\r\n // Called whenever flags change, if there are listeners.\r\n onUpdate: (keys: string[]) => void;\r\n // Method to check if event listeners have been registered.\r\n // If none are registered, then onUpdate will never be called.\r\n hasEventListeners: () => boolean;\r\n}\r\n\r\nexport class FbClientCore implements IFbClientCore {\r\n private state: ClientState = ClientState.Initializing;\r\n\r\n private store?: IStore;\r\n\r\n private dataSynchronizer?: IDataSynchronizer;\r\n\r\n private eventProcessor?: IEventProcessor;\r\n\r\n private evaluator?: Evaluator;\r\n\r\n private initResolve?: (value: IFbClientCore | PromiseLike) => void;\r\n\r\n private initReject?: (err: Error) => void;\r\n\r\n private rejectionReason: Error | undefined;\r\n\r\n private initializedPromise?: Promise;\r\n\r\n private config: Configuration;\r\n\r\n private dataSourceUpdates?: DataSourceUpdates;\r\n\r\n private onError: (err: Error) => void;\r\n\r\n private onFailed: (err: Error) => void;\r\n\r\n private onReady: () => void;\r\n\r\n logger?: ILogger;\r\n\r\n constructor(\r\n private options: IOptions,\r\n private platform: IPlatform,\r\n callbacks: IClientCallbacks\r\n ) {\r\n this.onError = callbacks.onError;\r\n this.onFailed = callbacks.onFailed;\r\n this.onReady = callbacks.onReady;\r\n\r\n const {onUpdate, hasEventListeners} = callbacks;\r\n const config = new Configuration(options);\r\n\r\n if (!config.sdkKey && !config.offline) {\r\n throw new Error('You must configure the client with an SDK key');\r\n }\r\n\r\n if (!config.user) {\r\n throw new Error('You must configure the client with a user');\r\n }\r\n\r\n this.config = config;\r\n this.logger = config.logger;\r\n\r\n this.init(platform, onUpdate, hasEventListeners);\r\n }\r\n\r\n private async init(platform: IPlatform, onUpdate: (keys: string[]) => void, hasEventListeners: () => boolean) {\r\n const clientContext = new ClientContext(this.config.sdkKey, this.config, platform);\r\n this.store = this.config.storeFactory(clientContext);\r\n await this.store.identify(this.config.user);\r\n this.dataSourceUpdates = new DataSourceUpdates(this.store, hasEventListeners, onUpdate);\r\n this.evaluator = new Evaluator(this.store);\r\n\r\n // use bootstrap provider to populate store\r\n await this.config.bootstrapProvider.populate(this.config.user.keyId, this.dataSourceUpdates);\r\n\r\n if (this.config.offline) {\r\n this.eventProcessor = new NullEventProcessor();\r\n this.dataSynchronizer = new NullDataSynchronizer();\r\n\r\n this.initSuccess();\r\n } else {\r\n this.eventProcessor = new DefaultEventProcessor(clientContext);\r\n\r\n const listeners = createStreamListeners(this.dataSourceUpdates, this.logger, {\r\n put: () => this.initSuccess(),\r\n patch: () => this.initSuccess()\r\n });\r\n\r\n const dataSynchronizer = this.config.dataSyncMode === DataSyncModeEnum.STREAMING\r\n ? new WebSocketDataSynchronizer(\r\n this.config.sdkKey,\r\n this.config.user,\r\n clientContext,\r\n platform.webSocket,\r\n () => this.store!.version,\r\n listeners,\r\n this.config.webSocketPingInterval\r\n )\r\n : new PollingDataSynchronizer(\r\n this.config,\r\n new Requestor(this.config.sdkKey, this.config, this.platform.info, this.platform.requests),\r\n () => this.store!.version,\r\n listeners,\r\n (e) => this.dataSourceErrorHandler(e),\r\n );\r\n\r\n this.dataSynchronizer = this.config.dataSynchronizerFactory?.(\r\n clientContext,\r\n this.store,\r\n this.dataSourceUpdates,\r\n () => this.initSuccess(),\r\n (e) => this.dataSourceErrorHandler(e),\r\n ) ?? dataSynchronizer;\r\n }\r\n\r\n this.start();\r\n }\r\n\r\n async identify(user: IUser) {\r\n const validator = new UserValidator();\r\n if (!validator.is(user)) {\r\n validator.messages.forEach((error: string) => {\r\n this.logger?.warn(error);\r\n });\r\n\r\n return;\r\n }\r\n\r\n this.store!.identify(user);\r\n this.dataSynchronizer!.identify(user);\r\n const [ flags ] = this.store!.all(DataKinds.Flags);\r\n if (Object.keys(flags).length === 0) {\r\n await this.config.bootstrapProvider.populate(user.keyId, this.dataSourceUpdates!);\r\n }\r\n }\r\n\r\n private start() {\r\n if (this.config.offline) {\r\n return;\r\n }\r\n\r\n this.dataSynchronizer!.start();\r\n setTimeout(() => {\r\n if (!this.initialized()) {\r\n const msg = `FbClient failed to start successfully within ${ this.config.startWaitTime } milliseconds. ` +\r\n 'This error usually indicates a connection issue with FeatBit or an invalid sdkKey.' +\r\n 'Please double-check your sdkKey and streamingUri/pollingUri configuration. ' +\r\n 'We will continue to initialize the FbClient, it still have a chance to get to work ' +\r\n 'if it\\'s a temporary network issue';\r\n\r\n const error = new Error(msg);\r\n this.state = ClientState.Failed;\r\n this.rejectionReason = error;\r\n this.initReject?.(error);\r\n\r\n return this.logger?.warn(msg);\r\n }\r\n }, this.config.startWaitTime);\r\n }\r\n\r\n initialized(): boolean {\r\n return this.state === ClientState.Initialized;\r\n }\r\n\r\n waitForInitialization(): Promise {\r\n // An initialization promise is only created if someone is going to use that promise.\r\n // If we always created an initialization promise, and there was no call waitForInitialization\r\n // by the time the promise was rejected, then that would result in an unhandled promise\r\n // rejection.\r\n\r\n // Initialization promise was created by a previous call to waitForInitialization.\r\n if (this.initializedPromise) {\r\n return this.initializedPromise;\r\n }\r\n\r\n // Initialization completed before waitForInitialization was called, so we have completed\r\n // and there was no promise. So we make a resolved promise and return it.\r\n if (this.state === ClientState.Initialized) {\r\n this.initializedPromise = Promise.resolve(this);\r\n return this.initializedPromise;\r\n }\r\n\r\n // Initialization failed before waitForInitialization was called, so we have completed\r\n // and there was no promise. So we make a rejected promise and return it.\r\n if (this.state === ClientState.Failed) {\r\n this.initializedPromise = Promise.reject(this.rejectionReason);\r\n return this.initializedPromise;\r\n }\r\n\r\n if (!this.initializedPromise) {\r\n this.initializedPromise = new Promise((resolve, reject) => {\r\n this.initResolve = resolve;\r\n this.initReject = reject;\r\n });\r\n }\r\n return this.initializedPromise;\r\n }\r\n\r\n boolVariation(\r\n key: string,\r\n defaultValue: boolean\r\n ): boolean {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.bool).value!;\r\n }\r\n\r\n boolVariationDetail(\r\n key: string,\r\n defaultValue: boolean\r\n ): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.bool);\r\n }\r\n\r\n jsonVariation(key: string, defaultValue: any): any {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.json).value!;\r\n }\r\n\r\n jsonVariationDetail(key: string, defaultValue: any): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.json);\r\n }\r\n\r\n numberVariation(key: string, defaultValue: number): number {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.number).value!;\r\n }\r\n\r\n numberVariationDetail(key: string, defaultValue: number): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.number);\r\n }\r\n\r\n stringVariation(key: string, defaultValue: string): string {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string).value!;\r\n }\r\n\r\n stringVariationDetail(key: string, defaultValue: string): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string);\r\n }\r\n\r\n variation(key: string, defaultValue: string): string {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string).value!;\r\n }\r\n\r\n variationDetail(key: string, defaultValue: string): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string);\r\n }\r\n\r\n getAllVariations(): Promise[]> {\r\n const context = Context.fromUser(this.config.user);\r\n if (!context.valid) {\r\n const error = new ClientError(\r\n `${ context.message ?? 'User not valid;' } returning default value.`,\r\n );\r\n this.onError(error);\r\n\r\n return Promise.resolve([]);\r\n }\r\n\r\n const [flags, _] = this.store!.all(DataKinds.Flags);\r\n const result = Object.keys(flags).map(flagKey => {\r\n const evalResult = this.evaluator!.evaluate(flagKey);\r\n return {flagKey, kind: evalResult.kind, reason: evalResult.reason, value: evalResult.value?.variation};\r\n });\r\n\r\n return Promise.resolve(result);\r\n }\r\n\r\n async close(): Promise {\r\n await this.eventProcessor!.close();\r\n this.dataSynchronizer?.close();\r\n this.store!.close();\r\n }\r\n\r\n track(eventName: string, metricValue?: number | undefined): void {\r\n const metricEvent = new MetricEvent(this.config.user, eventName, this.platform.info.appType, metricValue ?? 1);\r\n this.eventProcessor!.record(metricEvent);\r\n return;\r\n }\r\n\r\n async flush(callback?: (res: boolean) => void): Promise {\r\n try {\r\n await this.eventProcessor!.flush();\r\n callback?.(true);\r\n return true;\r\n } catch (err) {\r\n callback?.(false);\r\n return false;\r\n }\r\n }\r\n\r\n evaluateCore(\r\n flagKey: string,\r\n defaultValue: TValue,\r\n typeConverter: (value: string) => IConvertResult\r\n ): IEvalDetail {\r\n const context = Context.fromUser(this.config.user);\r\n if (!context.valid) {\r\n const error = new ClientError(\r\n `${ context.message ?? 'User not valid;' } returning default value.`,\r\n );\r\n this.onError(error);\r\n\r\n return {flagKey, kind: ReasonKinds.Error, reason: error.message, value: defaultValue};\r\n }\r\n\r\n const evalResult = this.evaluator!.evaluate(flagKey);\r\n\r\n if (evalResult.kind === ReasonKinds.FlagNotFound) {\r\n // flag not found, return default value\r\n const error = new ClientError(evalResult.reason!);\r\n this.onError(error);\r\n\r\n return {flagKey, kind: evalResult.kind, reason: evalResult.reason, value: defaultValue};\r\n }\r\n\r\n if (!this.initialized()) {\r\n this.logger?.warn(\r\n 'Variation called before FeatBit client initialization completed (did you wait for the' +\r\n \"'ready' event?)\",\r\n );\r\n } else {\r\n // send event\r\n this.eventProcessor!.record(evalResult.toEvalEvent(this.config.user));\r\n }\r\n\r\n const {isSucceeded, value} = typeConverter(evalResult.value?.variation!);\r\n return isSucceeded\r\n ? {flagKey, kind: evalResult.kind, reason: evalResult.reason, value}\r\n : {flagKey, kind: ReasonKinds.WrongType, reason: 'type mismatch', value: defaultValue};\r\n }\r\n\r\n private dataSourceErrorHandler(e: any) {\r\n const error =\r\n e.code === 401 ? new Error('Authentication failed. Double check your SDK key.') : e;\r\n\r\n this.onError(error);\r\n this.onFailed(error);\r\n\r\n if (!this.initialized()) {\r\n this.state = ClientState.Failed;\r\n this.rejectionReason = error;\r\n this.initReject?.(error);\r\n }\r\n }\r\n\r\n private initSuccess() {\r\n if (!this.initialized()) {\r\n this.state = ClientState.Initialized;\r\n this.logger?.info('FbClient started successfully.');\r\n this.initResolve?.(this);\r\n this.onReady();\r\n }\r\n }\r\n}\r\n","import { IBootstrapProvider } from \"./IBootstrapProvider\";\r\nimport { deserializeAll } from \"../store/serialization\";\r\nimport { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\nimport { isNullOrUndefined } from \"../utils/isNullOrUndefined\";\r\nimport { IFlag, IFlagBase } from \"../evaluation/data/IFlag\";\r\n\r\nexport class JsonBootstrapProvider implements IBootstrapProvider {\r\n private dataSet?: IStoreDataStorage;\r\n\r\n constructor(bootstrap: IFlagBase[]) {\r\n const flags: IFlag[] = (bootstrap || []).map((flag: IFlagBase) => ({...flag, variationOptions: flag.variationOptions || [{id: null, variation: flag.variation}]})) as IFlag[];\r\n\r\n const data = deserializeAll(flags);\r\n this.dataSet = {\r\n flags: data.flags,\r\n version: 0\r\n };\r\n }\r\n\r\n populate(userKeyId: string, dataSourceUpdates: IDataSourceUpdates, callback?: () => void): Promise {\r\n return new Promise((resolve, reject) => {\r\n if (isNullOrUndefined(this.dataSet)) {\r\n return resolve();\r\n }\r\n\r\n const internalCallback = () => {\r\n resolve();\r\n callback?.();\r\n }\r\n\r\n dataSourceUpdates.init(userKeyId, this.dataSet!, internalCallback);\r\n });\r\n }\r\n}","import { IBootstrapProvider } from \"./IBootstrapProvider\";\r\nimport { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\n\r\nexport class NullBootstrapProvider implements IBootstrapProvider {\r\n private dataSet?: IStoreDataStorage;\r\n\r\n constructor() {\r\n this.dataSet = {\r\n flags: {},\r\n version: 0\r\n };\r\n }\r\n\r\n populate(userKeyId: string, dataSourceUpdates: IDataSourceUpdates, callback?: () => void): Promise {\r\n return new Promise((resolve, reject) => {\r\n resolve();\r\n callback?.();\r\n });\r\n }\r\n}","export * from './IBootstrapProvider';\r\nexport * from './JsonBootstrapProvider';\r\nexport * from './NullBootstrapProvider';","export const EmptyString = '';\r\nexport const MinInt: number = 0x80000000;","import { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport {\r\n IStoreDataStorage,\r\n IStoreItem,\r\n IKeyedStoreItem\r\n} from \"../store/store\";\r\nimport { IStore } from \"../platform/IStore\";\r\nimport { IDataKind } from \"../IDataKind\";\r\nimport DataKinds from \"../store/DataKinds\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class DataSourceUpdates implements IDataSourceUpdates {\r\n\r\n constructor(\r\n private readonly store: IStore,\r\n private readonly hasEventListeners: () => boolean,\r\n private readonly onChange: (keys: string[]) => void,\r\n ) {\r\n }\r\n\r\n init(userKeyId: string, allData: IStoreDataStorage, callback?: () => void): void {\r\n if (userKeyId !== this.store.user.keyId) {\r\n callback?.();\r\n return;\r\n }\r\n\r\n const checkForChanges = this.hasEventListeners();\r\n const doInit = async (oldData?: IStoreDataStorage) => {\r\n await this.store.init(allData);\r\n Promise.resolve().then(() => {\r\n if (checkForChanges) {\r\n const updatedKeys = Object.keys(allData)\r\n .flatMap((namespace) => {\r\n const oldDataForKind = oldData?.[namespace] || {};\r\n const newDataForKind = allData[namespace];\r\n const mergedData = {...oldDataForKind, ...newDataForKind};\r\n return Object.keys(mergedData)\r\n .filter((key: string) => this.isUpdated(oldDataForKind && oldDataForKind[key], newDataForKind && newDataForKind[key]));\r\n });\r\n updatedKeys.length > 0 && this.onChange(updatedKeys);\r\n }\r\n });\r\n callback?.();\r\n };\r\n\r\n if (checkForChanges) {\r\n const [flags, version] = this.store.all(DataKinds.Flags);\r\n const oldData = {\r\n flags,\r\n version\r\n };\r\n doInit(oldData);\r\n } else {\r\n doInit();\r\n }\r\n }\r\n\r\n upsert(userKeyId: string, kind: IDataKind, data: IKeyedStoreItem, callback: () => void): void {\r\n if (userKeyId !== this.store.user.keyId) {\r\n callback?.();\r\n return;\r\n }\r\n\r\n const {key} = data;\r\n const checkForChanges = this.hasEventListeners();\r\n const doUpsert = async (oldItem?: IStoreItem) => {\r\n await this.store.upsert(kind, data);\r\n Promise.resolve().then(() => {\r\n if (checkForChanges && this.isUpdated(oldItem, data[key])) {\r\n this.onChange([key]);\r\n }\r\n });\r\n\r\n callback?.();\r\n };\r\n if (checkForChanges) {\r\n const item = this.store.get(kind, key);\r\n doUpsert(item || undefined);\r\n } else {\r\n doUpsert();\r\n }\r\n }\r\n\r\n private isUpdated(oldData?: IStoreItem, newData?: IStoreItem): boolean {\r\n return !oldData || !newData || newData.version > oldData.version\r\n }\r\n}","import { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport { VoidFunction } from \"../utils/VoidFunction\";\r\nimport {\r\n deserializeAll,\r\n deserializePatch,\r\n IPatchData,\r\n Flags\r\n} from \"../store/serialization\";\r\nimport DataKinds from \"../store/DataKinds\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\nimport { EventName, ProcessStreamResponse } from \"../data-sync/types\";\r\n\r\nexport const createPutListener = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onPutCompleteHandler: VoidFunction = () => {\r\n },\r\n) => ({\r\n deserializeData: deserializeAll,\r\n processJson: async (userKeyId: string, {flags}: Flags) => {\r\n const initData: IStoreDataStorage = {\r\n flags: flags,\r\n version: 0\r\n };\r\n\r\n logger?.debug('Initializing all data');\r\n dataSourceUpdates.init(userKeyId, initData, onPutCompleteHandler);\r\n },\r\n});\r\n\r\nexport const createPatchListener = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onPatchCompleteHandler: VoidFunction = () => {\r\n },\r\n) => ({\r\n deserializeData: deserializePatch,\r\n processJson: async (userKeyId: string, data: IPatchData[]) => {\r\n if (data?.length === 0) {\r\n onPatchCompleteHandler?.();\r\n return;\r\n }\r\n\r\n data?.forEach(item => {\r\n logger?.debug(`Updating ${ item.data.key } in ${ item.kind.namespace }`);\r\n dataSourceUpdates.upsert(userKeyId, item.kind, item.data, onPatchCompleteHandler);\r\n })\r\n },\r\n});\r\n\r\n\r\nexport const createStreamListeners = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onCompleteHandlers?: {\r\n put?: VoidFunction;\r\n patch?: VoidFunction;\r\n delete?: VoidFunction;\r\n },\r\n) => {\r\n const listeners = new Map();\r\n listeners.set('put', createPutListener(dataSourceUpdates, logger, onCompleteHandlers?.put));\r\n listeners.set('patch', createPatchListener(dataSourceUpdates, logger, onCompleteHandlers?.patch));\r\n return listeners;\r\n};\r\n","export * from './createStreamListeners';\r\nexport * from './DataSourceUpdates';","export enum DataSyncModeEnum {\r\n POLLING = 'polling',\r\n STREAMING = 'streaming'\r\n}","import { IDataSynchronizer } from \"./IDataSynchronizer\";\r\n\r\nexport class NullDataSynchronizer implements IDataSynchronizer {\r\n close(): void {\r\n }\r\n\r\n start(): void {\r\n }\r\n\r\n stop(): void {\r\n }\r\n\r\n identify(): void {\r\n }\r\n}","import { isHttpRecoverable, PollingError } from \"../errors\";\r\nimport { IDataSynchronizer } from \"./IDataSynchronizer\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport Configuration from \"../Configuration\";\r\nimport { EventName, PollingErrorHandler, ProcessStreamResponse, StreamResponseEventType } from \"./types\";\r\nimport Requestor from \"./Requestor\";\r\nimport { httpErrorMessage } from \"../utils/http\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\nexport default class PollingDataSynchronizer implements IDataSynchronizer {\r\n private stopped = false;\r\n\r\n private logger?: ILogger;\r\n\r\n private pollingInterval: number;\r\n\r\n private user: IUser | undefined;\r\n\r\n private timeoutHandle: any;\r\n\r\n constructor(\r\n config: Configuration,\r\n private readonly requestor: Requestor,\r\n private readonly getStoreTimestamp: () => number,\r\n private readonly listeners: Map,\r\n private readonly errorHandler?: PollingErrorHandler,\r\n ) {\r\n this.logger = config.logger;\r\n this.pollingInterval = config.pollingInterval;\r\n this.user = config.user;\r\n }\r\n\r\n private poll() {\r\n if (this.stopped) {\r\n return;\r\n }\r\n\r\n const startTime = Date.now();\r\n this.logger?.debug('Polling for feature flag and segments updates');\r\n this.requestor.requestData(this.getStoreTimestamp(), this.user, (err, body) => {\r\n const elapsed = Date.now() - startTime;\r\n const sleepFor = Math.max(this.pollingInterval - elapsed, 0);\r\n\r\n this.logger?.debug('Elapsed: %d ms, sleeping for %d ms', elapsed, sleepFor);\r\n if (err) {\r\n const {status} = err;\r\n if (status && !isHttpRecoverable(status)) {\r\n const message = httpErrorMessage(err, 'polling request');\r\n this.logger?.error(message);\r\n this.errorHandler?.(new PollingError(message, status));\r\n // It is not recoverable, return and do not trigger another\r\n // poll.\r\n return;\r\n }\r\n this.logger?.warn(httpErrorMessage(err, 'polling request', 'will retry'));\r\n } else {\r\n let featureFlags = [];\r\n let userKeyId = this.user?.keyId!;\r\n let processStreamResponse: ProcessStreamResponse | undefined = this.listeners.get('patch');\r\n\r\n if (body) {\r\n const message = JSON.parse(body);\r\n if (message.messageType === 'data-sync') {\r\n switch (message.data.eventType) {\r\n case StreamResponseEventType.patch:\r\n processStreamResponse = this.listeners.get('patch');\r\n break;\r\n case StreamResponseEventType.full:\r\n processStreamResponse = this.listeners.get('put');\r\n break;\r\n }\r\n\r\n ({featureFlags, userKeyId} = message.data);\r\n }\r\n }\r\n\r\n const data = processStreamResponse?.deserializeData?.(featureFlags);\r\n processStreamResponse?.processJson?.(userKeyId, data);\r\n }\r\n\r\n // Falling through, there was some type of error and we need to trigger\r\n // a new poll.\r\n this.timeoutHandle = setTimeout(() => {\r\n this.poll();\r\n }, sleepFor);\r\n });\r\n }\r\n\r\n identify(user: IUser) {\r\n this.user = {...user};\r\n }\r\n\r\n close(): void {\r\n this.stop();\r\n }\r\n\r\n start(): void {\r\n this.poll();\r\n }\r\n\r\n stop(): void {\r\n if (this.timeoutHandle) {\r\n clearTimeout(this.timeoutHandle);\r\n this.timeoutHandle = undefined;\r\n }\r\n this.stopped = true;\r\n }\r\n}\r\n\r\n\r\n\r\n","import { IRequestor } from \"./IRequestor\";\r\nimport Configuration from \"../Configuration\";\r\nimport { IInfo } from \"../platform/IInfo\";\r\nimport { IRequestOptions, IRequests, IResponse } from \"../platform/requests\";\r\nimport { StreamingError } from \"../errors\";\r\nimport { defaultHeaders } from \"../utils/http\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class Requestor implements IRequestor {\r\n private readonly headers: Record;\r\n\r\n private readonly uri: string;\r\n\r\n constructor(\r\n sdkKey: string,\r\n config: Configuration,\r\n info: IInfo,\r\n private readonly requests: IRequests,\r\n ) {\r\n this.headers = defaultHeaders(sdkKey, info);\r\n this.uri = config.pollingUri;\r\n }\r\n\r\n /**\r\n * Perform a request and utilize the ETag cache. The ETags are cached in the\r\n * requestor instance.\r\n */\r\n private async request(\r\n requestUrl: string,\r\n options: IRequestOptions,\r\n ): Promise<{\r\n res: IResponse;\r\n body: string;\r\n }> {\r\n const res = await this.requests.fetch(requestUrl, options);\r\n\r\n const body = await res.text();\r\n\r\n return {res, body};\r\n }\r\n\r\n async requestData(timestamp: number, payload: any, cb: (err: any, body: any) => void) {\r\n const options: IRequestOptions = {\r\n method: 'POST',\r\n headers: this.headers,\r\n body: JSON.stringify(payload)\r\n };\r\n try {\r\n const {res, body} = await this.request(`${ this.uri }?timestamp=${ timestamp ?? 0 }`, options);\r\n if (res.status !== 200 && res.status !== 304) {\r\n const err = new StreamingError(`Unexpected status code: ${ res.status }`, res.status);\r\n return cb(err, undefined);\r\n }\r\n return cb(undefined, res.status === 304 ? null : body);\r\n } catch (err) {\r\n return cb(err, undefined);\r\n }\r\n }\r\n}\r\n","import { IDataSynchronizer } from \"./IDataSynchronizer\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { EventName, ProcessStreamResponse } from \"./types\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport { IWebSocketWithEvents } from \"../platform/IWebSocket\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\nclass WebSocketDataSynchronizer implements IDataSynchronizer {\r\n private socket?: IWebSocketWithEvents;\r\n private readonly logger?: ILogger;\r\n\r\n private connectionAttemptStartTime?: number;\r\n\r\n constructor(\r\n sdkKey: string,\r\n user: IUser,\r\n clientContext: ClientContext,\r\n socket: IWebSocketWithEvents,\r\n private readonly getStoreTimestamp: () => number,\r\n private readonly listeners: Map,\r\n webSocketPingInterval: number\r\n ) {\r\n const {logger, streamingUri} = clientContext;\r\n\r\n this.logger = logger;\r\n this.socket = socket;\r\n this.socket.config({\r\n sdkKey,\r\n streamingUri,\r\n pingInterval: webSocketPingInterval,\r\n user,\r\n logger,\r\n getStoreTimestamp\r\n });\r\n\r\n this.listeners.forEach(({deserializeData, processJson}, eventName) => {\r\n this.socket?.addListener(eventName, (event) => {\r\n this.logger?.debug(`Received ${ eventName } event`);\r\n\r\n if (event?.data) {\r\n const {featureFlags, userKeyId} = event.data;\r\n const data = deserializeData(featureFlags);\r\n processJson(userKeyId, data);\r\n }\r\n });\r\n })\r\n }\r\n\r\n identify(user: IUser): void {\r\n this.socket?.identify(user);\r\n }\r\n\r\n start(): void {\r\n this.logConnectionStarted();\r\n\r\n this.socket?.connect();\r\n }\r\n\r\n private logConnectionStarted() {\r\n this.connectionAttemptStartTime = Date.now();\r\n this.logger?.info(`Stream connection attempt StartTime ${ this.connectionAttemptStartTime }`);\r\n }\r\n\r\n close(): void {\r\n this.stop();\r\n }\r\n\r\n stop(): void {\r\n this.socket?.close();\r\n this.socket = undefined;\r\n }\r\n}\r\n\r\nexport default WebSocketDataSynchronizer;","export * from './DataSyncMode';\r\nexport * from './IDataSynchronizer';\r\nexport * from './IRequestor';\r\nexport * from './NullDataSynchronizer';\r\nexport * from './PollingDataSynchronizer';\r\nexport * from './Requestor';\r\nexport * from './types';\r\nexport * from './utils';\r\nexport * from './WebSocketDataSynchronizer';","import { PollingError } from \"../errors\";\r\nimport { IFlag } from \"../evaluation/data/IFlag\";\r\n\r\nexport type PollingErrorHandler = (err: PollingError) => void;\r\n\r\nexport enum StreamResponseEventType {\r\n full = 'full',\r\n patch = 'patch'\r\n}\r\n\r\nexport interface IStreamResponse {\r\n eventType: StreamResponseEventType,\r\n featureFlags: IFlag[]\r\n}\r\n\r\nexport type EventName = 'delete' | 'patch' | 'ping' | 'put';\r\nexport type ProcessStreamResponse = {\r\n deserializeData: (flags: IFlag[]) => any;\r\n processJson: (userKeyId: string, json: any) => void;\r\n};","/********************** encode text begin *****************************/\r\nconst alphabet: Record = {\r\n \"0\": \"Q\",\r\n \"1\": \"B\",\r\n \"2\": \"W\",\r\n \"3\": \"S\",\r\n \"4\": \"P\",\r\n \"5\": \"H\",\r\n \"6\": \"D\",\r\n \"7\": \"X\",\r\n \"8\": \"Z\",\r\n \"9\": \"U\",\r\n}\r\n\r\nfunction encodeNumber(param: number, length: number): string {\r\n var s = \"000000000000\" + param;\r\n const numberWithLeadingZeros = s.slice(s.length - length);\r\n return numberWithLeadingZeros.split('').map(n => alphabet[n]).join('');\r\n}\r\n\r\n// generate connection token\r\nexport function generateConnectionToken(text: string): string {\r\n text = text.replace(/=*$/, '');\r\n const timestamp = Date.now();\r\n const timestampCode = encodeNumber(timestamp, timestamp.toString().length);\r\n // get random number less than the length of the text as the start point, and it must be greater or equal to 2\r\n const start = Math.max(Math.floor(Math.random() * text.length), 2);\r\n\r\n return `${ encodeNumber(start, 3) }${ encodeNumber(timestampCode.length, 2) }${ text.slice(0, start) }${ timestampCode }${ text.slice(start) }`;\r\n}\r\n\r\n/********************** encode text end *****************************/","export class PollingError extends Error {\r\n public readonly status?: number;\r\n\r\n constructor(message: string, status?: number) {\r\n super(message);\r\n this.status = status;\r\n this.name = 'FbPollingError';\r\n }\r\n}\r\n\r\nexport class StreamingError extends Error {\r\n public readonly code?: number;\r\n\r\n constructor(message: string, code?: number) {\r\n super(message);\r\n this.code = code;\r\n this.name = 'FbStreamingError';\r\n }\r\n}\r\n\r\nexport class UnexpectedResponseError extends Error {\r\n constructor(message: string) {\r\n super(message);\r\n this.name = 'FbUnexpectedResponseError';\r\n }\r\n}\r\n\r\n\r\nexport class ClientError extends Error {\r\n constructor(message: string) {\r\n super(message);\r\n this.name = 'FbClientError';\r\n }\r\n}\r\n\r\nexport function isHttpRecoverable(status: number) {\r\n if (status >= 400 && status < 500) {\r\n return status === 400 || status === 408 || status === 429;\r\n }\r\n return true;\r\n}","import { ReasonKinds } from \"./ReasonKinds\";\r\nimport { IFlag } from \"./data/IFlag\";\r\nimport { EvalEvent } from \"../events/event\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\n/**\r\n * A class which encapsulates the result of an evaluation. It allows for differentiating between\r\n * successful and error result types.\r\n *\r\n * @internal\r\n */\r\nexport default class EvalResult {\r\n protected constructor(\r\n public kind: ReasonKinds,\r\n public value: IFlag | null,\r\n public reason?: string,\r\n ) {\r\n }\r\n\r\n static flagNotFound(flagKey: string) {\r\n return new EvalResult(ReasonKinds.FlagNotFound, null, `flag not found: ${ flagKey }`);\r\n }\r\n\r\n static matched(val: IFlag) {\r\n return new EvalResult(ReasonKinds.Match, val, 'target match');\r\n }\r\n\r\n toEvalEvent(user: IUser): EvalEvent | null {\r\n if (this.kind !== ReasonKinds.Match) {\r\n return null;\r\n }\r\n\r\n const targetedVariation = this.value?.variations.find(v => v.value === this.value?.variation);\r\n return new EvalEvent(user, this.value?.id!, targetedVariation!, this.value?.sendToExperiment!);\r\n }\r\n}","import { IFlag } from \"./data/IFlag\";\r\nimport EvalResult from \"./EvalResult\";\r\nimport { IStore } from \"../platform/IStore\";\r\nimport DataKinds from \"../store/DataKinds\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class Evaluator {\r\n constructor(private store: IStore) {\r\n }\r\n\r\n /**\r\n * Evaluate the given flag against the given context.\r\n * @param flagKey The key of the feature flag.\r\n */\r\n evaluate(\r\n flagKey: string,\r\n ): EvalResult {\r\n const flag = this.store.get(DataKinds.Flags, flagKey) as unknown as IFlag;\r\n if (!flag) {\r\n return EvalResult.flagNotFound(flagKey);\r\n }\r\n\r\n return EvalResult.matched(flag);\r\n }\r\n}","/**\r\n * Different kinds of error which may be encountered during evaluation.\r\n */\r\nexport enum ReasonKinds {\r\n ClientNotReady = 'ClientNotReady',\r\n Match = 'Match',\r\n WrongType = 'WrongType',\r\n FlagNotFound = 'FlagNotFound',\r\n Error = 'Error'\r\n}","export type FlagValue = any;\r\n\r\nexport enum VariationDataType {\r\n string = 'string',\r\n boolean = 'boolean',\r\n number = 'number',\r\n json = 'json',\r\n empty = ''\r\n}\r\n\r\nexport interface IVariation {\r\n id: number,\r\n value: FlagValue\r\n}\r\n\r\nexport interface IFlagBase {\r\n id: string, // the key\r\n variation: FlagValue,\r\n variationType: VariationDataType,\r\n sendToExperiment?: boolean,\r\n timestamp?: number,\r\n variationOptions?: IVariation[],\r\n}\r\n\r\nexport interface IFlag extends IFlagBase {\r\n key: string, // the same value to id\r\n variations: IVariation[],// the same value to variationOptions\r\n version: number\r\n}\r\n","export * from './IFlag';","export * from './data';\r\nexport * from './EvalResult';\r\nexport * from './Evaluator';\r\nexport * from './IEvalDetail';\r\nexport * from './ReasonKinds';","import { IEventProcessor } from \"./IEventProcessor\";\r\nimport { EventDispatcher } from \"./EventDispatcher\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { FlushEvent, IEvent, ShutdownEvent } from \"./event\";\r\nimport { isNullOrUndefined } from \"../utils/isNullOrUndefined\";\r\nimport { IEventQueue } from \"./IEventQueue\";\r\nimport { DefaultEventQueue } from \"./DefaultEventQueue\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\n\r\nexport class DefaultEventProcessor implements IEventProcessor {\r\n private readonly logger: ILogger;\r\n private readonly flushInterval: number;\r\n private readonly eventDispatcher: EventDispatcher;\r\n private readonly eventQueue: IEventQueue;\r\n private closed: boolean = false;\r\n\r\n constructor(clientContext: ClientContext) {\r\n const {logger, flushInterval, maxEventsInQueue} = clientContext;\r\n this.logger = logger!;\r\n this.flushInterval = flushInterval;\r\n this.eventQueue = new DefaultEventQueue(maxEventsInQueue, this.logger);\r\n this.eventDispatcher = new EventDispatcher(clientContext, this.eventQueue);\r\n\r\n this.flushLoop();\r\n }\r\n\r\n private flushLoop() {\r\n if (this.closed) {\r\n return;\r\n }\r\n\r\n setTimeout(async () => {\r\n try {\r\n await this.flush();\r\n } catch (err) {\r\n this.logger.error('Unexpected error while flushing events in event processor.', err);\r\n }\r\n\r\n this.flushLoop();\r\n }, this.flushInterval);\r\n }\r\n\r\n flush(): Promise {\r\n const flushEvent = new FlushEvent();\r\n this.record(flushEvent);\r\n return flushEvent.waitForCompletion();\r\n }\r\n\r\n async close(): Promise {\r\n if (this.closed) {\r\n return;\r\n }\r\n\r\n // send a shutdown event to dispatcher\r\n const shutdown = new ShutdownEvent();\r\n this.record(shutdown);\r\n\r\n try {\r\n await shutdown.waitForCompletion();\r\n } catch (err) {\r\n this.logger.error('Event processor shutdown but not complete.');\r\n }\r\n\r\n // mark the event queue as complete for adding\r\n this.eventQueue.close();\r\n this.closed = true;\r\n }\r\n\r\n record(event: IEvent | null): boolean {\r\n if (isNullOrUndefined(event)) {\r\n return false;\r\n }\r\n\r\n if (!this.eventQueue.addEvent(event!)) {\r\n if (event instanceof FlushEvent) {\r\n event.complete();\r\n }\r\n\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n}","import { IEventQueue } from \"./IEventQueue\";\r\nimport { IEvent } from \"./event\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\n\r\nexport class DefaultEventQueue implements IEventQueue {\r\n private events: IEvent[];\r\n private closed: boolean = false;\r\n\r\n constructor(private readonly capacity: number, private readonly logger: ILogger) {\r\n this.events = [];\r\n }\r\n\r\n addEvent(event: IEvent): boolean {\r\n if (this.closed) {\r\n return false;\r\n }\r\n\r\n if (this.events.length >= this.capacity) {\r\n this.logger.warn(\"Events are being produced faster than they can be processed. We shouldn't see this.\");\r\n return false;\r\n }\r\n\r\n this.events.push(event);\r\n return true;\r\n }\r\n\r\n clear(): void {\r\n this.events = [];\r\n }\r\n\r\n shift(): IEvent | undefined {\r\n return this.events.shift();\r\n }\r\n\r\n close(): void {\r\n this.closed = true;\r\n }\r\n\r\n get eventsSnapshot(): IEvent[] {\r\n return [...this.events];\r\n }\r\n\r\n get length(): number {\r\n return this.events.length;\r\n }\r\n\r\n get isEmpty(): boolean {\r\n return this.length === 0;\r\n }\r\n}","import { DeliveryStatus, IEventSender, IEventSenderResult } from \"./IEventSender\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { defaultHeaders, httpErrorMessage } from \"../utils/http\";\r\nimport { IRequests } from \"../platform/requests\";\r\nimport { isHttpRecoverable, UnexpectedResponseError } from \"../errors\";\r\nimport sleep from \"../utils/sleep\";\r\n\r\nexport class DefaultEventSender implements IEventSender {\r\n private readonly defaultHeaders: {\r\n [key: string]: string;\r\n };\r\n private readonly eventsUri: string;\r\n private requests: IRequests;\r\n\r\n constructor(clientContext: ClientContext) {\r\n const {\r\n sdkKey,\r\n eventsUri,\r\n platform\r\n } = clientContext;\r\n\r\n const {info, requests} = platform;\r\n this.defaultHeaders = defaultHeaders(sdkKey, info);\r\n this.eventsUri = eventsUri;\r\n this.requests = requests;\r\n }\r\n\r\n async send(payload: string, retry: boolean): Promise {\r\n const res: IEventSenderResult = {\r\n status: DeliveryStatus.Succeeded,\r\n };\r\n\r\n const headers: Record = {\r\n ...this.defaultHeaders,\r\n 'content-type': 'application/json',\r\n }\r\n\r\n let error;\r\n try {\r\n const {status} = await this.requests.fetch(this.eventsUri, {\r\n headers,\r\n body: payload,\r\n method: 'POST',\r\n });\r\n\r\n if (status >= 200 && status <= 299) {\r\n return res;\r\n }\r\n\r\n error = new UnexpectedResponseError(\r\n httpErrorMessage({status, message: 'some events were dropped'}, 'event posting'),\r\n );\r\n\r\n if (!isHttpRecoverable(status)) {\r\n res.status = DeliveryStatus.FailedAndMustShutDown;\r\n res.error = error;\r\n return res;\r\n }\r\n } catch (err) {\r\n error = err;\r\n }\r\n\r\n // recoverable but not retrying\r\n if (error && !retry) {\r\n res.status = DeliveryStatus.Failed;\r\n res.error = error;\r\n return res;\r\n }\r\n\r\n // wait 1 second before retrying\r\n await sleep();\r\n\r\n return this.send(payload, false);\r\n }\r\n}","import { IEventSerializer } from \"./EventSerializer\";\r\nimport { EvalEvent, IEvent, MetricEvent } from \"./event\";\r\n\r\nexport class DefaultEventSerializer implements IEventSerializer {\r\n serialize(events: IEvent[]): string {\r\n const payload = events\r\n .map(event => event instanceof EvalEvent || event instanceof MetricEvent ? event.toPayload() : null)\r\n .filter(event => event !== null);\r\n\r\n return JSON.stringify(payload);\r\n }\r\n}","import { ILogger } from \"../logging/ILogger\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { DeliveryStatus, IEventSender } from \"./IEventSender\";\r\nimport { IEventQueue } from \"./IEventQueue\";\r\nimport { DefaultEventQueue } from \"./DefaultEventQueue\";\r\nimport { DefaultEventSender } from \"./DefaultEventSender\";\r\nimport { AsyncEvent, FlushEvent, IEvent, PayloadEvent, ShutdownEvent } from \"./event\";\r\nimport { IEventSerializer } from \"./EventSerializer\";\r\nimport { DefaultEventSerializer } from \"./DefaultEventSerializer\";\r\nimport sleep from \"../utils/sleep\";\r\n\r\nexport class EventDispatcher {\r\n private readonly logger: ILogger;\r\n private sender: IEventSender;\r\n private buffer: IEventQueue;\r\n private serializer: IEventSerializer;\r\n\r\n private maxEventPerRequest = 50;\r\n private stopped: boolean = false;\r\n\r\n constructor(clientContext: ClientContext, queue: IEventQueue) {\r\n const {logger, maxEventsInQueue} = clientContext;\r\n this.logger = logger!;\r\n\r\n this.buffer = new DefaultEventQueue(maxEventsInQueue, this.logger);\r\n this.sender = new DefaultEventSender(clientContext);\r\n this.serializer = new DefaultEventSerializer();\r\n\r\n this.dispatchLoop(queue).then();\r\n }\r\n\r\n private async dispatchLoop(queue: IEventQueue) {\r\n this.logger.debug('Start dispatch loop.');\r\n\r\n let running = true;\r\n while (running) {\r\n try {\r\n const event = queue.shift();\r\n\r\n if (event === undefined) {\r\n await sleep(1000);\r\n continue;\r\n }\r\n\r\n if (event instanceof PayloadEvent) {\r\n this.addEventToBuffer(event);\r\n } else if (event instanceof FlushEvent) {\r\n await this.triggerFlush(event);\r\n } else if (event instanceof ShutdownEvent) {\r\n await this.triggerFlush(event);\r\n this.stopped = true;\r\n running = false;\r\n }\r\n } catch (err) {\r\n this.logger.error('Unexpected error in event dispatcher.', err);\r\n }\r\n }\r\n\r\n this.logger.debug('Finish dispatch loop.');\r\n }\r\n\r\n private addEventToBuffer(event: IEvent) {\r\n if (this.stopped) {\r\n return;\r\n }\r\n\r\n if (this.buffer.addEvent(event)) {\r\n this.logger.debug('Added event to buffer.');\r\n } else {\r\n this.logger.warn('Exceeded event queue capacity, event will be dropped. Increase capacity to avoid dropping events.');\r\n }\r\n }\r\n\r\n private async triggerFlush(event: AsyncEvent) {\r\n if (this.stopped) {\r\n event.complete();\r\n return;\r\n }\r\n\r\n if (this.buffer.isEmpty) {\r\n event.complete();\r\n this.logger.debug('Flush empty buffer.');\r\n // There are no events to flush. If we don't complete the message, then the async task may never\r\n // complete (if it had a non-zero positive timeout, then it would complete after the timeout).\r\n return;\r\n }\r\n\r\n const snapshot = this.buffer.eventsSnapshot;\r\n this.buffer.clear();\r\n try {\r\n await this.flushEvents(snapshot);\r\n this.logger.debug(`${ snapshot.length } events has been flushed.`);\r\n } catch (err) {\r\n this.logger.warn('Exception happened when flushing events', err);\r\n }\r\n\r\n event.complete();\r\n }\r\n\r\n private async flushEvents(events: IEvent[]) {\r\n events = this.getUniqueEvents(events);\r\n const total = events.length;\r\n for (let i = 0; i < total; i += this.maxEventPerRequest) {\r\n const length = Math.min(this.maxEventPerRequest, total - i);\r\n const slice = events.slice(i, i + length);\r\n const payload = this.serializer.serialize(slice);\r\n\r\n const {status} = await this.sender.send(payload, true);\r\n if (status === DeliveryStatus.FailedAndMustShutDown) {\r\n this.stopped = true;\r\n }\r\n }\r\n }\r\n\r\n private getUniqueEvents(events: IEvent[]): IEvent[] {\r\n const uniqueEvents: IEvent[] = [];\r\n const hashes: string[] = [];\r\n\r\n for (const event of events) {\r\n if (!hashes.includes(event.hash)) {\r\n uniqueEvents.push(event);\r\n hashes.push(event.hash);\r\n }\r\n }\r\n\r\n return uniqueEvents;\r\n }\r\n}","export enum DeliveryStatus {\r\n Succeeded,\r\n Failed,\r\n FailedAndMustShutDown\r\n}\r\n\r\nexport interface IEventSenderResult {\r\n status: DeliveryStatus,\r\n error?: any\r\n}\r\n\r\nexport interface IEventSender {\r\n send(payload: string, retry: boolean): Promise;\r\n}","import { IEventProcessor } from \"./IEventProcessor\";\r\nimport { IEvent } from \"./event\";\r\n\r\nexport class NullEventProcessor implements IEventProcessor {\r\n flush(): Promise {\r\n return Promise.resolve();\r\n }\r\n\r\n close(): Promise {\r\n return Promise.resolve();\r\n }\r\n\r\n record(event: IEvent | null): boolean {\r\n return false;\r\n }\r\n}","import { IUser } from \"../options/IUser\";\r\nimport { IVariation } from \"../evaluation/data/IFlag\";\r\n\r\nexport interface IEvent {\r\n hash: string;\r\n}\r\n\r\nexport class AsyncEvent implements IEvent {\r\n private readonly isCompletedPromise?: Promise;\r\n private resolveFn?: (value: AsyncEvent) => void;\r\n timestamp = (new Date()).getTime();\r\n\r\n get hash(): string {\r\n return this.timestamp.toString();\r\n }\r\n\r\n constructor() {\r\n this.isCompletedPromise = new Promise((resolve) => {\r\n this.resolveFn = resolve;\r\n });\r\n }\r\n\r\n waitForCompletion(): Promise {\r\n return this.isCompletedPromise!;\r\n }\r\n\r\n complete() {\r\n this.resolveFn?.(this);\r\n }\r\n}\r\n\r\nexport class FlushEvent extends AsyncEvent {\r\n}\r\n\r\nexport class ShutdownEvent extends AsyncEvent {\r\n}\r\n\r\nexport class PayloadEvent implements IEvent {\r\n timestamp = (new Date()).getTime();\r\n\r\n get hash(): string {\r\n return this.timestamp.toString();\r\n }\r\n\r\n toPayload(): any {\r\n };\r\n}\r\n\r\nexport class MetricEvent extends PayloadEvent {\r\n constructor(\r\n public user: IUser,\r\n public eventName: string,\r\n public appType: string,\r\n public metricValue: number\r\n ) {\r\n super();\r\n }\r\n\r\n private userPayload() {\r\n return {\r\n keyId: this.user.keyId,\r\n name: this.user.name,\r\n customizedProperties: this.user.customizedProperties\r\n }\r\n }\r\n\r\n toPayload(): any {\r\n return {\r\n user: this.userPayload(),\r\n metrics: [{\r\n route: 'index/metric',\r\n timestamp: this.timestamp,\r\n numericValue: this.metricValue,\r\n appType: this.appType,\r\n eventName: this.eventName,\r\n type: 'CustomEvent'\r\n }]\r\n }\r\n }\r\n\r\n get hash(): string {\r\n const payload = this.toPayload();\r\n const hasObject = {\r\n user: payload.user,\r\n metrics: payload.metrics.map((m: any) => ({...m, timestamp: undefined}))\r\n }\r\n return JSON.stringify(hasObject);\r\n }\r\n}\r\n\r\nexport class EvalEvent extends PayloadEvent {\r\n constructor(\r\n public user: IUser,\r\n public flagKey: string,\r\n public variation: IVariation,\r\n public sendToExperiment: boolean\r\n ) {\r\n super();\r\n }\r\n\r\n private userPayload() {\r\n return {\r\n keyId: this.user.keyId,\r\n name: this.user.name,\r\n customizedProperties: this.user.customizedProperties\r\n }\r\n }\r\n\r\n toPayload(): any {\r\n return {\r\n user: this.userPayload(),\r\n variations: [{\r\n featureFlagKey: this.flagKey,\r\n sendToExperiment: this.sendToExperiment,\r\n timestamp: this.timestamp,\r\n variation: this.variation\r\n }]\r\n }\r\n }\r\n\r\n get hash(): string {\r\n const payload = this.toPayload();\r\n const hasObject = {\r\n user: payload.user,\r\n variations: payload.variations.map((m: any) => ({...m, timestamp: undefined}))\r\n }\r\n\r\n return JSON.stringify(hasObject);\r\n }\r\n}","export * from './DefaultEventProcessor';\r\nexport * from './DefaultEventQueue';\r\nexport * from './DefaultEventSender';\r\nexport * from './DefaultEventSerializer';\r\nexport * from './event';\r\nexport * from './EventDispatcher';\r\nexport * from './EventSerializer';\r\nexport * from './IEventProcessor';\r\nexport * from './IEventQueue';\r\nexport * from './IEventSender';\r\nexport * from './NullEventProcessor';\r\n","export * from './bootstrap';\r\nexport * from './data-sources';\r\nexport * from './evaluation';\r\nexport * from './events';\r\nexport * from './logging';\r\nexport * from './options';\r\nexport * from './platform';\r\nexport * from './store';\r\nexport * from './data-sync';\r\nexport * from './utils';\r\n\r\nexport * from './Configuration';\r\nexport * from './constants';\r\nexport * from './Context';\r\nexport * from './errors';\r\nexport * from './FbClientBuilder';\r\nexport * from './IContextProperty';\r\nexport * from './IDataKind';\r\nexport * from './IFbClient';\r\nexport * from './IVersionedData';\r\nexport * from './FbClientCore';\r\n\r\n","import format from './format';\r\nimport { ILogger } from \"./ILogger\";\r\nimport { IBasicLoggerOptions } from \"./IBasicLoggerOptions\";\r\n\r\nconst LogPriority = {\r\n debug: 0,\r\n info: 1,\r\n warn: 2,\r\n error: 3,\r\n none: 4,\r\n};\r\n\r\nconst LevelNames = ['debug', 'info', 'warn', 'error', 'none'];\r\n\r\n/**\r\n * A basic logger which handles filtering by level.\r\n *\r\n * With the default options it will write to `console.error`\r\n * and it will use the formatting provided by `console.error`.\r\n * If the destination is overwritten, then it will use an included\r\n * formatter similar to `util.format`.\r\n *\r\n * If a formatter is available, then that should be overridden\r\n * as well for performance.\r\n */\r\nexport class BasicLogger implements ILogger {\r\n private logLevel: number;\r\n\r\n private name: string;\r\n\r\n private destination?: (line: string) => void;\r\n\r\n private formatter?: (...args: any[]) => string;\r\n\r\n /**\r\n * This should only be used as a default fallback and not as a convenient\r\n * solution. In most cases you should construct a new instance with the\r\n * appropriate options for your specific needs.\r\n */\r\n static get() {\r\n return new BasicLogger({});\r\n }\r\n\r\n constructor(options: IBasicLoggerOptions) {\r\n this.logLevel = LogPriority[options.level ?? 'info'] ?? LogPriority.info;\r\n this.name = options.name ?? 'FeatBit';\r\n // eslint-disable-next-line no-console\r\n this.destination = options.destination;\r\n this.formatter = options.formatter;\r\n }\r\n\r\n private tryFormat(...args: any[]): string {\r\n try {\r\n if (this.formatter) {\r\n // In case the provided formatter fails.\r\n return this.formatter?.(...args);\r\n }\r\n return format(...args);\r\n } catch {\r\n return format(...args);\r\n }\r\n }\r\n\r\n private tryWrite(msg: string) {\r\n try {\r\n this.destination!(msg);\r\n } catch {\r\n // eslint-disable-next-line no-console\r\n console.error(msg);\r\n }\r\n }\r\n\r\n private log(level: number, args: any[]) {\r\n if (level >= this.logLevel) {\r\n const prefix = `${ LevelNames[level] }: [${ this.name }]`;\r\n try {\r\n if (this.destination) {\r\n this.tryWrite(`${ prefix } ${ this.tryFormat(...args) }`);\r\n } else {\r\n // `console.error` has its own formatter.\r\n // So we don't need to do anything.\r\n // eslint-disable-next-line no-console\r\n console.error(...args);\r\n }\r\n } catch {\r\n // If all else fails do not break.\r\n // eslint-disable-next-line no-console\r\n console.error(...args);\r\n }\r\n }\r\n }\r\n\r\n error(...args: any[]): void {\r\n this.log(LogPriority.error, args);\r\n }\r\n\r\n warn(...args: any[]): void {\r\n this.log(LogPriority.warn, args);\r\n }\r\n\r\n info(...args: any[]): void {\r\n this.log(LogPriority.info, args);\r\n }\r\n\r\n debug(...args: any[]): void {\r\n this.log(LogPriority.debug, args);\r\n }\r\n}\r\n","import { ILogger } from \"./ILogger\";\r\nimport { TypeValidators } from \"../options/Validators\";\r\n\r\nconst loggerRequirements = {\r\n error: TypeValidators.Function,\r\n warn: TypeValidators.Function,\r\n info: TypeValidators.Function,\r\n debug: TypeValidators.Function,\r\n};\r\n\r\n/**\r\n * The safeLogger logic exists because we allow the application to pass in a custom logger, but\r\n * there is no guarantee that the logger works correctly and if it ever throws exceptions there\r\n * could be serious consequences (e.g. an uncaught exception within an error event handler, due\r\n * to the SDK trying to log the error, can terminate the application). An exception could result\r\n * from faulty logic in the logger implementation, or it could be that this is not a logger at\r\n * all but some other kind of object; the former is handled by a catch block that logs an error\r\n * message to the SDK's default logger, and we can at least partly guard against the latter by\r\n * checking for the presence of required methods at configuration time.\r\n */\r\nexport class SafeLogger implements ILogger {\r\n private logger: ILogger;\r\n\r\n private fallback: ILogger;\r\n\r\n /**\r\n * Construct a safe logger with the specified logger.\r\n * @param logger The logger to use.\r\n * @param fallback A fallback logger to use in case an issue is encountered using\r\n * the provided logger.\r\n */\r\n constructor(logger: ILogger, fallback: ILogger) {\r\n Object.entries(loggerRequirements).forEach(([level, validator]) => {\r\n if (!validator.is((logger as any)[level])) {\r\n throw new Error(`Provided logger instance must support logger.${ level }(...) method`);\r\n // Note that the SDK normally does not throw exceptions to the application, but that rule\r\n // does not apply to FbClientNode.init() which will throw an exception if the parameters are so\r\n // invalid that we cannot proceed with creating the client. An invalid logger meets those\r\n // criteria since the SDK calls the logger during nearly all of its operations.\r\n }\r\n });\r\n this.logger = logger;\r\n this.fallback = fallback;\r\n }\r\n\r\n private log(level: 'error' | 'warn' | 'info' | 'debug', args: any[]) {\r\n try {\r\n this.logger[level](...args);\r\n } catch {\r\n // If all else fails do not break.\r\n this.fallback[level](...args);\r\n }\r\n }\r\n\r\n error(...args: any[]): void {\r\n this.log('error', args);\r\n }\r\n\r\n warn(...args: any[]): void {\r\n this.log('warn', args);\r\n }\r\n\r\n info(...args: any[]): void {\r\n this.log('info', args);\r\n }\r\n\r\n debug(...args: any[]): void {\r\n this.log('debug', args);\r\n }\r\n}","import { TypeValidators } from \"../options/Validators\";\r\n\r\n\r\n/**\r\n * Attempt to produce a string representation of a value.\r\n * The format should be roughly comparable to `util.format`\r\n * aside from object which will be JSON versus the `util.inspect`\r\n * format.\r\n * @param val\r\n * @returns A string representation of the value if possible.\r\n */\r\nfunction tryStringify(val: any) {\r\n if (typeof val === 'string') {\r\n return val;\r\n }\r\n if (val === undefined) {\r\n return 'undefined';\r\n }\r\n if (val === null) {\r\n return 'null';\r\n }\r\n if (Object.prototype.hasOwnProperty.call(val, 'toString')) {\r\n try {\r\n return val.toString();\r\n } catch {\r\n /* Keep going */\r\n }\r\n }\r\n\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n try {\r\n return JSON.stringify(val);\r\n } catch (error) {\r\n if (error instanceof TypeError && error.message.indexOf('circular') >= 0) {\r\n return '[Circular]';\r\n }\r\n return '[Not Stringifiable]';\r\n }\r\n}\r\n\r\n/**\r\n * Attempt to produce a numeric representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The numeric representation or 'NaN' if not numeric.\r\n */\r\nfunction toNumber(val: any): string {\r\n // Symbol has to be treated special because it will\r\n // throw an exception if an attempt is made to convert it.\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n return String(Number(val));\r\n}\r\n\r\n/**\r\n * Attempt to produce an integer representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The integer representation or 'NaN' if not numeric.\r\n */\r\nfunction toInt(val: any): string {\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n return String(parseInt(val, 10));\r\n}\r\n\r\n/**\r\n * Attempt to produce a float representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The integer representation or 'NaN' if not numeric.\r\n */\r\nfunction toFloat(val: any): string {\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n return String(parseFloat(val));\r\n}\r\n\r\n// Based on:\r\n// https://nodejs.org/api/util.html#utilformatformat-args\r\n// The result will not match browser exactly, but it should get the\r\n// right information through.\r\nconst escapes: Record string> = {\r\n s: (val: any) => tryStringify(val),\r\n d: (val: any) => toNumber(val),\r\n i: (val: any) => toInt(val),\r\n f: (val: any) => toFloat(val),\r\n j: (val: any) => tryStringify(val),\r\n o: (val: any) => tryStringify(val),\r\n O: (val: any) => tryStringify(val),\r\n c: () => '',\r\n};\r\n\r\n/**\r\n * A basic formatted for use where `util.format` is not available.\r\n * This will not be as performant, but it will produce formatted\r\n * messages.\r\n *\r\n * @internal\r\n *\r\n * @param args\r\n * @returns Formatted string.\r\n */\r\nexport default function format(...args: any[]): string {\r\n const formatString = args.shift();\r\n if (TypeValidators.String.is(formatString)) {\r\n let out = '';\r\n let i = 0;\r\n while (i < formatString.length) {\r\n const char = formatString.charAt(i);\r\n if (char === '%') {\r\n const nextIndex = i + 1;\r\n if (nextIndex < formatString.length) {\r\n const nextChar = formatString.charAt(i + 1);\r\n if (nextChar in escapes && args.length) {\r\n const value = args.shift();\r\n // This rule is for math.\r\n // eslint-disable-next-line no-unsafe-optional-chaining\r\n out += escapes[nextChar]?.(value);\r\n } else if (nextChar === '%') {\r\n out += '%';\r\n } else {\r\n out += `%${ nextChar }`;\r\n }\r\n i += 2;\r\n }\r\n } else {\r\n out += char;\r\n i += 1;\r\n }\r\n }\r\n // If there are any args left after we exhaust the format string\r\n // then just stick those on the end.\r\n if (args.length) {\r\n if (out.length) {\r\n out += ' ';\r\n }\r\n out += args.map(tryStringify).join(' ');\r\n }\r\n return out;\r\n }\r\n return args.map(tryStringify).join(' ');\r\n}\r\n","export * from './BasicLogger';\r\nexport * from './format';\r\nexport * from './IBasicLoggerOptions';\r\nexport * from './ILogger';\r\nexport * from './LogLevel';\r\nexport * from './SafeLogger';","import { ILogger } from \"../logging/ILogger\";\r\nimport { IPlatform } from \"../platform/IPlatform\";\r\nimport { IClientContext } from \"./IClientContext\";\r\nimport { IUser } from \"./IUser\";\r\n\r\n/**\r\n * The client context provides basic configuration and platform support which are required\r\n * when building SDK components.\r\n */\r\nexport default class ClientContext implements IClientContext {\r\n flushInterval: number;\r\n maxEventsInQueue: number;\r\n offline: boolean;\r\n logger: ILogger;\r\n eventsUri: string;\r\n pollingUri: string;\r\n streamingUri: string;\r\n\r\n constructor(\r\n public readonly sdkKey: string,\r\n configuration: {\r\n logger?: ILogger;\r\n offline?: boolean;\r\n flushInterval: number;\r\n maxEventsInQueue: number;\r\n streamingUri: string;\r\n pollingUri: string;\r\n eventsUri: string;\r\n },\r\n public readonly platform: IPlatform,\r\n ) {\r\n this.logger = configuration.logger!;\r\n this.offline = configuration.offline!;\r\n this.flushInterval = configuration.flushInterval;\r\n this.maxEventsInQueue = configuration.maxEventsInQueue;\r\n this.streamingUri = configuration.streamingUri;\r\n this.pollingUri = configuration.pollingUri;\r\n this.eventsUri = configuration.eventsUri;\r\n }\r\n}","/**\r\n * Messages for issues which can be encountered from processing the configuration options.\r\n */\r\nexport default class OptionMessages {\r\n static optionBelowMinimum(name: string, value: number, min: number): string {\r\n return `Config option \"${ name }\" had invalid value of ${ value }, using minimum of ${ min } instead`;\r\n }\r\n\r\n static unknownOption(name: string): string {\r\n return `Ignoring unknown config option \"${ name }\"`;\r\n }\r\n\r\n static wrongOptionType(name: string, expectedType: string, actualType: string): string {\r\n return `Config option \"${ name }\" should be of type ${ expectedType }, got ${ actualType }, using default value`;\r\n }\r\n\r\n static wrongOptionTypeBoolean(name: string, actualType: string): string {\r\n return `Config option \"${ name }\" should be a boolean, got ${ actualType }, converting to boolean`;\r\n }\r\n\r\n static partialEndpoint(name: string): string {\r\n return `You have set custom uris without specifying the ${ name } URI; connections may not work properly`;\r\n }\r\n\r\n static mandatory(name: string): string {\r\n return `${ name } is mandatory`;\r\n }\r\n\r\n static invalidOptionValue(name: string): string {\r\n return `Invalid option value: ${ name }`;\r\n }\r\n\r\n static missingKeyInBootstrapValue(key: string): string {\r\n return `Missing key \"${ key }\" in bootstrap value`;\r\n }\r\n}","import { IUser } from \"./IUser\";\r\nimport {IContextProperty} from \"../IContextProperty\";\r\n\r\n/**\r\n * Creates an instance of the FeatBit user.\r\n *\r\n * @return\r\n * The new {@link IUser} instance.\r\n */\r\nexport class UserBuilder {\r\n private _keyId: string = '';\r\n private _name: string = '';\r\n private _custom: IContextProperty[] = [];\r\n\r\n constructor(keyId: string) {\r\n this._keyId = keyId;\r\n }\r\n\r\n name(name: string): UserBuilder {\r\n this._name = name;\r\n return this;\r\n }\r\n\r\n custom(propertyName: string, value: string): UserBuilder {\r\n this._custom?.push({ name: propertyName, value: value });\r\n return this;\r\n }\r\n\r\n build(): IUser {\r\n return {\r\n name: this._name,\r\n keyId: this._keyId,\r\n customizedProperties: this._custom\r\n };\r\n }\r\n}","/* eslint-disable class-methods-use-this */\r\n/* eslint-disable max-classes-per-file */\r\n\r\n// The classes here are static, but needs to be instantiated to\r\n// support the generic functionality. Which is why we do not care about using\r\n// `this`\r\n\r\n// These validators are also of trivial complexity, so we are allowing more than\r\n// one per file.\r\n\r\nimport OptionMessages from \"./OptionMessages\";\r\nimport { IFlagBase } from \"../evaluation\";\r\n\r\n/**\r\n * Interface for type validation.\r\n */\r\nexport interface TypeValidator {\r\n // holding validation error messages\r\n messages?: string[];\r\n\r\n is(u: unknown): boolean;\r\n\r\n getType(): string;\r\n}\r\n\r\n/**\r\n * Validate a factory or instance.\r\n */\r\nexport class FactoryOrInstance implements TypeValidator {\r\n is(factoryOrInstance: unknown) {\r\n if (Array.isArray(factoryOrInstance)) {\r\n return false;\r\n }\r\n const anyFactory = factoryOrInstance as any;\r\n const typeOfFactory = typeof anyFactory;\r\n return typeOfFactory === 'function' || typeOfFactory === 'object';\r\n }\r\n\r\n getType(): string {\r\n return 'factory method or object';\r\n }\r\n}\r\n\r\n/**\r\n * Validate a basic type.\r\n */\r\nexport class Type implements TypeValidator {\r\n private typeName: string;\r\n\r\n protected typeOf: string;\r\n\r\n constructor(typeName: string, example: T) {\r\n this.typeName = typeName;\r\n this.typeOf = typeof example;\r\n }\r\n\r\n is(u: unknown): u is T {\r\n if (Array.isArray(u)) {\r\n return false;\r\n }\r\n return typeof u === this.typeOf;\r\n }\r\n\r\n getType(): string {\r\n return this.typeName;\r\n }\r\n}\r\n\r\n/**\r\n * Validate an array of the specified type.\r\n *\r\n * This does not validate instances of types. All class instances\r\n * of classes will simply objects.\r\n */\r\nexport class TypeArray implements TypeValidator {\r\n private typeName: string;\r\n\r\n protected typeOf: string;\r\n\r\n constructor(typeName: string, example: T) {\r\n this.typeName = typeName;\r\n this.typeOf = typeof example;\r\n }\r\n\r\n is(u: unknown): u is T {\r\n if (Array.isArray(u)) {\r\n if (u.length > 0) {\r\n return u.every((val) => typeof val === this.typeOf);\r\n }\r\n return true;\r\n }\r\n return false;\r\n }\r\n\r\n getType(): string {\r\n return this.typeName;\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a number and is greater or eval than a minimum.\r\n */\r\nexport class NumberWithMinimum extends Type {\r\n readonly min: number;\r\n\r\n constructor(min: number) {\r\n super(`number with minimum value of ${ min }`, 0);\r\n this.min = min;\r\n }\r\n\r\n override is(u: unknown): u is number {\r\n return typeof u === this.typeOf && (u as number) >= this.min;\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a string and it matches the given expression.\r\n */\r\nexport class StringMatchingRegex extends Type {\r\n readonly expression: RegExp;\r\n\r\n constructor(expression: RegExp) {\r\n super(`string matching ${ expression }`, '');\r\n this.expression = expression;\r\n }\r\n\r\n override is(u: unknown): u is string {\r\n return !!(u as string).match(this.expression);\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a function.\r\n */\r\nexport class Function implements TypeValidator {\r\n is(u: unknown): u is (...args: any[]) => void {\r\n // We cannot inspect the parameters and there isn't really\r\n // a generic function type we can instantiate.\r\n // So the type guard is here just to make TS comfortable\r\n // calling something after using this guard.\r\n return typeof u === 'function';\r\n }\r\n\r\n getType(): string {\r\n return 'function';\r\n }\r\n}\r\n\r\nexport class NullableBoolean implements TypeValidator {\r\n is(u: unknown): boolean {\r\n return typeof u === 'boolean' || typeof u === 'undefined' || u === null;\r\n }\r\n\r\n getType(): string {\r\n return 'boolean | undefined | null';\r\n }\r\n}\r\n\r\nexport class BootstrapValidator implements TypeValidator {\r\n messages: string[] = [];\r\n\r\n is(u: unknown): boolean {\r\n if (typeof u !== 'object' || u === null) {\r\n this.messages.push(OptionMessages.invalidOptionValue('bootstrap'));\r\n return false;\r\n }\r\n\r\n try {\r\n const bootstrap = u as IFlagBase[];\r\n for (let flag of bootstrap) {\r\n const hasMandatoryKeys = ['id', 'variation'].every((key) => Object.keys(flag).includes(key));\r\n const keys = Object.keys(flag);\r\n\r\n if (keys.includes('id')) {\r\n this.messages.push(OptionMessages.missingKeyInBootstrapValue('id'));\r\n }\r\n\r\n if (keys.includes('variation')) {\r\n this.messages.push(OptionMessages.missingKeyInBootstrapValue('variation'));\r\n }\r\n\r\n if (this.messages.length > 0) {\r\n return false;\r\n }\r\n }\r\n } catch (_) {\r\n this.messages.push(OptionMessages.wrongOptionType('bootstrap', this.getType(), typeof u));\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n\r\n getType(): string {\r\n return 'IFlagBase[]';\r\n }\r\n}\r\n\r\nexport class UserValidator implements TypeValidator {\r\n messages: string[] = [];\r\n\r\n is(u: unknown): boolean {\r\n if (typeof u !== 'object' || u === null) {\r\n this.messages.push(OptionMessages.mandatory('user'));\r\n return false;\r\n }\r\n\r\n const user = u as any;\r\n\r\n if (typeof user.keyId !== 'string' || user.keyId.trim() === '') {\r\n this.messages.push(OptionMessages.mandatory('user.keyId'));\r\n return false;\r\n }\r\n\r\n if (typeof user.name !== 'string' || user.name.trim() === '') {\r\n this.messages.push(OptionMessages.mandatory('user.name'));\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n\r\n getType(): string {\r\n return 'user';\r\n }\r\n}\r\n\r\n// Our reference SDK, Go, parses date/time strings with the time.RFC3339Nano format.\r\n// This regex should match strings that are valid in that format, and no others.\r\n// Acceptable:\r\n// 2019-10-31T23:59:59Z, 2019-10-31T23:59:59.100Z,\r\n// 2019-10-31T23:59:59-07, 2019-10-31T23:59:59-07:00, etc.\r\n// Unacceptable: no \"T\", no time zone designation\r\nconst DATE_REGEX = /^\\d\\d\\d\\d-\\d\\d-\\d\\dT\\d\\d:\\d\\d:\\d\\d(\\.\\d\\d*)?(Z|[-+]\\d\\d(:\\d\\d)?)/;\r\n\r\n/**\r\n * Validate a value is a date. Values which are numbers are treated as dates and any string\r\n * which if compliant with `time.RFC3339Nano` is a date.\r\n */\r\nexport class DateValidator implements TypeValidator {\r\n is(u: unknown): boolean {\r\n return typeof u === 'number' || (typeof u === 'string' && DATE_REGEX.test(u));\r\n }\r\n\r\n getType(): string {\r\n return 'date';\r\n }\r\n}\r\n\r\n/**\r\n * Validates that a string is a valid kind.\r\n */\r\nexport class KindValidator extends StringMatchingRegex {\r\n constructor() {\r\n super(/^(\\w|\\.|-)+$/);\r\n }\r\n\r\n override is(u: unknown): u is string {\r\n return super.is(u) && u !== 'kind';\r\n }\r\n}\r\n\r\n/**\r\n * A set of standard type validators.\r\n */\r\nexport class TypeValidators {\r\n static readonly String = new Type('string', '');\r\n\r\n static readonly Number = new Type('number', 0);\r\n\r\n static readonly ObjectOrFactory = new FactoryOrInstance();\r\n\r\n static readonly Object = new Type('object', {});\r\n\r\n static readonly StringArray = new TypeArray('string[]', '');\r\n\r\n static readonly Boolean = new Type('boolean', true);\r\n\r\n static readonly User = new Type('object', {});\r\n\r\n static readonly Bootstrap = new Type('object', {});\r\n\r\n static readonly Function = new Function();\r\n\r\n static createTypeArray(typeName: string, example: T) {\r\n return new TypeArray(typeName, example);\r\n }\r\n\r\n static numberWithMin(min: number): NumberWithMinimum {\r\n return new NumberWithMinimum(min);\r\n }\r\n\r\n static stringMatchingRegex(expression: RegExp): StringMatchingRegex {\r\n return new StringMatchingRegex(expression);\r\n }\r\n\r\n static readonly Date = new DateValidator();\r\n\r\n static readonly Kind = new KindValidator();\r\n static readonly NullableBoolean = new NullableBoolean();\r\n}","export * from './ClientContext';\r\nexport * from './IClientContext';\r\nexport * from './IOptions';\r\nexport * from './IUser';\r\nexport * from './IValidatedOptions';\r\nexport * from './OptionMessages';\r\nexport * from './UserBuilder';\r\nexport * from './Validators';","import { IInfo, IPlatformData, ISdkData } from \"../IInfo\";\r\nimport { name, version } from '../../version';\r\n\r\n\r\nexport default class BrowserInfo implements IInfo {\r\n get appType(): string {\r\n return 'Browser-Client-SDK';\r\n }\r\n\r\n platformData(): IPlatformData {\r\n return {\r\n os: {},\r\n name: 'Browser',\r\n additional: {},\r\n };\r\n }\r\n\r\n sdkData(): ISdkData {\r\n return {\r\n name: name,\r\n version: version,\r\n userAgentBase: this.appType\r\n };\r\n }\r\n}","import { IPlatform } from \"../IPlatform\";\r\nimport { IInfo } from \"../IInfo\";\r\nimport { IRequests } from \"../requests\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport BrowserInfo from \"./BrowserInfo\";\r\nimport { BrowserRequests } from \"./BrowserRequests\";\r\nimport { IWebSocketWithEvents } from \"../IWebSocket\";\r\nimport BrowserWebSocket from \"./BrowserWebSocket\";\r\n\r\nexport default class BrowserPlatform implements IPlatform {\r\n info: IInfo = new BrowserInfo();\r\n\r\n requests: IRequests;\r\n webSocket: IWebSocketWithEvents;\r\n\r\n constructor(options: IOptions) {\r\n this.requests = new BrowserRequests();\r\n this.webSocket = new BrowserWebSocket();\r\n }\r\n}","import { IRequestOptions, IRequests } from \"../requests\";\r\n\r\nexport class BrowserRequests implements IRequests {\r\n fetch(url: string, options: IRequestOptions = {}): Promise {\r\n return fetch(url, options);\r\n }\r\n}","import { IWebSocket, IWebSocketConfig } from \"../IWebSocket\";\r\nimport { Emits } from \"../../utils/Emits\";\r\nimport { IEventEmitter } from \"../../utils/IEventEmitter\";\r\nimport { EventEmitter } from \"../../utils/EventEmitter\";\r\nimport { generateConnectionToken } from \"../../data-sync/utils\";\r\nimport { StreamResponseEventType } from \"../../data-sync/types\";\r\nimport { IUser } from \"../../options/IUser\";\r\n\r\nconst socketConnectionIntervals = [1000, 3000, 5000, 7000, 11000, 13000, 30000, 60000];\r\n\r\nclass BrowserWebSocket implements IWebSocket {\r\n emitter: IEventEmitter;\r\n private ws?: WebSocket;\r\n private retryCounter = 0;\r\n private closed: boolean = false;\r\n\r\n private _config: IWebSocketConfig = {} as IWebSocketConfig;\r\n\r\n constructor() {\r\n this.emitter = new EventEmitter();\r\n }\r\n\r\n identify(user: IUser) {\r\n this._config.user = user;\r\n this.doDataSync();\r\n }\r\n\r\n connect() {\r\n let that = this;\r\n const startTime = Date.now();\r\n const url = this._config.streamingUri.replace(/^http/, 'ws') + `?type=client&token=${ generateConnectionToken(this._config.sdkKey) }`;\r\n this.ws = new WebSocket(url);\r\n\r\n // Connection opened\r\n that.ws?.addEventListener('open', function (this: WebSocket, event) {\r\n // this is the websocket instance to which the current listener is binded to, it's different from that.socket\r\n that._config.logger.info(`WebSocket connection succeeded, connection time: ${ Date.now() - startTime } ms`);\r\n that.doDataSync();\r\n that.sendPingMessage();\r\n });\r\n\r\n // Connection closed\r\n that.ws?.addEventListener('close', function (event) {\r\n that._config.logger.warn('WebSocket closed');\r\n if (event.code === 4003) { // do not reconnect when 4003\r\n return;\r\n }\r\n\r\n that.reconnect();\r\n });\r\n\r\n // Connection error\r\n that.ws?.addEventListener('error', function (event) {\r\n // reconnect\r\n that._config.logger.debug('error');\r\n });\r\n\r\n // Listen for messages\r\n that.ws?.addEventListener('message', function (event) {\r\n const message = JSON.parse(event.data as string);\r\n if (message.messageType === 'data-sync') {\r\n switch (message.data.eventType) {\r\n case StreamResponseEventType.patch:\r\n that.emitter.emit('patch', message);\r\n break;\r\n case StreamResponseEventType.full:\r\n that.emitter.emit('put', message);\r\n break;\r\n }\r\n }\r\n });\r\n }\r\n\r\n close() {\r\n this.closed = true;\r\n this.ws?.close(4003, 'The client is closed by user');\r\n this.ws = undefined;\r\n }\r\n\r\n config(param: IWebSocketConfig) {\r\n if (param.emitter) {\r\n this.emitter = param.emitter;\r\n }\r\n\r\n this._config = {...param};\r\n }\r\n\r\n private sendPingMessage() {\r\n const payload = {\r\n messageType: 'ping',\r\n data: null\r\n };\r\n\r\n setTimeout(() => {\r\n try {\r\n if (this.ws?.readyState === WebSocket.OPEN) {\r\n this._config.logger.debug('sending ping')\r\n this.ws.send(JSON.stringify(payload));\r\n this.sendPingMessage();\r\n } else {\r\n this._config.logger.debug(`socket closed at ${ new Date() }`);\r\n }\r\n } catch (err) {\r\n this._config.logger.debug(err);\r\n }\r\n }, this._config.pingInterval);\r\n }\r\n\r\n private doDataSync() {\r\n const payload = {\r\n messageType: 'data-sync',\r\n data: {\r\n timestamp: this._config.getStoreTimestamp(),\r\n user: this._config.user\r\n }\r\n };\r\n\r\n try {\r\n if (this.ws?.readyState === WebSocket.OPEN) {\r\n this._config.logger.debug('requesting data');\r\n this.ws?.send(JSON.stringify(payload));\r\n } else {\r\n this._config.logger.error(`not requesting data because socket not open`);\r\n }\r\n } catch (err) {\r\n this._config.logger.debug(err);\r\n }\r\n }\r\n\r\n private reconnect() {\r\n if (!this.closed) {\r\n this.ws = undefined;\r\n const waitTime = socketConnectionIntervals[Math.min(this.retryCounter++, socketConnectionIntervals.length - 1)];\r\n this._config.logger.info(`The client will try to reconnect in ${ waitTime } milliseconds.`);\r\n setTimeout(() => {\r\n this._config.logger.info(`The client is trying to reconnect, flag evaluation results may be stale until reconnected, waited for: ${ waitTime } milliseconds`);\r\n this.connect();\r\n }, waitTime);\r\n }\r\n }\r\n}\r\n\r\nexport default Emits(BrowserWebSocket);","import { FbClientCore } from \"../../FbClientCore\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport { BasicLogger } from \"../../logging/BasicLogger\";\r\nimport { EventEmitter } from \"../../utils/EventEmitter\";\r\nimport { SafeLogger } from \"../../logging/SafeLogger\";\r\nimport { Emits } from \"../../utils/Emits\";\r\nimport { IEventEmitter } from \"../../utils/IEventEmitter\";\r\nimport BrowserPlatform from \"./BrowserPlatform\";\r\nimport LocalStorageStore from \"./LocalStorageStore\";\r\nimport { IPlatform } from \"../IPlatform\";\r\n\r\n/**\r\n * @ignore\r\n */\r\nclass FbClient extends FbClientCore {\r\n emitter: IEventEmitter;\r\n\r\n constructor(options: IOptions, platform: IPlatform | undefined = undefined) {\r\n const fallbackLogger = new BasicLogger({\r\n level: 'none',\r\n destination: console.log\r\n });\r\n\r\n const logger = options.logger ? new SafeLogger(options.logger, fallbackLogger) : fallbackLogger;\r\n\r\n const emitter = new EventEmitter(logger);\r\n\r\n let { store } = options;\r\n if (!store) {\r\n store = new LocalStorageStore(options);\r\n }\r\n\r\n super(\r\n {...options, logger, store },\r\n platform ?? new BrowserPlatform({...options, logger}),\r\n {\r\n onError: (err: Error) => {\r\n if (emitter.listenerCount('error')) {\r\n emitter.emit('error', err);\r\n }\r\n },\r\n onFailed: (err: Error) => {\r\n emitter.emit('failed', err);\r\n },\r\n onReady: () => {\r\n emitter.emit('ready');\r\n },\r\n onUpdate: (keys: string[]) => {\r\n emitter.emit('update', [keys]);\r\n keys.forEach((key) => emitter.emit(`update:${ key }`, key));\r\n },\r\n hasEventListeners: () =>\r\n emitter\r\n .eventNames()\r\n .some(\r\n (name) =>\r\n name === 'update' || (typeof name === 'string' && name.startsWith('update:')),\r\n ),\r\n },\r\n );\r\n\r\n this.emitter = emitter;\r\n }\r\n}\r\n\r\nexport default Emits(FbClient);","import {\r\n StoreStorageKey,\r\n IStoreDataStorage, CurrentUserStorageKey\r\n} from \"../../store/store\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport { BaseStore } from \"../../store/BaseStore\";\r\nimport { ILogger } from \"../../logging\";\r\nimport { serializeUser } from \"../../utils/serializeUser\";\r\n\r\nexport default class LocalStorageStore extends BaseStore {\r\n private logger: ILogger;\r\n\r\n constructor(options: IOptions) {\r\n super();\r\n\r\n this.logger = options.logger!;\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get description(): string {\r\n return 'local-storage-store'\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async saveUser(): Promise {\r\n localStorage.setItem(CurrentUserStorageKey, serializeUser(this._user));\r\n }\r\n\r\n protected override async dumpStoreToStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n localStorage.setItem(storageKey, JSON.stringify(this.store));\r\n }\r\n\r\n protected override async loadStoreFromStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n const dataStoreStr = localStorage.getItem(storageKey);\r\n let store: IStoreDataStorage | null = null;\r\n\r\n try {\r\n if (dataStoreStr && dataStoreStr.trim().length > 0) {\r\n store = JSON.parse(dataStoreStr);\r\n }\r\n } catch (err) {\r\n this.logger.error(`error while loading local data store: ${storageKey}`, err);\r\n }\r\n\r\n if (!!store) {\r\n this.store = store;\r\n } else {\r\n this.store = {\r\n flags: {},\r\n version: 0\r\n };\r\n }\r\n }\r\n}","export * from './IInfo';\r\nexport * from './IStore';\r\nexport * from './IPlatform';\r\nexport * from './IWebSocket';\r\nexport * from './requests';\r\nexport * from './browser/BrowserRequests';\r\n\r\nimport BrowserWebSocket from './browser/BrowserWebSocket';\r\n\r\nexport {\r\n BrowserWebSocket\r\n};","import { IStore } from \"../platform\";\r\nimport { IKeyedStoreItem, IStoreDataStorage, IStoreItem, IStoreKindData } from \"./store\";\r\nimport { IUser } from \"../options\";\r\nimport { IDataKind } from \"../IDataKind\";\r\n\r\nexport class BaseStore implements IStore {\r\n protected store: IStoreDataStorage = {} as IStoreDataStorage;\r\n\r\n protected initCalled = false;\r\n\r\n protected _user: IUser = {} as IUser;\r\n\r\n constructor() {\r\n }\r\n\r\n async identify(user: IUser) {\r\n this._user = {...user};\r\n\r\n await this.saveUser();\r\n await this.loadStoreFromStorage();\r\n }\r\n\r\n get user(): IUser {\r\n return this._user;\r\n }\r\n\r\n protected async addItem(kind: IDataKind, key: string, item: IStoreItem) {\r\n let items = this.store[kind.namespace];\r\n if (!items) {\r\n items = {};\r\n this.store[kind.namespace] = items;\r\n }\r\n if (Object.hasOwnProperty.call(items, key)) {\r\n const old = items[key];\r\n if (!old || old.version < item.version) {\r\n items[key] = item;\r\n }\r\n } else {\r\n items[key] = item;\r\n }\r\n\r\n if (item.version > this.store.version) {\r\n this.store.version = item.version;\r\n }\r\n\r\n await this.dumpStoreToStorage();\r\n }\r\n\r\n get(kind: IDataKind, key: string): IStoreItem | null {\r\n const items = this.store[kind.namespace];\r\n if (items) {\r\n if (Object.prototype.hasOwnProperty.call(items, key)) {\r\n const item = items[key];\r\n if (item) {\r\n return item;\r\n }\r\n }\r\n }\r\n return null;\r\n }\r\n\r\n all(kind: IDataKind): [IStoreKindData, number] {\r\n const result: IStoreKindData = {};\r\n const items = this.store[kind.namespace] ?? {};\r\n Object.entries(items).forEach(([key, item]) => {\r\n if (item) {\r\n result[key] = item;\r\n }\r\n });\r\n\r\n return [result, this.store.version];\r\n }\r\n\r\n async init(allData: IStoreDataStorage) {\r\n this.store = allData as IStoreDataStorage;\r\n\r\n Object.keys(allData).map(namespace => {\r\n Object.entries(allData[namespace]).forEach(([_, item]) => {\r\n const ele = item as IStoreItem;\r\n if (ele.version > this.store.version) {\r\n this.store.version = ele.version;\r\n }\r\n })\r\n });\r\n\r\n await this.dumpStoreToStorage();\r\n this.initCalled = true;\r\n }\r\n\r\n async upsert(kind: IDataKind, data: IKeyedStoreItem) {\r\n await this.addItem(kind, data.key, data);\r\n }\r\n\r\n initialized(): boolean {\r\n return this.initCalled;\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get version(): number {\r\n return this.store.version;\r\n }\r\n\r\n // This getter needs to be overridden in the child class\r\n get description(): string {\r\n return '';\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async saveUser(): Promise {\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async loadStoreFromStorage(): Promise {\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async dumpStoreToStorage(): Promise {\r\n }\r\n}","import { IDataKind } from \"../IDataKind\";\r\n\r\nexport default class DataKinds {\r\n static readonly Flags: IDataKind = {\r\n namespace: 'flags'\r\n };\r\n}","import {\r\n StoreStorageKey,\r\n IStoreDataStorage\r\n} from \"./store\";\r\nimport { BaseStore } from \"./BaseStore\";\r\n\r\nexport default class InMemoryStore extends BaseStore {\r\n private allStores: { [DataStoreStorageKey: string]: IStoreDataStorage } = {};\r\n\r\n constructor() {\r\n super();\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get description(): string {\r\n return 'in-memory-store'\r\n }\r\n\r\n protected async saveUser(): Promise {\r\n // For in-memory store, this is a no-op.\r\n }\r\n\r\n protected override async dumpStoreToStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n this.allStores[storageKey] = {...this.store};\r\n }\r\n\r\n protected override async loadStoreFromStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n\r\n this.store = this.allStores[storageKey] ?? { flags: {}, version: 0 };\r\n }\r\n}","export * from './DataKinds';\r\nexport * from './IDataSourceUpdates';\r\nexport * from './InMemoryStore';\r\nexport * from './serialization';\r\nexport * from './store';\r\nexport * from './BaseStore';","import { IFlag } from \"../evaluation/data/IFlag\";\r\nimport DataKinds from \"./DataKinds\";\r\nimport { IVersionedData } from \"../IVersionedData\";\r\nimport { IDataKind } from \"../IDataKind\";\r\n\r\nexport interface Flags {\r\n flags: { [name: string]: IFlag };\r\n}\r\n\r\ntype VersionedFlag = IVersionedData & IFlag;\r\n\r\nexport interface IPatchData {\r\n data: VersionedFlag;\r\n kind: IDataKind;\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport function deserializeAll(flags: IFlag[]): Flags {\r\n const result = {\r\n [DataKinds.Flags.namespace]: {}\r\n };\r\n\r\n if (flags?.length) {\r\n result[DataKinds.Flags.namespace] = flags.reduce((acc: any, cur: any) => {\r\n acc[cur.id] = {...cur, version: cur.timestamp || 0, key: cur.id, variations: cur.variationOptions};\r\n return acc;\r\n }, {});\r\n }\r\n\r\n return result as any as Flags;\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport function deserializePatch(flags: IFlag[]): IPatchData[] {\r\n const result = [\r\n ...flags?.map(item => ({\r\n data: {\r\n ...item,\r\n version:item.timestamp,\r\n key: item.id,\r\n variations: item.variationOptions\r\n },\r\n kind: DataKinds.Flags\r\n })) || []\r\n ];\r\n\r\n return result as any as IPatchData[];\r\n}\r\n","export const StoreStorageKey = 'fb-datastore';\r\n\r\nexport const CurrentUserStorageKey = 'fb-user';\r\n\r\n/**\r\n * Represents an item which can be stored in the feature store.\r\n */\r\nexport interface IStoreItem {\r\n version: number;\r\n\r\n // The actual data associated with the item.\r\n [attribute: string]: any;\r\n}\r\n\r\n/**\r\n * When upserting an item it must contain a key.\r\n */\r\nexport interface IKeyedStoreItem extends IStoreItem {\r\n key: string;\r\n}\r\n\r\n/**\r\n * Represents the storage for a single kind of data. e.g. 'flag' or 'segment'.\r\n */\r\nexport interface IStoreKindData {\r\n [key: string]: IStoreItem;\r\n}\r\n\r\n/**\r\n * Represents the storage for the full data store.\r\n */\r\nexport interface IStoreDataStorage {\r\n flags: IStoreKindData;\r\n version: number;\r\n\r\n // This attribute is to ingore the type check error\r\n [attribute: string]: any;\r\n}","import { IEventEmitter } from \"./IEventEmitter\";\r\n\r\nexport type EventableConstructor = new (...args: any[]) => T;\r\nexport type Eventable = EventableConstructor<{ emitter: IEventEmitter }>;\r\n\r\n/**\r\n * Adds the implementation of an event emitter to something that contains\r\n * a field of `emitter` with type `EventEmitter`.\r\n * @param Base The class to derive the mixin from.\r\n * @returns A class extending the base with an event emitter.\r\n */\r\nexport function Emits(Base: TBase) {\r\n return class WithEvents extends Base implements IEventEmitter {\r\n on(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.on(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n addListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.addListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n once(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.once(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n removeListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.removeListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n off(eventName: string | symbol, listener: (...args: any) => void, context?: any): this {\r\n this.emitter.off(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n removeAllListeners(event?: string | symbol): this {\r\n this.emitter.removeAllListeners(event);\r\n return this;\r\n }\r\n\r\n listeners(eventName: string | symbol): Function[] {\r\n return this.emitter.listeners(eventName);\r\n }\r\n\r\n emit(eventName: string | symbol, ...args: any[]): this {\r\n this.emitter.emit(eventName, args);\r\n return this;\r\n }\r\n\r\n listenerCount(eventName: string | symbol): number {\r\n return this.emitter.listenerCount(eventName);\r\n }\r\n\r\n prependListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.prependListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n prependOnceListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.prependOnceListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n eventNames(): (string | symbol)[] {\r\n return this.emitter.eventNames();\r\n }\r\n\r\n maybeReportError (error: any): this {\r\n this.emitter.maybeReportError(error);\r\n return this;\r\n }\r\n };\r\n}","import { ILogger } from \"../logging/ILogger\";\r\nimport { IEventEmitter } from \"./IEventEmitter\";\r\n\r\ninterface Events {\r\n [key: string | symbol]: {\r\n handler: (...args: any[]) => void;\r\n context: any;\r\n }[];\r\n}\r\n\r\nexport class EventEmitter implements IEventEmitter {\r\n private events: Events = {};\r\n\r\n constructor(private logger?: ILogger) {}\r\n\r\n private listeningTo (event: string) {\r\n return !!this.events[event];\r\n }\r\n\r\n on (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n this.events[event] = this.events[event] || [];\r\n this.events[event] = this.events[event].concat({\r\n handler: handler,\r\n context: context,\r\n });\r\n\r\n return this;\r\n }\r\n\r\n addListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n return this.on(event, handler, context);\r\n }\r\n\r\n once (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n const onceHandler = (...args: any[]) => {\r\n this.off(event, onceHandler, context);\r\n handler.apply(context, args);\r\n };\r\n return this.on(event, onceHandler, context);\r\n }\r\n\r\n off (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n if (!this.events[event]) {\r\n return this;\r\n }\r\n for (let i = 0; i < this.events[event].length; i++) {\r\n if (this.events[event][i].handler === handler && this.events[event][i].context === context) {\r\n this.events[event] = this.events[event].slice(0, i).concat(this.events[event].slice(i + 1));\r\n }\r\n }\r\n\r\n return this;\r\n }\r\n\r\n removeListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n return this.off(event, handler, context);\r\n }\r\n\r\n removeAllListeners (event?: string | symbol): this {\r\n if (event) {\r\n delete this.events[event];\r\n } else {\r\n this.events = {};\r\n }\r\n\r\n return this;\r\n }\r\n\r\n listeners (event: string | symbol): Function[] {\r\n return this.events[event] ? this.events[event].map((event) => event.handler) : [];\r\n }\r\n\r\n emit (event: string | symbol, ...args: any[]): this {\r\n if (!this.events[event]) {\r\n return this;\r\n }\r\n // Copy the list of handlers before iterating, in case any handler adds or removes another handler.\r\n // Any such changes should not affect what we do here-- we want to notify every handler that existed\r\n // at the moment that the event was fired.\r\n const copiedHandlers = [...this.events[event]];\r\n for (let i = 0; i < copiedHandlers.length; i++) {\r\n copiedHandlers[i].handler.apply(copiedHandlers[i].context, Array.prototype.slice.call(arguments, 1));\r\n }\r\n\r\n return this;\r\n }\r\n\r\n listenerCount (event: string | symbol): number {\r\n return this.events[event] ? this.events[event].length : 0;\r\n }\r\n\r\n prependListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n this.events[event] = this.events[event] || [];\r\n this.events[event] = [\r\n {\r\n handler: handler,\r\n context: context,\r\n },\r\n ...this.events[event]\r\n ];\r\n\r\n return this;\r\n }\r\n\r\n prependOnceListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n const onceHandler = (...args: any[]) => {\r\n this.off(event, onceHandler, context);\r\n handler.apply(context, args);\r\n };\r\n return this.prependListener(event, onceHandler, context);\r\n }\r\n\r\n eventNames (): (string | symbol)[] {\r\n return Object.keys(this.events);\r\n }\r\n\r\n maybeReportError (error: any): this {\r\n if (!error) {\r\n return this;\r\n }\r\n if (this.listeningTo('error')) {\r\n this.emit('error', error);\r\n } else {\r\n this.logger?.error(error);\r\n }\r\n\r\n return this;\r\n }\r\n}","import { Regex } from \"./Regex\";\r\n\r\nexport interface IConvertResult {\r\n isSucceeded: boolean,\r\n value?: TValue\r\n}\r\n\r\nexport class ValueConverters {\r\n static bool(value: string): IConvertResult {\r\n if (value?.toUpperCase() === 'TRUE') {\r\n return ValueConverters.success(true);\r\n }\r\n\r\n if (value?.toUpperCase() === 'FALSE') {\r\n return ValueConverters.success(false);\r\n }\r\n\r\n return ValueConverters.error();\r\n }\r\n\r\n static number(value: string): IConvertResult {\r\n const num = Number(value);\r\n\r\n if (Number.isNaN(num)) {\r\n return ValueConverters.error();\r\n }\r\n\r\n return ValueConverters.success(num);\r\n }\r\n\r\n static string(value: string): IConvertResult {\r\n return ValueConverters.success(value);\r\n }\r\n\r\n static json(value: string): IConvertResult {\r\n try {\r\n const val = JSON.parse(value);\r\n return ValueConverters.success(val);\r\n } catch (err) {\r\n return ValueConverters.error();\r\n }\r\n }\r\n\r\n private static success(value: TValue): IConvertResult {\r\n return {\r\n isSucceeded: true,\r\n value: value\r\n }\r\n }\r\n\r\n private static error(): IConvertResult {\r\n return {\r\n isSucceeded: false\r\n }\r\n }\r\n}","// This function is designed to remove any trailing forward slashes at the end of the provided URI string\r\nexport function canonicalizeUri(uri: string): string {\r\n return uri.replace(/\\/+$/, '');\r\n}","/**\r\n * Wait before calling the same function. Useful for expensive calls.\r\n * Adapted from https://amitd.co/code/typescript/debounce.\r\n *\r\n * @return The debounced function.\r\n *\r\n * @example\r\n *\r\n * ```js\r\n * const debouncedFunction = debounce(e => {\r\n * console.log(e);\r\n * }, 5000);\r\n *\r\n * // Console logs 'Hello world again ' after 5 seconds\r\n * debouncedFunction('Hello world');\r\n * debouncedFunction('Hello world again');\r\n * ```\r\n * @param fn The function to be debounced.\r\n * @param delayMs Defaults to 5 seconds.\r\n */\r\nexport const debounce = ReturnType>(\r\n fn: T,\r\n delayMs: number = 5000,\r\n): ((...args: Parameters) => void) => {\r\n let timer: ReturnType;\r\n\r\n return (...args: Parameters) => {\r\n clearTimeout(timer);\r\n timer = setTimeout(() => {\r\n fn(...args);\r\n }, delayMs);\r\n };\r\n};\r\n","import { IInfo } from \"../platform/IInfo\";\r\n\r\nexport type Headers = {\r\n Authorization: string;\r\n 'User-Agent': string;\r\n 'Content-Type': string;\r\n};\r\n\r\nexport function defaultHeaders(\r\n sdkKey: string,\r\n info: IInfo\r\n): Headers {\r\n const {userAgentBase, version} = info.sdkData();\r\n\r\n const headers: Headers = {\r\n 'Content-Type': 'application/json',\r\n 'User-Agent': `${ userAgentBase ?? info.appType }/${ version }`,\r\n 'Authorization': sdkKey\r\n };\r\n\r\n return headers;\r\n}\r\n\r\nexport function httpErrorMessage(\r\n err: {\r\n status: number;\r\n message: string;\r\n },\r\n context: string,\r\n retryMessage?: string,\r\n): string {\r\n let desc;\r\n if (err.status) {\r\n desc = `error ${ err.status }${ err.status === 401 ? ' (invalid SDK key)' : '' }`;\r\n } else {\r\n desc = `I/O error (${ err.message || err })`;\r\n }\r\n const action = retryMessage ?? 'giving up permanently';\r\n return `Received ${ desc } for ${ context } - ${ action }`;\r\n}\r\n","export * from './isNullOrUndefined';\r\nexport * from './sleep';\r\nexport * from './ValueConverters';\r\nexport * from './VoidFunction';\r\nexport * from './serializeUser';\r\nexport * from './debounce';","export function isNullOrUndefined(val: any) {\r\n return val === null || val === undefined;\r\n}","import { IUser } from \"../options/IUser\";\r\n\r\nexport function serializeUser(user: IUser | undefined): string {\r\n if (!user) {\r\n return '';\r\n }\r\n\r\n const builtInProperties = `${user.keyId},${user.name}`;\r\n\r\n const customizedProperties = user.customizedProperties\r\n ?.sort((a, b) => {\r\n const nameA = a.name.toLowerCase();\r\n const nameB = b.name.toLowerCase();\r\n if (nameA < nameB) {\r\n return -1;\r\n }\r\n\r\n if (nameA > nameB) {\r\n return 1;\r\n }\r\n\r\n return 0;\r\n })\r\n .map(p => `${p.name}:${p.value}`)\r\n .join(',');\r\n\r\n return `${builtInProperties},${customizedProperties}`;\r\n}","const sleep = async (delayMillis: number = 1000) =>\r\n new Promise((resolve) => {\r\n setTimeout(resolve, delayMillis);\r\n });\r\n\r\nexport default sleep;","export const version = \"3.0.3\"; export const name = \"@featbit/js-client-sdk\";\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// startup\n// Load entry module and return exports\n// This entry module is referenced by other modules so it can't be inlined\nvar __webpack_exports__ = __webpack_require__(9872);\n"],"names":["root","factory","exports","module","define","amd","a","i","this","validations","startWaitTime","TypeValidators","Number","sdkKey","String","pollingUri","streamingUri","eventsUri","webSocketPingInterval","logger","Object","store","ObjectOrFactory","dataSynchronizer","flushInterval","maxEventsInQueue","pollingInterval","offline","Boolean","dataSyncMode","bootstrap","Bootstrap","user","User","defaultValues","DataSyncModeEnum","STREAMING","sendEvents","options","undefined","constructor","bootstrapProvider","NullBootstrapProvider","errors","validatedOptions","keys","forEach","optionName","optionValue","validator","is","getType","push","wrongOptionTypeBoolean","NumberWithMinimum","min","optionBelowMinimum","UserValidator","messages","wrongOptionType","warn","unknownOption","validateTypesAndNames","error","streamingUriMissing","isNullOrUndefined","EmptyString","pollingUriMissing","eventsUriMissing","partialEndpoint","POLLING","validateEndpoints","canonicalizeUri","length","JsonBootstrapProvider","_","info","Function","dataSynchronizerFactory","storeFactory","Context","valid","message","fromUser","contextForError","keyId","name","trim","context","_user","value","property","customizedProperties","find","x","_options","build","platform","_platform","mode","flags","ClientState","callbacks","state","Initializing","onError","onFailed","onReady","onUpdate","hasEventListeners","config","Error","init","clientContext","identify","dataSourceUpdates","evaluator","populate","eventProcessor","NullEventProcessor","NullDataSynchronizer","initSuccess","DefaultEventProcessor","listeners","createStreamListeners","put","patch","webSocket","version","requests","e","dataSourceErrorHandler","start","all","Flags","setTimeout","initialized","msg","Failed","rejectionReason","initReject","Initialized","waitForInitialization","initializedPromise","Promise","resolve","reject","initResolve","boolVariation","key","defaultValue","evaluateCore","ValueConverters","bool","boolVariationDetail","jsonVariation","json","jsonVariationDetail","numberVariation","number","numberVariationDetail","stringVariation","string","stringVariationDetail","variation","variationDetail","getAllVariations","ClientError","result","map","flagKey","evalResult","evaluate","kind","reason","close","track","eventName","metricValue","metricEvent","MetricEvent","appType","record","flush","callback","err","typeConverter","ReasonKinds","FlagNotFound","toEvalEvent","isSucceeded","WrongType","code","flag","variationOptions","id","data","deserializeAll","dataSet","userKeyId","MinInt","onChange","allData","checkForChanges","doInit","oldData","then","updatedKeys","flatMap","namespace","oldDataForKind","newDataForKind","mergedData","filter","isUpdated","upsert","doUpsert","oldItem","get","newData","createPutListener","onPutCompleteHandler","deserializeData","processJson","initData","debug","createPatchListener","onPatchCompleteHandler","deserializePatch","item","onCompleteHandlers","Map","set","stop","requestor","getStoreTimestamp","errorHandler","stopped","poll","startTime","Date","now","requestData","body","elapsed","sleepFor","Math","max","status","isHttpRecoverable","httpErrorMessage","PollingError","featureFlags","processStreamResponse","JSON","parse","messageType","eventType","StreamResponseEventType","full","timeoutHandle","clearTimeout","headers","defaultHeaders","uri","request","requestUrl","res","fetch","text","timestamp","payload","cb","method","stringify","StreamingError","socket","pingInterval","addListener","event","logConnectionStarted","connect","connectionAttemptStartTime","alphabet","encodeNumber","param","s","slice","split","n","join","replace","timestampCode","toString","floor","random","super","UnexpectedResponseError","EvalResult","flagNotFound","matched","val","Match","targetedVariation","variations","v","EvalEvent","sendToExperiment","VariationDataType","closed","eventQueue","DefaultEventQueue","eventDispatcher","EventDispatcher","flushLoop","flushEvent","FlushEvent","waitForCompletion","shutdown","ShutdownEvent","addEvent","complete","capacity","events","clear","shift","eventsSnapshot","isEmpty","send","retry","DeliveryStatus","Succeeded","FailedAndMustShutDown","serialize","toPayload","queue","maxEventPerRequest","buffer","sender","DefaultEventSender","serializer","DefaultEventSerializer","dispatchLoop","running","PayloadEvent","addEventToBuffer","triggerFlush","snapshot","flushEvents","total","getUniqueEvents","uniqueEvents","hashes","includes","hash","AsyncEvent","getTime","isCompletedPromise","resolveFn","userPayload","metrics","route","numericValue","type","hasObject","m","featureFlagKey","LogPriority","none","LevelNames","BasicLogger","logLevel","level","destination","formatter","tryFormat","args","tryWrite","console","log","prefix","loggerRequirements","fallback","entries","tryStringify","prototype","hasOwnProperty","call","TypeError","indexOf","escapes","d","toNumber","parseInt","toInt","f","parseFloat","toFloat","j","o","O","c","formatString","out","char","charAt","nextChar","configuration","expectedType","actualType","mandatory","invalidOptionValue","missingKeyInBootstrapValue","_keyId","_name","_custom","custom","propertyName","FactoryOrInstance","factoryOrInstance","Array","isArray","typeOfFactory","Type","typeName","example","typeOf","u","TypeArray","every","StringMatchingRegex","expression","match","NullableBoolean","DATE_REGEX","DateValidator","test","KindValidator","createTypeArray","numberWithMin","stringMatchingRegex","StringArray","Kind","platformData","os","additional","sdkData","userAgentBase","BrowserRequests","url","socketConnectionIntervals","Emits","retryCounter","_config","emitter","EventEmitter","doDataSync","that","generateConnectionToken","ws","WebSocket","addEventListener","sendPingMessage","reconnect","emit","readyState","OPEN","waitTime","FbClient","FbClientCore","fallbackLogger","SafeLogger","listenerCount","eventNames","some","startsWith","LocalStorageStore","BaseStore","description","saveUser","localStorage","setItem","CurrentUserStorageKey","serializeUser","dumpStoreToStorage","storageKey","StoreStorageKey","loadStoreFromStorage","dataStoreStr","getItem","BrowserWebSocket","initCalled","addItem","items","old","ele","DataKinds","InMemoryStore","allStores","reduce","acc","cur","Base","on","listener","once","removeListener","off","removeAllListeners","prependListener","prependOnceListener","maybeReportError","listeningTo","handler","concat","onceHandler","apply","copiedHandlers","arguments","toUpperCase","success","num","isNaN","debounce","fn","delayMs","timer","retryMessage","desc","sort","b","nameA","toLowerCase","nameB","p","delayMillis","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__"],"sourceRoot":""} \ No newline at end of file diff --git a/examples/web-app/umd/featbit-js-client-sdk.js b/examples/web-app/umd/featbit-js-client-sdk.js index c7599a1..9a918ea 100644 --- a/examples/web-app/umd/featbit-js-client-sdk.js +++ b/examples/web-app/umd/featbit-js-client-sdk.js @@ -1,2 +1,2 @@ -!function(e,t){if("object"==typeof exports&&"object"==typeof module)module.exports=t();else if("function"==typeof define&&define.amd)define([],t);else{var i=t();for(var r in i)("object"==typeof exports?exports:e)[r]=i[r]}}(this,(()=>(()=>{"use strict";var e={1058:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.defaultValues=void 0;const n=i(5862),s=r(i(9176)),o=r(i(7783)),a=i(5562),l=i(1624),u=i(665),c=i(7837),d=i(607),h=i(8317),f={startWaitTime:n.TypeValidators.Number,sdkKey:n.TypeValidators.String,pollingUri:n.TypeValidators.String,streamingUri:n.TypeValidators.String,eventsUri:n.TypeValidators.String,webSocketPingInterval:n.TypeValidators.Number,logger:n.TypeValidators.Object,store:n.TypeValidators.ObjectOrFactory,dataSynchronizer:n.TypeValidators.ObjectOrFactory,flushInterval:n.TypeValidators.Number,maxEventsInQueue:n.TypeValidators.Number,pollingInterval:n.TypeValidators.Number,offline:n.TypeValidators.Boolean,dataSyncMode:n.TypeValidators.String,bootstrap:n.TypeValidators.Bootstrap,user:n.TypeValidators.User};t.defaultValues={startWaitTime:5e3,sdkKey:"",pollingUri:"",streamingUri:"",eventsUri:"",dataSyncMode:d.DataSyncModeEnum.STREAMING,sendEvents:!0,webSocketPingInterval:18e3,flushInterval:2e3,maxEventsInQueue:1e4,pollingInterval:3e4,offline:!1,store:e=>new o.default,bootstrap:void 0,user:void 0},t.default=class{constructor(e={}){var i,r;this.bootstrapProvider=new u.NullBootstrapProvider,e=e||{},this.logger=e.logger;const{errors:o,validatedOptions:v}=function(e){let i=[];const r=Object.assign({},t.defaultValues);return Object.keys(e).forEach((o=>{var a;const l=e[o],u=f[o];if(u)if(u.is(l))r[o]=l;else if("boolean"===u.getType())i.push(s.default.wrongOptionTypeBoolean(o,typeof l)),r[o]=!!l;else if(u instanceof n.NumberWithMinimum&&n.TypeValidators.Number.is(l)){const{min:e}=u;i.push(s.default.optionBelowMinimum(o,l,e)),r[o]=e}else u instanceof n.UserValidator?(i=[...i,...u.messages],r[o]=t.defaultValues[o]):(i.push(s.default.wrongOptionType(o,u.getType(),typeof l)),r[o]=t.defaultValues[o]);else null===(a=e.logger)||void 0===a||a.warn(s.default.unknownOption(o))})),{errors:i,validatedOptions:r}}(e);if(o.forEach((e=>{var t;null===(t=this.logger)||void 0===t||t.warn(e)})),this.user=e.user,function(e,t){var i,r,n;const{streamingUri:o,pollingUri:l,eventsUri:u}=e,h=(0,a.isNullOrUndefined)(o)||o===c.EmptyString,f=(0,a.isNullOrUndefined)(l)||l===c.EmptyString,v=(0,a.isNullOrUndefined)(u)||u===c.EmptyString;!t.offline&&(v||h&&f)&&(v&&(null===(i=t.logger)||void 0===i||i.error(s.default.partialEndpoint("eventsUri"))),t.dataSyncMode===d.DataSyncModeEnum.STREAMING&&h&&(null===(r=t.logger)||void 0===r||r.error(s.default.partialEndpoint("streamingUri"))),t.dataSyncMode===d.DataSyncModeEnum.POLLING&&f&&(null===(n=t.logger)||void 0===n||n.error(s.default.partialEndpoint("pollingUri"))))}(e,v),this.streamingUri=`${(0,l.canonicalizeUri)(v.streamingUri)}/streaming`,this.pollingUri=`${(0,l.canonicalizeUri)(v.pollingUri)}/api/public/sdk/client/latest-all`,this.eventsUri=`${(0,l.canonicalizeUri)(v.eventsUri)}/api/public/insight/track`,this.startWaitTime=v.startWaitTime,this.sdkKey=v.sdkKey,this.webSocketPingInterval=v.webSocketPingInterval,this.flushInterval=v.flushInterval,this.maxEventsInQueue=v.maxEventsInQueue,this.pollingInterval=v.pollingInterval,this.offline=v.offline,v.bootstrap&&v.bootstrap.length>0)try{this.bootstrapProvider=new h.JsonBootstrapProvider(v.bootstrap)}catch(e){null===(i=this.logger)||void 0===i||i.error("Failed to parse bootstrap JSON, use NullBootstrapProvider.")}this.offline&&(null===(r=this.logger)||void 0===r||r.info("Offline mode enabled. No data synchronization with the FeatBit server will occur.")),this.dataSyncMode=v.dataSyncMode,n.TypeValidators.Function.is(v.dataSynchronizer)?this.dataSynchronizerFactory=v.dataSynchronizer:this.dataSynchronizerFactory=()=>v.dataSynchronizer,n.TypeValidators.Function.is(v.store)?this.storeFactory=v.store:this.storeFactory=()=>v.store}}},1731:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0});class i{constructor(e,t){this.valid=e,this.message=t}static fromUser(e){if(!e)return i.contextForError("No user specified");const{keyId:t,name:r}=e;if(null==t||""===t.trim())return i.contextForError("key is mandatory");const n=new i(!0);return n._user=e,n}get user(){return this._user}get keyId(){return this._user.keyId}value(e){var t,i,r,n,s;return"keyId"===e?null===(t=this._user)||void 0===t?void 0:t.keyId:"name"===e?null===(i=this._user)||void 0===i?void 0:i.name:null===(s=null===(n=null===(r=this._user)||void 0===r?void 0:r.customizedProperties)||void 0===n?void 0:n.find((t=>t.name===e)))||void 0===s?void 0:s.value}static contextForError(e){return new i(!1,e)}}t.default=i},70:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.FbClientBuilder=void 0;const n=r(i(8322));t.FbClientBuilder=class{constructor(e){this._options=null!=e?e:{}}build(){return new n.default(this._options)}platform(e){return this._platform=e,this}startWaitTime(e){return this._options.startWaitTime=e,this}sdkKey(e){return this._options.sdkKey=e,this}user(e){return this._options.user=e,this}streamingUri(e){return this._options.streamingUri=e,this}pollingUri(e){return this._options.pollingUri=e,this}eventsUri(e){return this._options.eventsUri=e,this}dataSyncMode(e){return this._options.dataSyncMode=e,this}pollingInterval(e){return this._options.pollingInterval=e,this}flushInterval(e){return this._options.flushInterval=e,this}maxEventsInQueue(e){return this._options.maxEventsInQueue=e,this}logger(e){return this._options.logger=e,this}offline(e){return this._options.offline=e,this}bootstrap(e){return this._options.bootstrap=e,this}dataSynchronizer(e){return this._options.dataSynchronizer=e,this}}},4129:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.FbClientCore=void 0;const s=n(i(1058)),o=n(i(8311)),a=n(i(4659)),l=i(7539),u=n(i(6100)),c=n(i(3148)),d=n(i(4943)),h=n(i(2093)),f=n(i(8874)),v=i(5192),p=i(7449),g=n(i(1731)),y=i(1142),m=i(8722),_=i(407),b=i(2305),O=i(7584),w=i(607),P=i(5862);var S;!function(e){e[e.Initializing=0]="Initializing",e[e.Initialized=1]="Initialized",e[e.Failed=2]="Failed"}(S||(S={})),t.FbClientCore=class{constructor(e,t,i){this.options=e,this.platform=t,this.state=S.Initializing,this.onError=i.onError,this.onFailed=i.onFailed,this.onReady=i.onReady;const{onUpdate:r,hasEventListeners:n}=i,o=new s.default(e);if(!o.sdkKey&&!o.offline)throw new Error("You must configure the client with an SDK key");if(!o.user)throw new Error("You must configure the client with a user");this.config=o,this.logger=o.logger,this.init(t,r,n)}init(e,t,i){var n,s,h;return r(this,void 0,void 0,(function*(){const r=new o.default(this.config.sdkKey,this.config,e);if(this.store=this.config.storeFactory(r),yield this.store.identify(this.config.user),this.dataSourceUpdates=new a.default(this.store,i,t),this.evaluator=new f.default(this.store),yield this.config.bootstrapProvider.populate(this.config.user.keyId,this.dataSourceUpdates),this.config.offline)this.eventProcessor=new _.NullEventProcessor,this.dataSynchronizer=new m.NullDataSynchronizer,this.initSuccess();else{this.eventProcessor=new b.DefaultEventProcessor(r);const t=(0,l.createStreamListeners)(this.dataSourceUpdates,this.logger,{put:()=>this.initSuccess(),patch:()=>this.initSuccess()}),i=this.config.dataSyncMode===w.DataSyncModeEnum.STREAMING?new u.default(this.config.sdkKey,this.config.user,r,e.webSocket,(()=>this.store.version),t,this.config.webSocketPingInterval):new c.default(this.config,new d.default(this.config.sdkKey,this.config,this.platform.info,this.platform.requests),(()=>this.store.version),t,(e=>this.dataSourceErrorHandler(e)));this.dataSynchronizer=null!==(h=null===(s=(n=this.config).dataSynchronizerFactory)||void 0===s?void 0:s.call(n,r,this.store,this.dataSourceUpdates,(()=>this.initSuccess()),(e=>this.dataSourceErrorHandler(e))))&&void 0!==h?h:i}this.start()}))}identify(e){return r(this,void 0,void 0,(function*(){const t=new P.UserValidator;if(!t.is(e))return void t.messages.forEach((e=>{var t;null===(t=this.logger)||void 0===t||t.warn(e)}));this.store.identify(e),this.dataSynchronizer.identify(e);const[i]=this.store.all(h.default.Flags);0===Object.keys(i).length&&(yield this.config.bootstrapProvider.populate(e.keyId,this.dataSourceUpdates))}))}start(){this.config.offline||(this.dataSynchronizer.start(),setTimeout((()=>{var e,t;if(!this.initialized()){const i=`FbClient failed to start successfully within ${this.config.startWaitTime} milliseconds. This error usually indicates a connection issue with FeatBit or an invalid sdkKey.Please double-check your sdkKey and streamingUri/pollingUri configuration. We will continue to initialize the FbClient, it still have a chance to get to work if it's a temporary network issue`,r=new Error(i);return this.state=S.Failed,this.rejectionReason=r,null===(e=this.initReject)||void 0===e||e.call(this,r),null===(t=this.logger)||void 0===t?void 0:t.warn(i)}}),this.config.startWaitTime))}initialized(){return this.state===S.Initialized}waitForInitialization(){return this.initializedPromise?this.initializedPromise:this.state===S.Initialized?(this.initializedPromise=Promise.resolve(this),this.initializedPromise):this.state===S.Failed?(this.initializedPromise=Promise.reject(this.rejectionReason),this.initializedPromise):(this.initializedPromise||(this.initializedPromise=new Promise(((e,t)=>{this.initResolve=e,this.initReject=t}))),this.initializedPromise)}boolVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.bool).value}boolVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.bool)}jsonVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.json).value}jsonVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.json)}numberVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.number).value}numberVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.number)}stringVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.string).value}stringVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.string)}variation(e,t){return this.evaluateCore(e,t,y.ValueConverters.string).value}variationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.string)}getAllVariations(){var e;const t=g.default.fromUser(this.config.user);if(!t.valid){const i=new p.ClientError(`${null!==(e=t.message)&&void 0!==e?e:"User not valid;"} returning default value.`);return this.onError(i),Promise.resolve([])}const[i,r]=this.store.all(h.default.Flags),n=Object.keys(i).map((e=>{var t;const i=this.evaluator.evaluate(e);return{flagKey:e,kind:i.kind,reason:i.reason,value:null===(t=i.value)||void 0===t?void 0:t.variation}}));return Promise.resolve(n)}close(){var e;return r(this,void 0,void 0,(function*(){yield this.eventProcessor.close(),null===(e=this.dataSynchronizer)||void 0===e||e.close(),this.store.close()}))}track(e,t){const i=new O.MetricEvent(this.config.user,e,this.platform.info.appType,null!=t?t:1);this.eventProcessor.record(i)}flush(e){return r(this,void 0,void 0,(function*(){try{return yield this.eventProcessor.flush(),null==e||e(!0),!0}catch(t){return null==e||e(!1),!1}}))}evaluateCore(e,t,i){var r,n,s;const o=g.default.fromUser(this.config.user);if(!o.valid){const i=new p.ClientError(`${null!==(r=o.message)&&void 0!==r?r:"User not valid;"} returning default value.`);return this.onError(i),{flagKey:e,kind:v.ReasonKinds.Error,reason:i.message,value:t}}const a=this.evaluator.evaluate(e);if(a.kind===v.ReasonKinds.FlagNotFound){const i=new p.ClientError(a.reason);return this.onError(i),{flagKey:e,kind:a.kind,reason:a.reason,value:t}}this.initialized()?this.eventProcessor.record(a.toEvalEvent(this.config.user)):null===(n=this.logger)||void 0===n||n.warn("Variation called before FeatBit client initialization completed (did you wait for the'ready' event?)");const{isSucceeded:l,value:u}=i(null===(s=a.value)||void 0===s?void 0:s.variation);return l?{flagKey:e,kind:a.kind,reason:a.reason,value:u}:{flagKey:e,kind:v.ReasonKinds.WrongType,reason:"type mismatch",value:t}}dataSourceErrorHandler(e){var t;const i=401===e.code?new Error("Authentication failed. Double check your SDK key."):e;this.onError(i),this.onFailed(i),this.initialized()||(this.state=S.Failed,this.rejectionReason=i,null===(t=this.initReject)||void 0===t||t.call(this,i))}initSuccess(){var e,t;this.initialized()||(this.state=S.Initialized,null===(e=this.logger)||void 0===e||e.info("FbClient started successfully."),null===(t=this.initResolve)||void 0===t||t.call(this,this),this.onReady())}}},5717:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},4881:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},292:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},226:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6399:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},700:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.JsonBootstrapProvider=void 0;const r=i(4426),n=i(5562);t.JsonBootstrapProvider=class{constructor(e){const t=(e||[]).map((e=>Object.assign(Object.assign({},e),{variationOptions:e.variationOptions||[{id:null,variation:e.variation}]}))),i=(0,r.deserializeAll)(t);this.dataSet={flags:i.flags,version:0}}populate(e,t,i){return new Promise(((r,s)=>{if((0,n.isNullOrUndefined)(this.dataSet))return r();t.init(e,this.dataSet,(()=>{r(),null==i||i()}))}))}}},665:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullBootstrapProvider=void 0,t.NullBootstrapProvider=class{constructor(){this.dataSet={flags:{},version:0}}populate(e,t,i){return new Promise(((e,t)=>{e(),null==i||i()}))}}},8317:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(6399),t),n(i(700),t),n(i(665),t)},7837:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.MinInt=t.EmptyString=void 0,t.EmptyString="",t.MinInt=2147483648},4659:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const s=n(i(2093));t.default=class{constructor(e,t,i){this.store=e,this.hasEventListeners=t,this.onChange=i}init(e,t,i){if(e!==this.store.user.keyId)return void(null==i||i());const n=this.hasEventListeners(),o=e=>r(this,void 0,void 0,(function*(){yield this.store.init(t),Promise.resolve().then((()=>{if(n){const i=Object.keys(t).flatMap((i=>{const r=(null==e?void 0:e[i])||{},n=t[i],s=Object.assign(Object.assign({},r),n);return Object.keys(s).filter((e=>this.isUpdated(r&&r[e],n&&n[e])))}));i.length>0&&this.onChange(i)}})),null==i||i()}));if(n){const[e,t]=this.store.all(s.default.Flags);o({flags:e,version:t})}else o()}upsert(e,t,i,n){if(e!==this.store.user.keyId)return void(null==n||n());const{key:s}=i,o=this.hasEventListeners(),a=e=>r(this,void 0,void 0,(function*(){yield this.store.upsert(t,i),Promise.resolve().then((()=>{o&&this.isUpdated(e,i[s])&&this.onChange([s])})),null==n||n()}));o?a(this.store.get(t,s)||void 0):a()}isUpdated(e,t){return!e||!t||t.version>e.version}}},7539:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.createStreamListeners=t.createPatchListener=t.createPutListener=void 0;const n=i(4426);t.createPutListener=(e,t,i=(()=>{}))=>({deserializeData:n.deserializeAll,processJson:(n,{flags:s})=>r(void 0,void 0,void 0,(function*(){const r={flags:s,version:0};null==t||t.debug("Initializing all data"),e.init(n,r,i)}))}),t.createPatchListener=(e,t,i=(()=>{}))=>({deserializeData:n.deserializePatch,processJson:(n,s)=>r(void 0,void 0,void 0,(function*(){0!==(null==s?void 0:s.length)?null==s||s.forEach((r=>{null==t||t.debug(`Updating ${r.data.key} in ${r.kind.namespace}`),e.upsert(n,r.kind,r.data,i)})):null==i||i()}))}),t.createStreamListeners=(e,i,r)=>{const n=new Map;return n.set("put",(0,t.createPutListener)(e,i,null==r?void 0:r.put)),n.set("patch",(0,t.createPatchListener)(e,i,null==r?void 0:r.patch)),n}},3758:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(7539),t),n(i(4659),t)},607:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.DataSyncModeEnum=void 0,function(e){e.POLLING="polling",e.STREAMING="streaming"}(i||(t.DataSyncModeEnum=i={}))},304:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},450:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8722:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullDataSynchronizer=void 0,t.NullDataSynchronizer=class{close(){}start(){}stop(){}identify(){}}},3148:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(7449),n=i(1962),s=i(8688);t.default=class{constructor(e,t,i,r,n){this.requestor=t,this.getStoreTimestamp=i,this.listeners=r,this.errorHandler=n,this.stopped=!1,this.logger=e.logger,this.pollingInterval=e.pollingInterval,this.user=e.user}poll(){var e;if(this.stopped)return;const t=Date.now();null===(e=this.logger)||void 0===e||e.debug("Polling for feature flag and segments updates"),this.requestor.requestData(this.getStoreTimestamp(),this.user,((e,i)=>{var o,a,l,u,c,d,h;const f=Date.now()-t,v=Math.max(this.pollingInterval-f,0);if(null===(o=this.logger)||void 0===o||o.debug("Elapsed: %d ms, sleeping for %d ms",f,v),e){const{status:t}=e;if(t&&!(0,r.isHttpRecoverable)(t)){const i=(0,s.httpErrorMessage)(e,"polling request");return null===(a=this.logger)||void 0===a||a.error(i),void(null===(l=this.errorHandler)||void 0===l||l.call(this,new r.PollingError(i,t)))}null===(u=this.logger)||void 0===u||u.warn((0,s.httpErrorMessage)(e,"polling request","will retry"))}else{let e=[],t=null===(c=this.user)||void 0===c?void 0:c.keyId,r=this.listeners.get("patch");if(i){const s=JSON.parse(i);if("data-sync"===s.messageType){switch(s.data.eventType){case n.StreamResponseEventType.patch:r=this.listeners.get("patch");break;case n.StreamResponseEventType.full:r=this.listeners.get("put")}({featureFlags:e,userKeyId:t}=s.data)}}const s=null===(d=null==r?void 0:r.deserializeData)||void 0===d?void 0:d.call(r,e);null===(h=null==r?void 0:r.processJson)||void 0===h||h.call(r,t,s)}this.timeoutHandle=setTimeout((()=>{this.poll()}),v)}))}identify(e){this.user=Object.assign({},e)}close(){this.stop()}start(){this.poll()}stop(){this.timeoutHandle&&(clearTimeout(this.timeoutHandle),this.timeoutHandle=void 0),this.stopped=!0}}},4943:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(7449),s=i(8688);t.default=class{constructor(e,t,i,r){this.requests=r,this.headers=(0,s.defaultHeaders)(e,i),this.uri=t.pollingUri}request(e,t){return r(this,void 0,void 0,(function*(){const i=yield this.requests.fetch(e,t),r=yield i.text();return{res:i,body:r}}))}requestData(e,t,i){return r(this,void 0,void 0,(function*(){const r={method:"POST",headers:this.headers,body:JSON.stringify(t)};try{const{res:t,body:s}=yield this.request(`${this.uri}?timestamp=${null!=e?e:0}`,r);if(200!==t.status&&304!==t.status){const e=new n.StreamingError(`Unexpected status code: ${t.status}`,t.status);return i(e,void 0)}return i(void 0,304===t.status?null:s)}catch(e){return i(e,void 0)}}))}}},6100:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{constructor(e,t,i,r,n,s,o){this.getStoreTimestamp=n,this.listeners=s;const{logger:a,streamingUri:l}=i;this.logger=a,this.socket=r,this.socket.config({sdkKey:e,streamingUri:l,pingInterval:o,user:t,logger:a,getStoreTimestamp:n}),this.listeners.forEach((({deserializeData:e,processJson:t},i)=>{var r;null===(r=this.socket)||void 0===r||r.addListener(i,(r=>{var n;if(null===(n=this.logger)||void 0===n||n.debug(`Received ${i} event`),null==r?void 0:r.data){const{featureFlags:i,userKeyId:n}=r.data,s=e(i);t(n,s)}}))}))}identify(e){var t;null===(t=this.socket)||void 0===t||t.identify(e)}start(){var e;this.logConnectionStarted(),null===(e=this.socket)||void 0===e||e.connect()}logConnectionStarted(){var e;this.connectionAttemptStartTime=Date.now(),null===(e=this.logger)||void 0===e||e.info(`Stream connection attempt StartTime ${this.connectionAttemptStartTime}`)}close(){this.stop()}stop(){var e;null===(e=this.socket)||void 0===e||e.close(),this.socket=void 0}}},9999:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(607),t),n(i(304),t),n(i(450),t),n(i(8722),t),n(i(3148),t),n(i(4943),t),n(i(1962),t),n(i(6870),t),n(i(6100),t)},1962:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.StreamResponseEventType=void 0,function(e){e.full="full",e.patch="patch"}(i||(t.StreamResponseEventType=i={}))},6870:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.generateConnectionToken=void 0;const i={0:"Q",1:"B",2:"W",3:"S",4:"P",5:"H",6:"D",7:"X",8:"Z",9:"U"};function r(e,t){var r="000000000000"+e;return r.slice(r.length-t).split("").map((e=>i[e])).join("")}t.generateConnectionToken=function(e){e=e.replace(/=*$/,"");const t=Date.now(),i=r(t,t.toString().length),n=Math.max(Math.floor(Math.random()*e.length),2);return`${r(n,3)}${r(i.length,2)}${e.slice(0,n)}${i}${e.slice(n)}`}},7449:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.isHttpRecoverable=t.ClientError=t.UnexpectedResponseError=t.StreamingError=t.PollingError=void 0;class i extends Error{constructor(e,t){super(e),this.status=t,this.name="FbPollingError"}}t.PollingError=i;class r extends Error{constructor(e,t){super(e),this.code=t,this.name="FbStreamingError"}}t.StreamingError=r;class n extends Error{constructor(e){super(e),this.name="FbUnexpectedResponseError"}}t.UnexpectedResponseError=n;class s extends Error{constructor(e){super(e),this.name="FbClientError"}}t.ClientError=s,t.isHttpRecoverable=function(e){return!(e>=400&&e<500)||400===e||408===e||429===e}},3100:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5192),n=i(7584);class s{constructor(e,t,i){this.kind=e,this.value=t,this.reason=i}static flagNotFound(e){return new s(r.ReasonKinds.FlagNotFound,null,`flag not found: ${e}`)}static matched(e){return new s(r.ReasonKinds.Match,e,"target match")}toEvalEvent(e){var t,i,s;if(this.kind!==r.ReasonKinds.Match)return null;const o=null===(t=this.value)||void 0===t?void 0:t.variations.find((e=>{var t;return e.value===(null===(t=this.value)||void 0===t?void 0:t.variation)}));return new n.EvalEvent(e,null===(i=this.value)||void 0===i?void 0:i.id,o,null===(s=this.value)||void 0===s?void 0:s.sendToExperiment)}}t.default=s},8874:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=r(i(3100)),s=r(i(2093));t.default=class{constructor(e){this.store=e}evaluate(e){const t=this.store.get(s.default.Flags,e);return t?n.default.matched(t):n.default.flagNotFound(e)}}},3675:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5192:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.ReasonKinds=void 0,function(e){e.ClientNotReady="ClientNotReady",e.Match="Match",e.WrongType="WrongType",e.FlagNotFound="FlagNotFound",e.Error="Error"}(i||(t.ReasonKinds=i={}))},9653:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.VariationDataType=void 0,function(e){e.string="string",e.boolean="boolean",e.number="number",e.json="json",e.empty=""}(i||(t.VariationDataType=i={}))},4228:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(9653),t)},9823:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(4228),t),n(i(3100),t),n(i(8874),t),n(i(3675),t),n(i(5192),t)},2305:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventProcessor=void 0;const n=i(5381),s=i(7584),o=i(5562),a=i(1218);t.DefaultEventProcessor=class{constructor(e){this.closed=!1;const{logger:t,flushInterval:i,maxEventsInQueue:r}=e;this.logger=t,this.flushInterval=i,this.eventQueue=new a.DefaultEventQueue(r,this.logger),this.eventDispatcher=new n.EventDispatcher(e,this.eventQueue),this.flushLoop()}flushLoop(){this.closed||setTimeout((()=>r(this,void 0,void 0,(function*(){try{yield this.flush()}catch(e){this.logger.error("Unexpected error while flushing events in event processor.",e)}this.flushLoop()}))),this.flushInterval)}flush(){const e=new s.FlushEvent;return this.record(e),e.waitForCompletion()}close(){return r(this,void 0,void 0,(function*(){if(this.closed)return;const e=new s.ShutdownEvent;this.record(e);try{yield e.waitForCompletion()}catch(e){this.logger.error("Event processor shutdown but not complete.")}this.eventQueue.close(),this.closed=!0}))}record(e){return!((0,o.isNullOrUndefined)(e)||!this.eventQueue.addEvent(e)&&(e instanceof s.FlushEvent&&e.complete(),1))}}},1218:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventQueue=void 0,t.DefaultEventQueue=class{constructor(e,t){this.capacity=e,this.logger=t,this.closed=!1,this.events=[]}addEvent(e){return!this.closed&&(this.events.length>=this.capacity?(this.logger.warn("Events are being produced faster than they can be processed. We shouldn't see this."),!1):(this.events.push(e),!0))}clear(){this.events=[]}shift(){return this.events.shift()}close(){this.closed=!0}get eventsSnapshot(){return[...this.events]}get length(){return this.events.length}get isEmpty(){return 0===this.length}}},2580:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventSender=void 0;const s=i(8174),o=i(8688),a=i(7449),l=n(i(1773));t.DefaultEventSender=class{constructor(e){const{sdkKey:t,eventsUri:i,platform:r}=e,{info:n,requests:s}=r;this.defaultHeaders=(0,o.defaultHeaders)(t,n),this.eventsUri=i,this.requests=s}send(e,t){return r(this,void 0,void 0,(function*(){const i={status:s.DeliveryStatus.Succeeded},r=Object.assign(Object.assign({},this.defaultHeaders),{"content-type":"application/json"});let n;try{const{status:t}=yield this.requests.fetch(this.eventsUri,{headers:r,body:e,method:"POST"});if(t>=200&&t<=299)return i;if(n=new a.UnexpectedResponseError((0,o.httpErrorMessage)({status:t,message:"some events were dropped"},"event posting")),!(0,a.isHttpRecoverable)(t))return i.status=s.DeliveryStatus.FailedAndMustShutDown,i.error=n,i}catch(e){n=e}return n&&!t?(i.status=s.DeliveryStatus.Failed,i.error=n,i):(yield(0,l.default)(),this.send(e,!1))}))}}},9657:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventSerializer=void 0;const r=i(7584);t.DefaultEventSerializer=class{serialize(e){const t=e.map((e=>e instanceof r.EvalEvent||e instanceof r.MetricEvent?e.toPayload():null)).filter((e=>null!==e));return JSON.stringify(t)}}},5381:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.EventDispatcher=void 0;const s=i(8174),o=i(1218),a=i(2580),l=i(7584),u=i(9657),c=n(i(1773));t.EventDispatcher=class{constructor(e,t){this.maxEventPerRequest=50,this.stopped=!1;const{logger:i,maxEventsInQueue:r}=e;this.logger=i,this.buffer=new o.DefaultEventQueue(r,this.logger),this.sender=new a.DefaultEventSender(e),this.serializer=new u.DefaultEventSerializer,this.dispatchLoop(t).then()}dispatchLoop(e){return r(this,void 0,void 0,(function*(){this.logger.debug("Start dispatch loop.");let t=!0;for(;t;)try{const i=e.shift();if(void 0===i){yield(0,c.default)(1e3);continue}i instanceof l.PayloadEvent?this.addEventToBuffer(i):i instanceof l.FlushEvent?yield this.triggerFlush(i):i instanceof l.ShutdownEvent&&(yield this.triggerFlush(i),this.stopped=!0,t=!1)}catch(e){this.logger.error("Unexpected error in event dispatcher.",e)}this.logger.debug("Finish dispatch loop.")}))}addEventToBuffer(e){this.stopped||(this.buffer.addEvent(e)?this.logger.debug("Added event to buffer."):this.logger.warn("Exceeded event queue capacity, event will be dropped. Increase capacity to avoid dropping events."))}triggerFlush(e){return r(this,void 0,void 0,(function*(){if(this.stopped)return void e.complete();if(this.buffer.isEmpty)return e.complete(),void this.logger.debug("Flush empty buffer.");const t=this.buffer.eventsSnapshot;this.buffer.clear();try{yield this.flushEvents(t),this.logger.debug(`${t.length} events has been flushed.`)}catch(e){this.logger.warn("Exception happened when flushing events",e)}e.complete()}))}flushEvents(e){return r(this,void 0,void 0,(function*(){const t=(e=this.getUniqueEvents(e)).length;for(let i=0;i{Object.defineProperty(t,"__esModule",{value:!0})},6735:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},1564:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8174:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.DeliveryStatus=void 0,function(e){e[e.Succeeded=0]="Succeeded",e[e.Failed=1]="Failed",e[e.FailedAndMustShutDown=2]="FailedAndMustShutDown"}(i||(t.DeliveryStatus=i={}))},407:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullEventProcessor=void 0,t.NullEventProcessor=class{flush(){return Promise.resolve()}close(){return Promise.resolve()}record(e){return!1}}},7584:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.EvalEvent=t.MetricEvent=t.PayloadEvent=t.ShutdownEvent=t.FlushEvent=t.AsyncEvent=void 0;class i{get hash(){return this.timestamp.toString()}constructor(){this.timestamp=(new Date).getTime(),this.isCompletedPromise=new Promise((e=>{this.resolveFn=e}))}waitForCompletion(){return this.isCompletedPromise}complete(){var e;null===(e=this.resolveFn)||void 0===e||e.call(this,this)}}t.AsyncEvent=i,t.FlushEvent=class extends i{},t.ShutdownEvent=class extends i{};class r{constructor(){this.timestamp=(new Date).getTime()}get hash(){return this.timestamp.toString()}toPayload(){}}t.PayloadEvent=r,t.MetricEvent=class extends r{constructor(e,t,i,r){super(),this.user=e,this.eventName=t,this.appType=i,this.metricValue=r}userPayload(){return{keyId:this.user.keyId,name:this.user.name,customizedProperties:this.user.customizedProperties}}toPayload(){return{user:this.userPayload(),metrics:[{route:"index/metric",timestamp:this.timestamp,numericValue:this.metricValue,appType:this.appType,eventName:this.eventName,type:"CustomEvent"}]}}get hash(){const e=this.toPayload(),t={user:e.user,metrics:e.metrics.map((e=>Object.assign(Object.assign({},e),{timestamp:void 0})))};return JSON.stringify(t)}},t.EvalEvent=class extends r{constructor(e,t,i,r){super(),this.user=e,this.flagKey=t,this.variation=i,this.sendToExperiment=r}userPayload(){return{keyId:this.user.keyId,name:this.user.name,customizedProperties:this.user.customizedProperties}}toPayload(){return{user:this.userPayload(),variations:[{featureFlagKey:this.flagKey,sendToExperiment:this.sendToExperiment,timestamp:this.timestamp,variation:this.variation}]}}get hash(){const e=this.toPayload(),t={user:e.user,variations:e.variations.map((e=>Object.assign(Object.assign({},e),{timestamp:void 0})))};return JSON.stringify(t)}}},4008:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(2305),t),n(i(1218),t),n(i(2580),t),n(i(9657),t),n(i(7584),t),n(i(5381),t),n(i(8284),t),n(i(6735),t),n(i(1564),t),n(i(8174),t),n(i(407),t)},9872:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(8317),t),n(i(3758),t),n(i(9823),t),n(i(4008),t),n(i(7302),t),n(i(1045),t),n(i(9718),t),n(i(8598),t),n(i(9999),t),n(i(2710),t),n(i(1058),t),n(i(7837),t),n(i(1731),t),n(i(7449),t),n(i(70),t),n(i(5717),t),n(i(4881),t),n(i(292),t),n(i(226),t),n(i(4129),t)},5768:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.BasicLogger=void 0;const n=r(i(3919)),s={debug:0,info:1,warn:2,error:3,none:4},o=["debug","info","warn","error","none"];class a{static get(){return new a({})}constructor(e){var t,i,r;this.logLevel=null!==(i=s[null!==(t=e.level)&&void 0!==t?t:"info"])&&void 0!==i?i:s.info,this.name=null!==(r=e.name)&&void 0!==r?r:"FeatBit",this.destination=e.destination,this.formatter=e.formatter}tryFormat(...e){var t;try{return this.formatter?null===(t=this.formatter)||void 0===t?void 0:t.call(this,...e):(0,n.default)(...e)}catch(t){return(0,n.default)(...e)}}tryWrite(e){try{this.destination(e)}catch(t){console.error(e)}}log(e,t){if(e>=this.logLevel){const i=`${o[e]}: [${this.name}]`;try{this.destination?this.tryWrite(`${i} ${this.tryFormat(...t)}`):console.error(...t)}catch(e){console.error(...t)}}}error(...e){this.log(s.error,e)}warn(...e){this.log(s.warn,e)}info(...e){this.log(s.info,e)}debug(...e){this.log(s.debug,e)}}t.BasicLogger=a},7973:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5781:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7076:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7689:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.SafeLogger=void 0;const r=i(5862),n={error:r.TypeValidators.Function,warn:r.TypeValidators.Function,info:r.TypeValidators.Function,debug:r.TypeValidators.Function};t.SafeLogger=class{constructor(e,t){Object.entries(n).forEach((([t,i])=>{if(!i.is(e[t]))throw new Error(`Provided logger instance must support logger.${t}(...) method`)})),this.logger=e,this.fallback=t}log(e,t){try{this.logger[e](...t)}catch(i){this.fallback[e](...t)}}error(...e){this.log("error",e)}warn(...e){this.log("warn",e)}info(...e){this.log("info",e)}debug(...e){this.log("debug",e)}}},3919:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5862);function n(e){if("string"==typeof e)return e;if(void 0===e)return"undefined";if(null===e)return"null";if(Object.prototype.hasOwnProperty.call(e,"toString"))try{return e.toString()}catch(e){}if("bigint"==typeof e)return`${e}n`;try{return JSON.stringify(e)}catch(e){return e instanceof TypeError&&e.message.indexOf("circular")>=0?"[Circular]":"[Not Stringifiable]"}}const s={s:e=>n(e),d:e=>function(e){return"symbol"==typeof e?"NaN":"bigint"==typeof e?`${e}n`:String(Number(e))}(e),i:e=>function(e){return"symbol"==typeof e?"NaN":"bigint"==typeof e?`${e}n`:String(parseInt(e,10))}(e),f:e=>function(e){return"symbol"==typeof e?"NaN":String(parseFloat(e))}(e),j:e=>n(e),o:e=>n(e),O:e=>n(e),c:()=>""};t.default=function(...e){var t;const i=e.shift();if(r.TypeValidators.String.is(i)){let r="",o=0;for(;o{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{constructor(e,t,i){this.sdkKey=e,this.platform=i,this.logger=t.logger,this.offline=t.offline,this.flushInterval=t.flushInterval,this.maxEventsInQueue=t.maxEventsInQueue,this.streamingUri=t.streamingUri,this.pollingUri=t.pollingUri,this.eventsUri=t.eventsUri}}},8222:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},4670:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6273:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8758:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},9176:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{static optionBelowMinimum(e,t,i){return`Config option "${e}" had invalid value of ${t}, using minimum of ${i} instead`}static unknownOption(e){return`Ignoring unknown config option "${e}"`}static wrongOptionType(e,t,i){return`Config option "${e}" should be of type ${t}, got ${i}, using default value`}static wrongOptionTypeBoolean(e,t){return`Config option "${e}" should be a boolean, got ${t}, converting to boolean`}static partialEndpoint(e){return`You have set custom uris without specifying the ${e} URI; connections may not work properly`}static mandatory(e){return`${e} is mandatory`}static invalidOptionValue(e){return`Invalid option value: ${e}`}static missingKeyInBootstrapValue(e){return`Missing key "${e}" in bootstrap value`}}},595:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.UserBuilder=void 0,t.UserBuilder=class{constructor(e){this._keyId="",this._name="",this._custom=[],this._keyId=e}name(e){return this._name=e,this}custom(e,t){var i;return null===(i=this._custom)||void 0===i||i.push({name:e,value:t}),this}build(){return{name:this._name,keyId:this._keyId,customizedProperties:this._custom}}}},5862:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.TypeValidators=t.KindValidator=t.DateValidator=t.UserValidator=t.BootstrapValidator=t.NullableBoolean=t.Function=t.StringMatchingRegex=t.NumberWithMinimum=t.TypeArray=t.Type=t.FactoryOrInstance=void 0;const n=r(i(9176));class s{is(e){if(Array.isArray(e))return!1;const t=typeof e;return"function"===t||"object"===t}getType(){return"factory method or object"}}t.FactoryOrInstance=s;class o{constructor(e,t){this.typeName=e,this.typeOf=typeof t}is(e){return!Array.isArray(e)&&typeof e===this.typeOf}getType(){return this.typeName}}t.Type=o;class a{constructor(e,t){this.typeName=e,this.typeOf=typeof t}is(e){return!!Array.isArray(e)&&(!(e.length>0)||e.every((e=>typeof e===this.typeOf)))}getType(){return this.typeName}}t.TypeArray=a;class l extends o{constructor(e){super(`number with minimum value of ${e}`,0),this.min=e}is(e){return typeof e===this.typeOf&&e>=this.min}}t.NumberWithMinimum=l;class u extends o{constructor(e){super(`string matching ${e}`,""),this.expression=e}is(e){return!!e.match(this.expression)}}t.StringMatchingRegex=u;class c{is(e){return"function"==typeof e}getType(){return"function"}}t.Function=c;class d{is(e){return"boolean"==typeof e||null==e}getType(){return"boolean | undefined | null"}}t.NullableBoolean=d,t.BootstrapValidator=class{constructor(){this.messages=[]}is(e){if("object"!=typeof e||null===e)return this.messages.push(n.default.invalidOptionValue("bootstrap")),!1;try{const t=e;for(let e of t){["id","variation"].every((t=>Object.keys(e).includes(t)));const t=Object.keys(e);if(t.includes("id")&&this.messages.push(n.default.missingKeyInBootstrapValue("id")),t.includes("variation")&&this.messages.push(n.default.missingKeyInBootstrapValue("variation")),this.messages.length>0)return!1}}catch(t){return this.messages.push(n.default.wrongOptionType("bootstrap",this.getType(),typeof e)),!1}return!0}getType(){return"IFlagBase[]"}},t.UserValidator=class{constructor(){this.messages=[]}is(e){if("object"!=typeof e||null===e)return this.messages.push(n.default.mandatory("user")),!1;const t=e;return"string"!=typeof t.keyId||""===t.keyId.trim()?(this.messages.push(n.default.mandatory("user.keyId")),!1):"string"==typeof t.name&&""!==t.name.trim()||(this.messages.push(n.default.mandatory("user.name")),!1)}getType(){return"user"}};const h=/^\d\d\d\d-\d\d-\d\dT\d\d:\d\d:\d\d(\.\d\d*)?(Z|[-+]\d\d(:\d\d)?)/;class f{is(e){return"number"==typeof e||"string"==typeof e&&h.test(e)}getType(){return"date"}}t.DateValidator=f;class v extends u{constructor(){super(/^(\w|\.|-)+$/)}is(e){return super.is(e)&&"kind"!==e}}t.KindValidator=v;class p{static createTypeArray(e,t){return new a(e,t)}static numberWithMin(e){return new l(e)}static stringMatchingRegex(e){return new u(e)}}t.TypeValidators=p,p.String=new o("string",""),p.Number=new o("number",0),p.ObjectOrFactory=new s,p.Object=new o("object",{}),p.StringArray=new a("string[]",""),p.Boolean=new o("boolean",!0),p.User=new o("object",{}),p.Bootstrap=new o("object",{}),p.Function=new c,p.Date=new f,p.Kind=new v,p.NullableBoolean=new d},1045:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(8311),t),n(i(8222),t),n(i(4670),t),n(i(6273),t),n(i(8758),t),n(i(9176),t),n(i(595),t),n(i(5862),t)},5309:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},9938:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5800:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6510:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},2833:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5972);t.default=class{get appType(){return"Browser-Client-SDK"}platformData(){return{os:{},name:"Browser",additional:{}}}sdkData(){return{name:r.name,version:r.version,userAgentBase:this.appType}}}},9174:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=r(i(2833)),s=i(891),o=r(i(9018));t.default=class{constructor(e){this.info=new n.default,this.requests=new s.BrowserRequests,this.webSocket=new o.default}}},891:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.BrowserRequests=void 0,t.BrowserRequests=class{fetch(e,t={}){return fetch(e,t)}}},9018:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(3046),n=i(6842),s=i(6870),o=i(1962),a=[1e3,3e3,5e3,7e3,11e3,13e3,3e4,6e4];t.default=(0,r.Emits)(class{constructor(){this.retryCounter=0,this.closed=!1,this._config={},this.emitter=new n.EventEmitter}identify(e){this._config.user=e,this.doDataSync()}connect(){var e,t,i,r;let n=this;const a=Date.now(),l=this._config.streamingUri.replace(/^http/,"ws")+`?type=client&token=${(0,s.generateConnectionToken)(this._config.sdkKey)}`;this.ws=new WebSocket(l),null===(e=n.ws)||void 0===e||e.addEventListener("open",(function(e){n._config.logger.info(`WebSocket connection succeeded, connection time: ${Date.now()-a} ms`),n.doDataSync(),n.sendPingMessage()})),null===(t=n.ws)||void 0===t||t.addEventListener("close",(function(e){n._config.logger.warn("WebSocket closed"),4003!==e.code&&n.reconnect()})),null===(i=n.ws)||void 0===i||i.addEventListener("error",(function(e){n._config.logger.debug("error")})),null===(r=n.ws)||void 0===r||r.addEventListener("message",(function(e){const t=JSON.parse(e.data);if("data-sync"===t.messageType)switch(t.data.eventType){case o.StreamResponseEventType.patch:n.emitter.emit("patch",t);break;case o.StreamResponseEventType.full:n.emitter.emit("put",t)}}))}close(){var e;this.closed=!0,null===(e=this.ws)||void 0===e||e.close(4003,"The client is closed by user"),this.ws=void 0}config(e){e.emitter&&(this.emitter=e.emitter),this._config=Object.assign({},e)}sendPingMessage(){const e={messageType:"ping",data:null};setTimeout((()=>{var t;try{(null===(t=this.ws)||void 0===t?void 0:t.readyState)===WebSocket.OPEN?(this._config.logger.debug("sending ping"),this.ws.send(JSON.stringify(e)),this.sendPingMessage()):this._config.logger.debug(`socket closed at ${new Date}`)}catch(e){this._config.logger.debug(e)}}),this._config.pingInterval)}doDataSync(){var e,t;const i={messageType:"data-sync",data:{timestamp:this._config.getStoreTimestamp(),user:this._config.user}};try{(null===(e=this.ws)||void 0===e?void 0:e.readyState)===WebSocket.OPEN?(this._config.logger.debug("requesting data"),null===(t=this.ws)||void 0===t||t.send(JSON.stringify(i))):this._config.logger.error("not requesting data because socket not open")}catch(e){this._config.logger.debug(e)}}reconnect(){if(!this.closed){this.ws=void 0;const e=a[Math.min(this.retryCounter++,a.length-1)];this._config.logger.info(`The client will try to reconnect in ${e} milliseconds.`),setTimeout((()=>{this._config.logger.info(`The client is trying to reconnect, flag evaluation results may be stale until reconnected, waited for: ${e} milliseconds`),this.connect()}),e)}}})},8322:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=i(4129),s=i(5768),o=i(6842),a=i(7689),l=i(3046),u=r(i(9174)),c=r(i(6940));class d extends n.FbClientCore{constructor(e,t=void 0){const i=new s.BasicLogger({level:"none",destination:console.log}),r=e.logger?new a.SafeLogger(e.logger,i):i,n=new o.EventEmitter(r);let{store:l}=e;l||(l=new c.default(e)),super(Object.assign(Object.assign({},e),{logger:r,store:l}),null!=t?t:new u.default(Object.assign(Object.assign({},e),{logger:r})),{onError:e=>{n.listenerCount("error")&&n.emit("error",e)},onFailed:e=>{n.emit("failed",e)},onReady:()=>{n.emit("ready")},onUpdate:e=>{n.emit("update",[e]),e.forEach((e=>n.emit(`update:${e}`,e)))},hasEventListeners:()=>n.eventNames().some((e=>"update"===e||"string"==typeof e&&e.startsWith("update:")))}),this.emitter=n}}t.default=(0,l.Emits)(d)},6940:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(443),s=i(6860),o=i(5067);class a extends s.BaseStore{constructor(e){super(),this.logger=e.logger}close(){}get description(){return"local-storage-store"}saveUser(){return r(this,void 0,void 0,(function*(){localStorage.setItem(n.CurrentUserStorageKey,(0,o.serializeUser)(this._user))}))}dumpStoreToStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`;localStorage.setItem(e,JSON.stringify(this.store))}))}loadStoreFromStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`,t=localStorage.getItem(e);let i=null;try{t&&t.trim().length>0&&(i=JSON.parse(t))}catch(t){this.logger.error(`error while loading local data store: ${e}`,t)}this.store=i||{flags:{},version:0}}))}}t.default=a},9718:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)},s=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.BrowserWebSocket=void 0,n(i(5309),t),n(i(5800),t),n(i(9938),t),n(i(6510),t),n(i(2894),t),n(i(891),t);const o=s(i(9018));t.BrowserWebSocket=o.default},2894:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6860:function(e,t){var i=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.BaseStore=void 0,t.BaseStore=class{constructor(){this.store={},this.initCalled=!1,this._user={}}identify(e){return i(this,void 0,void 0,(function*(){this._user=Object.assign({},e),yield this.saveUser(),yield this.loadStoreFromStorage()}))}get user(){return this._user}addItem(e,t,r){return i(this,void 0,void 0,(function*(){let i=this.store[e.namespace];if(i||(i={},this.store[e.namespace]=i),Object.hasOwnProperty.call(i,t)){const e=i[t];(!e||e.versionthis.store.version&&(this.store.version=r.version),yield this.dumpStoreToStorage()}))}get(e,t){const i=this.store[e.namespace];if(i&&Object.prototype.hasOwnProperty.call(i,t)){const e=i[t];if(e)return e}return null}all(e){var t;const i={},r=null!==(t=this.store[e.namespace])&&void 0!==t?t:{};return Object.entries(r).forEach((([e,t])=>{t&&(i[e]=t)})),[i,this.store.version]}init(e){return i(this,void 0,void 0,(function*(){this.store=e,Object.keys(e).map((t=>{Object.entries(e[t]).forEach((([e,t])=>{const i=t;i.version>this.store.version&&(this.store.version=i.version)}))})),yield this.dumpStoreToStorage(),this.initCalled=!0}))}upsert(e,t){return i(this,void 0,void 0,(function*(){yield this.addItem(e,t.key,t)}))}initialized(){return this.initCalled}close(){}get version(){return this.store.version}get description(){return""}saveUser(){return i(this,void 0,void 0,(function*(){}))}loadStoreFromStorage(){return i(this,void 0,void 0,(function*(){}))}dumpStoreToStorage(){return i(this,void 0,void 0,(function*(){}))}}},2093:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0});class i{}i.Flags={namespace:"flags"},t.default=i},356:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7783:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(443),s=i(6860);class o extends s.BaseStore{constructor(){super(),this.allStores={}}close(){}get description(){return"in-memory-store"}saveUser(){return r(this,void 0,void 0,(function*(){}))}dumpStoreToStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`;this.allStores[e]=Object.assign({},this.store)}))}loadStoreFromStorage(){var e;return r(this,void 0,void 0,(function*(){const t=`${n.StoreStorageKey}-${this._user.keyId}`;this.store=null!==(e=this.allStores[t])&&void 0!==e?e:{flags:{},version:0}}))}}t.default=o},8598:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(2093),t),n(i(356),t),n(i(7783),t),n(i(4426),t),n(i(443),t),n(i(6860),t)},4426:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.deserializePatch=t.deserializeAll=void 0;const n=r(i(2093));t.deserializeAll=function(e){const t={[n.default.Flags.namespace]:{}};return(null==e?void 0:e.length)&&(t[n.default.Flags.namespace]=e.reduce(((e,t)=>(e[t.id]=Object.assign(Object.assign({},t),{version:t.timestamp||0,key:t.id,variations:t.variationOptions}),e)),{})),t},t.deserializePatch=function(e){return[...(null==e?void 0:e.map((e=>({data:Object.assign(Object.assign({},e),{version:e.timestamp,key:e.id,variations:e.variationOptions}),kind:n.default.Flags}))))||[]]}},443:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.CurrentUserStorageKey=t.StoreStorageKey=void 0,t.StoreStorageKey="fb-datastore",t.CurrentUserStorageKey="fb-user"},3046:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.Emits=void 0,t.Emits=function(e){return class extends e{on(e,t,i){return this.emitter.on(e,t,i),this}addListener(e,t,i){return this.emitter.addListener(e,t,i),this}once(e,t,i){return this.emitter.once(e,t,i),this}removeListener(e,t,i){return this.emitter.removeListener(e,t,i),this}off(e,t,i){return this.emitter.off(e,t,i),this}removeAllListeners(e){return this.emitter.removeAllListeners(e),this}listeners(e){return this.emitter.listeners(e)}emit(e,...t){return this.emitter.emit(e,t),this}listenerCount(e){return this.emitter.listenerCount(e)}prependListener(e,t,i){return this.emitter.prependListener(e,t,i),this}prependOnceListener(e,t,i){return this.emitter.prependOnceListener(e,t,i),this}eventNames(){return this.emitter.eventNames()}maybeReportError(e){return this.emitter.maybeReportError(e),this}}}},6842:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.EventEmitter=void 0,t.EventEmitter=class{constructor(e){this.logger=e,this.events={}}listeningTo(e){return!!this.events[e]}on(e,t,i){return this.events[e]=this.events[e]||[],this.events[e]=this.events[e].concat({handler:t,context:i}),this}addListener(e,t,i){return this.on(e,t,i)}once(e,t,i){const r=(...n)=>{this.off(e,r,i),t.apply(i,n)};return this.on(e,r,i)}off(e,t,i){if(!this.events[e])return this;for(let r=0;re.handler)):[]}emit(e,...t){if(!this.events[e])return this;const i=[...this.events[e]];for(let e=0;e{this.off(e,r,i),t.apply(i,n)};return this.prependListener(e,r,i)}eventNames(){return Object.keys(this.events)}maybeReportError(e){var t;return e?(this.listeningTo("error")?this.emit("error",e):null===(t=this.logger)||void 0===t||t.error(e),this):this}}},1142:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.ValueConverters=void 0;class i{static bool(e){return"TRUE"===(null==e?void 0:e.toUpperCase())?i.success(!0):"FALSE"===(null==e?void 0:e.toUpperCase())?i.success(!1):i.error()}static number(e){const t=Number(e);return Number.isNaN(t)?i.error():i.success(t)}static string(e){return i.success(e)}static json(e){try{const t=JSON.parse(e);return i.success(t)}catch(e){return i.error()}}static success(e){return{isSucceeded:!0,value:e}}static error(){return{isSucceeded:!1}}}t.ValueConverters=i},7266:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},1624:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.canonicalizeUri=void 0,t.canonicalizeUri=function(e){return e.replace(/\/+$/,"")}},9183:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.debounce=void 0,t.debounce=(e,t=5e3)=>{let i;return(...r)=>{clearTimeout(i),i=setTimeout((()=>{e(...r)}),t)}}},8688:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.httpErrorMessage=t.defaultHeaders=void 0,t.defaultHeaders=function(e,t){const{userAgentBase:i,version:r}=t.sdkData();return{"Content-Type":"application/json","User-Agent":`${null!=i?i:t.appType}/${r}`,Authorization:e}},t.httpErrorMessage=function(e,t,i){let r;return r=e.status?`error ${e.status}${401===e.status?" (invalid SDK key)":""}`:`I/O error (${e.message||e})`,`Received ${r} for ${t} - ${null!=i?i:"giving up permanently"}`}},2710:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(5562),t),n(i(1773),t),n(i(1142),t),n(i(7266),t),n(i(5067),t),n(i(9183),t)},5562:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.isNullOrUndefined=void 0,t.isNullOrUndefined=function(e){return null==e}},5067:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.serializeUser=void 0,t.serializeUser=function(e){var t;return e?`${e.keyId},${e.name},${null===(t=e.customizedProperties)||void 0===t?void 0:t.sort(((e,t)=>{const i=e.name.toLowerCase(),r=t.name.toLowerCase();return ir?1:0})).map((e=>`${e.name}:${e.value}`)).join(",")}`:""}},1773:function(e,t){var i=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.default=(e=1e3)=>i(void 0,void 0,void 0,(function*(){return new Promise((t=>{setTimeout(t,e)}))}))},5972:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.name=t.version=void 0,t.version="3.0.2",t.name="@featbit/js-client-sdk"}},t={};return function i(r){var n=t[r];if(void 0!==n)return n.exports;var s=t[r]={exports:{}};return e[r].call(s.exports,s,s.exports,i),s.exports}(9872)})())); +!function(e,t){if("object"==typeof exports&&"object"==typeof module)module.exports=t();else if("function"==typeof define&&define.amd)define([],t);else{var i=t();for(var r in i)("object"==typeof exports?exports:e)[r]=i[r]}}(this,(()=>(()=>{"use strict";var e={1058:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.defaultValues=void 0;const n=i(5862),s=r(i(9176)),o=r(i(7783)),a=i(5562),l=i(1624),u=i(665),c=i(7837),d=i(607),h=i(8317),f={startWaitTime:n.TypeValidators.Number,sdkKey:n.TypeValidators.String,pollingUri:n.TypeValidators.String,streamingUri:n.TypeValidators.String,eventsUri:n.TypeValidators.String,webSocketPingInterval:n.TypeValidators.Number,logger:n.TypeValidators.Object,store:n.TypeValidators.ObjectOrFactory,dataSynchronizer:n.TypeValidators.ObjectOrFactory,flushInterval:n.TypeValidators.Number,maxEventsInQueue:n.TypeValidators.Number,pollingInterval:n.TypeValidators.Number,offline:n.TypeValidators.Boolean,dataSyncMode:n.TypeValidators.String,bootstrap:n.TypeValidators.Bootstrap,user:n.TypeValidators.User};t.defaultValues={startWaitTime:5e3,sdkKey:"",pollingUri:"",streamingUri:"",eventsUri:"",dataSyncMode:d.DataSyncModeEnum.STREAMING,sendEvents:!0,webSocketPingInterval:18e3,flushInterval:2e3,maxEventsInQueue:1e4,pollingInterval:3e4,offline:!1,store:e=>new o.default,bootstrap:void 0,user:void 0},t.default=class{constructor(e={}){var i,r;this.bootstrapProvider=new u.NullBootstrapProvider,e=e||{},this.logger=e.logger;const{errors:o,validatedOptions:v}=function(e){let i=[];const r=Object.assign({},t.defaultValues);return Object.keys(e).forEach((o=>{var a;const l=e[o],u=f[o];if(u)if(u.is(l))r[o]=l;else if("boolean"===u.getType())i.push(s.default.wrongOptionTypeBoolean(o,typeof l)),r[o]=!!l;else if(u instanceof n.NumberWithMinimum&&n.TypeValidators.Number.is(l)){const{min:e}=u;i.push(s.default.optionBelowMinimum(o,l,e)),r[o]=e}else u instanceof n.UserValidator?(i=[...i,...u.messages],r[o]=t.defaultValues[o]):(i.push(s.default.wrongOptionType(o,u.getType(),typeof l)),r[o]=t.defaultValues[o]);else null===(a=e.logger)||void 0===a||a.warn(s.default.unknownOption(o))})),{errors:i,validatedOptions:r}}(e);if(o.forEach((e=>{var t;null===(t=this.logger)||void 0===t||t.warn(e)})),this.user=e.user,function(e,t){var i,r,n;const{streamingUri:o,pollingUri:l,eventsUri:u}=e,h=(0,a.isNullOrUndefined)(o)||o===c.EmptyString,f=(0,a.isNullOrUndefined)(l)||l===c.EmptyString,v=(0,a.isNullOrUndefined)(u)||u===c.EmptyString;!t.offline&&(v||h&&f)&&(v&&(null===(i=t.logger)||void 0===i||i.error(s.default.partialEndpoint("eventsUri"))),t.dataSyncMode===d.DataSyncModeEnum.STREAMING&&h&&(null===(r=t.logger)||void 0===r||r.error(s.default.partialEndpoint("streamingUri"))),t.dataSyncMode===d.DataSyncModeEnum.POLLING&&f&&(null===(n=t.logger)||void 0===n||n.error(s.default.partialEndpoint("pollingUri"))))}(e,v),this.streamingUri=`${(0,l.canonicalizeUri)(v.streamingUri)}/streaming`,this.pollingUri=`${(0,l.canonicalizeUri)(v.pollingUri)}/api/public/sdk/client/latest-all`,this.eventsUri=`${(0,l.canonicalizeUri)(v.eventsUri)}/api/public/insight/track`,this.startWaitTime=v.startWaitTime,this.sdkKey=v.sdkKey,this.webSocketPingInterval=v.webSocketPingInterval,this.flushInterval=v.flushInterval,this.maxEventsInQueue=v.maxEventsInQueue,this.pollingInterval=v.pollingInterval,this.offline=v.offline,v.bootstrap&&v.bootstrap.length>0)try{this.bootstrapProvider=new h.JsonBootstrapProvider(v.bootstrap)}catch(e){null===(i=this.logger)||void 0===i||i.error("Failed to parse bootstrap JSON, use NullBootstrapProvider.")}this.offline&&(null===(r=this.logger)||void 0===r||r.info("Offline mode enabled. No data synchronization with the FeatBit server will occur.")),this.dataSyncMode=v.dataSyncMode,n.TypeValidators.Function.is(v.dataSynchronizer)?this.dataSynchronizerFactory=v.dataSynchronizer:this.dataSynchronizerFactory=()=>v.dataSynchronizer,n.TypeValidators.Function.is(v.store)?this.storeFactory=v.store:this.storeFactory=()=>v.store}}},1731:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0});class i{constructor(e,t){this.valid=e,this.message=t}static fromUser(e){if(!e)return i.contextForError("No user specified");const{keyId:t,name:r}=e;if(null==t||""===t.trim())return i.contextForError("key is mandatory");const n=new i(!0);return n._user=e,n}get user(){return this._user}get keyId(){return this._user.keyId}value(e){var t,i,r,n,s;return"keyId"===e?null===(t=this._user)||void 0===t?void 0:t.keyId:"name"===e?null===(i=this._user)||void 0===i?void 0:i.name:null===(s=null===(n=null===(r=this._user)||void 0===r?void 0:r.customizedProperties)||void 0===n?void 0:n.find((t=>t.name===e)))||void 0===s?void 0:s.value}static contextForError(e){return new i(!1,e)}}t.default=i},70:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.FbClientBuilder=void 0;const n=r(i(8322));t.FbClientBuilder=class{constructor(e){this._options=null!=e?e:{}}build(){return new n.default(this._options)}platform(e){return this._platform=e,this}startWaitTime(e){return this._options.startWaitTime=e,this}sdkKey(e){return this._options.sdkKey=e,this}user(e){return this._options.user=e,this}streamingUri(e){return this._options.streamingUri=e,this}pollingUri(e){return this._options.pollingUri=e,this}eventsUri(e){return this._options.eventsUri=e,this}dataSyncMode(e){return this._options.dataSyncMode=e,this}pollingInterval(e){return this._options.pollingInterval=e,this}flushInterval(e){return this._options.flushInterval=e,this}maxEventsInQueue(e){return this._options.maxEventsInQueue=e,this}logger(e){return this._options.logger=e,this}offline(e){return this._options.offline=e,this}bootstrap(e){return this._options.bootstrap=e,this}dataSynchronizer(e){return this._options.dataSynchronizer=e,this}}},4129:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.FbClientCore=void 0;const s=n(i(1058)),o=n(i(8311)),a=n(i(4659)),l=i(7539),u=n(i(6100)),c=n(i(3148)),d=n(i(4943)),h=n(i(2093)),f=n(i(8874)),v=i(5192),p=i(7449),g=n(i(1731)),y=i(1142),m=i(8722),_=i(407),b=i(2305),O=i(7584),w=i(607),P=i(5862);var S;!function(e){e[e.Initializing=0]="Initializing",e[e.Initialized=1]="Initialized",e[e.Failed=2]="Failed"}(S||(S={})),t.FbClientCore=class{constructor(e,t,i){this.options=e,this.platform=t,this.state=S.Initializing,this.onError=i.onError,this.onFailed=i.onFailed,this.onReady=i.onReady;const{onUpdate:r,hasEventListeners:n}=i,o=new s.default(e);if(!o.sdkKey&&!o.offline)throw new Error("You must configure the client with an SDK key");if(!o.user)throw new Error("You must configure the client with a user");this.config=o,this.logger=o.logger,this.init(t,r,n)}init(e,t,i){var n,s,h;return r(this,void 0,void 0,(function*(){const r=new o.default(this.config.sdkKey,this.config,e);if(this.store=this.config.storeFactory(r),yield this.store.identify(this.config.user),this.dataSourceUpdates=new a.default(this.store,i,t),this.evaluator=new f.default(this.store),yield this.config.bootstrapProvider.populate(this.config.user.keyId,this.dataSourceUpdates),this.config.offline)this.eventProcessor=new _.NullEventProcessor,this.dataSynchronizer=new m.NullDataSynchronizer,this.initSuccess();else{this.eventProcessor=new b.DefaultEventProcessor(r);const t=(0,l.createStreamListeners)(this.dataSourceUpdates,this.logger,{put:()=>this.initSuccess(),patch:()=>this.initSuccess()}),i=this.config.dataSyncMode===w.DataSyncModeEnum.STREAMING?new u.default(this.config.sdkKey,this.config.user,r,e.webSocket,(()=>this.store.version),t,this.config.webSocketPingInterval):new c.default(this.config,new d.default(this.config.sdkKey,this.config,this.platform.info,this.platform.requests),(()=>this.store.version),t,(e=>this.dataSourceErrorHandler(e)));this.dataSynchronizer=null!==(h=null===(s=(n=this.config).dataSynchronizerFactory)||void 0===s?void 0:s.call(n,r,this.store,this.dataSourceUpdates,(()=>this.initSuccess()),(e=>this.dataSourceErrorHandler(e))))&&void 0!==h?h:i}this.start()}))}identify(e){return r(this,void 0,void 0,(function*(){const t=new P.UserValidator;if(!t.is(e))return void t.messages.forEach((e=>{var t;null===(t=this.logger)||void 0===t||t.warn(e)}));this.store.identify(e),this.dataSynchronizer.identify(e);const[i]=this.store.all(h.default.Flags);0===Object.keys(i).length&&(yield this.config.bootstrapProvider.populate(e.keyId,this.dataSourceUpdates))}))}start(){this.config.offline||(this.dataSynchronizer.start(),setTimeout((()=>{var e,t;if(!this.initialized()){const i=`FbClient failed to start successfully within ${this.config.startWaitTime} milliseconds. This error usually indicates a connection issue with FeatBit or an invalid sdkKey.Please double-check your sdkKey and streamingUri/pollingUri configuration. We will continue to initialize the FbClient, it still have a chance to get to work if it's a temporary network issue`,r=new Error(i);return this.state=S.Failed,this.rejectionReason=r,null===(e=this.initReject)||void 0===e||e.call(this,r),null===(t=this.logger)||void 0===t?void 0:t.warn(i)}}),this.config.startWaitTime))}initialized(){return this.state===S.Initialized}waitForInitialization(){return this.initializedPromise?this.initializedPromise:this.state===S.Initialized?(this.initializedPromise=Promise.resolve(this),this.initializedPromise):this.state===S.Failed?(this.initializedPromise=Promise.reject(this.rejectionReason),this.initializedPromise):(this.initializedPromise||(this.initializedPromise=new Promise(((e,t)=>{this.initResolve=e,this.initReject=t}))),this.initializedPromise)}boolVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.bool).value}boolVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.bool)}jsonVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.json).value}jsonVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.json)}numberVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.number).value}numberVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.number)}stringVariation(e,t){return this.evaluateCore(e,t,y.ValueConverters.string).value}stringVariationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.string)}variation(e,t){return this.evaluateCore(e,t,y.ValueConverters.string).value}variationDetail(e,t){return this.evaluateCore(e,t,y.ValueConverters.string)}getAllVariations(){var e;const t=g.default.fromUser(this.config.user);if(!t.valid){const i=new p.ClientError(`${null!==(e=t.message)&&void 0!==e?e:"User not valid;"} returning default value.`);return this.onError(i),Promise.resolve([])}const[i,r]=this.store.all(h.default.Flags),n=Object.keys(i).map((e=>{var t;const i=this.evaluator.evaluate(e);return{flagKey:e,kind:i.kind,reason:i.reason,value:null===(t=i.value)||void 0===t?void 0:t.variation}}));return Promise.resolve(n)}close(){var e;return r(this,void 0,void 0,(function*(){yield this.eventProcessor.close(),null===(e=this.dataSynchronizer)||void 0===e||e.close(),this.store.close()}))}track(e,t){const i=new O.MetricEvent(this.config.user,e,this.platform.info.appType,null!=t?t:1);this.eventProcessor.record(i)}flush(e){return r(this,void 0,void 0,(function*(){try{return yield this.eventProcessor.flush(),null==e||e(!0),!0}catch(t){return null==e||e(!1),!1}}))}evaluateCore(e,t,i){var r,n,s;const o=g.default.fromUser(this.config.user);if(!o.valid){const i=new p.ClientError(`${null!==(r=o.message)&&void 0!==r?r:"User not valid;"} returning default value.`);return this.onError(i),{flagKey:e,kind:v.ReasonKinds.Error,reason:i.message,value:t}}const a=this.evaluator.evaluate(e);if(a.kind===v.ReasonKinds.FlagNotFound){const i=new p.ClientError(a.reason);return this.onError(i),{flagKey:e,kind:a.kind,reason:a.reason,value:t}}this.initialized()?this.eventProcessor.record(a.toEvalEvent(this.config.user)):null===(n=this.logger)||void 0===n||n.warn("Variation called before FeatBit client initialization completed (did you wait for the'ready' event?)");const{isSucceeded:l,value:u}=i(null===(s=a.value)||void 0===s?void 0:s.variation);return l?{flagKey:e,kind:a.kind,reason:a.reason,value:u}:{flagKey:e,kind:v.ReasonKinds.WrongType,reason:"type mismatch",value:t}}dataSourceErrorHandler(e){var t;const i=401===e.code?new Error("Authentication failed. Double check your SDK key."):e;this.onError(i),this.onFailed(i),this.initialized()||(this.state=S.Failed,this.rejectionReason=i,null===(t=this.initReject)||void 0===t||t.call(this,i))}initSuccess(){var e,t;this.initialized()||(this.state=S.Initialized,null===(e=this.logger)||void 0===e||e.info("FbClient started successfully."),null===(t=this.initResolve)||void 0===t||t.call(this,this),this.onReady())}}},5717:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},4881:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},292:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},226:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6399:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},700:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.JsonBootstrapProvider=void 0;const r=i(4426),n=i(5562);t.JsonBootstrapProvider=class{constructor(e){const t=(e||[]).map((e=>Object.assign(Object.assign({},e),{variationOptions:e.variationOptions||[{id:null,variation:e.variation}]}))),i=(0,r.deserializeAll)(t);this.dataSet={flags:i.flags,version:0}}populate(e,t,i){return new Promise(((r,s)=>{if((0,n.isNullOrUndefined)(this.dataSet))return r();t.init(e,this.dataSet,(()=>{r(),null==i||i()}))}))}}},665:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullBootstrapProvider=void 0,t.NullBootstrapProvider=class{constructor(){this.dataSet={flags:{},version:0}}populate(e,t,i){return new Promise(((e,t)=>{e(),null==i||i()}))}}},8317:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(6399),t),n(i(700),t),n(i(665),t)},7837:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.MinInt=t.EmptyString=void 0,t.EmptyString="",t.MinInt=2147483648},4659:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const s=n(i(2093));t.default=class{constructor(e,t,i){this.store=e,this.hasEventListeners=t,this.onChange=i}init(e,t,i){if(e!==this.store.user.keyId)return void(null==i||i());const n=this.hasEventListeners(),o=e=>r(this,void 0,void 0,(function*(){yield this.store.init(t),Promise.resolve().then((()=>{if(n){const i=Object.keys(t).flatMap((i=>{const r=(null==e?void 0:e[i])||{},n=t[i],s=Object.assign(Object.assign({},r),n);return Object.keys(s).filter((e=>this.isUpdated(r&&r[e],n&&n[e])))}));i.length>0&&this.onChange(i)}})),null==i||i()}));if(n){const[e,t]=this.store.all(s.default.Flags);o({flags:e,version:t})}else o()}upsert(e,t,i,n){if(e!==this.store.user.keyId)return void(null==n||n());const{key:s}=i,o=this.hasEventListeners(),a=e=>r(this,void 0,void 0,(function*(){yield this.store.upsert(t,i),Promise.resolve().then((()=>{o&&this.isUpdated(e,i[s])&&this.onChange([s])})),null==n||n()}));o?a(this.store.get(t,s)||void 0):a()}isUpdated(e,t){return!e||!t||t.version>e.version}}},7539:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.createStreamListeners=t.createPatchListener=t.createPutListener=void 0;const n=i(4426);t.createPutListener=(e,t,i=(()=>{}))=>({deserializeData:n.deserializeAll,processJson:(n,{flags:s})=>r(void 0,void 0,void 0,(function*(){const r={flags:s,version:0};null==t||t.debug("Initializing all data"),e.init(n,r,i)}))}),t.createPatchListener=(e,t,i=(()=>{}))=>({deserializeData:n.deserializePatch,processJson:(n,s)=>r(void 0,void 0,void 0,(function*(){0!==(null==s?void 0:s.length)?null==s||s.forEach((r=>{null==t||t.debug(`Updating ${r.data.key} in ${r.kind.namespace}`),e.upsert(n,r.kind,r.data,i)})):null==i||i()}))}),t.createStreamListeners=(e,i,r)=>{const n=new Map;return n.set("put",(0,t.createPutListener)(e,i,null==r?void 0:r.put)),n.set("patch",(0,t.createPatchListener)(e,i,null==r?void 0:r.patch)),n}},3758:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(7539),t),n(i(4659),t)},607:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.DataSyncModeEnum=void 0,function(e){e.POLLING="polling",e.STREAMING="streaming"}(i||(t.DataSyncModeEnum=i={}))},304:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},450:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8722:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullDataSynchronizer=void 0,t.NullDataSynchronizer=class{close(){}start(){}stop(){}identify(){}}},3148:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(7449),n=i(1962),s=i(8688);t.default=class{constructor(e,t,i,r,n){this.requestor=t,this.getStoreTimestamp=i,this.listeners=r,this.errorHandler=n,this.stopped=!1,this.logger=e.logger,this.pollingInterval=e.pollingInterval,this.user=e.user}poll(){var e;if(this.stopped)return;const t=Date.now();null===(e=this.logger)||void 0===e||e.debug("Polling for feature flag and segments updates"),this.requestor.requestData(this.getStoreTimestamp(),this.user,((e,i)=>{var o,a,l,u,c,d,h;const f=Date.now()-t,v=Math.max(this.pollingInterval-f,0);if(null===(o=this.logger)||void 0===o||o.debug("Elapsed: %d ms, sleeping for %d ms",f,v),e){const{status:t}=e;if(t&&!(0,r.isHttpRecoverable)(t)){const i=(0,s.httpErrorMessage)(e,"polling request");return null===(a=this.logger)||void 0===a||a.error(i),void(null===(l=this.errorHandler)||void 0===l||l.call(this,new r.PollingError(i,t)))}null===(u=this.logger)||void 0===u||u.warn((0,s.httpErrorMessage)(e,"polling request","will retry"))}else{let e=[],t=null===(c=this.user)||void 0===c?void 0:c.keyId,r=this.listeners.get("patch");if(i){const s=JSON.parse(i);if("data-sync"===s.messageType){switch(s.data.eventType){case n.StreamResponseEventType.patch:r=this.listeners.get("patch");break;case n.StreamResponseEventType.full:r=this.listeners.get("put")}({featureFlags:e,userKeyId:t}=s.data)}}const s=null===(d=null==r?void 0:r.deserializeData)||void 0===d?void 0:d.call(r,e);null===(h=null==r?void 0:r.processJson)||void 0===h||h.call(r,t,s)}this.timeoutHandle=setTimeout((()=>{this.poll()}),v)}))}identify(e){this.user=Object.assign({},e)}close(){this.stop()}start(){this.poll()}stop(){this.timeoutHandle&&(clearTimeout(this.timeoutHandle),this.timeoutHandle=void 0),this.stopped=!0}}},4943:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(7449),s=i(8688);t.default=class{constructor(e,t,i,r){this.requests=r,this.headers=(0,s.defaultHeaders)(e,i),this.uri=t.pollingUri}request(e,t){return r(this,void 0,void 0,(function*(){const i=yield this.requests.fetch(e,t),r=yield i.text();return{res:i,body:r}}))}requestData(e,t,i){return r(this,void 0,void 0,(function*(){const r={method:"POST",headers:this.headers,body:JSON.stringify(t)};try{const{res:t,body:s}=yield this.request(`${this.uri}?timestamp=${null!=e?e:0}`,r);if(200!==t.status&&304!==t.status){const e=new n.StreamingError(`Unexpected status code: ${t.status}`,t.status);return i(e,void 0)}return i(void 0,304===t.status?null:s)}catch(e){return i(e,void 0)}}))}}},6100:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{constructor(e,t,i,r,n,s,o){this.getStoreTimestamp=n,this.listeners=s;const{logger:a,streamingUri:l}=i;this.logger=a,this.socket=r,this.socket.config({sdkKey:e,streamingUri:l,pingInterval:o,user:t,logger:a,getStoreTimestamp:n}),this.listeners.forEach((({deserializeData:e,processJson:t},i)=>{var r;null===(r=this.socket)||void 0===r||r.addListener(i,(r=>{var n;if(null===(n=this.logger)||void 0===n||n.debug(`Received ${i} event`),null==r?void 0:r.data){const{featureFlags:i,userKeyId:n}=r.data,s=e(i);t(n,s)}}))}))}identify(e){var t;null===(t=this.socket)||void 0===t||t.identify(e)}start(){var e;this.logConnectionStarted(),null===(e=this.socket)||void 0===e||e.connect()}logConnectionStarted(){var e;this.connectionAttemptStartTime=Date.now(),null===(e=this.logger)||void 0===e||e.info(`Stream connection attempt StartTime ${this.connectionAttemptStartTime}`)}close(){this.stop()}stop(){var e;null===(e=this.socket)||void 0===e||e.close(),this.socket=void 0}}},9999:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(607),t),n(i(304),t),n(i(450),t),n(i(8722),t),n(i(3148),t),n(i(4943),t),n(i(1962),t),n(i(6870),t),n(i(6100),t)},1962:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.StreamResponseEventType=void 0,function(e){e.full="full",e.patch="patch"}(i||(t.StreamResponseEventType=i={}))},6870:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.generateConnectionToken=void 0;const i={0:"Q",1:"B",2:"W",3:"S",4:"P",5:"H",6:"D",7:"X",8:"Z",9:"U"};function r(e,t){var r="000000000000"+e;return r.slice(r.length-t).split("").map((e=>i[e])).join("")}t.generateConnectionToken=function(e){e=e.replace(/=*$/,"");const t=Date.now(),i=r(t,t.toString().length),n=Math.max(Math.floor(Math.random()*e.length),2);return`${r(n,3)}${r(i.length,2)}${e.slice(0,n)}${i}${e.slice(n)}`}},7449:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.isHttpRecoverable=t.ClientError=t.UnexpectedResponseError=t.StreamingError=t.PollingError=void 0;class i extends Error{constructor(e,t){super(e),this.status=t,this.name="FbPollingError"}}t.PollingError=i;class r extends Error{constructor(e,t){super(e),this.code=t,this.name="FbStreamingError"}}t.StreamingError=r;class n extends Error{constructor(e){super(e),this.name="FbUnexpectedResponseError"}}t.UnexpectedResponseError=n;class s extends Error{constructor(e){super(e),this.name="FbClientError"}}t.ClientError=s,t.isHttpRecoverable=function(e){return!(e>=400&&e<500)||400===e||408===e||429===e}},3100:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5192),n=i(7584);class s{constructor(e,t,i){this.kind=e,this.value=t,this.reason=i}static flagNotFound(e){return new s(r.ReasonKinds.FlagNotFound,null,`flag not found: ${e}`)}static matched(e){return new s(r.ReasonKinds.Match,e,"target match")}toEvalEvent(e){var t,i,s;if(this.kind!==r.ReasonKinds.Match)return null;const o=null===(t=this.value)||void 0===t?void 0:t.variations.find((e=>{var t;return e.value===(null===(t=this.value)||void 0===t?void 0:t.variation)}));return new n.EvalEvent(e,null===(i=this.value)||void 0===i?void 0:i.id,o,null===(s=this.value)||void 0===s?void 0:s.sendToExperiment)}}t.default=s},8874:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=r(i(3100)),s=r(i(2093));t.default=class{constructor(e){this.store=e}evaluate(e){const t=this.store.get(s.default.Flags,e);return t?n.default.matched(t):n.default.flagNotFound(e)}}},3675:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5192:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.ReasonKinds=void 0,function(e){e.ClientNotReady="ClientNotReady",e.Match="Match",e.WrongType="WrongType",e.FlagNotFound="FlagNotFound",e.Error="Error"}(i||(t.ReasonKinds=i={}))},9653:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.VariationDataType=void 0,function(e){e.string="string",e.boolean="boolean",e.number="number",e.json="json",e.empty=""}(i||(t.VariationDataType=i={}))},4228:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(9653),t)},9823:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(4228),t),n(i(3100),t),n(i(8874),t),n(i(3675),t),n(i(5192),t)},2305:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventProcessor=void 0;const n=i(5381),s=i(7584),o=i(5562),a=i(1218);t.DefaultEventProcessor=class{constructor(e){this.closed=!1;const{logger:t,flushInterval:i,maxEventsInQueue:r}=e;this.logger=t,this.flushInterval=i,this.eventQueue=new a.DefaultEventQueue(r,this.logger),this.eventDispatcher=new n.EventDispatcher(e,this.eventQueue),this.flushLoop()}flushLoop(){this.closed||setTimeout((()=>r(this,void 0,void 0,(function*(){try{yield this.flush()}catch(e){this.logger.error("Unexpected error while flushing events in event processor.",e)}this.flushLoop()}))),this.flushInterval)}flush(){const e=new s.FlushEvent;return this.record(e),e.waitForCompletion()}close(){return r(this,void 0,void 0,(function*(){if(this.closed)return;const e=new s.ShutdownEvent;this.record(e);try{yield e.waitForCompletion()}catch(e){this.logger.error("Event processor shutdown but not complete.")}this.eventQueue.close(),this.closed=!0}))}record(e){return!((0,o.isNullOrUndefined)(e)||!this.eventQueue.addEvent(e)&&(e instanceof s.FlushEvent&&e.complete(),1))}}},1218:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventQueue=void 0,t.DefaultEventQueue=class{constructor(e,t){this.capacity=e,this.logger=t,this.closed=!1,this.events=[]}addEvent(e){return!this.closed&&(this.events.length>=this.capacity?(this.logger.warn("Events are being produced faster than they can be processed. We shouldn't see this."),!1):(this.events.push(e),!0))}clear(){this.events=[]}shift(){return this.events.shift()}close(){this.closed=!0}get eventsSnapshot(){return[...this.events]}get length(){return this.events.length}get isEmpty(){return 0===this.length}}},2580:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventSender=void 0;const s=i(8174),o=i(8688),a=i(7449),l=n(i(1773));t.DefaultEventSender=class{constructor(e){const{sdkKey:t,eventsUri:i,platform:r}=e,{info:n,requests:s}=r;this.defaultHeaders=(0,o.defaultHeaders)(t,n),this.eventsUri=i,this.requests=s}send(e,t){return r(this,void 0,void 0,(function*(){const i={status:s.DeliveryStatus.Succeeded},r=Object.assign(Object.assign({},this.defaultHeaders),{"content-type":"application/json"});let n;try{const{status:t}=yield this.requests.fetch(this.eventsUri,{headers:r,body:e,method:"POST"});if(t>=200&&t<=299)return i;if(n=new a.UnexpectedResponseError((0,o.httpErrorMessage)({status:t,message:"some events were dropped"},"event posting")),!(0,a.isHttpRecoverable)(t))return i.status=s.DeliveryStatus.FailedAndMustShutDown,i.error=n,i}catch(e){n=e}return n&&!t?(i.status=s.DeliveryStatus.Failed,i.error=n,i):(yield(0,l.default)(),this.send(e,!1))}))}}},9657:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.DefaultEventSerializer=void 0;const r=i(7584);t.DefaultEventSerializer=class{serialize(e){const t=e.map((e=>e instanceof r.EvalEvent||e instanceof r.MetricEvent?e.toPayload():null)).filter((e=>null!==e));return JSON.stringify(t)}}},5381:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))},n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.EventDispatcher=void 0;const s=i(8174),o=i(1218),a=i(2580),l=i(7584),u=i(9657),c=n(i(1773));t.EventDispatcher=class{constructor(e,t){this.maxEventPerRequest=50,this.stopped=!1;const{logger:i,maxEventsInQueue:r}=e;this.logger=i,this.buffer=new o.DefaultEventQueue(r,this.logger),this.sender=new a.DefaultEventSender(e),this.serializer=new u.DefaultEventSerializer,this.dispatchLoop(t).then()}dispatchLoop(e){return r(this,void 0,void 0,(function*(){this.logger.debug("Start dispatch loop.");let t=!0;for(;t;)try{const i=e.shift();if(void 0===i){yield(0,c.default)(1e3);continue}i instanceof l.PayloadEvent?this.addEventToBuffer(i):i instanceof l.FlushEvent?yield this.triggerFlush(i):i instanceof l.ShutdownEvent&&(yield this.triggerFlush(i),this.stopped=!0,t=!1)}catch(e){this.logger.error("Unexpected error in event dispatcher.",e)}this.logger.debug("Finish dispatch loop.")}))}addEventToBuffer(e){this.stopped||(this.buffer.addEvent(e)?this.logger.debug("Added event to buffer."):this.logger.warn("Exceeded event queue capacity, event will be dropped. Increase capacity to avoid dropping events."))}triggerFlush(e){return r(this,void 0,void 0,(function*(){if(this.stopped)return void e.complete();if(this.buffer.isEmpty)return e.complete(),void this.logger.debug("Flush empty buffer.");const t=this.buffer.eventsSnapshot;this.buffer.clear();try{yield this.flushEvents(t),this.logger.debug(`${t.length} events has been flushed.`)}catch(e){this.logger.warn("Exception happened when flushing events",e)}e.complete()}))}flushEvents(e){return r(this,void 0,void 0,(function*(){const t=(e=this.getUniqueEvents(e)).length;for(let i=0;i{Object.defineProperty(t,"__esModule",{value:!0})},6735:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},1564:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8174:(e,t)=>{var i;Object.defineProperty(t,"__esModule",{value:!0}),t.DeliveryStatus=void 0,function(e){e[e.Succeeded=0]="Succeeded",e[e.Failed=1]="Failed",e[e.FailedAndMustShutDown=2]="FailedAndMustShutDown"}(i||(t.DeliveryStatus=i={}))},407:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.NullEventProcessor=void 0,t.NullEventProcessor=class{flush(){return Promise.resolve()}close(){return Promise.resolve()}record(e){return!1}}},7584:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.EvalEvent=t.MetricEvent=t.PayloadEvent=t.ShutdownEvent=t.FlushEvent=t.AsyncEvent=void 0;class i{get hash(){return this.timestamp.toString()}constructor(){this.timestamp=(new Date).getTime(),this.isCompletedPromise=new Promise((e=>{this.resolveFn=e}))}waitForCompletion(){return this.isCompletedPromise}complete(){var e;null===(e=this.resolveFn)||void 0===e||e.call(this,this)}}t.AsyncEvent=i,t.FlushEvent=class extends i{},t.ShutdownEvent=class extends i{};class r{constructor(){this.timestamp=(new Date).getTime()}get hash(){return this.timestamp.toString()}toPayload(){}}t.PayloadEvent=r,t.MetricEvent=class extends r{constructor(e,t,i,r){super(),this.user=e,this.eventName=t,this.appType=i,this.metricValue=r}userPayload(){return{keyId:this.user.keyId,name:this.user.name,customizedProperties:this.user.customizedProperties}}toPayload(){return{user:this.userPayload(),metrics:[{route:"index/metric",timestamp:this.timestamp,numericValue:this.metricValue,appType:this.appType,eventName:this.eventName,type:"CustomEvent"}]}}get hash(){const e=this.toPayload(),t={user:e.user,metrics:e.metrics.map((e=>Object.assign(Object.assign({},e),{timestamp:void 0})))};return JSON.stringify(t)}},t.EvalEvent=class extends r{constructor(e,t,i,r){super(),this.user=e,this.flagKey=t,this.variation=i,this.sendToExperiment=r}userPayload(){return{keyId:this.user.keyId,name:this.user.name,customizedProperties:this.user.customizedProperties}}toPayload(){return{user:this.userPayload(),variations:[{featureFlagKey:this.flagKey,sendToExperiment:this.sendToExperiment,timestamp:this.timestamp,variation:this.variation}]}}get hash(){const e=this.toPayload(),t={user:e.user,variations:e.variations.map((e=>Object.assign(Object.assign({},e),{timestamp:void 0})))};return JSON.stringify(t)}}},4008:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(2305),t),n(i(1218),t),n(i(2580),t),n(i(9657),t),n(i(7584),t),n(i(5381),t),n(i(8284),t),n(i(6735),t),n(i(1564),t),n(i(8174),t),n(i(407),t)},9872:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(8317),t),n(i(3758),t),n(i(9823),t),n(i(4008),t),n(i(7302),t),n(i(1045),t),n(i(9718),t),n(i(8598),t),n(i(9999),t),n(i(2710),t),n(i(1058),t),n(i(7837),t),n(i(1731),t),n(i(7449),t),n(i(70),t),n(i(5717),t),n(i(4881),t),n(i(292),t),n(i(226),t),n(i(4129),t)},5768:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.BasicLogger=void 0;const n=r(i(3919)),s={debug:0,info:1,warn:2,error:3,none:4},o=["debug","info","warn","error","none"];class a{static get(){return new a({})}constructor(e){var t,i,r;this.logLevel=null!==(i=s[null!==(t=e.level)&&void 0!==t?t:"info"])&&void 0!==i?i:s.info,this.name=null!==(r=e.name)&&void 0!==r?r:"FeatBit",this.destination=e.destination,this.formatter=e.formatter}tryFormat(...e){var t;try{return this.formatter?null===(t=this.formatter)||void 0===t?void 0:t.call(this,...e):(0,n.default)(...e)}catch(t){return(0,n.default)(...e)}}tryWrite(e){try{this.destination(e)}catch(t){console.error(e)}}log(e,t){if(e>=this.logLevel){const i=`${o[e]}: [${this.name}]`;try{this.destination?this.tryWrite(`${i} ${this.tryFormat(...t)}`):console.error(...t)}catch(e){console.error(...t)}}}error(...e){this.log(s.error,e)}warn(...e){this.log(s.warn,e)}info(...e){this.log(s.info,e)}debug(...e){this.log(s.debug,e)}}t.BasicLogger=a},7973:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5781:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7076:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7689:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.SafeLogger=void 0;const r=i(5862),n={error:r.TypeValidators.Function,warn:r.TypeValidators.Function,info:r.TypeValidators.Function,debug:r.TypeValidators.Function};t.SafeLogger=class{constructor(e,t){Object.entries(n).forEach((([t,i])=>{if(!i.is(e[t]))throw new Error(`Provided logger instance must support logger.${t}(...) method`)})),this.logger=e,this.fallback=t}log(e,t){try{this.logger[e](...t)}catch(i){this.fallback[e](...t)}}error(...e){this.log("error",e)}warn(...e){this.log("warn",e)}info(...e){this.log("info",e)}debug(...e){this.log("debug",e)}}},3919:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5862);function n(e){if("string"==typeof e)return e;if(void 0===e)return"undefined";if(null===e)return"null";if(Object.prototype.hasOwnProperty.call(e,"toString"))try{return e.toString()}catch(e){}if("bigint"==typeof e)return`${e}n`;try{return JSON.stringify(e)}catch(e){return e instanceof TypeError&&e.message.indexOf("circular")>=0?"[Circular]":"[Not Stringifiable]"}}const s={s:e=>n(e),d:e=>function(e){return"symbol"==typeof e?"NaN":"bigint"==typeof e?`${e}n`:String(Number(e))}(e),i:e=>function(e){return"symbol"==typeof e?"NaN":"bigint"==typeof e?`${e}n`:String(parseInt(e,10))}(e),f:e=>function(e){return"symbol"==typeof e?"NaN":String(parseFloat(e))}(e),j:e=>n(e),o:e=>n(e),O:e=>n(e),c:()=>""};t.default=function(...e){var t;const i=e.shift();if(r.TypeValidators.String.is(i)){let r="",o=0;for(;o{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{constructor(e,t,i){this.sdkKey=e,this.platform=i,this.logger=t.logger,this.offline=t.offline,this.flushInterval=t.flushInterval,this.maxEventsInQueue=t.maxEventsInQueue,this.streamingUri=t.streamingUri,this.pollingUri=t.pollingUri,this.eventsUri=t.eventsUri}}},8222:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},4670:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6273:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},8758:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},9176:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.default=class{static optionBelowMinimum(e,t,i){return`Config option "${e}" had invalid value of ${t}, using minimum of ${i} instead`}static unknownOption(e){return`Ignoring unknown config option "${e}"`}static wrongOptionType(e,t,i){return`Config option "${e}" should be of type ${t}, got ${i}, using default value`}static wrongOptionTypeBoolean(e,t){return`Config option "${e}" should be a boolean, got ${t}, converting to boolean`}static partialEndpoint(e){return`You have set custom uris without specifying the ${e} URI; connections may not work properly`}static mandatory(e){return`${e} is mandatory`}static invalidOptionValue(e){return`Invalid option value: ${e}`}static missingKeyInBootstrapValue(e){return`Missing key "${e}" in bootstrap value`}}},595:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.UserBuilder=void 0,t.UserBuilder=class{constructor(e){this._keyId="",this._name="",this._custom=[],this._keyId=e}name(e){return this._name=e,this}custom(e,t){var i;return null===(i=this._custom)||void 0===i||i.push({name:e,value:t}),this}build(){return{name:this._name,keyId:this._keyId,customizedProperties:this._custom}}}},5862:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.TypeValidators=t.KindValidator=t.DateValidator=t.UserValidator=t.BootstrapValidator=t.NullableBoolean=t.Function=t.StringMatchingRegex=t.NumberWithMinimum=t.TypeArray=t.Type=t.FactoryOrInstance=void 0;const n=r(i(9176));class s{is(e){if(Array.isArray(e))return!1;const t=typeof e;return"function"===t||"object"===t}getType(){return"factory method or object"}}t.FactoryOrInstance=s;class o{constructor(e,t){this.typeName=e,this.typeOf=typeof t}is(e){return!Array.isArray(e)&&typeof e===this.typeOf}getType(){return this.typeName}}t.Type=o;class a{constructor(e,t){this.typeName=e,this.typeOf=typeof t}is(e){return!!Array.isArray(e)&&(!(e.length>0)||e.every((e=>typeof e===this.typeOf)))}getType(){return this.typeName}}t.TypeArray=a;class l extends o{constructor(e){super(`number with minimum value of ${e}`,0),this.min=e}is(e){return typeof e===this.typeOf&&e>=this.min}}t.NumberWithMinimum=l;class u extends o{constructor(e){super(`string matching ${e}`,""),this.expression=e}is(e){return!!e.match(this.expression)}}t.StringMatchingRegex=u;class c{is(e){return"function"==typeof e}getType(){return"function"}}t.Function=c;class d{is(e){return"boolean"==typeof e||null==e}getType(){return"boolean | undefined | null"}}t.NullableBoolean=d,t.BootstrapValidator=class{constructor(){this.messages=[]}is(e){if("object"!=typeof e||null===e)return this.messages.push(n.default.invalidOptionValue("bootstrap")),!1;try{const t=e;for(let e of t){["id","variation"].every((t=>Object.keys(e).includes(t)));const t=Object.keys(e);if(t.includes("id")&&this.messages.push(n.default.missingKeyInBootstrapValue("id")),t.includes("variation")&&this.messages.push(n.default.missingKeyInBootstrapValue("variation")),this.messages.length>0)return!1}}catch(t){return this.messages.push(n.default.wrongOptionType("bootstrap",this.getType(),typeof e)),!1}return!0}getType(){return"IFlagBase[]"}},t.UserValidator=class{constructor(){this.messages=[]}is(e){if("object"!=typeof e||null===e)return this.messages.push(n.default.mandatory("user")),!1;const t=e;return"string"!=typeof t.keyId||""===t.keyId.trim()?(this.messages.push(n.default.mandatory("user.keyId")),!1):"string"==typeof t.name&&""!==t.name.trim()||(this.messages.push(n.default.mandatory("user.name")),!1)}getType(){return"user"}};const h=/^\d\d\d\d-\d\d-\d\dT\d\d:\d\d:\d\d(\.\d\d*)?(Z|[-+]\d\d(:\d\d)?)/;class f{is(e){return"number"==typeof e||"string"==typeof e&&h.test(e)}getType(){return"date"}}t.DateValidator=f;class v extends u{constructor(){super(/^(\w|\.|-)+$/)}is(e){return super.is(e)&&"kind"!==e}}t.KindValidator=v;class p{static createTypeArray(e,t){return new a(e,t)}static numberWithMin(e){return new l(e)}static stringMatchingRegex(e){return new u(e)}}t.TypeValidators=p,p.String=new o("string",""),p.Number=new o("number",0),p.ObjectOrFactory=new s,p.Object=new o("object",{}),p.StringArray=new a("string[]",""),p.Boolean=new o("boolean",!0),p.User=new o("object",{}),p.Bootstrap=new o("object",{}),p.Function=new c,p.Date=new f,p.Kind=new v,p.NullableBoolean=new d},1045:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(8311),t),n(i(8222),t),n(i(4670),t),n(i(6273),t),n(i(8758),t),n(i(9176),t),n(i(595),t),n(i(5862),t)},5309:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},9938:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},5800:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6510:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},2833:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(5972);t.default=class{get appType(){return"Browser-Client-SDK"}platformData(){return{os:{},name:"Browser",additional:{}}}sdkData(){return{name:r.name,version:r.version,userAgentBase:this.appType}}}},9174:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=r(i(2833)),s=i(891),o=r(i(9018));t.default=class{constructor(e){this.info=new n.default,this.requests=new s.BrowserRequests,this.webSocket=new o.default}}},891:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.BrowserRequests=void 0,t.BrowserRequests=class{fetch(e,t={}){return fetch(e,t)}}},9018:(e,t,i)=>{Object.defineProperty(t,"__esModule",{value:!0});const r=i(3046),n=i(6842),s=i(6870),o=i(1962),a=[1e3,3e3,5e3,7e3,11e3,13e3,3e4,6e4];t.default=(0,r.Emits)(class{constructor(){this.retryCounter=0,this.closed=!1,this._config={},this.emitter=new n.EventEmitter}identify(e){this._config.user=e,this.doDataSync()}connect(){var e,t,i,r;let n=this;const a=Date.now(),l=this._config.streamingUri.replace(/^http/,"ws")+`?type=client&token=${(0,s.generateConnectionToken)(this._config.sdkKey)}`;this.ws=new WebSocket(l),null===(e=n.ws)||void 0===e||e.addEventListener("open",(function(e){n._config.logger.info(`WebSocket connection succeeded, connection time: ${Date.now()-a} ms`),n.doDataSync(),n.sendPingMessage()})),null===(t=n.ws)||void 0===t||t.addEventListener("close",(function(e){n._config.logger.warn("WebSocket closed"),4003!==e.code&&n.reconnect()})),null===(i=n.ws)||void 0===i||i.addEventListener("error",(function(e){n._config.logger.debug("error")})),null===(r=n.ws)||void 0===r||r.addEventListener("message",(function(e){const t=JSON.parse(e.data);if("data-sync"===t.messageType)switch(t.data.eventType){case o.StreamResponseEventType.patch:n.emitter.emit("patch",t);break;case o.StreamResponseEventType.full:n.emitter.emit("put",t)}}))}close(){var e;this.closed=!0,null===(e=this.ws)||void 0===e||e.close(4003,"The client is closed by user"),this.ws=void 0}config(e){e.emitter&&(this.emitter=e.emitter),this._config=Object.assign({},e)}sendPingMessage(){const e={messageType:"ping",data:null};setTimeout((()=>{var t;try{(null===(t=this.ws)||void 0===t?void 0:t.readyState)===WebSocket.OPEN?(this._config.logger.debug("sending ping"),this.ws.send(JSON.stringify(e)),this.sendPingMessage()):this._config.logger.debug(`socket closed at ${new Date}`)}catch(e){this._config.logger.debug(e)}}),this._config.pingInterval)}doDataSync(){var e,t;const i={messageType:"data-sync",data:{timestamp:this._config.getStoreTimestamp(),user:this._config.user}};try{(null===(e=this.ws)||void 0===e?void 0:e.readyState)===WebSocket.OPEN?(this._config.logger.debug("requesting data"),null===(t=this.ws)||void 0===t||t.send(JSON.stringify(i))):this._config.logger.error("not requesting data because socket not open")}catch(e){this._config.logger.debug(e)}}reconnect(){if(!this.closed){this.ws=void 0;const e=a[Math.min(this.retryCounter++,a.length-1)];this._config.logger.info(`The client will try to reconnect in ${e} milliseconds.`),setTimeout((()=>{this._config.logger.info(`The client is trying to reconnect, flag evaluation results may be stale until reconnected, waited for: ${e} milliseconds`),this.connect()}),e)}}})},8322:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0});const n=i(4129),s=i(5768),o=i(6842),a=i(7689),l=i(3046),u=r(i(9174)),c=r(i(6940));class d extends n.FbClientCore{constructor(e,t=void 0){const i=new s.BasicLogger({level:"none",destination:console.log}),r=e.logger?new a.SafeLogger(e.logger,i):i,n=new o.EventEmitter(r);let{store:l}=e;l||(l=new c.default(e)),super(Object.assign(Object.assign({},e),{logger:r,store:l}),null!=t?t:new u.default(Object.assign(Object.assign({},e),{logger:r})),{onError:e=>{n.listenerCount("error")&&n.emit("error",e)},onFailed:e=>{n.emit("failed",e)},onReady:()=>{n.emit("ready")},onUpdate:e=>{n.emit("update",[e]),e.forEach((e=>n.emit(`update:${e}`,e)))},hasEventListeners:()=>n.eventNames().some((e=>"update"===e||"string"==typeof e&&e.startsWith("update:")))}),this.emitter=n}}t.default=(0,l.Emits)(d)},6940:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(443),s=i(6860),o=i(5067);class a extends s.BaseStore{constructor(e){super(),this.logger=e.logger}close(){}get description(){return"local-storage-store"}saveUser(){return r(this,void 0,void 0,(function*(){localStorage.setItem(n.CurrentUserStorageKey,(0,o.serializeUser)(this._user))}))}dumpStoreToStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`;localStorage.setItem(e,JSON.stringify(this.store))}))}loadStoreFromStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`,t=localStorage.getItem(e);let i=null;try{t&&t.trim().length>0&&(i=JSON.parse(t))}catch(t){this.logger.error(`error while loading local data store: ${e}`,t)}this.store=i||{flags:{},version:0}}))}}t.default=a},9718:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)},s=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.BrowserWebSocket=void 0,n(i(5309),t),n(i(5800),t),n(i(9938),t),n(i(6510),t),n(i(2894),t),n(i(891),t);const o=s(i(9018));t.BrowserWebSocket=o.default},2894:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},6860:function(e,t){var i=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.BaseStore=void 0,t.BaseStore=class{constructor(){this.store={},this.initCalled=!1,this._user={}}identify(e){return i(this,void 0,void 0,(function*(){this._user=Object.assign({},e),yield this.saveUser(),yield this.loadStoreFromStorage()}))}get user(){return this._user}addItem(e,t,r){return i(this,void 0,void 0,(function*(){let i=this.store[e.namespace];if(i||(i={},this.store[e.namespace]=i),Object.hasOwnProperty.call(i,t)){const e=i[t];(!e||e.versionthis.store.version&&(this.store.version=r.version),yield this.dumpStoreToStorage()}))}get(e,t){const i=this.store[e.namespace];if(i&&Object.prototype.hasOwnProperty.call(i,t)){const e=i[t];if(e)return e}return null}all(e){var t;const i={},r=null!==(t=this.store[e.namespace])&&void 0!==t?t:{};return Object.entries(r).forEach((([e,t])=>{t&&(i[e]=t)})),[i,this.store.version]}init(e){return i(this,void 0,void 0,(function*(){this.store=e,Object.keys(e).map((t=>{Object.entries(e[t]).forEach((([e,t])=>{const i=t;i.version>this.store.version&&(this.store.version=i.version)}))})),yield this.dumpStoreToStorage(),this.initCalled=!0}))}upsert(e,t){return i(this,void 0,void 0,(function*(){yield this.addItem(e,t.key,t)}))}initialized(){return this.initCalled}close(){}get version(){return this.store.version}get description(){return""}saveUser(){return i(this,void 0,void 0,(function*(){}))}loadStoreFromStorage(){return i(this,void 0,void 0,(function*(){}))}dumpStoreToStorage(){return i(this,void 0,void 0,(function*(){}))}}},2093:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0});class i{}i.Flags={namespace:"flags"},t.default=i},356:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},7783:function(e,t,i){var r=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0});const n=i(443),s=i(6860);class o extends s.BaseStore{constructor(){super(),this.allStores={}}close(){}get description(){return"in-memory-store"}saveUser(){return r(this,void 0,void 0,(function*(){}))}dumpStoreToStorage(){return r(this,void 0,void 0,(function*(){const e=`${n.StoreStorageKey}-${this._user.keyId}`;this.allStores[e]=Object.assign({},this.store)}))}loadStoreFromStorage(){var e;return r(this,void 0,void 0,(function*(){const t=`${n.StoreStorageKey}-${this._user.keyId}`;this.store=null!==(e=this.allStores[t])&&void 0!==e?e:{flags:{},version:0}}))}}t.default=o},8598:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(2093),t),n(i(356),t),n(i(7783),t),n(i(4426),t),n(i(443),t),n(i(6860),t)},4426:function(e,t,i){var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}};Object.defineProperty(t,"__esModule",{value:!0}),t.deserializePatch=t.deserializeAll=void 0;const n=r(i(2093));t.deserializeAll=function(e){const t={[n.default.Flags.namespace]:{}};return(null==e?void 0:e.length)&&(t[n.default.Flags.namespace]=e.reduce(((e,t)=>(e[t.id]=Object.assign(Object.assign({},t),{version:t.timestamp||0,key:t.id,variations:t.variationOptions}),e)),{})),t},t.deserializePatch=function(e){return[...(null==e?void 0:e.map((e=>({data:Object.assign(Object.assign({},e),{version:e.timestamp,key:e.id,variations:e.variationOptions}),kind:n.default.Flags}))))||[]]}},443:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.CurrentUserStorageKey=t.StoreStorageKey=void 0,t.StoreStorageKey="fb-datastore",t.CurrentUserStorageKey="fb-user"},3046:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.Emits=void 0,t.Emits=function(e){return class extends e{on(e,t,i){return this.emitter.on(e,t,i),this}addListener(e,t,i){return this.emitter.addListener(e,t,i),this}once(e,t,i){return this.emitter.once(e,t,i),this}removeListener(e,t,i){return this.emitter.removeListener(e,t,i),this}off(e,t,i){return this.emitter.off(e,t,i),this}removeAllListeners(e){return this.emitter.removeAllListeners(e),this}listeners(e){return this.emitter.listeners(e)}emit(e,...t){return this.emitter.emit(e,t),this}listenerCount(e){return this.emitter.listenerCount(e)}prependListener(e,t,i){return this.emitter.prependListener(e,t,i),this}prependOnceListener(e,t,i){return this.emitter.prependOnceListener(e,t,i),this}eventNames(){return this.emitter.eventNames()}maybeReportError(e){return this.emitter.maybeReportError(e),this}}}},6842:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.EventEmitter=void 0,t.EventEmitter=class{constructor(e){this.logger=e,this.events={}}listeningTo(e){return!!this.events[e]}on(e,t,i){return this.events[e]=this.events[e]||[],this.events[e]=this.events[e].concat({handler:t,context:i}),this}addListener(e,t,i){return this.on(e,t,i)}once(e,t,i){const r=(...n)=>{this.off(e,r,i),t.apply(i,n)};return this.on(e,r,i)}off(e,t,i){if(!this.events[e])return this;for(let r=0;re.handler)):[]}emit(e,...t){if(!this.events[e])return this;const i=[...this.events[e]];for(let e=0;e{this.off(e,r,i),t.apply(i,n)};return this.prependListener(e,r,i)}eventNames(){return Object.keys(this.events)}maybeReportError(e){var t;return e?(this.listeningTo("error")?this.emit("error",e):null===(t=this.logger)||void 0===t||t.error(e),this):this}}},1142:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.ValueConverters=void 0;class i{static bool(e){return"TRUE"===(null==e?void 0:e.toUpperCase())?i.success(!0):"FALSE"===(null==e?void 0:e.toUpperCase())?i.success(!1):i.error()}static number(e){const t=Number(e);return Number.isNaN(t)?i.error():i.success(t)}static string(e){return i.success(e)}static json(e){try{const t=JSON.parse(e);return i.success(t)}catch(e){return i.error()}}static success(e){return{isSucceeded:!0,value:e}}static error(){return{isSucceeded:!1}}}t.ValueConverters=i},7266:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0})},1624:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.canonicalizeUri=void 0,t.canonicalizeUri=function(e){return e.replace(/\/+$/,"")}},9183:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.debounce=void 0,t.debounce=(e,t=5e3)=>{let i;return(...r)=>{clearTimeout(i),i=setTimeout((()=>{e(...r)}),t)}}},8688:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.httpErrorMessage=t.defaultHeaders=void 0,t.defaultHeaders=function(e,t){const{userAgentBase:i,version:r}=t.sdkData();return{"Content-Type":"application/json","User-Agent":`${null!=i?i:t.appType}/${r}`,Authorization:e}},t.httpErrorMessage=function(e,t,i){let r;return r=e.status?`error ${e.status}${401===e.status?" (invalid SDK key)":""}`:`I/O error (${e.message||e})`,`Received ${r} for ${t} - ${null!=i?i:"giving up permanently"}`}},2710:function(e,t,i){var r=this&&this.__createBinding||(Object.create?function(e,t,i,r){void 0===r&&(r=i);var n=Object.getOwnPropertyDescriptor(t,i);n&&!("get"in n?!t.__esModule:n.writable||n.configurable)||(n={enumerable:!0,get:function(){return t[i]}}),Object.defineProperty(e,r,n)}:function(e,t,i,r){void 0===r&&(r=i),e[r]=t[i]}),n=this&&this.__exportStar||function(e,t){for(var i in e)"default"===i||Object.prototype.hasOwnProperty.call(t,i)||r(t,e,i)};Object.defineProperty(t,"__esModule",{value:!0}),n(i(5562),t),n(i(1773),t),n(i(1142),t),n(i(7266),t),n(i(5067),t),n(i(9183),t)},5562:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.isNullOrUndefined=void 0,t.isNullOrUndefined=function(e){return null==e}},5067:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.serializeUser=void 0,t.serializeUser=function(e){var t;return e?`${e.keyId},${e.name},${null===(t=e.customizedProperties)||void 0===t?void 0:t.sort(((e,t)=>{const i=e.name.toLowerCase(),r=t.name.toLowerCase();return ir?1:0})).map((e=>`${e.name}:${e.value}`)).join(",")}`:""}},1773:function(e,t){var i=this&&this.__awaiter||function(e,t,i,r){return new(i||(i=Promise))((function(n,s){function o(e){try{l(r.next(e))}catch(e){s(e)}}function a(e){try{l(r.throw(e))}catch(e){s(e)}}function l(e){var t;e.done?n(e.value):(t=e.value,t instanceof i?t:new i((function(e){e(t)}))).then(o,a)}l((r=r.apply(e,t||[])).next())}))};Object.defineProperty(t,"__esModule",{value:!0}),t.default=(e=1e3)=>i(void 0,void 0,void 0,(function*(){return new Promise((t=>{setTimeout(t,e)}))}))},5972:(e,t)=>{Object.defineProperty(t,"__esModule",{value:!0}),t.name=t.version=void 0,t.version="3.0.3",t.name="@featbit/js-client-sdk"}},t={};return function i(r){var n=t[r];if(void 0!==n)return n.exports;var s=t[r]={exports:{}};return e[r].call(s.exports,s,s.exports,i),s.exports}(9872)})())); //# sourceMappingURL=featbit-js-client-sdk.js.map \ No newline at end of file diff --git a/examples/web-app/umd/featbit-js-client-sdk.js.map b/examples/web-app/umd/featbit-js-client-sdk.js.map index 96c7dc6..e17cc77 100644 --- a/examples/web-app/umd/featbit-js-client-sdk.js.map +++ b/examples/web-app/umd/featbit-js-client-sdk.js.map @@ -1 +1 @@ -{"version":3,"file":"featbit-js-client-sdk.js","mappings":"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","sources":["webpack://@featbit/js-client-sdk/webpack/universalModuleDefinition","webpack://@featbit/js-client-sdk/./src/Configuration.ts","webpack://@featbit/js-client-sdk/./src/Context.ts","webpack://@featbit/js-client-sdk/./src/FbClientBuilder.ts","webpack://@featbit/js-client-sdk/./src/FbClientCore.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/JsonBootstrapProvider.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/NullBootstrapProvider.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/index.ts","webpack://@featbit/js-client-sdk/./src/constants.ts","webpack://@featbit/js-client-sdk/./src/data-sources/DataSourceUpdates.ts","webpack://@featbit/js-client-sdk/./src/data-sources/createStreamListeners.ts","webpack://@featbit/js-client-sdk/./src/data-sources/index.ts","webpack://@featbit/js-client-sdk/./src/data-sync/DataSyncMode.ts","webpack://@featbit/js-client-sdk/./src/data-sync/NullDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/PollingDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/Requestor.ts","webpack://@featbit/js-client-sdk/./src/data-sync/WebSocketDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/index.ts","webpack://@featbit/js-client-sdk/./src/data-sync/types.ts","webpack://@featbit/js-client-sdk/./src/data-sync/utils.ts","webpack://@featbit/js-client-sdk/./src/errors.ts","webpack://@featbit/js-client-sdk/./src/evaluation/EvalResult.ts","webpack://@featbit/js-client-sdk/./src/evaluation/Evaluator.ts","webpack://@featbit/js-client-sdk/./src/evaluation/ReasonKinds.ts","webpack://@featbit/js-client-sdk/./src/evaluation/data/IFlag.ts","webpack://@featbit/js-client-sdk/./src/evaluation/data/index.ts","webpack://@featbit/js-client-sdk/./src/evaluation/index.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventProcessor.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventQueue.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventSender.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventSerializer.ts","webpack://@featbit/js-client-sdk/./src/events/EventDispatcher.ts","webpack://@featbit/js-client-sdk/./src/events/IEventSender.ts","webpack://@featbit/js-client-sdk/./src/events/NullEventProcessor.ts","webpack://@featbit/js-client-sdk/./src/events/event.ts","webpack://@featbit/js-client-sdk/./src/events/index.ts","webpack://@featbit/js-client-sdk/./src/index.ts","webpack://@featbit/js-client-sdk/./src/logging/BasicLogger.ts","webpack://@featbit/js-client-sdk/./src/logging/SafeLogger.ts","webpack://@featbit/js-client-sdk/./src/logging/format.ts","webpack://@featbit/js-client-sdk/./src/logging/index.ts","webpack://@featbit/js-client-sdk/./src/options/ClientContext.ts","webpack://@featbit/js-client-sdk/./src/options/OptionMessages.ts","webpack://@featbit/js-client-sdk/./src/options/UserBuilder.ts","webpack://@featbit/js-client-sdk/./src/options/Validators.ts","webpack://@featbit/js-client-sdk/./src/options/index.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserInfo.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserPlatform.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserRequests.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserWebSocket.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/FbClient.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/LocalStorageStore.ts","webpack://@featbit/js-client-sdk/./src/platform/index.ts","webpack://@featbit/js-client-sdk/./src/store/BaseStore.ts","webpack://@featbit/js-client-sdk/./src/store/DataKinds.ts","webpack://@featbit/js-client-sdk/./src/store/InMemoryStore.ts","webpack://@featbit/js-client-sdk/./src/store/index.ts","webpack://@featbit/js-client-sdk/./src/store/serialization.ts","webpack://@featbit/js-client-sdk/./src/store/store.ts","webpack://@featbit/js-client-sdk/./src/utils/Emits.ts","webpack://@featbit/js-client-sdk/./src/utils/EventEmitter.ts","webpack://@featbit/js-client-sdk/./src/utils/ValueConverters.ts","webpack://@featbit/js-client-sdk/./src/utils/canonicalizeUri.ts","webpack://@featbit/js-client-sdk/./src/utils/debounce.ts","webpack://@featbit/js-client-sdk/./src/utils/http.ts","webpack://@featbit/js-client-sdk/./src/utils/index.ts","webpack://@featbit/js-client-sdk/./src/utils/isNullOrUndefined.ts","webpack://@featbit/js-client-sdk/./src/utils/serializeUser.ts","webpack://@featbit/js-client-sdk/./src/utils/sleep.ts","webpack://@featbit/js-client-sdk/./src/version.ts","webpack://@featbit/js-client-sdk/webpack/bootstrap","webpack://@featbit/js-client-sdk/webpack/startup"],"sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse {\n\t\tvar a = factory();\n\t\tfor(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i];\n\t}\n})(this, () => {\nreturn ","import { IOptions } from \"./options/IOptions\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport { IValidatedOptions } from \"./options/IValidatedOptions\";\r\nimport { NumberWithMinimum, TypeValidator, TypeValidators, UserValidator } from \"./options/Validators\";\r\nimport OptionMessages from \"./options/OptionMessages\";\r\nimport { IStore } from \"./platform/IStore\";\r\nimport { IClientContext } from \"./options/IClientContext\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport { IDataSourceUpdates } from \"./store/IDataSourceUpdates\";\r\nimport InMemoryStore from \"./store/InMemoryStore\";\r\nimport { VoidFunction } from \"./utils/VoidFunction\";\r\nimport { isNullOrUndefined } from \"./utils/isNullOrUndefined\";\r\nimport { canonicalizeUri } from \"./utils/canonicalizeUri\";\r\nimport { IBootstrapProvider } from \"./bootstrap/IBootstrapProvider\";\r\nimport { NullBootstrapProvider } from \"./bootstrap/NullBootstrapProvider\";\r\nimport { EmptyString } from \"./constants\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { JsonBootstrapProvider } from \"./bootstrap\";\r\n\r\n// Once things are internal to the implementation of the SDK we can depend on\r\n// types. Calls to the SDK could contain anything without any regard to typing.\r\n// So, data we take from external sources must be normalized into something\r\n// that can be trusted.\r\n\r\n/**\r\n * These perform cursory validations. Complex objects are implemented with classes\r\n * and these should allow for conditional construction.\r\n */\r\nconst validations: Record = {\r\n startWaitTime: TypeValidators.Number,\r\n sdkKey: TypeValidators.String,\r\n pollingUri: TypeValidators.String,\r\n streamingUri: TypeValidators.String,\r\n eventsUri: TypeValidators.String,\r\n webSocketPingInterval: TypeValidators.Number,\r\n logger: TypeValidators.Object,\r\n store: TypeValidators.ObjectOrFactory,\r\n dataSynchronizer: TypeValidators.ObjectOrFactory,\r\n flushInterval: TypeValidators.Number,\r\n maxEventsInQueue: TypeValidators.Number,\r\n pollingInterval: TypeValidators.Number,\r\n offline: TypeValidators.Boolean,\r\n dataSyncMode: TypeValidators.String,\r\n bootstrap: TypeValidators.Bootstrap,\r\n user: TypeValidators.User\r\n};\r\n\r\n/**\r\n * @internal\r\n */\r\nexport const defaultValues: IValidatedOptions = {\r\n startWaitTime: 5000,\r\n sdkKey: '',\r\n pollingUri: '',\r\n streamingUri: '',\r\n eventsUri: '',\r\n dataSyncMode: DataSyncModeEnum.STREAMING,\r\n sendEvents: true,\r\n webSocketPingInterval: 18 * 1000,\r\n flushInterval: 2000,\r\n maxEventsInQueue: 10000,\r\n pollingInterval: 30000,\r\n offline: false,\r\n store: (options: IOptions) => new InMemoryStore(),\r\n bootstrap: undefined,\r\n user: undefined,\r\n};\r\n\r\nfunction validateTypesAndNames(options: IOptions): {\r\n errors: string[];\r\n validatedOptions: IValidatedOptions;\r\n} {\r\n let errors: string[] = [];\r\n const validatedOptions: IValidatedOptions = {...defaultValues};\r\n Object.keys(options).forEach((optionName) => {\r\n // We need to tell typescript it doesn't actually know what options are.\r\n // If we don't then it complains we are doing crazy things with it.\r\n const optionValue = (options as unknown as any)[optionName];\r\n const validator = validations[optionName];\r\n if (validator) {\r\n if (!validator.is(optionValue)) {\r\n if (validator.getType() === 'boolean') {\r\n errors.push(OptionMessages.wrongOptionTypeBoolean(optionName, typeof optionValue));\r\n validatedOptions[optionName] = !!optionValue;\r\n } else if (\r\n validator instanceof NumberWithMinimum &&\r\n TypeValidators.Number.is(optionValue)\r\n ) {\r\n const {min} = validator as NumberWithMinimum;\r\n errors.push(OptionMessages.optionBelowMinimum(optionName, optionValue, min));\r\n validatedOptions[optionName] = min;\r\n } else if (validator instanceof UserValidator) {\r\n errors = [...errors, ...validator.messages];\r\n validatedOptions[optionName] = defaultValues[optionName];\r\n } else {\r\n errors.push(\r\n OptionMessages.wrongOptionType(optionName, validator.getType(), typeof optionValue),\r\n );\r\n validatedOptions[optionName] = defaultValues[optionName];\r\n }\r\n } else {\r\n validatedOptions[optionName] = optionValue;\r\n }\r\n } else {\r\n options.logger?.warn(OptionMessages.unknownOption(optionName));\r\n }\r\n });\r\n return {errors, validatedOptions};\r\n}\r\n\r\nfunction validateEndpoints(options: IOptions, validatedOptions: IValidatedOptions) {\r\n const {streamingUri, pollingUri, eventsUri} = options;\r\n const streamingUriMissing = isNullOrUndefined(streamingUri) || streamingUri === EmptyString;\r\n const pollingUriMissing = isNullOrUndefined(pollingUri) || pollingUri === EmptyString;\r\n const eventsUriMissing = isNullOrUndefined(eventsUri) || eventsUri === EmptyString;\r\n\r\n if (!validatedOptions.offline && (eventsUriMissing || (streamingUriMissing && pollingUriMissing))) {\r\n if (eventsUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('eventsUri'));\r\n }\r\n\r\n if (validatedOptions.dataSyncMode === DataSyncModeEnum.STREAMING && streamingUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('streamingUri'));\r\n }\r\n\r\n if (validatedOptions.dataSyncMode === DataSyncModeEnum.POLLING && pollingUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('pollingUri'));\r\n }\r\n }\r\n}\r\n\r\nexport default class Configuration {\r\n public readonly startWaitTime: number;\r\n\r\n public readonly sdkKey: string;\r\n\r\n public readonly streamingUri: string;\r\n\r\n public readonly pollingUri: string;\r\n\r\n public readonly eventsUri: string;\r\n\r\n public readonly webSocketPingInterval: number;\r\n\r\n public readonly logger?: ILogger;\r\n\r\n public readonly flushInterval: number;\r\n\r\n public readonly maxEventsInQueue: number;\r\n\r\n public readonly pollingInterval: number;\r\n\r\n public readonly offline: boolean;\r\n\r\n public readonly dataSyncMode: DataSyncModeEnum;\r\n\r\n public readonly bootstrapProvider: IBootstrapProvider = new NullBootstrapProvider();\r\n\r\n public readonly user: IUser;\r\n\r\n public readonly storeFactory: (clientContext: IClientContext) => IStore;\r\n\r\n public readonly dataSynchronizerFactory?: (\r\n clientContext: IClientContext,\r\n store: IStore,\r\n dataSourceUpdates: IDataSourceUpdates,\r\n initSuccessHandler: VoidFunction,\r\n errorHandler?: (e: Error) => void,\r\n ) => IDataSynchronizer;\r\n\r\n constructor(options: IOptions = {}) {\r\n // The default will handle undefined, but not null.\r\n // Because we can be called from JS we need to be extra defensive.\r\n options = options || {};\r\n // If there isn't a valid logger from the platform, then logs would go nowhere.\r\n this.logger = options.logger;\r\n\r\n const {errors, validatedOptions} = validateTypesAndNames(options);\r\n errors.forEach((error) => {\r\n this.logger?.warn(error);\r\n });\r\n\r\n this.user = options.user!;\r\n\r\n validateEndpoints(options, validatedOptions);\r\n this.streamingUri = `${ canonicalizeUri(validatedOptions.streamingUri) }/streaming`;\r\n this.pollingUri = `${ canonicalizeUri(validatedOptions.pollingUri) }/api/public/sdk/client/latest-all`;\r\n this.eventsUri = `${ canonicalizeUri(validatedOptions.eventsUri) }/api/public/insight/track`;\r\n\r\n this.startWaitTime = validatedOptions.startWaitTime;\r\n\r\n this.sdkKey = validatedOptions.sdkKey;\r\n this.webSocketPingInterval = validatedOptions.webSocketPingInterval!;\r\n\r\n this.flushInterval = validatedOptions.flushInterval;\r\n this.maxEventsInQueue = validatedOptions.maxEventsInQueue;\r\n this.pollingInterval = validatedOptions.pollingInterval;\r\n\r\n this.offline = validatedOptions.offline;\r\n if (validatedOptions.bootstrap && validatedOptions.bootstrap.length > 0) {\r\n try {\r\n this.bootstrapProvider = new JsonBootstrapProvider(validatedOptions.bootstrap);\r\n } catch (_) {\r\n this.logger?.error('Failed to parse bootstrap JSON, use NullBootstrapProvider.');\r\n }\r\n }\r\n\r\n if (this.offline) {\r\n this.logger?.info('Offline mode enabled. No data synchronization with the FeatBit server will occur.');\r\n }\r\n\r\n this.dataSyncMode = validatedOptions.dataSyncMode;\r\n\r\n if (TypeValidators.Function.is(validatedOptions.dataSynchronizer)) {\r\n // @ts-ignore\r\n this.dataSynchronizerFactory = validatedOptions.dataSynchronizer;\r\n } else {\r\n // The processor is already created, just have the method return it.\r\n // @ts-ignore\r\n this.dataSynchronizerFactory = () => validatedOptions.dataSynchronizer;\r\n }\r\n\r\n if (TypeValidators.Function.is(validatedOptions.store)) {\r\n // @ts-ignore\r\n this.storeFactory = validatedOptions.store;\r\n } else {\r\n // The store is already created, just have the method return it.\r\n // @ts-ignore\r\n this.storeFactory = () => validatedOptions.store;\r\n }\r\n }\r\n}","import { IUser } from \"./options/IUser\";\r\n\r\nexport default class Context {\r\n private _user?: IUser;\r\n /**\r\n * Is this a valid context. If a valid context cannot be created, then this flag will be true.\r\n * The validity of a context should be tested before it is used.\r\n */\r\n public readonly valid: boolean;\r\n\r\n public readonly message?: string;\r\n\r\n /**\r\n * Contexts should be created using the static factory method {@link Context.fromUser}.\r\n *\r\n * The factory methods are static functions within the class because they access private\r\n * implementation details, so they cannot be free functions.\r\n */\r\n private constructor(valid: boolean, message?: string) {\r\n this.valid = valid;\r\n this.message = message;\r\n }\r\n\r\n public static fromUser(user: IUser): Context {\r\n if (!user) {\r\n return Context.contextForError('No user specified');\r\n }\r\n\r\n const {keyId, name} = user;\r\n\r\n if (keyId === undefined || keyId === null || keyId.trim() === '') {\r\n return Context.contextForError('key is mandatory');\r\n }\r\n\r\n const context = new Context(true);\r\n context._user = user;\r\n\r\n return context;\r\n }\r\n\r\n get user(): IUser {\r\n return this._user!;\r\n }\r\n\r\n get keyId(): string {\r\n return this._user!.keyId;\r\n }\r\n\r\n value(property: string): any {\r\n if (property === 'keyId') {\r\n return this._user?.keyId;\r\n } else if (property === 'name') {\r\n return this._user?.name;\r\n } else {\r\n return this._user?.customizedProperties?.find(x => x.name === property)?.value;\r\n }\r\n }\r\n\r\n private static contextForError(message: string) {\r\n return new Context(false, message);\r\n }\r\n}","import { IFbClient } from \"./IFbClient\";\r\nimport { IOptions } from \"./options/IOptions\";\r\nimport FbClient from \"./platform/browser/FbClient\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport { IClientContext } from \"./options/IClientContext\";\r\nimport { IDataSourceUpdates } from \"./store/IDataSourceUpdates\";\r\nimport { VoidFunction } from \"./utils/VoidFunction\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { IFlagBase } from \"./evaluation\";\r\nimport { IPlatform } from \"./platform\";\r\n\r\n/**\r\n * Creates an instance of the FeatBit client.\r\n *\r\n * Applications should instantiate a single instance for the lifetime of the application.\r\n * The client will begin attempting to connect to FeatBit as soon as it is created. To\r\n * determine when it is ready to use, call {@link IFbClient.waitForInitialization}, or register an\r\n * event listener for the `\"ready\"` event using {@link IFbClient.on}.\r\n *\r\n * **Important:** Do **not** try to instantiate `FbClient` with its constructor\r\n * (`new FbClientNode()`); the SDK does not currently support\r\n * this.\r\n *\r\n * @return\r\n * The new {@link IFbClient} instance.\r\n */\r\nexport class FbClientBuilder {\r\n private _options: IOptions;\r\n private _platform: IPlatform | undefined;\r\n\r\n constructor(options?: IOptions) {\r\n this._options = options ?? {};\r\n }\r\n\r\n /**\r\n * Creates a new instance of the FeatBit client.\r\n */\r\n build(): IFbClient {\r\n return new FbClient(this._options);\r\n }\r\n\r\n platform(platform: IPlatform): FbClientBuilder {\r\n this._platform = platform;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.startWaitTime}.\r\n */\r\n startWaitTime(startWaitTime: number): FbClientBuilder {\r\n this._options.startWaitTime = startWaitTime;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.sdkKey}.\r\n */\r\n sdkKey(sdkKey: string): FbClientBuilder {\r\n this._options.sdkKey = sdkKey;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.user}.\r\n */\r\n user(user: IUser): FbClientBuilder {\r\n this._options.user = user;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.streamingUri}.\r\n */\r\n streamingUri(streamingUri: string): FbClientBuilder {\r\n this._options.streamingUri = streamingUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.pollingUri}.\r\n */\r\n pollingUri(pollingUri: string): FbClientBuilder {\r\n this._options.pollingUri = pollingUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.eventsUri}.\r\n */\r\n eventsUri(eventsUri: string): FbClientBuilder {\r\n this._options.eventsUri = eventsUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.dataSyncMode}.\r\n */\r\n dataSyncMode(mode: DataSyncModeEnum): FbClientBuilder {\r\n this._options.dataSyncMode = mode;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.pollingInterval}.\r\n */\r\n pollingInterval(pollingInterval: number): FbClientBuilder {\r\n this._options.pollingInterval = pollingInterval;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.flushInterval}.\r\n */\r\n flushInterval(flushInterval: number): FbClientBuilder {\r\n this._options.flushInterval = flushInterval;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.maxEventsInQueue}.\r\n */\r\n maxEventsInQueue(maxEventsInQueue: number): FbClientBuilder {\r\n this._options.maxEventsInQueue = maxEventsInQueue;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.logger}.\r\n */\r\n logger(logger: ILogger): FbClientBuilder {\r\n this._options.logger = logger;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.offline}.\r\n */\r\n offline(offline: boolean): FbClientBuilder {\r\n this._options.offline = offline;\r\n return this;\r\n }\r\n\r\n /**\r\n * Use the JsonBootstrapProvider.\r\n */\r\n bootstrap(flags: IFlagBase[]): FbClientBuilder {\r\n this._options.bootstrap = flags;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.dataSynchronizer}.\r\n */\r\n dataSynchronizer(\r\n dataSynchronizer: IDataSynchronizer |\r\n ((\r\n clientContext: IClientContext,\r\n dataSourceUpdates: IDataSourceUpdates,\r\n initSuccessHandler: VoidFunction,\r\n errorHandler?: (e: Error) => void,\r\n ) => IDataSynchronizer)\r\n ): FbClientBuilder {\r\n this._options.dataSynchronizer = dataSynchronizer;\r\n return this;\r\n }\r\n}","import { IFbClientCore } from \"./IFbClientCore\";\r\nimport { IPlatform } from \"./platform/IPlatform\";\r\nimport Configuration from \"./Configuration\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport ClientContext from \"./options/ClientContext\";\r\nimport DataSourceUpdates from \"./data-sources/DataSourceUpdates\";\r\nimport { createStreamListeners } from \"./data-sources/createStreamListeners\";\r\nimport { IEvalDetail } from \"./evaluation/IEvalDetail\";\r\nimport WebSocketDataSynchronizer from \"./data-sync/WebSocketDataSynchronizer\";\r\nimport PollingDataSynchronizer from \"./data-sync/PollingDataSynchronizer\";\r\nimport Requestor from \"./data-sync/Requestor\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport DataKinds from \"./store/DataKinds\";\r\nimport Evaluator from \"./evaluation/Evaluator\";\r\nimport { ReasonKinds } from \"./evaluation/ReasonKinds\";\r\nimport { ClientError } from \"./errors\";\r\nimport Context from \"./Context\";\r\nimport { IConvertResult, ValueConverters } from \"./utils/ValueConverters\";\r\nimport { NullDataSynchronizer } from \"./data-sync/NullDataSynchronizer\";\r\nimport { IEventProcessor } from \"./events/IEventProcessor\";\r\nimport { NullEventProcessor } from \"./events/NullEventProcessor\";\r\nimport { DefaultEventProcessor } from \"./events/DefaultEventProcessor\";\r\nimport { IStore } from \"./platform/IStore\";\r\nimport { IOptions } from \"./options/IOptions\";\r\nimport { MetricEvent } from \"./events/event\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { UserValidator } from \"./options/Validators\";\r\n\r\nenum ClientState {\r\n Initializing,\r\n Initialized,\r\n Failed,\r\n}\r\n\r\nexport interface IClientCallbacks {\r\n onError: (err: Error) => void;\r\n onFailed: (err: Error) => void;\r\n onReady: () => void;\r\n // Called whenever flags change, if there are listeners.\r\n onUpdate: (keys: string[]) => void;\r\n // Method to check if event listeners have been registered.\r\n // If none are registered, then onUpdate will never be called.\r\n hasEventListeners: () => boolean;\r\n}\r\n\r\nexport class FbClientCore implements IFbClientCore {\r\n private state: ClientState = ClientState.Initializing;\r\n\r\n private store?: IStore;\r\n\r\n private dataSynchronizer?: IDataSynchronizer;\r\n\r\n private eventProcessor?: IEventProcessor;\r\n\r\n private evaluator?: Evaluator;\r\n\r\n private initResolve?: (value: IFbClientCore | PromiseLike) => void;\r\n\r\n private initReject?: (err: Error) => void;\r\n\r\n private rejectionReason: Error | undefined;\r\n\r\n private initializedPromise?: Promise;\r\n\r\n private config: Configuration;\r\n\r\n private dataSourceUpdates?: DataSourceUpdates;\r\n\r\n private onError: (err: Error) => void;\r\n\r\n private onFailed: (err: Error) => void;\r\n\r\n private onReady: () => void;\r\n\r\n logger?: ILogger;\r\n\r\n constructor(\r\n private options: IOptions,\r\n private platform: IPlatform,\r\n callbacks: IClientCallbacks\r\n ) {\r\n this.onError = callbacks.onError;\r\n this.onFailed = callbacks.onFailed;\r\n this.onReady = callbacks.onReady;\r\n\r\n const {onUpdate, hasEventListeners} = callbacks;\r\n const config = new Configuration(options);\r\n\r\n if (!config.sdkKey && !config.offline) {\r\n throw new Error('You must configure the client with an SDK key');\r\n }\r\n\r\n if (!config.user) {\r\n throw new Error('You must configure the client with a user');\r\n }\r\n\r\n this.config = config;\r\n this.logger = config.logger;\r\n\r\n this.init(platform, onUpdate, hasEventListeners);\r\n }\r\n\r\n private async init(platform: IPlatform, onUpdate: (keys: string[]) => void, hasEventListeners: () => boolean) {\r\n const clientContext = new ClientContext(this.config.sdkKey, this.config, platform);\r\n this.store = this.config.storeFactory(clientContext);\r\n await this.store.identify(this.config.user);\r\n this.dataSourceUpdates = new DataSourceUpdates(this.store, hasEventListeners, onUpdate);\r\n this.evaluator = new Evaluator(this.store);\r\n\r\n // use bootstrap provider to populate store\r\n await this.config.bootstrapProvider.populate(this.config.user.keyId, this.dataSourceUpdates);\r\n\r\n if (this.config.offline) {\r\n this.eventProcessor = new NullEventProcessor();\r\n this.dataSynchronizer = new NullDataSynchronizer();\r\n\r\n this.initSuccess();\r\n } else {\r\n this.eventProcessor = new DefaultEventProcessor(clientContext);\r\n\r\n const listeners = createStreamListeners(this.dataSourceUpdates, this.logger, {\r\n put: () => this.initSuccess(),\r\n patch: () => this.initSuccess()\r\n });\r\n\r\n const dataSynchronizer = this.config.dataSyncMode === DataSyncModeEnum.STREAMING\r\n ? new WebSocketDataSynchronizer(\r\n this.config.sdkKey,\r\n this.config.user,\r\n clientContext,\r\n platform.webSocket,\r\n () => this.store!.version,\r\n listeners,\r\n this.config.webSocketPingInterval\r\n )\r\n : new PollingDataSynchronizer(\r\n this.config,\r\n new Requestor(this.config.sdkKey, this.config, this.platform.info, this.platform.requests),\r\n () => this.store!.version,\r\n listeners,\r\n (e) => this.dataSourceErrorHandler(e),\r\n );\r\n\r\n this.dataSynchronizer = this.config.dataSynchronizerFactory?.(\r\n clientContext,\r\n this.store,\r\n this.dataSourceUpdates,\r\n () => this.initSuccess(),\r\n (e) => this.dataSourceErrorHandler(e),\r\n ) ?? dataSynchronizer;\r\n }\r\n\r\n this.start();\r\n }\r\n\r\n async identify(user: IUser) {\r\n const validator = new UserValidator();\r\n if (!validator.is(user)) {\r\n validator.messages.forEach((error: string) => {\r\n this.logger?.warn(error);\r\n });\r\n\r\n return;\r\n }\r\n\r\n this.store!.identify(user);\r\n this.dataSynchronizer!.identify(user);\r\n const [ flags ] = this.store!.all(DataKinds.Flags);\r\n if (Object.keys(flags).length === 0) {\r\n await this.config.bootstrapProvider.populate(user.keyId, this.dataSourceUpdates!);\r\n }\r\n }\r\n\r\n private start() {\r\n if (this.config.offline) {\r\n return;\r\n }\r\n\r\n this.dataSynchronizer!.start();\r\n setTimeout(() => {\r\n if (!this.initialized()) {\r\n const msg = `FbClient failed to start successfully within ${ this.config.startWaitTime } milliseconds. ` +\r\n 'This error usually indicates a connection issue with FeatBit or an invalid sdkKey.' +\r\n 'Please double-check your sdkKey and streamingUri/pollingUri configuration. ' +\r\n 'We will continue to initialize the FbClient, it still have a chance to get to work ' +\r\n 'if it\\'s a temporary network issue';\r\n\r\n const error = new Error(msg);\r\n this.state = ClientState.Failed;\r\n this.rejectionReason = error;\r\n this.initReject?.(error);\r\n\r\n return this.logger?.warn(msg);\r\n }\r\n }, this.config.startWaitTime);\r\n }\r\n\r\n initialized(): boolean {\r\n return this.state === ClientState.Initialized;\r\n }\r\n\r\n waitForInitialization(): Promise {\r\n // An initialization promise is only created if someone is going to use that promise.\r\n // If we always created an initialization promise, and there was no call waitForInitialization\r\n // by the time the promise was rejected, then that would result in an unhandled promise\r\n // rejection.\r\n\r\n // Initialization promise was created by a previous call to waitForInitialization.\r\n if (this.initializedPromise) {\r\n return this.initializedPromise;\r\n }\r\n\r\n // Initialization completed before waitForInitialization was called, so we have completed\r\n // and there was no promise. So we make a resolved promise and return it.\r\n if (this.state === ClientState.Initialized) {\r\n this.initializedPromise = Promise.resolve(this);\r\n return this.initializedPromise;\r\n }\r\n\r\n // Initialization failed before waitForInitialization was called, so we have completed\r\n // and there was no promise. So we make a rejected promise and return it.\r\n if (this.state === ClientState.Failed) {\r\n this.initializedPromise = Promise.reject(this.rejectionReason);\r\n return this.initializedPromise;\r\n }\r\n\r\n if (!this.initializedPromise) {\r\n this.initializedPromise = new Promise((resolve, reject) => {\r\n this.initResolve = resolve;\r\n this.initReject = reject;\r\n });\r\n }\r\n return this.initializedPromise;\r\n }\r\n\r\n boolVariation(\r\n key: string,\r\n defaultValue: boolean\r\n ): boolean {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.bool).value!;\r\n }\r\n\r\n boolVariationDetail(\r\n key: string,\r\n defaultValue: boolean\r\n ): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.bool);\r\n }\r\n\r\n jsonVariation(key: string, defaultValue: any): any {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.json).value!;\r\n }\r\n\r\n jsonVariationDetail(key: string, defaultValue: any): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.json);\r\n }\r\n\r\n numberVariation(key: string, defaultValue: number): number {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.number).value!;\r\n }\r\n\r\n numberVariationDetail(key: string, defaultValue: number): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.number);\r\n }\r\n\r\n stringVariation(key: string, defaultValue: string): string {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string).value!;\r\n }\r\n\r\n stringVariationDetail(key: string, defaultValue: string): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string);\r\n }\r\n\r\n variation(key: string, defaultValue: string): string {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string).value!;\r\n }\r\n\r\n variationDetail(key: string, defaultValue: string): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string);\r\n }\r\n\r\n getAllVariations(): Promise[]> {\r\n const context = Context.fromUser(this.config.user);\r\n if (!context.valid) {\r\n const error = new ClientError(\r\n `${ context.message ?? 'User not valid;' } returning default value.`,\r\n );\r\n this.onError(error);\r\n\r\n return Promise.resolve([]);\r\n }\r\n\r\n const [flags, _] = this.store!.all(DataKinds.Flags);\r\n const result = Object.keys(flags).map(flagKey => {\r\n const evalResult = this.evaluator!.evaluate(flagKey);\r\n return {flagKey, kind: evalResult.kind, reason: evalResult.reason, value: evalResult.value?.variation};\r\n });\r\n\r\n return Promise.resolve(result);\r\n }\r\n\r\n async close(): Promise {\r\n await this.eventProcessor!.close();\r\n this.dataSynchronizer?.close();\r\n this.store!.close();\r\n }\r\n\r\n track(eventName: string, metricValue?: number | undefined): void {\r\n const metricEvent = new MetricEvent(this.config.user, eventName, this.platform.info.appType, metricValue ?? 1);\r\n this.eventProcessor!.record(metricEvent);\r\n return;\r\n }\r\n\r\n async flush(callback?: (res: boolean) => void): Promise {\r\n try {\r\n await this.eventProcessor!.flush();\r\n callback?.(true);\r\n return true;\r\n } catch (err) {\r\n callback?.(false);\r\n return false;\r\n }\r\n }\r\n\r\n evaluateCore(\r\n flagKey: string,\r\n defaultValue: TValue,\r\n typeConverter: (value: string) => IConvertResult\r\n ): IEvalDetail {\r\n const context = Context.fromUser(this.config.user);\r\n if (!context.valid) {\r\n const error = new ClientError(\r\n `${ context.message ?? 'User not valid;' } returning default value.`,\r\n );\r\n this.onError(error);\r\n\r\n return {flagKey, kind: ReasonKinds.Error, reason: error.message, value: defaultValue};\r\n }\r\n\r\n const evalResult = this.evaluator!.evaluate(flagKey);\r\n\r\n if (evalResult.kind === ReasonKinds.FlagNotFound) {\r\n // flag not found, return default value\r\n const error = new ClientError(evalResult.reason!);\r\n this.onError(error);\r\n\r\n return {flagKey, kind: evalResult.kind, reason: evalResult.reason, value: defaultValue};\r\n }\r\n\r\n if (!this.initialized()) {\r\n this.logger?.warn(\r\n 'Variation called before FeatBit client initialization completed (did you wait for the' +\r\n \"'ready' event?)\",\r\n );\r\n } else {\r\n // send event\r\n this.eventProcessor!.record(evalResult.toEvalEvent(this.config.user));\r\n }\r\n\r\n const {isSucceeded, value} = typeConverter(evalResult.value?.variation!);\r\n return isSucceeded\r\n ? {flagKey, kind: evalResult.kind, reason: evalResult.reason, value}\r\n : {flagKey, kind: ReasonKinds.WrongType, reason: 'type mismatch', value: defaultValue};\r\n }\r\n\r\n private dataSourceErrorHandler(e: any) {\r\n const error =\r\n e.code === 401 ? new Error('Authentication failed. Double check your SDK key.') : e;\r\n\r\n this.onError(error);\r\n this.onFailed(error);\r\n\r\n if (!this.initialized()) {\r\n this.state = ClientState.Failed;\r\n this.rejectionReason = error;\r\n this.initReject?.(error);\r\n }\r\n }\r\n\r\n private initSuccess() {\r\n if (!this.initialized()) {\r\n this.state = ClientState.Initialized;\r\n this.logger?.info('FbClient started successfully.');\r\n this.initResolve?.(this);\r\n this.onReady();\r\n }\r\n }\r\n}\r\n","import { IBootstrapProvider } from \"./IBootstrapProvider\";\r\nimport { deserializeAll } from \"../store/serialization\";\r\nimport { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\nimport { isNullOrUndefined } from \"../utils/isNullOrUndefined\";\r\nimport { IFlag, IFlagBase } from \"../evaluation/data/IFlag\";\r\n\r\nexport class JsonBootstrapProvider implements IBootstrapProvider {\r\n private dataSet?: IStoreDataStorage;\r\n\r\n constructor(bootstrap: IFlagBase[]) {\r\n const flags: IFlag[] = (bootstrap || []).map((flag: IFlagBase) => ({...flag, variationOptions: flag.variationOptions || [{id: null, variation: flag.variation}]})) as IFlag[];\r\n\r\n const data = deserializeAll(flags);\r\n this.dataSet = {\r\n flags: data.flags,\r\n version: 0\r\n };\r\n }\r\n\r\n populate(userKeyId: string, dataSourceUpdates: IDataSourceUpdates, callback?: () => void): Promise {\r\n return new Promise((resolve, reject) => {\r\n if (isNullOrUndefined(this.dataSet)) {\r\n return resolve();\r\n }\r\n\r\n const internalCallback = () => {\r\n resolve();\r\n callback?.();\r\n }\r\n\r\n dataSourceUpdates.init(userKeyId, this.dataSet!, internalCallback);\r\n });\r\n }\r\n}","import { IBootstrapProvider } from \"./IBootstrapProvider\";\r\nimport { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\n\r\nexport class NullBootstrapProvider implements IBootstrapProvider {\r\n private dataSet?: IStoreDataStorage;\r\n\r\n constructor() {\r\n this.dataSet = {\r\n flags: {},\r\n version: 0\r\n };\r\n }\r\n\r\n populate(userKeyId: string, dataSourceUpdates: IDataSourceUpdates, callback?: () => void): Promise {\r\n return new Promise((resolve, reject) => {\r\n resolve();\r\n callback?.();\r\n });\r\n }\r\n}","export * from './IBootstrapProvider';\r\nexport * from './JsonBootstrapProvider';\r\nexport * from './NullBootstrapProvider';","export const EmptyString = '';\r\nexport const MinInt: number = 0x80000000;","import { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport {\r\n IStoreDataStorage,\r\n IStoreItem,\r\n IKeyedStoreItem\r\n} from \"../store/store\";\r\nimport { IStore } from \"../platform/IStore\";\r\nimport { IDataKind } from \"../IDataKind\";\r\nimport DataKinds from \"../store/DataKinds\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class DataSourceUpdates implements IDataSourceUpdates {\r\n\r\n constructor(\r\n private readonly store: IStore,\r\n private readonly hasEventListeners: () => boolean,\r\n private readonly onChange: (keys: string[]) => void,\r\n ) {\r\n }\r\n\r\n init(userKeyId: string, allData: IStoreDataStorage, callback?: () => void): void {\r\n if (userKeyId !== this.store.user.keyId) {\r\n callback?.();\r\n return;\r\n }\r\n\r\n const checkForChanges = this.hasEventListeners();\r\n const doInit = async (oldData?: IStoreDataStorage) => {\r\n await this.store.init(allData);\r\n Promise.resolve().then(() => {\r\n if (checkForChanges) {\r\n const updatedKeys = Object.keys(allData)\r\n .flatMap((namespace) => {\r\n const oldDataForKind = oldData?.[namespace] || {};\r\n const newDataForKind = allData[namespace];\r\n const mergedData = {...oldDataForKind, ...newDataForKind};\r\n return Object.keys(mergedData)\r\n .filter((key: string) => this.isUpdated(oldDataForKind && oldDataForKind[key], newDataForKind && newDataForKind[key]));\r\n });\r\n updatedKeys.length > 0 && this.onChange(updatedKeys);\r\n }\r\n });\r\n callback?.();\r\n };\r\n\r\n if (checkForChanges) {\r\n const [flags, version] = this.store.all(DataKinds.Flags);\r\n const oldData = {\r\n flags,\r\n version\r\n };\r\n doInit(oldData);\r\n } else {\r\n doInit();\r\n }\r\n }\r\n\r\n upsert(userKeyId: string, kind: IDataKind, data: IKeyedStoreItem, callback: () => void): void {\r\n if (userKeyId !== this.store.user.keyId) {\r\n callback?.();\r\n return;\r\n }\r\n\r\n const {key} = data;\r\n const checkForChanges = this.hasEventListeners();\r\n const doUpsert = async (oldItem?: IStoreItem) => {\r\n await this.store.upsert(kind, data);\r\n Promise.resolve().then(() => {\r\n if (checkForChanges && this.isUpdated(oldItem, data[key])) {\r\n this.onChange([key]);\r\n }\r\n });\r\n\r\n callback?.();\r\n };\r\n if (checkForChanges) {\r\n const item = this.store.get(kind, key);\r\n doUpsert(item || undefined);\r\n } else {\r\n doUpsert();\r\n }\r\n }\r\n\r\n private isUpdated(oldData?: IStoreItem, newData?: IStoreItem): boolean {\r\n return !oldData || !newData || newData.version > oldData.version\r\n }\r\n}","import { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport { VoidFunction } from \"../utils/VoidFunction\";\r\nimport {\r\n deserializeAll,\r\n deserializePatch,\r\n IPatchData,\r\n Flags\r\n} from \"../store/serialization\";\r\nimport DataKinds from \"../store/DataKinds\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\nimport { EventName, ProcessStreamResponse } from \"../data-sync/types\";\r\n\r\nexport const createPutListener = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onPutCompleteHandler: VoidFunction = () => {\r\n },\r\n) => ({\r\n deserializeData: deserializeAll,\r\n processJson: async (userKeyId: string, {flags}: Flags) => {\r\n const initData: IStoreDataStorage = {\r\n flags: flags,\r\n version: 0\r\n };\r\n\r\n logger?.debug('Initializing all data');\r\n dataSourceUpdates.init(userKeyId, initData, onPutCompleteHandler);\r\n },\r\n});\r\n\r\nexport const createPatchListener = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onPatchCompleteHandler: VoidFunction = () => {\r\n },\r\n) => ({\r\n deserializeData: deserializePatch,\r\n processJson: async (userKeyId: string, data: IPatchData[]) => {\r\n if (data?.length === 0) {\r\n onPatchCompleteHandler?.();\r\n return;\r\n }\r\n\r\n data?.forEach(item => {\r\n logger?.debug(`Updating ${ item.data.key } in ${ item.kind.namespace }`);\r\n dataSourceUpdates.upsert(userKeyId, item.kind, item.data, onPatchCompleteHandler);\r\n })\r\n },\r\n});\r\n\r\n\r\nexport const createStreamListeners = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onCompleteHandlers?: {\r\n put?: VoidFunction;\r\n patch?: VoidFunction;\r\n delete?: VoidFunction;\r\n },\r\n) => {\r\n const listeners = new Map();\r\n listeners.set('put', createPutListener(dataSourceUpdates, logger, onCompleteHandlers?.put));\r\n listeners.set('patch', createPatchListener(dataSourceUpdates, logger, onCompleteHandlers?.patch));\r\n return listeners;\r\n};\r\n","export * from './createStreamListeners';\r\nexport * from './DataSourceUpdates';","export enum DataSyncModeEnum {\r\n POLLING = 'polling',\r\n STREAMING = 'streaming'\r\n}","import { IDataSynchronizer } from \"./IDataSynchronizer\";\r\n\r\nexport class NullDataSynchronizer implements IDataSynchronizer {\r\n close(): void {\r\n }\r\n\r\n start(): void {\r\n }\r\n\r\n stop(): void {\r\n }\r\n\r\n identify(): void {\r\n }\r\n}","import { isHttpRecoverable, PollingError } from \"../errors\";\r\nimport { IDataSynchronizer } from \"./IDataSynchronizer\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport Configuration from \"../Configuration\";\r\nimport { EventName, PollingErrorHandler, ProcessStreamResponse, StreamResponseEventType } from \"./types\";\r\nimport Requestor from \"./Requestor\";\r\nimport { httpErrorMessage } from \"../utils/http\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\nexport default class PollingDataSynchronizer implements IDataSynchronizer {\r\n private stopped = false;\r\n\r\n private logger?: ILogger;\r\n\r\n private pollingInterval: number;\r\n\r\n private user: IUser | undefined;\r\n\r\n private timeoutHandle: any;\r\n\r\n constructor(\r\n config: Configuration,\r\n private readonly requestor: Requestor,\r\n private readonly getStoreTimestamp: () => number,\r\n private readonly listeners: Map,\r\n private readonly errorHandler?: PollingErrorHandler,\r\n ) {\r\n this.logger = config.logger;\r\n this.pollingInterval = config.pollingInterval;\r\n this.user = config.user;\r\n }\r\n\r\n private poll() {\r\n if (this.stopped) {\r\n return;\r\n }\r\n\r\n const startTime = Date.now();\r\n this.logger?.debug('Polling for feature flag and segments updates');\r\n this.requestor.requestData(this.getStoreTimestamp(), this.user, (err, body) => {\r\n const elapsed = Date.now() - startTime;\r\n const sleepFor = Math.max(this.pollingInterval - elapsed, 0);\r\n\r\n this.logger?.debug('Elapsed: %d ms, sleeping for %d ms', elapsed, sleepFor);\r\n if (err) {\r\n const {status} = err;\r\n if (status && !isHttpRecoverable(status)) {\r\n const message = httpErrorMessage(err, 'polling request');\r\n this.logger?.error(message);\r\n this.errorHandler?.(new PollingError(message, status));\r\n // It is not recoverable, return and do not trigger another\r\n // poll.\r\n return;\r\n }\r\n this.logger?.warn(httpErrorMessage(err, 'polling request', 'will retry'));\r\n } else {\r\n let featureFlags = [];\r\n let userKeyId = this.user?.keyId!;\r\n let processStreamResponse: ProcessStreamResponse | undefined = this.listeners.get('patch');\r\n\r\n if (body) {\r\n const message = JSON.parse(body);\r\n if (message.messageType === 'data-sync') {\r\n switch (message.data.eventType) {\r\n case StreamResponseEventType.patch:\r\n processStreamResponse = this.listeners.get('patch');\r\n break;\r\n case StreamResponseEventType.full:\r\n processStreamResponse = this.listeners.get('put');\r\n break;\r\n }\r\n\r\n ({featureFlags, userKeyId} = message.data);\r\n }\r\n }\r\n\r\n const data = processStreamResponse?.deserializeData?.(featureFlags);\r\n processStreamResponse?.processJson?.(userKeyId, data);\r\n }\r\n\r\n // Falling through, there was some type of error and we need to trigger\r\n // a new poll.\r\n this.timeoutHandle = setTimeout(() => {\r\n this.poll();\r\n }, sleepFor);\r\n });\r\n }\r\n\r\n identify(user: IUser) {\r\n this.user = {...user};\r\n }\r\n\r\n close(): void {\r\n this.stop();\r\n }\r\n\r\n start(): void {\r\n this.poll();\r\n }\r\n\r\n stop(): void {\r\n if (this.timeoutHandle) {\r\n clearTimeout(this.timeoutHandle);\r\n this.timeoutHandle = undefined;\r\n }\r\n this.stopped = true;\r\n }\r\n}\r\n\r\n\r\n\r\n","import { IRequestor } from \"./IRequestor\";\r\nimport Configuration from \"../Configuration\";\r\nimport { IInfo } from \"../platform/IInfo\";\r\nimport { IRequestOptions, IRequests, IResponse } from \"../platform/requests\";\r\nimport { StreamingError } from \"../errors\";\r\nimport { defaultHeaders } from \"../utils/http\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class Requestor implements IRequestor {\r\n private readonly headers: Record;\r\n\r\n private readonly uri: string;\r\n\r\n constructor(\r\n sdkKey: string,\r\n config: Configuration,\r\n info: IInfo,\r\n private readonly requests: IRequests,\r\n ) {\r\n this.headers = defaultHeaders(sdkKey, info);\r\n this.uri = config.pollingUri;\r\n }\r\n\r\n /**\r\n * Perform a request and utilize the ETag cache. The ETags are cached in the\r\n * requestor instance.\r\n */\r\n private async request(\r\n requestUrl: string,\r\n options: IRequestOptions,\r\n ): Promise<{\r\n res: IResponse;\r\n body: string;\r\n }> {\r\n const res = await this.requests.fetch(requestUrl, options);\r\n\r\n const body = await res.text();\r\n\r\n return {res, body};\r\n }\r\n\r\n async requestData(timestamp: number, payload: any, cb: (err: any, body: any) => void) {\r\n const options: IRequestOptions = {\r\n method: 'POST',\r\n headers: this.headers,\r\n body: JSON.stringify(payload)\r\n };\r\n try {\r\n const {res, body} = await this.request(`${ this.uri }?timestamp=${ timestamp ?? 0 }`, options);\r\n if (res.status !== 200 && res.status !== 304) {\r\n const err = new StreamingError(`Unexpected status code: ${ res.status }`, res.status);\r\n return cb(err, undefined);\r\n }\r\n return cb(undefined, res.status === 304 ? null : body);\r\n } catch (err) {\r\n return cb(err, undefined);\r\n }\r\n }\r\n}\r\n","import { IDataSynchronizer } from \"./IDataSynchronizer\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { EventName, ProcessStreamResponse } from \"./types\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport { IWebSocketWithEvents } from \"../platform/IWebSocket\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\nclass WebSocketDataSynchronizer implements IDataSynchronizer {\r\n private socket?: IWebSocketWithEvents;\r\n private readonly logger?: ILogger;\r\n\r\n private connectionAttemptStartTime?: number;\r\n\r\n constructor(\r\n sdkKey: string,\r\n user: IUser,\r\n clientContext: ClientContext,\r\n socket: IWebSocketWithEvents,\r\n private readonly getStoreTimestamp: () => number,\r\n private readonly listeners: Map,\r\n webSocketPingInterval: number\r\n ) {\r\n const {logger, streamingUri} = clientContext;\r\n\r\n this.logger = logger;\r\n this.socket = socket;\r\n this.socket.config({\r\n sdkKey,\r\n streamingUri,\r\n pingInterval: webSocketPingInterval,\r\n user,\r\n logger,\r\n getStoreTimestamp\r\n });\r\n\r\n this.listeners.forEach(({deserializeData, processJson}, eventName) => {\r\n this.socket?.addListener(eventName, (event) => {\r\n this.logger?.debug(`Received ${ eventName } event`);\r\n\r\n if (event?.data) {\r\n const {featureFlags, userKeyId} = event.data;\r\n const data = deserializeData(featureFlags);\r\n processJson(userKeyId, data);\r\n }\r\n });\r\n })\r\n }\r\n\r\n identify(user: IUser): void {\r\n this.socket?.identify(user);\r\n }\r\n\r\n start(): void {\r\n this.logConnectionStarted();\r\n\r\n this.socket?.connect();\r\n }\r\n\r\n private logConnectionStarted() {\r\n this.connectionAttemptStartTime = Date.now();\r\n this.logger?.info(`Stream connection attempt StartTime ${ this.connectionAttemptStartTime }`);\r\n }\r\n\r\n close(): void {\r\n this.stop();\r\n }\r\n\r\n stop(): void {\r\n this.socket?.close();\r\n this.socket = undefined;\r\n }\r\n}\r\n\r\nexport default WebSocketDataSynchronizer;","export * from './DataSyncMode';\r\nexport * from './IDataSynchronizer';\r\nexport * from './IRequestor';\r\nexport * from './NullDataSynchronizer';\r\nexport * from './PollingDataSynchronizer';\r\nexport * from './Requestor';\r\nexport * from './types';\r\nexport * from './utils';\r\nexport * from './WebSocketDataSynchronizer';","import { PollingError } from \"../errors\";\r\nimport { IFlag } from \"../evaluation/data/IFlag\";\r\n\r\nexport type PollingErrorHandler = (err: PollingError) => void;\r\n\r\nexport enum StreamResponseEventType {\r\n full = 'full',\r\n patch = 'patch'\r\n}\r\n\r\nexport interface IStreamResponse {\r\n eventType: StreamResponseEventType,\r\n featureFlags: IFlag[]\r\n}\r\n\r\nexport type EventName = 'delete' | 'patch' | 'ping' | 'put';\r\nexport type ProcessStreamResponse = {\r\n deserializeData: (flags: IFlag[]) => any;\r\n processJson: (userKeyId: string, json: any) => void;\r\n};","/********************** encode text begin *****************************/\r\nconst alphabet: Record = {\r\n \"0\": \"Q\",\r\n \"1\": \"B\",\r\n \"2\": \"W\",\r\n \"3\": \"S\",\r\n \"4\": \"P\",\r\n \"5\": \"H\",\r\n \"6\": \"D\",\r\n \"7\": \"X\",\r\n \"8\": \"Z\",\r\n \"9\": \"U\",\r\n}\r\n\r\nfunction encodeNumber(param: number, length: number): string {\r\n var s = \"000000000000\" + param;\r\n const numberWithLeadingZeros = s.slice(s.length - length);\r\n return numberWithLeadingZeros.split('').map(n => alphabet[n]).join('');\r\n}\r\n\r\n// generate connection token\r\nexport function generateConnectionToken(text: string): string {\r\n text = text.replace(/=*$/, '');\r\n const timestamp = Date.now();\r\n const timestampCode = encodeNumber(timestamp, timestamp.toString().length);\r\n // get random number less than the length of the text as the start point, and it must be greater or equal to 2\r\n const start = Math.max(Math.floor(Math.random() * text.length), 2);\r\n\r\n return `${ encodeNumber(start, 3) }${ encodeNumber(timestampCode.length, 2) }${ text.slice(0, start) }${ timestampCode }${ text.slice(start) }`;\r\n}\r\n\r\n/********************** encode text end *****************************/","export class PollingError extends Error {\r\n public readonly status?: number;\r\n\r\n constructor(message: string, status?: number) {\r\n super(message);\r\n this.status = status;\r\n this.name = 'FbPollingError';\r\n }\r\n}\r\n\r\nexport class StreamingError extends Error {\r\n public readonly code?: number;\r\n\r\n constructor(message: string, code?: number) {\r\n super(message);\r\n this.code = code;\r\n this.name = 'FbStreamingError';\r\n }\r\n}\r\n\r\nexport class UnexpectedResponseError extends Error {\r\n constructor(message: string) {\r\n super(message);\r\n this.name = 'FbUnexpectedResponseError';\r\n }\r\n}\r\n\r\n\r\nexport class ClientError extends Error {\r\n constructor(message: string) {\r\n super(message);\r\n this.name = 'FbClientError';\r\n }\r\n}\r\n\r\nexport function isHttpRecoverable(status: number) {\r\n if (status >= 400 && status < 500) {\r\n return status === 400 || status === 408 || status === 429;\r\n }\r\n return true;\r\n}","import { ReasonKinds } from \"./ReasonKinds\";\r\nimport { IFlag } from \"./data/IFlag\";\r\nimport { EvalEvent } from \"../events/event\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\n/**\r\n * A class which encapsulates the result of an evaluation. It allows for differentiating between\r\n * successful and error result types.\r\n *\r\n * @internal\r\n */\r\nexport default class EvalResult {\r\n protected constructor(\r\n public kind: ReasonKinds,\r\n public value: IFlag | null,\r\n public reason?: string,\r\n ) {\r\n }\r\n\r\n static flagNotFound(flagKey: string) {\r\n return new EvalResult(ReasonKinds.FlagNotFound, null, `flag not found: ${ flagKey }`);\r\n }\r\n\r\n static matched(val: IFlag) {\r\n return new EvalResult(ReasonKinds.Match, val, 'target match');\r\n }\r\n\r\n toEvalEvent(user: IUser): EvalEvent | null {\r\n if (this.kind !== ReasonKinds.Match) {\r\n return null;\r\n }\r\n\r\n const targetedVariation = this.value?.variations.find(v => v.value === this.value?.variation);\r\n return new EvalEvent(user, this.value?.id!, targetedVariation!, this.value?.sendToExperiment!);\r\n }\r\n}","import { IFlag } from \"./data/IFlag\";\r\nimport EvalResult from \"./EvalResult\";\r\nimport { IStore } from \"../platform/IStore\";\r\nimport DataKinds from \"../store/DataKinds\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class Evaluator {\r\n constructor(private store: IStore) {\r\n }\r\n\r\n /**\r\n * Evaluate the given flag against the given context.\r\n * @param flagKey The key of the feature flag.\r\n */\r\n evaluate(\r\n flagKey: string,\r\n ): EvalResult {\r\n const flag = this.store.get(DataKinds.Flags, flagKey) as unknown as IFlag;\r\n if (!flag) {\r\n return EvalResult.flagNotFound(flagKey);\r\n }\r\n\r\n return EvalResult.matched(flag);\r\n }\r\n}","/**\r\n * Different kinds of error which may be encountered during evaluation.\r\n */\r\nexport enum ReasonKinds {\r\n ClientNotReady = 'ClientNotReady',\r\n Match = 'Match',\r\n WrongType = 'WrongType',\r\n FlagNotFound = 'FlagNotFound',\r\n Error = 'Error'\r\n}","export type FlagValue = any;\r\n\r\nexport enum VariationDataType {\r\n string = 'string',\r\n boolean = 'boolean',\r\n number = 'number',\r\n json = 'json',\r\n empty = ''\r\n}\r\n\r\nexport interface IVariation {\r\n id: number,\r\n value: FlagValue\r\n}\r\n\r\nexport interface IFlagBase {\r\n id: string, // the key\r\n variation: FlagValue,\r\n variationType: VariationDataType,\r\n sendToExperiment?: boolean,\r\n timestamp?: number,\r\n variationOptions?: IVariation[],\r\n}\r\n\r\nexport interface IFlag extends IFlagBase {\r\n key: string, // the same value to id\r\n variations: IVariation[],// the same value to variationOptions\r\n version: number\r\n}\r\n","export * from './IFlag';","export * from './data';\r\nexport * from './EvalResult';\r\nexport * from './Evaluator';\r\nexport * from './IEvalDetail';\r\nexport * from './ReasonKinds';","import { IEventProcessor } from \"./IEventProcessor\";\r\nimport { EventDispatcher } from \"./EventDispatcher\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { FlushEvent, IEvent, ShutdownEvent } from \"./event\";\r\nimport { isNullOrUndefined } from \"../utils/isNullOrUndefined\";\r\nimport { IEventQueue } from \"./IEventQueue\";\r\nimport { DefaultEventQueue } from \"./DefaultEventQueue\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\n\r\nexport class DefaultEventProcessor implements IEventProcessor {\r\n private readonly logger: ILogger;\r\n private readonly flushInterval: number;\r\n private readonly eventDispatcher: EventDispatcher;\r\n private readonly eventQueue: IEventQueue;\r\n private closed: boolean = false;\r\n\r\n constructor(clientContext: ClientContext) {\r\n const {logger, flushInterval, maxEventsInQueue} = clientContext;\r\n this.logger = logger!;\r\n this.flushInterval = flushInterval;\r\n this.eventQueue = new DefaultEventQueue(maxEventsInQueue, this.logger);\r\n this.eventDispatcher = new EventDispatcher(clientContext, this.eventQueue);\r\n\r\n this.flushLoop();\r\n }\r\n\r\n private flushLoop() {\r\n if (this.closed) {\r\n return;\r\n }\r\n\r\n setTimeout(async () => {\r\n try {\r\n await this.flush();\r\n } catch (err) {\r\n this.logger.error('Unexpected error while flushing events in event processor.', err);\r\n }\r\n\r\n this.flushLoop();\r\n }, this.flushInterval);\r\n }\r\n\r\n flush(): Promise {\r\n const flushEvent = new FlushEvent();\r\n this.record(flushEvent);\r\n return flushEvent.waitForCompletion();\r\n }\r\n\r\n async close(): Promise {\r\n if (this.closed) {\r\n return;\r\n }\r\n\r\n // send a shutdown event to dispatcher\r\n const shutdown = new ShutdownEvent();\r\n this.record(shutdown);\r\n\r\n try {\r\n await shutdown.waitForCompletion();\r\n } catch (err) {\r\n this.logger.error('Event processor shutdown but not complete.');\r\n }\r\n\r\n // mark the event queue as complete for adding\r\n this.eventQueue.close();\r\n this.closed = true;\r\n }\r\n\r\n record(event: IEvent | null): boolean {\r\n if (isNullOrUndefined(event)) {\r\n return false;\r\n }\r\n\r\n if (!this.eventQueue.addEvent(event!)) {\r\n if (event instanceof FlushEvent) {\r\n event.complete();\r\n }\r\n\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n}","import { IEventQueue } from \"./IEventQueue\";\r\nimport { IEvent } from \"./event\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\n\r\nexport class DefaultEventQueue implements IEventQueue {\r\n private events: IEvent[];\r\n private closed: boolean = false;\r\n\r\n constructor(private readonly capacity: number, private readonly logger: ILogger) {\r\n this.events = [];\r\n }\r\n\r\n addEvent(event: IEvent): boolean {\r\n if (this.closed) {\r\n return false;\r\n }\r\n\r\n if (this.events.length >= this.capacity) {\r\n this.logger.warn(\"Events are being produced faster than they can be processed. We shouldn't see this.\");\r\n return false;\r\n }\r\n\r\n this.events.push(event);\r\n return true;\r\n }\r\n\r\n clear(): void {\r\n this.events = [];\r\n }\r\n\r\n shift(): IEvent | undefined {\r\n return this.events.shift();\r\n }\r\n\r\n close(): void {\r\n this.closed = true;\r\n }\r\n\r\n get eventsSnapshot(): IEvent[] {\r\n return [...this.events];\r\n }\r\n\r\n get length(): number {\r\n return this.events.length;\r\n }\r\n\r\n get isEmpty(): boolean {\r\n return this.length === 0;\r\n }\r\n}","import { DeliveryStatus, IEventSender, IEventSenderResult } from \"./IEventSender\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { defaultHeaders, httpErrorMessage } from \"../utils/http\";\r\nimport { IRequests } from \"../platform/requests\";\r\nimport { isHttpRecoverable, UnexpectedResponseError } from \"../errors\";\r\nimport sleep from \"../utils/sleep\";\r\n\r\nexport class DefaultEventSender implements IEventSender {\r\n private readonly defaultHeaders: {\r\n [key: string]: string;\r\n };\r\n private readonly eventsUri: string;\r\n private requests: IRequests;\r\n\r\n constructor(clientContext: ClientContext) {\r\n const {\r\n sdkKey,\r\n eventsUri,\r\n platform\r\n } = clientContext;\r\n\r\n const {info, requests} = platform;\r\n this.defaultHeaders = defaultHeaders(sdkKey, info);\r\n this.eventsUri = eventsUri;\r\n this.requests = requests;\r\n }\r\n\r\n async send(payload: string, retry: boolean): Promise {\r\n const res: IEventSenderResult = {\r\n status: DeliveryStatus.Succeeded,\r\n };\r\n\r\n const headers: Record = {\r\n ...this.defaultHeaders,\r\n 'content-type': 'application/json',\r\n }\r\n\r\n let error;\r\n try {\r\n const {status} = await this.requests.fetch(this.eventsUri, {\r\n headers,\r\n body: payload,\r\n method: 'POST',\r\n });\r\n\r\n if (status >= 200 && status <= 299) {\r\n return res;\r\n }\r\n\r\n error = new UnexpectedResponseError(\r\n httpErrorMessage({status, message: 'some events were dropped'}, 'event posting'),\r\n );\r\n\r\n if (!isHttpRecoverable(status)) {\r\n res.status = DeliveryStatus.FailedAndMustShutDown;\r\n res.error = error;\r\n return res;\r\n }\r\n } catch (err) {\r\n error = err;\r\n }\r\n\r\n // recoverable but not retrying\r\n if (error && !retry) {\r\n res.status = DeliveryStatus.Failed;\r\n res.error = error;\r\n return res;\r\n }\r\n\r\n // wait 1 second before retrying\r\n await sleep();\r\n\r\n return this.send(payload, false);\r\n }\r\n}","import { IEventSerializer } from \"./EventSerializer\";\r\nimport { EvalEvent, IEvent, MetricEvent } from \"./event\";\r\n\r\nexport class DefaultEventSerializer implements IEventSerializer {\r\n serialize(events: IEvent[]): string {\r\n const payload = events\r\n .map(event => event instanceof EvalEvent || event instanceof MetricEvent ? event.toPayload() : null)\r\n .filter(event => event !== null);\r\n\r\n return JSON.stringify(payload);\r\n }\r\n}","import { ILogger } from \"../logging/ILogger\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { DeliveryStatus, IEventSender } from \"./IEventSender\";\r\nimport { IEventQueue } from \"./IEventQueue\";\r\nimport { DefaultEventQueue } from \"./DefaultEventQueue\";\r\nimport { DefaultEventSender } from \"./DefaultEventSender\";\r\nimport { AsyncEvent, FlushEvent, IEvent, PayloadEvent, ShutdownEvent } from \"./event\";\r\nimport { IEventSerializer } from \"./EventSerializer\";\r\nimport { DefaultEventSerializer } from \"./DefaultEventSerializer\";\r\nimport sleep from \"../utils/sleep\";\r\n\r\nexport class EventDispatcher {\r\n private readonly logger: ILogger;\r\n private sender: IEventSender;\r\n private buffer: IEventQueue;\r\n private serializer: IEventSerializer;\r\n\r\n private maxEventPerRequest = 50;\r\n private stopped: boolean = false;\r\n\r\n constructor(clientContext: ClientContext, queue: IEventQueue) {\r\n const {logger, maxEventsInQueue} = clientContext;\r\n this.logger = logger!;\r\n\r\n this.buffer = new DefaultEventQueue(maxEventsInQueue, this.logger);\r\n this.sender = new DefaultEventSender(clientContext);\r\n this.serializer = new DefaultEventSerializer();\r\n\r\n this.dispatchLoop(queue).then();\r\n }\r\n\r\n private async dispatchLoop(queue: IEventQueue) {\r\n this.logger.debug('Start dispatch loop.');\r\n\r\n let running = true;\r\n while (running) {\r\n try {\r\n const event = queue.shift();\r\n\r\n if (event === undefined) {\r\n await sleep(1000);\r\n continue;\r\n }\r\n\r\n if (event instanceof PayloadEvent) {\r\n this.addEventToBuffer(event);\r\n } else if (event instanceof FlushEvent) {\r\n await this.triggerFlush(event);\r\n } else if (event instanceof ShutdownEvent) {\r\n await this.triggerFlush(event);\r\n this.stopped = true;\r\n running = false;\r\n }\r\n } catch (err) {\r\n this.logger.error('Unexpected error in event dispatcher.', err);\r\n }\r\n }\r\n\r\n this.logger.debug('Finish dispatch loop.');\r\n }\r\n\r\n private addEventToBuffer(event: IEvent) {\r\n if (this.stopped) {\r\n return;\r\n }\r\n\r\n if (this.buffer.addEvent(event)) {\r\n this.logger.debug('Added event to buffer.');\r\n } else {\r\n this.logger.warn('Exceeded event queue capacity, event will be dropped. Increase capacity to avoid dropping events.');\r\n }\r\n }\r\n\r\n private async triggerFlush(event: AsyncEvent) {\r\n if (this.stopped) {\r\n event.complete();\r\n return;\r\n }\r\n\r\n if (this.buffer.isEmpty) {\r\n event.complete();\r\n this.logger.debug('Flush empty buffer.');\r\n // There are no events to flush. If we don't complete the message, then the async task may never\r\n // complete (if it had a non-zero positive timeout, then it would complete after the timeout).\r\n return;\r\n }\r\n\r\n const snapshot = this.buffer.eventsSnapshot;\r\n this.buffer.clear();\r\n try {\r\n await this.flushEvents(snapshot);\r\n this.logger.debug(`${ snapshot.length } events has been flushed.`);\r\n } catch (err) {\r\n this.logger.warn('Exception happened when flushing events', err);\r\n }\r\n\r\n event.complete();\r\n }\r\n\r\n private async flushEvents(events: IEvent[]) {\r\n events = this.getUniqueEvents(events);\r\n const total = events.length;\r\n for (let i = 0; i < total; i += this.maxEventPerRequest) {\r\n const length = Math.min(this.maxEventPerRequest, total - i);\r\n const slice = events.slice(i, i + length);\r\n const payload = this.serializer.serialize(slice);\r\n\r\n const {status} = await this.sender.send(payload, true);\r\n if (status === DeliveryStatus.FailedAndMustShutDown) {\r\n this.stopped = true;\r\n }\r\n }\r\n }\r\n\r\n private getUniqueEvents(events: IEvent[]): IEvent[] {\r\n const uniqueEvents: IEvent[] = [];\r\n const hashes: string[] = [];\r\n\r\n for (const event of events) {\r\n if (!hashes.includes(event.hash)) {\r\n uniqueEvents.push(event);\r\n hashes.push(event.hash);\r\n }\r\n }\r\n\r\n return uniqueEvents;\r\n }\r\n}","export enum DeliveryStatus {\r\n Succeeded,\r\n Failed,\r\n FailedAndMustShutDown\r\n}\r\n\r\nexport interface IEventSenderResult {\r\n status: DeliveryStatus,\r\n error?: any\r\n}\r\n\r\nexport interface IEventSender {\r\n send(payload: string, retry: boolean): Promise;\r\n}","import { IEventProcessor } from \"./IEventProcessor\";\r\nimport { IEvent } from \"./event\";\r\n\r\nexport class NullEventProcessor implements IEventProcessor {\r\n flush(): Promise {\r\n return Promise.resolve();\r\n }\r\n\r\n close(): Promise {\r\n return Promise.resolve();\r\n }\r\n\r\n record(event: IEvent | null): boolean {\r\n return false;\r\n }\r\n}","import { IUser } from \"../options/IUser\";\r\nimport { IVariation } from \"../evaluation/data/IFlag\";\r\n\r\nexport interface IEvent {\r\n hash: string;\r\n}\r\n\r\nexport class AsyncEvent implements IEvent {\r\n private readonly isCompletedPromise?: Promise;\r\n private resolveFn?: (value: AsyncEvent) => void;\r\n timestamp = (new Date()).getTime();\r\n\r\n get hash(): string {\r\n return this.timestamp.toString();\r\n }\r\n\r\n constructor() {\r\n this.isCompletedPromise = new Promise((resolve) => {\r\n this.resolveFn = resolve;\r\n });\r\n }\r\n\r\n waitForCompletion(): Promise {\r\n return this.isCompletedPromise!;\r\n }\r\n\r\n complete() {\r\n this.resolveFn?.(this);\r\n }\r\n}\r\n\r\nexport class FlushEvent extends AsyncEvent {\r\n}\r\n\r\nexport class ShutdownEvent extends AsyncEvent {\r\n}\r\n\r\nexport class PayloadEvent implements IEvent {\r\n timestamp = (new Date()).getTime();\r\n\r\n get hash(): string {\r\n return this.timestamp.toString();\r\n }\r\n\r\n toPayload(): any {\r\n };\r\n}\r\n\r\nexport class MetricEvent extends PayloadEvent {\r\n constructor(\r\n public user: IUser,\r\n public eventName: string,\r\n public appType: string,\r\n public metricValue: number\r\n ) {\r\n super();\r\n }\r\n\r\n private userPayload() {\r\n return {\r\n keyId: this.user.keyId,\r\n name: this.user.name,\r\n customizedProperties: this.user.customizedProperties\r\n }\r\n }\r\n\r\n toPayload(): any {\r\n return {\r\n user: this.userPayload(),\r\n metrics: [{\r\n route: 'index/metric',\r\n timestamp: this.timestamp,\r\n numericValue: this.metricValue,\r\n appType: this.appType,\r\n eventName: this.eventName,\r\n type: 'CustomEvent'\r\n }]\r\n }\r\n }\r\n\r\n get hash(): string {\r\n const payload = this.toPayload();\r\n const hasObject = {\r\n user: payload.user,\r\n metrics: payload.metrics.map((m: any) => ({...m, timestamp: undefined}))\r\n }\r\n return JSON.stringify(hasObject);\r\n }\r\n}\r\n\r\nexport class EvalEvent extends PayloadEvent {\r\n constructor(\r\n public user: IUser,\r\n public flagKey: string,\r\n public variation: IVariation,\r\n public sendToExperiment: boolean\r\n ) {\r\n super();\r\n }\r\n\r\n private userPayload() {\r\n return {\r\n keyId: this.user.keyId,\r\n name: this.user.name,\r\n customizedProperties: this.user.customizedProperties\r\n }\r\n }\r\n\r\n toPayload(): any {\r\n return {\r\n user: this.userPayload(),\r\n variations: [{\r\n featureFlagKey: this.flagKey,\r\n sendToExperiment: this.sendToExperiment,\r\n timestamp: this.timestamp,\r\n variation: this.variation\r\n }]\r\n }\r\n }\r\n\r\n get hash(): string {\r\n const payload = this.toPayload();\r\n const hasObject = {\r\n user: payload.user,\r\n variations: payload.variations.map((m: any) => ({...m, timestamp: undefined}))\r\n }\r\n\r\n return JSON.stringify(hasObject);\r\n }\r\n}","export * from './DefaultEventProcessor';\r\nexport * from './DefaultEventQueue';\r\nexport * from './DefaultEventSender';\r\nexport * from './DefaultEventSerializer';\r\nexport * from './event';\r\nexport * from './EventDispatcher';\r\nexport * from './EventSerializer';\r\nexport * from './IEventProcessor';\r\nexport * from './IEventQueue';\r\nexport * from './IEventSender';\r\nexport * from './NullEventProcessor';\r\n","export * from './bootstrap';\r\nexport * from './data-sources';\r\nexport * from './evaluation';\r\nexport * from './events';\r\nexport * from './logging';\r\nexport * from './options';\r\nexport * from './platform';\r\nexport * from './store';\r\nexport * from './data-sync';\r\nexport * from './utils';\r\n\r\nexport * from './Configuration';\r\nexport * from './constants';\r\nexport * from './Context';\r\nexport * from './errors';\r\nexport * from './FbClientBuilder';\r\nexport * from './IContextProperty';\r\nexport * from './IDataKind';\r\nexport * from './IFbClient';\r\nexport * from './IVersionedData';\r\nexport * from './FbClientCore';\r\n\r\n","import format from './format';\r\nimport { ILogger } from \"./ILogger\";\r\nimport { IBasicLoggerOptions } from \"./IBasicLoggerOptions\";\r\n\r\nconst LogPriority = {\r\n debug: 0,\r\n info: 1,\r\n warn: 2,\r\n error: 3,\r\n none: 4,\r\n};\r\n\r\nconst LevelNames = ['debug', 'info', 'warn', 'error', 'none'];\r\n\r\n/**\r\n * A basic logger which handles filtering by level.\r\n *\r\n * With the default options it will write to `console.error`\r\n * and it will use the formatting provided by `console.error`.\r\n * If the destination is overwritten, then it will use an included\r\n * formatter similar to `util.format`.\r\n *\r\n * If a formatter is available, then that should be overridden\r\n * as well for performance.\r\n */\r\nexport class BasicLogger implements ILogger {\r\n private logLevel: number;\r\n\r\n private name: string;\r\n\r\n private destination?: (line: string) => void;\r\n\r\n private formatter?: (...args: any[]) => string;\r\n\r\n /**\r\n * This should only be used as a default fallback and not as a convenient\r\n * solution. In most cases you should construct a new instance with the\r\n * appropriate options for your specific needs.\r\n */\r\n static get() {\r\n return new BasicLogger({});\r\n }\r\n\r\n constructor(options: IBasicLoggerOptions) {\r\n this.logLevel = LogPriority[options.level ?? 'info'] ?? LogPriority.info;\r\n this.name = options.name ?? 'FeatBit';\r\n // eslint-disable-next-line no-console\r\n this.destination = options.destination;\r\n this.formatter = options.formatter;\r\n }\r\n\r\n private tryFormat(...args: any[]): string {\r\n try {\r\n if (this.formatter) {\r\n // In case the provided formatter fails.\r\n return this.formatter?.(...args);\r\n }\r\n return format(...args);\r\n } catch {\r\n return format(...args);\r\n }\r\n }\r\n\r\n private tryWrite(msg: string) {\r\n try {\r\n this.destination!(msg);\r\n } catch {\r\n // eslint-disable-next-line no-console\r\n console.error(msg);\r\n }\r\n }\r\n\r\n private log(level: number, args: any[]) {\r\n if (level >= this.logLevel) {\r\n const prefix = `${ LevelNames[level] }: [${ this.name }]`;\r\n try {\r\n if (this.destination) {\r\n this.tryWrite(`${ prefix } ${ this.tryFormat(...args) }`);\r\n } else {\r\n // `console.error` has its own formatter.\r\n // So we don't need to do anything.\r\n // eslint-disable-next-line no-console\r\n console.error(...args);\r\n }\r\n } catch {\r\n // If all else fails do not break.\r\n // eslint-disable-next-line no-console\r\n console.error(...args);\r\n }\r\n }\r\n }\r\n\r\n error(...args: any[]): void {\r\n this.log(LogPriority.error, args);\r\n }\r\n\r\n warn(...args: any[]): void {\r\n this.log(LogPriority.warn, args);\r\n }\r\n\r\n info(...args: any[]): void {\r\n this.log(LogPriority.info, args);\r\n }\r\n\r\n debug(...args: any[]): void {\r\n this.log(LogPriority.debug, args);\r\n }\r\n}\r\n","import { ILogger } from \"./ILogger\";\r\nimport { TypeValidators } from \"../options/Validators\";\r\n\r\nconst loggerRequirements = {\r\n error: TypeValidators.Function,\r\n warn: TypeValidators.Function,\r\n info: TypeValidators.Function,\r\n debug: TypeValidators.Function,\r\n};\r\n\r\n/**\r\n * The safeLogger logic exists because we allow the application to pass in a custom logger, but\r\n * there is no guarantee that the logger works correctly and if it ever throws exceptions there\r\n * could be serious consequences (e.g. an uncaught exception within an error event handler, due\r\n * to the SDK trying to log the error, can terminate the application). An exception could result\r\n * from faulty logic in the logger implementation, or it could be that this is not a logger at\r\n * all but some other kind of object; the former is handled by a catch block that logs an error\r\n * message to the SDK's default logger, and we can at least partly guard against the latter by\r\n * checking for the presence of required methods at configuration time.\r\n */\r\nexport class SafeLogger implements ILogger {\r\n private logger: ILogger;\r\n\r\n private fallback: ILogger;\r\n\r\n /**\r\n * Construct a safe logger with the specified logger.\r\n * @param logger The logger to use.\r\n * @param fallback A fallback logger to use in case an issue is encountered using\r\n * the provided logger.\r\n */\r\n constructor(logger: ILogger, fallback: ILogger) {\r\n Object.entries(loggerRequirements).forEach(([level, validator]) => {\r\n if (!validator.is((logger as any)[level])) {\r\n throw new Error(`Provided logger instance must support logger.${ level }(...) method`);\r\n // Note that the SDK normally does not throw exceptions to the application, but that rule\r\n // does not apply to FbClientNode.init() which will throw an exception if the parameters are so\r\n // invalid that we cannot proceed with creating the client. An invalid logger meets those\r\n // criteria since the SDK calls the logger during nearly all of its operations.\r\n }\r\n });\r\n this.logger = logger;\r\n this.fallback = fallback;\r\n }\r\n\r\n private log(level: 'error' | 'warn' | 'info' | 'debug', args: any[]) {\r\n try {\r\n this.logger[level](...args);\r\n } catch {\r\n // If all else fails do not break.\r\n this.fallback[level](...args);\r\n }\r\n }\r\n\r\n error(...args: any[]): void {\r\n this.log('error', args);\r\n }\r\n\r\n warn(...args: any[]): void {\r\n this.log('warn', args);\r\n }\r\n\r\n info(...args: any[]): void {\r\n this.log('info', args);\r\n }\r\n\r\n debug(...args: any[]): void {\r\n this.log('debug', args);\r\n }\r\n}","import { TypeValidators } from \"../options/Validators\";\r\n\r\n\r\n/**\r\n * Attempt to produce a string representation of a value.\r\n * The format should be roughly comparable to `util.format`\r\n * aside from object which will be JSON versus the `util.inspect`\r\n * format.\r\n * @param val\r\n * @returns A string representation of the value if possible.\r\n */\r\nfunction tryStringify(val: any) {\r\n if (typeof val === 'string') {\r\n return val;\r\n }\r\n if (val === undefined) {\r\n return 'undefined';\r\n }\r\n if (val === null) {\r\n return 'null';\r\n }\r\n if (Object.prototype.hasOwnProperty.call(val, 'toString')) {\r\n try {\r\n return val.toString();\r\n } catch {\r\n /* Keep going */\r\n }\r\n }\r\n\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n try {\r\n return JSON.stringify(val);\r\n } catch (error) {\r\n if (error instanceof TypeError && error.message.indexOf('circular') >= 0) {\r\n return '[Circular]';\r\n }\r\n return '[Not Stringifiable]';\r\n }\r\n}\r\n\r\n/**\r\n * Attempt to produce a numeric representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The numeric representation or 'NaN' if not numeric.\r\n */\r\nfunction toNumber(val: any): string {\r\n // Symbol has to be treated special because it will\r\n // throw an exception if an attempt is made to convert it.\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n return String(Number(val));\r\n}\r\n\r\n/**\r\n * Attempt to produce an integer representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The integer representation or 'NaN' if not numeric.\r\n */\r\nfunction toInt(val: any): string {\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n return String(parseInt(val, 10));\r\n}\r\n\r\n/**\r\n * Attempt to produce a float representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The integer representation or 'NaN' if not numeric.\r\n */\r\nfunction toFloat(val: any): string {\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n return String(parseFloat(val));\r\n}\r\n\r\n// Based on:\r\n// https://nodejs.org/api/util.html#utilformatformat-args\r\n// The result will not match browser exactly, but it should get the\r\n// right information through.\r\nconst escapes: Record string> = {\r\n s: (val: any) => tryStringify(val),\r\n d: (val: any) => toNumber(val),\r\n i: (val: any) => toInt(val),\r\n f: (val: any) => toFloat(val),\r\n j: (val: any) => tryStringify(val),\r\n o: (val: any) => tryStringify(val),\r\n O: (val: any) => tryStringify(val),\r\n c: () => '',\r\n};\r\n\r\n/**\r\n * A basic formatted for use where `util.format` is not available.\r\n * This will not be as performant, but it will produce formatted\r\n * messages.\r\n *\r\n * @internal\r\n *\r\n * @param args\r\n * @returns Formatted string.\r\n */\r\nexport default function format(...args: any[]): string {\r\n const formatString = args.shift();\r\n if (TypeValidators.String.is(formatString)) {\r\n let out = '';\r\n let i = 0;\r\n while (i < formatString.length) {\r\n const char = formatString.charAt(i);\r\n if (char === '%') {\r\n const nextIndex = i + 1;\r\n if (nextIndex < formatString.length) {\r\n const nextChar = formatString.charAt(i + 1);\r\n if (nextChar in escapes && args.length) {\r\n const value = args.shift();\r\n // This rule is for math.\r\n // eslint-disable-next-line no-unsafe-optional-chaining\r\n out += escapes[nextChar]?.(value);\r\n } else if (nextChar === '%') {\r\n out += '%';\r\n } else {\r\n out += `%${ nextChar }`;\r\n }\r\n i += 2;\r\n }\r\n } else {\r\n out += char;\r\n i += 1;\r\n }\r\n }\r\n // If there are any args left after we exhaust the format string\r\n // then just stick those on the end.\r\n if (args.length) {\r\n if (out.length) {\r\n out += ' ';\r\n }\r\n out += args.map(tryStringify).join(' ');\r\n }\r\n return out;\r\n }\r\n return args.map(tryStringify).join(' ');\r\n}\r\n","export * from './BasicLogger';\r\nexport * from './format';\r\nexport * from './IBasicLoggerOptions';\r\nexport * from './ILogger';\r\nexport * from './LogLevel';\r\nexport * from './SafeLogger';","import { ILogger } from \"../logging/ILogger\";\r\nimport { IPlatform } from \"../platform/IPlatform\";\r\nimport { IClientContext } from \"./IClientContext\";\r\nimport { IUser } from \"./IUser\";\r\n\r\n/**\r\n * The client context provides basic configuration and platform support which are required\r\n * when building SDK components.\r\n */\r\nexport default class ClientContext implements IClientContext {\r\n flushInterval: number;\r\n maxEventsInQueue: number;\r\n offline: boolean;\r\n logger: ILogger;\r\n eventsUri: string;\r\n pollingUri: string;\r\n streamingUri: string;\r\n\r\n constructor(\r\n public readonly sdkKey: string,\r\n configuration: {\r\n logger?: ILogger;\r\n offline?: boolean;\r\n flushInterval: number;\r\n maxEventsInQueue: number;\r\n streamingUri: string;\r\n pollingUri: string;\r\n eventsUri: string;\r\n },\r\n public readonly platform: IPlatform,\r\n ) {\r\n this.logger = configuration.logger!;\r\n this.offline = configuration.offline!;\r\n this.flushInterval = configuration.flushInterval;\r\n this.maxEventsInQueue = configuration.maxEventsInQueue;\r\n this.streamingUri = configuration.streamingUri;\r\n this.pollingUri = configuration.pollingUri;\r\n this.eventsUri = configuration.eventsUri;\r\n }\r\n}","/**\r\n * Messages for issues which can be encountered from processing the configuration options.\r\n */\r\nexport default class OptionMessages {\r\n static optionBelowMinimum(name: string, value: number, min: number): string {\r\n return `Config option \"${ name }\" had invalid value of ${ value }, using minimum of ${ min } instead`;\r\n }\r\n\r\n static unknownOption(name: string): string {\r\n return `Ignoring unknown config option \"${ name }\"`;\r\n }\r\n\r\n static wrongOptionType(name: string, expectedType: string, actualType: string): string {\r\n return `Config option \"${ name }\" should be of type ${ expectedType }, got ${ actualType }, using default value`;\r\n }\r\n\r\n static wrongOptionTypeBoolean(name: string, actualType: string): string {\r\n return `Config option \"${ name }\" should be a boolean, got ${ actualType }, converting to boolean`;\r\n }\r\n\r\n static partialEndpoint(name: string): string {\r\n return `You have set custom uris without specifying the ${ name } URI; connections may not work properly`;\r\n }\r\n\r\n static mandatory(name: string): string {\r\n return `${ name } is mandatory`;\r\n }\r\n\r\n static invalidOptionValue(name: string): string {\r\n return `Invalid option value: ${ name }`;\r\n }\r\n\r\n static missingKeyInBootstrapValue(key: string): string {\r\n return `Missing key \"${ key }\" in bootstrap value`;\r\n }\r\n}","import { IUser } from \"./IUser\";\r\nimport {IContextProperty} from \"../IContextProperty\";\r\n\r\n/**\r\n * Creates an instance of the FeatBit user.\r\n *\r\n * @return\r\n * The new {@link IUser} instance.\r\n */\r\nexport class UserBuilder {\r\n private _keyId: string = '';\r\n private _name: string = '';\r\n private _custom: IContextProperty[] = [];\r\n\r\n constructor(keyId: string) {\r\n this._keyId = keyId;\r\n }\r\n\r\n name(name: string): UserBuilder {\r\n this._name = name;\r\n return this;\r\n }\r\n\r\n custom(propertyName: string, value: string): UserBuilder {\r\n this._custom?.push({ name: propertyName, value: value });\r\n return this;\r\n }\r\n\r\n build(): IUser {\r\n return {\r\n name: this._name,\r\n keyId: this._keyId,\r\n customizedProperties: this._custom\r\n };\r\n }\r\n}","/* eslint-disable class-methods-use-this */\r\n/* eslint-disable max-classes-per-file */\r\n\r\n// The classes here are static, but needs to be instantiated to\r\n// support the generic functionality. Which is why we do not care about using\r\n// `this`\r\n\r\n// These validators are also of trivial complexity, so we are allowing more than\r\n// one per file.\r\n\r\nimport OptionMessages from \"./OptionMessages\";\r\nimport { IFlagBase } from \"../evaluation\";\r\n\r\n/**\r\n * Interface for type validation.\r\n */\r\nexport interface TypeValidator {\r\n // holding validation error messages\r\n messages?: string[];\r\n\r\n is(u: unknown): boolean;\r\n\r\n getType(): string;\r\n}\r\n\r\n/**\r\n * Validate a factory or instance.\r\n */\r\nexport class FactoryOrInstance implements TypeValidator {\r\n is(factoryOrInstance: unknown) {\r\n if (Array.isArray(factoryOrInstance)) {\r\n return false;\r\n }\r\n const anyFactory = factoryOrInstance as any;\r\n const typeOfFactory = typeof anyFactory;\r\n return typeOfFactory === 'function' || typeOfFactory === 'object';\r\n }\r\n\r\n getType(): string {\r\n return 'factory method or object';\r\n }\r\n}\r\n\r\n/**\r\n * Validate a basic type.\r\n */\r\nexport class Type implements TypeValidator {\r\n private typeName: string;\r\n\r\n protected typeOf: string;\r\n\r\n constructor(typeName: string, example: T) {\r\n this.typeName = typeName;\r\n this.typeOf = typeof example;\r\n }\r\n\r\n is(u: unknown): u is T {\r\n if (Array.isArray(u)) {\r\n return false;\r\n }\r\n return typeof u === this.typeOf;\r\n }\r\n\r\n getType(): string {\r\n return this.typeName;\r\n }\r\n}\r\n\r\n/**\r\n * Validate an array of the specified type.\r\n *\r\n * This does not validate instances of types. All class instances\r\n * of classes will simply objects.\r\n */\r\nexport class TypeArray implements TypeValidator {\r\n private typeName: string;\r\n\r\n protected typeOf: string;\r\n\r\n constructor(typeName: string, example: T) {\r\n this.typeName = typeName;\r\n this.typeOf = typeof example;\r\n }\r\n\r\n is(u: unknown): u is T {\r\n if (Array.isArray(u)) {\r\n if (u.length > 0) {\r\n return u.every((val) => typeof val === this.typeOf);\r\n }\r\n return true;\r\n }\r\n return false;\r\n }\r\n\r\n getType(): string {\r\n return this.typeName;\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a number and is greater or eval than a minimum.\r\n */\r\nexport class NumberWithMinimum extends Type {\r\n readonly min: number;\r\n\r\n constructor(min: number) {\r\n super(`number with minimum value of ${ min }`, 0);\r\n this.min = min;\r\n }\r\n\r\n override is(u: unknown): u is number {\r\n return typeof u === this.typeOf && (u as number) >= this.min;\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a string and it matches the given expression.\r\n */\r\nexport class StringMatchingRegex extends Type {\r\n readonly expression: RegExp;\r\n\r\n constructor(expression: RegExp) {\r\n super(`string matching ${ expression }`, '');\r\n this.expression = expression;\r\n }\r\n\r\n override is(u: unknown): u is string {\r\n return !!(u as string).match(this.expression);\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a function.\r\n */\r\nexport class Function implements TypeValidator {\r\n is(u: unknown): u is (...args: any[]) => void {\r\n // We cannot inspect the parameters and there isn't really\r\n // a generic function type we can instantiate.\r\n // So the type guard is here just to make TS comfortable\r\n // calling something after using this guard.\r\n return typeof u === 'function';\r\n }\r\n\r\n getType(): string {\r\n return 'function';\r\n }\r\n}\r\n\r\nexport class NullableBoolean implements TypeValidator {\r\n is(u: unknown): boolean {\r\n return typeof u === 'boolean' || typeof u === 'undefined' || u === null;\r\n }\r\n\r\n getType(): string {\r\n return 'boolean | undefined | null';\r\n }\r\n}\r\n\r\nexport class BootstrapValidator implements TypeValidator {\r\n messages: string[] = [];\r\n\r\n is(u: unknown): boolean {\r\n if (typeof u !== 'object' || u === null) {\r\n this.messages.push(OptionMessages.invalidOptionValue('bootstrap'));\r\n return false;\r\n }\r\n\r\n try {\r\n const bootstrap = u as IFlagBase[];\r\n for (let flag of bootstrap) {\r\n const hasMandatoryKeys = ['id', 'variation'].every((key) => Object.keys(flag).includes(key));\r\n const keys = Object.keys(flag);\r\n\r\n if (keys.includes('id')) {\r\n this.messages.push(OptionMessages.missingKeyInBootstrapValue('id'));\r\n }\r\n\r\n if (keys.includes('variation')) {\r\n this.messages.push(OptionMessages.missingKeyInBootstrapValue('variation'));\r\n }\r\n\r\n if (this.messages.length > 0) {\r\n return false;\r\n }\r\n }\r\n } catch (_) {\r\n this.messages.push(OptionMessages.wrongOptionType('bootstrap', this.getType(), typeof u));\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n\r\n getType(): string {\r\n return 'IFlagBase[]';\r\n }\r\n}\r\n\r\nexport class UserValidator implements TypeValidator {\r\n messages: string[] = [];\r\n\r\n is(u: unknown): boolean {\r\n if (typeof u !== 'object' || u === null) {\r\n this.messages.push(OptionMessages.mandatory('user'));\r\n return false;\r\n }\r\n\r\n const user = u as any;\r\n\r\n if (typeof user.keyId !== 'string' || user.keyId.trim() === '') {\r\n this.messages.push(OptionMessages.mandatory('user.keyId'));\r\n return false;\r\n }\r\n\r\n if (typeof user.name !== 'string' || user.name.trim() === '') {\r\n this.messages.push(OptionMessages.mandatory('user.name'));\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n\r\n getType(): string {\r\n return 'user';\r\n }\r\n}\r\n\r\n// Our reference SDK, Go, parses date/time strings with the time.RFC3339Nano format.\r\n// This regex should match strings that are valid in that format, and no others.\r\n// Acceptable:\r\n// 2019-10-31T23:59:59Z, 2019-10-31T23:59:59.100Z,\r\n// 2019-10-31T23:59:59-07, 2019-10-31T23:59:59-07:00, etc.\r\n// Unacceptable: no \"T\", no time zone designation\r\nconst DATE_REGEX = /^\\d\\d\\d\\d-\\d\\d-\\d\\dT\\d\\d:\\d\\d:\\d\\d(\\.\\d\\d*)?(Z|[-+]\\d\\d(:\\d\\d)?)/;\r\n\r\n/**\r\n * Validate a value is a date. Values which are numbers are treated as dates and any string\r\n * which if compliant with `time.RFC3339Nano` is a date.\r\n */\r\nexport class DateValidator implements TypeValidator {\r\n is(u: unknown): boolean {\r\n return typeof u === 'number' || (typeof u === 'string' && DATE_REGEX.test(u));\r\n }\r\n\r\n getType(): string {\r\n return 'date';\r\n }\r\n}\r\n\r\n/**\r\n * Validates that a string is a valid kind.\r\n */\r\nexport class KindValidator extends StringMatchingRegex {\r\n constructor() {\r\n super(/^(\\w|\\.|-)+$/);\r\n }\r\n\r\n override is(u: unknown): u is string {\r\n return super.is(u) && u !== 'kind';\r\n }\r\n}\r\n\r\n/**\r\n * A set of standard type validators.\r\n */\r\nexport class TypeValidators {\r\n static readonly String = new Type('string', '');\r\n\r\n static readonly Number = new Type('number', 0);\r\n\r\n static readonly ObjectOrFactory = new FactoryOrInstance();\r\n\r\n static readonly Object = new Type('object', {});\r\n\r\n static readonly StringArray = new TypeArray('string[]', '');\r\n\r\n static readonly Boolean = new Type('boolean', true);\r\n\r\n static readonly User = new Type('object', {});\r\n\r\n static readonly Bootstrap = new Type('object', {});\r\n\r\n static readonly Function = new Function();\r\n\r\n static createTypeArray(typeName: string, example: T) {\r\n return new TypeArray(typeName, example);\r\n }\r\n\r\n static numberWithMin(min: number): NumberWithMinimum {\r\n return new NumberWithMinimum(min);\r\n }\r\n\r\n static stringMatchingRegex(expression: RegExp): StringMatchingRegex {\r\n return new StringMatchingRegex(expression);\r\n }\r\n\r\n static readonly Date = new DateValidator();\r\n\r\n static readonly Kind = new KindValidator();\r\n static readonly NullableBoolean = new NullableBoolean();\r\n}","export * from './ClientContext';\r\nexport * from './IClientContext';\r\nexport * from './IOptions';\r\nexport * from './IUser';\r\nexport * from './IValidatedOptions';\r\nexport * from './OptionMessages';\r\nexport * from './UserBuilder';\r\nexport * from './Validators';","import { IInfo, IPlatformData, ISdkData } from \"../IInfo\";\r\nimport { name, version } from '../../version';\r\n\r\n\r\nexport default class BrowserInfo implements IInfo {\r\n get appType(): string {\r\n return 'Browser-Client-SDK';\r\n }\r\n\r\n platformData(): IPlatformData {\r\n return {\r\n os: {},\r\n name: 'Browser',\r\n additional: {},\r\n };\r\n }\r\n\r\n sdkData(): ISdkData {\r\n return {\r\n name: name,\r\n version: version,\r\n userAgentBase: this.appType\r\n };\r\n }\r\n}","import { IPlatform } from \"../IPlatform\";\r\nimport { IInfo } from \"../IInfo\";\r\nimport { IRequests } from \"../requests\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport BrowserInfo from \"./BrowserInfo\";\r\nimport { BrowserRequests } from \"./BrowserRequests\";\r\nimport { IWebSocketWithEvents } from \"../IWebSocket\";\r\nimport BrowserWebSocket from \"./BrowserWebSocket\";\r\n\r\nexport default class BrowserPlatform implements IPlatform {\r\n info: IInfo = new BrowserInfo();\r\n\r\n requests: IRequests;\r\n webSocket: IWebSocketWithEvents;\r\n\r\n constructor(options: IOptions) {\r\n this.requests = new BrowserRequests();\r\n this.webSocket = new BrowserWebSocket();\r\n }\r\n}","import { IRequestOptions, IRequests } from \"../requests\";\r\n\r\nexport class BrowserRequests implements IRequests {\r\n fetch(url: string, options: IRequestOptions = {}): Promise {\r\n return fetch(url, options);\r\n }\r\n}","import { IWebSocket, IWebSocketConfig } from \"../IWebSocket\";\r\nimport { Emits } from \"../../utils/Emits\";\r\nimport { IEventEmitter } from \"../../utils/IEventEmitter\";\r\nimport { EventEmitter } from \"../../utils/EventEmitter\";\r\nimport { generateConnectionToken } from \"../../data-sync/utils\";\r\nimport { StreamResponseEventType } from \"../../data-sync/types\";\r\nimport { IUser } from \"../../options/IUser\";\r\n\r\nconst socketConnectionIntervals = [1000, 3000, 5000, 7000, 11000, 13000, 30000, 60000];\r\n\r\nclass BrowserWebSocket implements IWebSocket {\r\n emitter: IEventEmitter;\r\n private ws?: WebSocket;\r\n private retryCounter = 0;\r\n private closed: boolean = false;\r\n\r\n private _config: IWebSocketConfig = {} as IWebSocketConfig;\r\n\r\n constructor() {\r\n this.emitter = new EventEmitter();\r\n }\r\n\r\n identify(user: IUser) {\r\n this._config.user = user;\r\n this.doDataSync();\r\n }\r\n\r\n connect() {\r\n let that = this;\r\n const startTime = Date.now();\r\n const url = this._config.streamingUri.replace(/^http/, 'ws') + `?type=client&token=${ generateConnectionToken(this._config.sdkKey) }`;\r\n this.ws = new WebSocket(url);\r\n\r\n // Connection opened\r\n that.ws?.addEventListener('open', function (this: WebSocket, event) {\r\n // this is the websocket instance to which the current listener is binded to, it's different from that.socket\r\n that._config.logger.info(`WebSocket connection succeeded, connection time: ${ Date.now() - startTime } ms`);\r\n that.doDataSync();\r\n that.sendPingMessage();\r\n });\r\n\r\n // Connection closed\r\n that.ws?.addEventListener('close', function (event) {\r\n that._config.logger.warn('WebSocket closed');\r\n if (event.code === 4003) { // do not reconnect when 4003\r\n return;\r\n }\r\n\r\n that.reconnect();\r\n });\r\n\r\n // Connection error\r\n that.ws?.addEventListener('error', function (event) {\r\n // reconnect\r\n that._config.logger.debug('error');\r\n });\r\n\r\n // Listen for messages\r\n that.ws?.addEventListener('message', function (event) {\r\n const message = JSON.parse(event.data as string);\r\n if (message.messageType === 'data-sync') {\r\n switch (message.data.eventType) {\r\n case StreamResponseEventType.patch:\r\n that.emitter.emit('patch', message);\r\n break;\r\n case StreamResponseEventType.full:\r\n that.emitter.emit('put', message);\r\n break;\r\n }\r\n }\r\n });\r\n }\r\n\r\n close() {\r\n this.closed = true;\r\n this.ws?.close(4003, 'The client is closed by user');\r\n this.ws = undefined;\r\n }\r\n\r\n config(param: IWebSocketConfig) {\r\n if (param.emitter) {\r\n this.emitter = param.emitter;\r\n }\r\n\r\n this._config = {...param};\r\n }\r\n\r\n private sendPingMessage() {\r\n const payload = {\r\n messageType: 'ping',\r\n data: null\r\n };\r\n\r\n setTimeout(() => {\r\n try {\r\n if (this.ws?.readyState === WebSocket.OPEN) {\r\n this._config.logger.debug('sending ping')\r\n this.ws.send(JSON.stringify(payload));\r\n this.sendPingMessage();\r\n } else {\r\n this._config.logger.debug(`socket closed at ${ new Date() }`);\r\n }\r\n } catch (err) {\r\n this._config.logger.debug(err);\r\n }\r\n }, this._config.pingInterval);\r\n }\r\n\r\n private doDataSync() {\r\n const payload = {\r\n messageType: 'data-sync',\r\n data: {\r\n timestamp: this._config.getStoreTimestamp(),\r\n user: this._config.user\r\n }\r\n };\r\n\r\n try {\r\n if (this.ws?.readyState === WebSocket.OPEN) {\r\n this._config.logger.debug('requesting data');\r\n this.ws?.send(JSON.stringify(payload));\r\n } else {\r\n this._config.logger.error(`not requesting data because socket not open`);\r\n }\r\n } catch (err) {\r\n this._config.logger.debug(err);\r\n }\r\n }\r\n\r\n private reconnect() {\r\n if (!this.closed) {\r\n this.ws = undefined;\r\n const waitTime = socketConnectionIntervals[Math.min(this.retryCounter++, socketConnectionIntervals.length - 1)];\r\n this._config.logger.info(`The client will try to reconnect in ${ waitTime } milliseconds.`);\r\n setTimeout(() => {\r\n this._config.logger.info(`The client is trying to reconnect, flag evaluation results may be stale until reconnected, waited for: ${ waitTime } milliseconds`);\r\n this.connect();\r\n }, waitTime);\r\n }\r\n }\r\n}\r\n\r\nexport default Emits(BrowserWebSocket);","import { FbClientCore } from \"../../FbClientCore\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport { BasicLogger } from \"../../logging/BasicLogger\";\r\nimport { EventEmitter } from \"../../utils/EventEmitter\";\r\nimport { SafeLogger } from \"../../logging/SafeLogger\";\r\nimport { Emits } from \"../../utils/Emits\";\r\nimport { IEventEmitter } from \"../../utils/IEventEmitter\";\r\nimport BrowserPlatform from \"./BrowserPlatform\";\r\nimport LocalStorageStore from \"./LocalStorageStore\";\r\nimport { IPlatform } from \"../IPlatform\";\r\n\r\n/**\r\n * @ignore\r\n */\r\nclass FbClient extends FbClientCore {\r\n emitter: IEventEmitter;\r\n\r\n constructor(options: IOptions, platform: IPlatform | undefined = undefined) {\r\n const fallbackLogger = new BasicLogger({\r\n level: 'none',\r\n destination: console.log\r\n });\r\n\r\n const logger = options.logger ? new SafeLogger(options.logger, fallbackLogger) : fallbackLogger;\r\n\r\n const emitter = new EventEmitter(logger);\r\n\r\n let { store } = options;\r\n if (!store) {\r\n store = new LocalStorageStore(options);\r\n }\r\n\r\n super(\r\n {...options, logger, store },\r\n platform ?? new BrowserPlatform({...options, logger}),\r\n {\r\n onError: (err: Error) => {\r\n if (emitter.listenerCount('error')) {\r\n emitter.emit('error', err);\r\n }\r\n },\r\n onFailed: (err: Error) => {\r\n emitter.emit('failed', err);\r\n },\r\n onReady: () => {\r\n emitter.emit('ready');\r\n },\r\n onUpdate: (keys: string[]) => {\r\n emitter.emit('update', [keys]);\r\n keys.forEach((key) => emitter.emit(`update:${ key }`, key));\r\n },\r\n hasEventListeners: () =>\r\n emitter\r\n .eventNames()\r\n .some(\r\n (name) =>\r\n name === 'update' || (typeof name === 'string' && name.startsWith('update:')),\r\n ),\r\n },\r\n );\r\n\r\n this.emitter = emitter;\r\n }\r\n}\r\n\r\nexport default Emits(FbClient);","import {\r\n StoreStorageKey,\r\n IStoreDataStorage, CurrentUserStorageKey\r\n} from \"../../store/store\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport { BaseStore } from \"../../store/BaseStore\";\r\nimport { ILogger } from \"../../logging\";\r\nimport { serializeUser } from \"../../utils/serializeUser\";\r\n\r\nexport default class LocalStorageStore extends BaseStore {\r\n private logger: ILogger;\r\n\r\n constructor(options: IOptions) {\r\n super();\r\n\r\n this.logger = options.logger!;\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get description(): string {\r\n return 'local-storage-store'\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async saveUser(): Promise {\r\n localStorage.setItem(CurrentUserStorageKey, serializeUser(this._user));\r\n }\r\n\r\n protected override async dumpStoreToStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n localStorage.setItem(storageKey, JSON.stringify(this.store));\r\n }\r\n\r\n protected override async loadStoreFromStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n const dataStoreStr = localStorage.getItem(storageKey);\r\n let store: IStoreDataStorage | null = null;\r\n\r\n try {\r\n if (dataStoreStr && dataStoreStr.trim().length > 0) {\r\n store = JSON.parse(dataStoreStr);\r\n }\r\n } catch (err) {\r\n this.logger.error(`error while loading local data store: ${storageKey}`, err);\r\n }\r\n\r\n if (!!store) {\r\n this.store = store;\r\n } else {\r\n this.store = {\r\n flags: {},\r\n version: 0\r\n };\r\n }\r\n }\r\n}","export * from './IInfo';\r\nexport * from './IStore';\r\nexport * from './IPlatform';\r\nexport * from './IWebSocket';\r\nexport * from './requests';\r\nexport * from './browser/BrowserRequests';\r\n\r\nimport BrowserWebSocket from './browser/BrowserWebSocket';\r\n\r\nexport {\r\n BrowserWebSocket\r\n};","import { IStore } from \"../platform\";\r\nimport { IKeyedStoreItem, IStoreDataStorage, IStoreItem, IStoreKindData } from \"./store\";\r\nimport { IUser } from \"../options\";\r\nimport { IDataKind } from \"../IDataKind\";\r\n\r\nexport class BaseStore implements IStore {\r\n protected store: IStoreDataStorage = {} as IStoreDataStorage;\r\n\r\n protected initCalled = false;\r\n\r\n protected _user: IUser = {} as IUser;\r\n\r\n constructor() {\r\n }\r\n\r\n async identify(user: IUser) {\r\n this._user = {...user};\r\n\r\n await this.saveUser();\r\n await this.loadStoreFromStorage();\r\n }\r\n\r\n get user(): IUser {\r\n return this._user;\r\n }\r\n\r\n protected async addItem(kind: IDataKind, key: string, item: IStoreItem) {\r\n let items = this.store[kind.namespace];\r\n if (!items) {\r\n items = {};\r\n this.store[kind.namespace] = items;\r\n }\r\n if (Object.hasOwnProperty.call(items, key)) {\r\n const old = items[key];\r\n if (!old || old.version < item.version) {\r\n items[key] = item;\r\n }\r\n } else {\r\n items[key] = item;\r\n }\r\n\r\n if (item.version > this.store.version) {\r\n this.store.version = item.version;\r\n }\r\n\r\n await this.dumpStoreToStorage();\r\n }\r\n\r\n get(kind: IDataKind, key: string): IStoreItem | null {\r\n const items = this.store[kind.namespace];\r\n if (items) {\r\n if (Object.prototype.hasOwnProperty.call(items, key)) {\r\n const item = items[key];\r\n if (item) {\r\n return item;\r\n }\r\n }\r\n }\r\n return null;\r\n }\r\n\r\n all(kind: IDataKind): [IStoreKindData, number] {\r\n const result: IStoreKindData = {};\r\n const items = this.store[kind.namespace] ?? {};\r\n Object.entries(items).forEach(([key, item]) => {\r\n if (item) {\r\n result[key] = item;\r\n }\r\n });\r\n\r\n return [result, this.store.version];\r\n }\r\n\r\n async init(allData: IStoreDataStorage) {\r\n this.store = allData as IStoreDataStorage;\r\n\r\n Object.keys(allData).map(namespace => {\r\n Object.entries(allData[namespace]).forEach(([_, item]) => {\r\n const ele = item as IStoreItem;\r\n if (ele.version > this.store.version) {\r\n this.store.version = ele.version;\r\n }\r\n })\r\n });\r\n\r\n await this.dumpStoreToStorage();\r\n this.initCalled = true;\r\n }\r\n\r\n async upsert(kind: IDataKind, data: IKeyedStoreItem) {\r\n await this.addItem(kind, data.key, data);\r\n }\r\n\r\n initialized(): boolean {\r\n return this.initCalled;\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get version(): number {\r\n return this.store.version;\r\n }\r\n\r\n // This getter needs to be overridden in the child class\r\n get description(): string {\r\n return '';\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async saveUser(): Promise {\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async loadStoreFromStorage(): Promise {\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async dumpStoreToStorage(): Promise {\r\n }\r\n}","import { IDataKind } from \"../IDataKind\";\r\n\r\nexport default class DataKinds {\r\n static readonly Flags: IDataKind = {\r\n namespace: 'flags'\r\n };\r\n}","import {\r\n StoreStorageKey,\r\n IStoreDataStorage\r\n} from \"./store\";\r\nimport { BaseStore } from \"./BaseStore\";\r\n\r\nexport default class InMemoryStore extends BaseStore {\r\n private allStores: { [DataStoreStorageKey: string]: IStoreDataStorage } = {};\r\n\r\n constructor() {\r\n super();\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get description(): string {\r\n return 'in-memory-store'\r\n }\r\n\r\n protected async saveUser(): Promise {\r\n // For in-memory store, this is a no-op.\r\n }\r\n\r\n protected override async dumpStoreToStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n this.allStores[storageKey] = {...this.store};\r\n }\r\n\r\n protected override async loadStoreFromStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n\r\n this.store = this.allStores[storageKey] ?? { flags: {}, version: 0 };\r\n }\r\n}","export * from './DataKinds';\r\nexport * from './IDataSourceUpdates';\r\nexport * from './InMemoryStore';\r\nexport * from './serialization';\r\nexport * from './store';\r\nexport * from './BaseStore';","import { IFlag } from \"../evaluation/data/IFlag\";\r\nimport DataKinds from \"./DataKinds\";\r\nimport { IVersionedData } from \"../IVersionedData\";\r\nimport { IDataKind } from \"../IDataKind\";\r\n\r\nexport interface Flags {\r\n flags: { [name: string]: IFlag };\r\n}\r\n\r\ntype VersionedFlag = IVersionedData & IFlag;\r\n\r\nexport interface IPatchData {\r\n data: VersionedFlag;\r\n kind: IDataKind;\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport function deserializeAll(flags: IFlag[]): Flags {\r\n const result = {\r\n [DataKinds.Flags.namespace]: {}\r\n };\r\n\r\n if (flags?.length) {\r\n result[DataKinds.Flags.namespace] = flags.reduce((acc: any, cur: any) => {\r\n acc[cur.id] = {...cur, version: cur.timestamp || 0, key: cur.id, variations: cur.variationOptions};\r\n return acc;\r\n }, {});\r\n }\r\n\r\n return result as any as Flags;\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport function deserializePatch(flags: IFlag[]): IPatchData[] {\r\n const result = [\r\n ...flags?.map(item => ({\r\n data: {\r\n ...item,\r\n version:item.timestamp,\r\n key: item.id,\r\n variations: item.variationOptions\r\n },\r\n kind: DataKinds.Flags\r\n })) || []\r\n ];\r\n\r\n return result as any as IPatchData[];\r\n}\r\n","export const StoreStorageKey = 'fb-datastore';\r\n\r\nexport const CurrentUserStorageKey = 'fb-user';\r\n\r\n/**\r\n * Represents an item which can be stored in the feature store.\r\n */\r\nexport interface IStoreItem {\r\n version: number;\r\n\r\n // The actual data associated with the item.\r\n [attribute: string]: any;\r\n}\r\n\r\n/**\r\n * When upserting an item it must contain a key.\r\n */\r\nexport interface IKeyedStoreItem extends IStoreItem {\r\n key: string;\r\n}\r\n\r\n/**\r\n * Represents the storage for a single kind of data. e.g. 'flag' or 'segment'.\r\n */\r\nexport interface IStoreKindData {\r\n [key: string]: IStoreItem;\r\n}\r\n\r\n/**\r\n * Represents the storage for the full data store.\r\n */\r\nexport interface IStoreDataStorage {\r\n flags: IStoreKindData;\r\n version: number;\r\n\r\n // This attribute is to ingore the type check error\r\n [attribute: string]: any;\r\n}","import { IEventEmitter } from \"./IEventEmitter\";\r\n\r\nexport type EventableConstructor = new (...args: any[]) => T;\r\nexport type Eventable = EventableConstructor<{ emitter: IEventEmitter }>;\r\n\r\n/**\r\n * Adds the implementation of an event emitter to something that contains\r\n * a field of `emitter` with type `EventEmitter`.\r\n * @param Base The class to derive the mixin from.\r\n * @returns A class extending the base with an event emitter.\r\n */\r\nexport function Emits(Base: TBase) {\r\n return class WithEvents extends Base implements IEventEmitter {\r\n on(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.on(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n addListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.addListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n once(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.once(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n removeListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.removeListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n off(eventName: string | symbol, listener: (...args: any) => void, context?: any): this {\r\n this.emitter.off(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n removeAllListeners(event?: string | symbol): this {\r\n this.emitter.removeAllListeners(event);\r\n return this;\r\n }\r\n\r\n listeners(eventName: string | symbol): Function[] {\r\n return this.emitter.listeners(eventName);\r\n }\r\n\r\n emit(eventName: string | symbol, ...args: any[]): this {\r\n this.emitter.emit(eventName, args);\r\n return this;\r\n }\r\n\r\n listenerCount(eventName: string | symbol): number {\r\n return this.emitter.listenerCount(eventName);\r\n }\r\n\r\n prependListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.prependListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n prependOnceListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.prependOnceListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n eventNames(): (string | symbol)[] {\r\n return this.emitter.eventNames();\r\n }\r\n\r\n maybeReportError (error: any): this {\r\n this.emitter.maybeReportError(error);\r\n return this;\r\n }\r\n };\r\n}","import { ILogger } from \"../logging/ILogger\";\r\nimport { IEventEmitter } from \"./IEventEmitter\";\r\n\r\ninterface Events {\r\n [key: string | symbol]: {\r\n handler: (...args: any[]) => void;\r\n context: any;\r\n }[];\r\n}\r\n\r\nexport class EventEmitter implements IEventEmitter {\r\n private events: Events = {};\r\n\r\n constructor(private logger?: ILogger) {}\r\n\r\n private listeningTo (event: string) {\r\n return !!this.events[event];\r\n }\r\n\r\n on (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n this.events[event] = this.events[event] || [];\r\n this.events[event] = this.events[event].concat({\r\n handler: handler,\r\n context: context,\r\n });\r\n\r\n return this;\r\n }\r\n\r\n addListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n return this.on(event, handler, context);\r\n }\r\n\r\n once (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n const onceHandler = (...args: any[]) => {\r\n this.off(event, onceHandler, context);\r\n handler.apply(context, args);\r\n };\r\n return this.on(event, onceHandler, context);\r\n }\r\n\r\n off (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n if (!this.events[event]) {\r\n return this;\r\n }\r\n for (let i = 0; i < this.events[event].length; i++) {\r\n if (this.events[event][i].handler === handler && this.events[event][i].context === context) {\r\n this.events[event] = this.events[event].slice(0, i).concat(this.events[event].slice(i + 1));\r\n }\r\n }\r\n\r\n return this;\r\n }\r\n\r\n removeListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n return this.off(event, handler, context);\r\n }\r\n\r\n removeAllListeners (event?: string | symbol): this {\r\n if (event) {\r\n delete this.events[event];\r\n } else {\r\n this.events = {};\r\n }\r\n\r\n return this;\r\n }\r\n\r\n listeners (event: string | symbol): Function[] {\r\n return this.events[event] ? this.events[event].map((event) => event.handler) : [];\r\n }\r\n\r\n emit (event: string | symbol, ...args: any[]): this {\r\n if (!this.events[event]) {\r\n return this;\r\n }\r\n // Copy the list of handlers before iterating, in case any handler adds or removes another handler.\r\n // Any such changes should not affect what we do here-- we want to notify every handler that existed\r\n // at the moment that the event was fired.\r\n const copiedHandlers = [...this.events[event]];\r\n for (let i = 0; i < copiedHandlers.length; i++) {\r\n copiedHandlers[i].handler.apply(copiedHandlers[i].context, Array.prototype.slice.call(arguments, 1));\r\n }\r\n\r\n return this;\r\n }\r\n\r\n listenerCount (event: string | symbol): number {\r\n return this.events[event] ? this.events[event].length : 0;\r\n }\r\n\r\n prependListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n this.events[event] = this.events[event] || [];\r\n this.events[event] = [\r\n {\r\n handler: handler,\r\n context: context,\r\n },\r\n ...this.events[event]\r\n ];\r\n\r\n return this;\r\n }\r\n\r\n prependOnceListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n const onceHandler = (...args: any[]) => {\r\n this.off(event, onceHandler, context);\r\n handler.apply(context, args);\r\n };\r\n return this.prependListener(event, onceHandler, context);\r\n }\r\n\r\n eventNames (): (string | symbol)[] {\r\n return Object.keys(this.events);\r\n }\r\n\r\n maybeReportError (error: any): this {\r\n if (!error) {\r\n return this;\r\n }\r\n if (this.listeningTo('error')) {\r\n this.emit('error', error);\r\n } else {\r\n this.logger?.error(error);\r\n }\r\n\r\n return this;\r\n }\r\n}","import { Regex } from \"./Regex\";\r\n\r\nexport interface IConvertResult {\r\n isSucceeded: boolean,\r\n value?: TValue\r\n}\r\n\r\nexport class ValueConverters {\r\n static bool(value: string): IConvertResult {\r\n if (value?.toUpperCase() === 'TRUE') {\r\n return ValueConverters.success(true);\r\n }\r\n\r\n if (value?.toUpperCase() === 'FALSE') {\r\n return ValueConverters.success(false);\r\n }\r\n\r\n return ValueConverters.error();\r\n }\r\n\r\n static number(value: string): IConvertResult {\r\n const num = Number(value);\r\n\r\n if (Number.isNaN(num)) {\r\n return ValueConverters.error();\r\n }\r\n\r\n return ValueConverters.success(num);\r\n }\r\n\r\n static string(value: string): IConvertResult {\r\n return ValueConverters.success(value);\r\n }\r\n\r\n static json(value: string): IConvertResult {\r\n try {\r\n const val = JSON.parse(value);\r\n return ValueConverters.success(val);\r\n } catch (err) {\r\n return ValueConverters.error();\r\n }\r\n }\r\n\r\n private static success(value: TValue): IConvertResult {\r\n return {\r\n isSucceeded: true,\r\n value: value\r\n }\r\n }\r\n\r\n private static error(): IConvertResult {\r\n return {\r\n isSucceeded: false\r\n }\r\n }\r\n}","// This function is designed to remove any trailing forward slashes at the end of the provided URI string\r\nexport function canonicalizeUri(uri: string): string {\r\n return uri.replace(/\\/+$/, '');\r\n}","/**\r\n * Wait before calling the same function. Useful for expensive calls.\r\n * Adapted from https://amitd.co/code/typescript/debounce.\r\n *\r\n * @return The debounced function.\r\n *\r\n * @example\r\n *\r\n * ```js\r\n * const debouncedFunction = debounce(e => {\r\n * console.log(e);\r\n * }, 5000);\r\n *\r\n * // Console logs 'Hello world again ' after 5 seconds\r\n * debouncedFunction('Hello world');\r\n * debouncedFunction('Hello world again');\r\n * ```\r\n * @param fn The function to be debounced.\r\n * @param delayMs Defaults to 5 seconds.\r\n */\r\nexport const debounce = ReturnType>(\r\n fn: T,\r\n delayMs: number = 5000,\r\n): ((...args: Parameters) => void) => {\r\n let timer: ReturnType;\r\n\r\n return (...args: Parameters) => {\r\n clearTimeout(timer);\r\n timer = setTimeout(() => {\r\n fn(...args);\r\n }, delayMs);\r\n };\r\n};\r\n","import { IInfo } from \"../platform/IInfo\";\r\n\r\nexport type Headers = {\r\n Authorization: string;\r\n 'User-Agent': string;\r\n 'Content-Type': string;\r\n};\r\n\r\nexport function defaultHeaders(\r\n sdkKey: string,\r\n info: IInfo\r\n): Headers {\r\n const {userAgentBase, version} = info.sdkData();\r\n\r\n const headers: Headers = {\r\n 'Content-Type': 'application/json',\r\n 'User-Agent': `${ userAgentBase ?? info.appType }/${ version }`,\r\n 'Authorization': sdkKey\r\n };\r\n\r\n return headers;\r\n}\r\n\r\nexport function httpErrorMessage(\r\n err: {\r\n status: number;\r\n message: string;\r\n },\r\n context: string,\r\n retryMessage?: string,\r\n): string {\r\n let desc;\r\n if (err.status) {\r\n desc = `error ${ err.status }${ err.status === 401 ? ' (invalid SDK key)' : '' }`;\r\n } else {\r\n desc = `I/O error (${ err.message || err })`;\r\n }\r\n const action = retryMessage ?? 'giving up permanently';\r\n return `Received ${ desc } for ${ context } - ${ action }`;\r\n}\r\n","export * from './isNullOrUndefined';\r\nexport * from './sleep';\r\nexport * from './ValueConverters';\r\nexport * from './VoidFunction';\r\nexport * from './serializeUser';\r\nexport * from './debounce';","export function isNullOrUndefined(val: any) {\r\n return val === null || val === undefined;\r\n}","import { IUser } from \"../options/IUser\";\r\n\r\nexport function serializeUser(user: IUser | undefined): string {\r\n if (!user) {\r\n return '';\r\n }\r\n\r\n const builtInProperties = `${user.keyId},${user.name}`;\r\n\r\n const customizedProperties = user.customizedProperties\r\n ?.sort((a, b) => {\r\n const nameA = a.name.toLowerCase();\r\n const nameB = b.name.toLowerCase();\r\n if (nameA < nameB) {\r\n return -1;\r\n }\r\n\r\n if (nameA > nameB) {\r\n return 1;\r\n }\r\n\r\n return 0;\r\n })\r\n .map(p => `${p.name}:${p.value}`)\r\n .join(',');\r\n\r\n return `${builtInProperties},${customizedProperties}`;\r\n}","const sleep = async (delayMillis: number = 1000) =>\r\n new Promise((resolve) => {\r\n setTimeout(resolve, delayMillis);\r\n });\r\n\r\nexport default sleep;","export const version = \"3.0.2\"; export const name = \"@featbit/js-client-sdk\";\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// startup\n// Load entry module and return exports\n// This entry module is referenced by other modules so it can't be inlined\nvar __webpack_exports__ = __webpack_require__(9872);\n"],"names":["root","factory","exports","module","define","amd","a","i","this","validations","startWaitTime","TypeValidators","Number","sdkKey","String","pollingUri","streamingUri","eventsUri","webSocketPingInterval","logger","Object","store","ObjectOrFactory","dataSynchronizer","flushInterval","maxEventsInQueue","pollingInterval","offline","Boolean","dataSyncMode","bootstrap","Bootstrap","user","User","defaultValues","DataSyncModeEnum","STREAMING","sendEvents","options","undefined","constructor","bootstrapProvider","NullBootstrapProvider","errors","validatedOptions","keys","forEach","optionName","optionValue","validator","is","getType","push","wrongOptionTypeBoolean","NumberWithMinimum","min","optionBelowMinimum","UserValidator","messages","wrongOptionType","warn","unknownOption","validateTypesAndNames","error","streamingUriMissing","isNullOrUndefined","EmptyString","pollingUriMissing","eventsUriMissing","partialEndpoint","POLLING","validateEndpoints","canonicalizeUri","length","JsonBootstrapProvider","_","info","Function","dataSynchronizerFactory","storeFactory","Context","valid","message","fromUser","contextForError","keyId","name","trim","context","_user","value","property","customizedProperties","find","x","_options","build","platform","_platform","mode","flags","ClientState","callbacks","state","Initializing","onError","onFailed","onReady","onUpdate","hasEventListeners","config","Error","init","clientContext","identify","dataSourceUpdates","evaluator","populate","eventProcessor","NullEventProcessor","NullDataSynchronizer","initSuccess","DefaultEventProcessor","listeners","createStreamListeners","put","patch","webSocket","version","requests","e","dataSourceErrorHandler","start","all","Flags","setTimeout","initialized","msg","Failed","rejectionReason","initReject","Initialized","waitForInitialization","initializedPromise","Promise","resolve","reject","initResolve","boolVariation","key","defaultValue","evaluateCore","ValueConverters","bool","boolVariationDetail","jsonVariation","json","jsonVariationDetail","numberVariation","number","numberVariationDetail","stringVariation","string","stringVariationDetail","variation","variationDetail","getAllVariations","ClientError","result","map","flagKey","evalResult","evaluate","kind","reason","close","track","eventName","metricValue","metricEvent","MetricEvent","appType","record","flush","callback","err","typeConverter","ReasonKinds","FlagNotFound","toEvalEvent","isSucceeded","WrongType","code","flag","variationOptions","id","data","deserializeAll","dataSet","userKeyId","MinInt","onChange","allData","checkForChanges","doInit","oldData","then","updatedKeys","flatMap","namespace","oldDataForKind","newDataForKind","mergedData","filter","isUpdated","upsert","doUpsert","oldItem","get","newData","createPutListener","onPutCompleteHandler","deserializeData","processJson","initData","debug","createPatchListener","onPatchCompleteHandler","deserializePatch","item","onCompleteHandlers","Map","set","stop","requestor","getStoreTimestamp","errorHandler","stopped","poll","startTime","Date","now","requestData","body","elapsed","sleepFor","Math","max","status","isHttpRecoverable","httpErrorMessage","PollingError","featureFlags","processStreamResponse","JSON","parse","messageType","eventType","StreamResponseEventType","full","timeoutHandle","clearTimeout","headers","defaultHeaders","uri","request","requestUrl","res","fetch","text","timestamp","payload","cb","method","stringify","StreamingError","socket","pingInterval","addListener","event","logConnectionStarted","connect","connectionAttemptStartTime","alphabet","encodeNumber","param","s","slice","split","n","join","replace","timestampCode","toString","floor","random","super","UnexpectedResponseError","EvalResult","flagNotFound","matched","val","Match","targetedVariation","variations","v","EvalEvent","sendToExperiment","VariationDataType","closed","eventQueue","DefaultEventQueue","eventDispatcher","EventDispatcher","flushLoop","flushEvent","FlushEvent","waitForCompletion","shutdown","ShutdownEvent","addEvent","complete","capacity","events","clear","shift","eventsSnapshot","isEmpty","send","retry","DeliveryStatus","Succeeded","FailedAndMustShutDown","serialize","toPayload","queue","maxEventPerRequest","buffer","sender","DefaultEventSender","serializer","DefaultEventSerializer","dispatchLoop","running","PayloadEvent","addEventToBuffer","triggerFlush","snapshot","flushEvents","total","getUniqueEvents","uniqueEvents","hashes","includes","hash","AsyncEvent","getTime","isCompletedPromise","resolveFn","userPayload","metrics","route","numericValue","type","hasObject","m","featureFlagKey","LogPriority","none","LevelNames","BasicLogger","logLevel","level","destination","formatter","tryFormat","args","tryWrite","console","log","prefix","loggerRequirements","fallback","entries","tryStringify","prototype","hasOwnProperty","call","TypeError","indexOf","escapes","d","toNumber","parseInt","toInt","f","parseFloat","toFloat","j","o","O","c","formatString","out","char","charAt","nextChar","configuration","expectedType","actualType","mandatory","invalidOptionValue","missingKeyInBootstrapValue","_keyId","_name","_custom","custom","propertyName","FactoryOrInstance","factoryOrInstance","Array","isArray","typeOfFactory","Type","typeName","example","typeOf","u","TypeArray","every","StringMatchingRegex","expression","match","NullableBoolean","DATE_REGEX","DateValidator","test","KindValidator","createTypeArray","numberWithMin","stringMatchingRegex","StringArray","Kind","platformData","os","additional","sdkData","userAgentBase","BrowserRequests","url","socketConnectionIntervals","Emits","retryCounter","_config","emitter","EventEmitter","doDataSync","that","generateConnectionToken","ws","WebSocket","addEventListener","sendPingMessage","reconnect","emit","readyState","OPEN","waitTime","FbClient","FbClientCore","fallbackLogger","SafeLogger","listenerCount","eventNames","some","startsWith","LocalStorageStore","BaseStore","description","saveUser","localStorage","setItem","CurrentUserStorageKey","serializeUser","dumpStoreToStorage","storageKey","StoreStorageKey","loadStoreFromStorage","dataStoreStr","getItem","BrowserWebSocket","initCalled","addItem","items","old","ele","DataKinds","InMemoryStore","allStores","reduce","acc","cur","Base","on","listener","once","removeListener","off","removeAllListeners","prependListener","prependOnceListener","maybeReportError","listeningTo","handler","concat","onceHandler","apply","copiedHandlers","arguments","toUpperCase","success","num","isNaN","debounce","fn","delayMs","timer","retryMessage","desc","sort","b","nameA","toLowerCase","nameB","p","delayMillis","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__"],"sourceRoot":""} \ No newline at end of file +{"version":3,"file":"featbit-js-client-sdk.js","mappings":"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","sources":["webpack://@featbit/js-client-sdk/webpack/universalModuleDefinition","webpack://@featbit/js-client-sdk/./src/Configuration.ts","webpack://@featbit/js-client-sdk/./src/Context.ts","webpack://@featbit/js-client-sdk/./src/FbClientBuilder.ts","webpack://@featbit/js-client-sdk/./src/FbClientCore.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/JsonBootstrapProvider.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/NullBootstrapProvider.ts","webpack://@featbit/js-client-sdk/./src/bootstrap/index.ts","webpack://@featbit/js-client-sdk/./src/constants.ts","webpack://@featbit/js-client-sdk/./src/data-sources/DataSourceUpdates.ts","webpack://@featbit/js-client-sdk/./src/data-sources/createStreamListeners.ts","webpack://@featbit/js-client-sdk/./src/data-sources/index.ts","webpack://@featbit/js-client-sdk/./src/data-sync/DataSyncMode.ts","webpack://@featbit/js-client-sdk/./src/data-sync/NullDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/PollingDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/Requestor.ts","webpack://@featbit/js-client-sdk/./src/data-sync/WebSocketDataSynchronizer.ts","webpack://@featbit/js-client-sdk/./src/data-sync/index.ts","webpack://@featbit/js-client-sdk/./src/data-sync/types.ts","webpack://@featbit/js-client-sdk/./src/data-sync/utils.ts","webpack://@featbit/js-client-sdk/./src/errors.ts","webpack://@featbit/js-client-sdk/./src/evaluation/EvalResult.ts","webpack://@featbit/js-client-sdk/./src/evaluation/Evaluator.ts","webpack://@featbit/js-client-sdk/./src/evaluation/ReasonKinds.ts","webpack://@featbit/js-client-sdk/./src/evaluation/data/IFlag.ts","webpack://@featbit/js-client-sdk/./src/evaluation/data/index.ts","webpack://@featbit/js-client-sdk/./src/evaluation/index.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventProcessor.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventQueue.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventSender.ts","webpack://@featbit/js-client-sdk/./src/events/DefaultEventSerializer.ts","webpack://@featbit/js-client-sdk/./src/events/EventDispatcher.ts","webpack://@featbit/js-client-sdk/./src/events/IEventSender.ts","webpack://@featbit/js-client-sdk/./src/events/NullEventProcessor.ts","webpack://@featbit/js-client-sdk/./src/events/event.ts","webpack://@featbit/js-client-sdk/./src/events/index.ts","webpack://@featbit/js-client-sdk/./src/index.ts","webpack://@featbit/js-client-sdk/./src/logging/BasicLogger.ts","webpack://@featbit/js-client-sdk/./src/logging/SafeLogger.ts","webpack://@featbit/js-client-sdk/./src/logging/format.ts","webpack://@featbit/js-client-sdk/./src/logging/index.ts","webpack://@featbit/js-client-sdk/./src/options/ClientContext.ts","webpack://@featbit/js-client-sdk/./src/options/OptionMessages.ts","webpack://@featbit/js-client-sdk/./src/options/UserBuilder.ts","webpack://@featbit/js-client-sdk/./src/options/Validators.ts","webpack://@featbit/js-client-sdk/./src/options/index.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserInfo.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserPlatform.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserRequests.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/BrowserWebSocket.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/FbClient.ts","webpack://@featbit/js-client-sdk/./src/platform/browser/LocalStorageStore.ts","webpack://@featbit/js-client-sdk/./src/platform/index.ts","webpack://@featbit/js-client-sdk/./src/store/BaseStore.ts","webpack://@featbit/js-client-sdk/./src/store/DataKinds.ts","webpack://@featbit/js-client-sdk/./src/store/InMemoryStore.ts","webpack://@featbit/js-client-sdk/./src/store/index.ts","webpack://@featbit/js-client-sdk/./src/store/serialization.ts","webpack://@featbit/js-client-sdk/./src/store/store.ts","webpack://@featbit/js-client-sdk/./src/utils/Emits.ts","webpack://@featbit/js-client-sdk/./src/utils/EventEmitter.ts","webpack://@featbit/js-client-sdk/./src/utils/ValueConverters.ts","webpack://@featbit/js-client-sdk/./src/utils/canonicalizeUri.ts","webpack://@featbit/js-client-sdk/./src/utils/debounce.ts","webpack://@featbit/js-client-sdk/./src/utils/http.ts","webpack://@featbit/js-client-sdk/./src/utils/index.ts","webpack://@featbit/js-client-sdk/./src/utils/isNullOrUndefined.ts","webpack://@featbit/js-client-sdk/./src/utils/serializeUser.ts","webpack://@featbit/js-client-sdk/./src/utils/sleep.ts","webpack://@featbit/js-client-sdk/./src/version.ts","webpack://@featbit/js-client-sdk/webpack/bootstrap","webpack://@featbit/js-client-sdk/webpack/startup"],"sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse {\n\t\tvar a = factory();\n\t\tfor(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i];\n\t}\n})(this, () => {\nreturn ","import { IOptions } from \"./options/IOptions\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport { IValidatedOptions } from \"./options/IValidatedOptions\";\r\nimport { NumberWithMinimum, TypeValidator, TypeValidators, UserValidator } from \"./options/Validators\";\r\nimport OptionMessages from \"./options/OptionMessages\";\r\nimport { IStore } from \"./platform/IStore\";\r\nimport { IClientContext } from \"./options/IClientContext\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport { IDataSourceUpdates } from \"./store/IDataSourceUpdates\";\r\nimport InMemoryStore from \"./store/InMemoryStore\";\r\nimport { VoidFunction } from \"./utils/VoidFunction\";\r\nimport { isNullOrUndefined } from \"./utils/isNullOrUndefined\";\r\nimport { canonicalizeUri } from \"./utils/canonicalizeUri\";\r\nimport { IBootstrapProvider } from \"./bootstrap/IBootstrapProvider\";\r\nimport { NullBootstrapProvider } from \"./bootstrap/NullBootstrapProvider\";\r\nimport { EmptyString } from \"./constants\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { JsonBootstrapProvider } from \"./bootstrap\";\r\n\r\n// Once things are internal to the implementation of the SDK we can depend on\r\n// types. Calls to the SDK could contain anything without any regard to typing.\r\n// So, data we take from external sources must be normalized into something\r\n// that can be trusted.\r\n\r\n/**\r\n * These perform cursory validations. Complex objects are implemented with classes\r\n * and these should allow for conditional construction.\r\n */\r\nconst validations: Record = {\r\n startWaitTime: TypeValidators.Number,\r\n sdkKey: TypeValidators.String,\r\n pollingUri: TypeValidators.String,\r\n streamingUri: TypeValidators.String,\r\n eventsUri: TypeValidators.String,\r\n webSocketPingInterval: TypeValidators.Number,\r\n logger: TypeValidators.Object,\r\n store: TypeValidators.ObjectOrFactory,\r\n dataSynchronizer: TypeValidators.ObjectOrFactory,\r\n flushInterval: TypeValidators.Number,\r\n maxEventsInQueue: TypeValidators.Number,\r\n pollingInterval: TypeValidators.Number,\r\n offline: TypeValidators.Boolean,\r\n dataSyncMode: TypeValidators.String,\r\n bootstrap: TypeValidators.Bootstrap,\r\n user: TypeValidators.User\r\n};\r\n\r\n/**\r\n * @internal\r\n */\r\nexport const defaultValues: IValidatedOptions = {\r\n startWaitTime: 5000,\r\n sdkKey: '',\r\n pollingUri: '',\r\n streamingUri: '',\r\n eventsUri: '',\r\n dataSyncMode: DataSyncModeEnum.STREAMING,\r\n sendEvents: true,\r\n webSocketPingInterval: 18 * 1000,\r\n flushInterval: 2000,\r\n maxEventsInQueue: 10000,\r\n pollingInterval: 30000,\r\n offline: false,\r\n store: (options: IOptions) => new InMemoryStore(),\r\n bootstrap: undefined,\r\n user: undefined,\r\n};\r\n\r\nfunction validateTypesAndNames(options: IOptions): {\r\n errors: string[];\r\n validatedOptions: IValidatedOptions;\r\n} {\r\n let errors: string[] = [];\r\n const validatedOptions: IValidatedOptions = {...defaultValues};\r\n Object.keys(options).forEach((optionName) => {\r\n // We need to tell typescript it doesn't actually know what options are.\r\n // If we don't then it complains we are doing crazy things with it.\r\n const optionValue = (options as unknown as any)[optionName];\r\n const validator = validations[optionName];\r\n if (validator) {\r\n if (!validator.is(optionValue)) {\r\n if (validator.getType() === 'boolean') {\r\n errors.push(OptionMessages.wrongOptionTypeBoolean(optionName, typeof optionValue));\r\n validatedOptions[optionName] = !!optionValue;\r\n } else if (\r\n validator instanceof NumberWithMinimum &&\r\n TypeValidators.Number.is(optionValue)\r\n ) {\r\n const {min} = validator as NumberWithMinimum;\r\n errors.push(OptionMessages.optionBelowMinimum(optionName, optionValue, min));\r\n validatedOptions[optionName] = min;\r\n } else if (validator instanceof UserValidator) {\r\n errors = [...errors, ...validator.messages];\r\n validatedOptions[optionName] = defaultValues[optionName];\r\n } else {\r\n errors.push(\r\n OptionMessages.wrongOptionType(optionName, validator.getType(), typeof optionValue),\r\n );\r\n validatedOptions[optionName] = defaultValues[optionName];\r\n }\r\n } else {\r\n validatedOptions[optionName] = optionValue;\r\n }\r\n } else {\r\n options.logger?.warn(OptionMessages.unknownOption(optionName));\r\n }\r\n });\r\n return {errors, validatedOptions};\r\n}\r\n\r\nfunction validateEndpoints(options: IOptions, validatedOptions: IValidatedOptions) {\r\n const {streamingUri, pollingUri, eventsUri} = options;\r\n const streamingUriMissing = isNullOrUndefined(streamingUri) || streamingUri === EmptyString;\r\n const pollingUriMissing = isNullOrUndefined(pollingUri) || pollingUri === EmptyString;\r\n const eventsUriMissing = isNullOrUndefined(eventsUri) || eventsUri === EmptyString;\r\n\r\n if (!validatedOptions.offline && (eventsUriMissing || (streamingUriMissing && pollingUriMissing))) {\r\n if (eventsUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('eventsUri'));\r\n }\r\n\r\n if (validatedOptions.dataSyncMode === DataSyncModeEnum.STREAMING && streamingUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('streamingUri'));\r\n }\r\n\r\n if (validatedOptions.dataSyncMode === DataSyncModeEnum.POLLING && pollingUriMissing) {\r\n validatedOptions.logger?.error(OptionMessages.partialEndpoint('pollingUri'));\r\n }\r\n }\r\n}\r\n\r\nexport default class Configuration {\r\n public readonly startWaitTime: number;\r\n\r\n public readonly sdkKey: string;\r\n\r\n public readonly streamingUri: string;\r\n\r\n public readonly pollingUri: string;\r\n\r\n public readonly eventsUri: string;\r\n\r\n public readonly webSocketPingInterval: number;\r\n\r\n public readonly logger?: ILogger;\r\n\r\n public readonly flushInterval: number;\r\n\r\n public readonly maxEventsInQueue: number;\r\n\r\n public readonly pollingInterval: number;\r\n\r\n public readonly offline: boolean;\r\n\r\n public readonly dataSyncMode: DataSyncModeEnum;\r\n\r\n public readonly bootstrapProvider: IBootstrapProvider = new NullBootstrapProvider();\r\n\r\n public readonly user: IUser;\r\n\r\n public readonly storeFactory: (clientContext: IClientContext) => IStore;\r\n\r\n public readonly dataSynchronizerFactory?: (\r\n clientContext: IClientContext,\r\n store: IStore,\r\n dataSourceUpdates: IDataSourceUpdates,\r\n initSuccessHandler: VoidFunction,\r\n errorHandler?: (e: Error) => void,\r\n ) => IDataSynchronizer;\r\n\r\n constructor(options: IOptions = {}) {\r\n // The default will handle undefined, but not null.\r\n // Because we can be called from JS we need to be extra defensive.\r\n options = options || {};\r\n // If there isn't a valid logger from the platform, then logs would go nowhere.\r\n this.logger = options.logger;\r\n\r\n const {errors, validatedOptions} = validateTypesAndNames(options);\r\n errors.forEach((error) => {\r\n this.logger?.warn(error);\r\n });\r\n\r\n this.user = options.user!;\r\n\r\n validateEndpoints(options, validatedOptions);\r\n this.streamingUri = `${ canonicalizeUri(validatedOptions.streamingUri) }/streaming`;\r\n this.pollingUri = `${ canonicalizeUri(validatedOptions.pollingUri) }/api/public/sdk/client/latest-all`;\r\n this.eventsUri = `${ canonicalizeUri(validatedOptions.eventsUri) }/api/public/insight/track`;\r\n\r\n this.startWaitTime = validatedOptions.startWaitTime;\r\n\r\n this.sdkKey = validatedOptions.sdkKey;\r\n this.webSocketPingInterval = validatedOptions.webSocketPingInterval!;\r\n\r\n this.flushInterval = validatedOptions.flushInterval;\r\n this.maxEventsInQueue = validatedOptions.maxEventsInQueue;\r\n this.pollingInterval = validatedOptions.pollingInterval;\r\n\r\n this.offline = validatedOptions.offline;\r\n if (validatedOptions.bootstrap && validatedOptions.bootstrap.length > 0) {\r\n try {\r\n this.bootstrapProvider = new JsonBootstrapProvider(validatedOptions.bootstrap);\r\n } catch (_) {\r\n this.logger?.error('Failed to parse bootstrap JSON, use NullBootstrapProvider.');\r\n }\r\n }\r\n\r\n if (this.offline) {\r\n this.logger?.info('Offline mode enabled. No data synchronization with the FeatBit server will occur.');\r\n }\r\n\r\n this.dataSyncMode = validatedOptions.dataSyncMode;\r\n\r\n if (TypeValidators.Function.is(validatedOptions.dataSynchronizer)) {\r\n // @ts-ignore\r\n this.dataSynchronizerFactory = validatedOptions.dataSynchronizer;\r\n } else {\r\n // The processor is already created, just have the method return it.\r\n // @ts-ignore\r\n this.dataSynchronizerFactory = () => validatedOptions.dataSynchronizer;\r\n }\r\n\r\n if (TypeValidators.Function.is(validatedOptions.store)) {\r\n // @ts-ignore\r\n this.storeFactory = validatedOptions.store;\r\n } else {\r\n // The store is already created, just have the method return it.\r\n // @ts-ignore\r\n this.storeFactory = () => validatedOptions.store;\r\n }\r\n }\r\n}","import { IUser } from \"./options/IUser\";\r\n\r\nexport default class Context {\r\n private _user?: IUser;\r\n /**\r\n * Is this a valid context. If a valid context cannot be created, then this flag will be true.\r\n * The validity of a context should be tested before it is used.\r\n */\r\n public readonly valid: boolean;\r\n\r\n public readonly message?: string;\r\n\r\n /**\r\n * Contexts should be created using the static factory method {@link Context.fromUser}.\r\n *\r\n * The factory methods are static functions within the class because they access private\r\n * implementation details, so they cannot be free functions.\r\n */\r\n private constructor(valid: boolean, message?: string) {\r\n this.valid = valid;\r\n this.message = message;\r\n }\r\n\r\n public static fromUser(user: IUser): Context {\r\n if (!user) {\r\n return Context.contextForError('No user specified');\r\n }\r\n\r\n const {keyId, name} = user;\r\n\r\n if (keyId === undefined || keyId === null || keyId.trim() === '') {\r\n return Context.contextForError('key is mandatory');\r\n }\r\n\r\n const context = new Context(true);\r\n context._user = user;\r\n\r\n return context;\r\n }\r\n\r\n get user(): IUser {\r\n return this._user!;\r\n }\r\n\r\n get keyId(): string {\r\n return this._user!.keyId;\r\n }\r\n\r\n value(property: string): any {\r\n if (property === 'keyId') {\r\n return this._user?.keyId;\r\n } else if (property === 'name') {\r\n return this._user?.name;\r\n } else {\r\n return this._user?.customizedProperties?.find(x => x.name === property)?.value;\r\n }\r\n }\r\n\r\n private static contextForError(message: string) {\r\n return new Context(false, message);\r\n }\r\n}","import { IFbClient } from \"./IFbClient\";\r\nimport { IOptions } from \"./options/IOptions\";\r\nimport FbClient from \"./platform/browser/FbClient\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport { IClientContext } from \"./options/IClientContext\";\r\nimport { IDataSourceUpdates } from \"./store/IDataSourceUpdates\";\r\nimport { VoidFunction } from \"./utils/VoidFunction\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { IFlagBase } from \"./evaluation\";\r\nimport { IPlatform } from \"./platform\";\r\n\r\n/**\r\n * Creates an instance of the FeatBit client.\r\n *\r\n * Applications should instantiate a single instance for the lifetime of the application.\r\n * The client will begin attempting to connect to FeatBit as soon as it is created. To\r\n * determine when it is ready to use, call {@link IFbClient.waitForInitialization}, or register an\r\n * event listener for the `\"ready\"` event using {@link IFbClient.on}.\r\n *\r\n * **Important:** Do **not** try to instantiate `FbClient` with its constructor\r\n * (`new FbClientNode()`); the SDK does not currently support\r\n * this.\r\n *\r\n * @return\r\n * The new {@link IFbClient} instance.\r\n */\r\nexport class FbClientBuilder {\r\n private _options: IOptions;\r\n private _platform: IPlatform | undefined;\r\n\r\n constructor(options?: IOptions) {\r\n this._options = options ?? {};\r\n }\r\n\r\n /**\r\n * Creates a new instance of the FeatBit client.\r\n */\r\n build(): IFbClient {\r\n return new FbClient(this._options);\r\n }\r\n\r\n platform(platform: IPlatform | undefined): FbClientBuilder {\r\n this._platform = platform;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.startWaitTime}.\r\n */\r\n startWaitTime(startWaitTime: number): FbClientBuilder {\r\n this._options.startWaitTime = startWaitTime;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.sdkKey}.\r\n */\r\n sdkKey(sdkKey: string): FbClientBuilder {\r\n this._options.sdkKey = sdkKey;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.user}.\r\n */\r\n user(user: IUser): FbClientBuilder {\r\n this._options.user = user;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.streamingUri}.\r\n */\r\n streamingUri(streamingUri: string): FbClientBuilder {\r\n this._options.streamingUri = streamingUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.pollingUri}.\r\n */\r\n pollingUri(pollingUri: string): FbClientBuilder {\r\n this._options.pollingUri = pollingUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.eventsUri}.\r\n */\r\n eventsUri(eventsUri: string): FbClientBuilder {\r\n this._options.eventsUri = eventsUri;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.dataSyncMode}.\r\n */\r\n dataSyncMode(mode: DataSyncModeEnum): FbClientBuilder {\r\n this._options.dataSyncMode = mode;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.pollingInterval}.\r\n */\r\n pollingInterval(pollingInterval: number): FbClientBuilder {\r\n this._options.pollingInterval = pollingInterval;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.flushInterval}.\r\n */\r\n flushInterval(flushInterval: number): FbClientBuilder {\r\n this._options.flushInterval = flushInterval;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.maxEventsInQueue}.\r\n */\r\n maxEventsInQueue(maxEventsInQueue: number): FbClientBuilder {\r\n this._options.maxEventsInQueue = maxEventsInQueue;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.logger}.\r\n */\r\n logger(logger: ILogger): FbClientBuilder {\r\n this._options.logger = logger;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.offline}.\r\n */\r\n offline(offline: boolean): FbClientBuilder {\r\n this._options.offline = offline;\r\n return this;\r\n }\r\n\r\n /**\r\n * Use the JsonBootstrapProvider.\r\n */\r\n bootstrap(flags: IFlagBase[]): FbClientBuilder {\r\n this._options.bootstrap = flags;\r\n return this;\r\n }\r\n\r\n /**\r\n * Refer to {@link IOptions.dataSynchronizer}.\r\n */\r\n dataSynchronizer(\r\n dataSynchronizer: IDataSynchronizer |\r\n ((\r\n clientContext: IClientContext,\r\n dataSourceUpdates: IDataSourceUpdates,\r\n initSuccessHandler: VoidFunction,\r\n errorHandler?: (e: Error) => void,\r\n ) => IDataSynchronizer)\r\n ): FbClientBuilder {\r\n this._options.dataSynchronizer = dataSynchronizer;\r\n return this;\r\n }\r\n}","import { IFbClientCore } from \"./IFbClientCore\";\r\nimport { IPlatform } from \"./platform/IPlatform\";\r\nimport Configuration from \"./Configuration\";\r\nimport { ILogger } from \"./logging/ILogger\";\r\nimport ClientContext from \"./options/ClientContext\";\r\nimport DataSourceUpdates from \"./data-sources/DataSourceUpdates\";\r\nimport { createStreamListeners } from \"./data-sources/createStreamListeners\";\r\nimport { IEvalDetail } from \"./evaluation/IEvalDetail\";\r\nimport WebSocketDataSynchronizer from \"./data-sync/WebSocketDataSynchronizer\";\r\nimport PollingDataSynchronizer from \"./data-sync/PollingDataSynchronizer\";\r\nimport Requestor from \"./data-sync/Requestor\";\r\nimport { IDataSynchronizer } from \"./data-sync/IDataSynchronizer\";\r\nimport DataKinds from \"./store/DataKinds\";\r\nimport Evaluator from \"./evaluation/Evaluator\";\r\nimport { ReasonKinds } from \"./evaluation/ReasonKinds\";\r\nimport { ClientError } from \"./errors\";\r\nimport Context from \"./Context\";\r\nimport { IConvertResult, ValueConverters } from \"./utils/ValueConverters\";\r\nimport { NullDataSynchronizer } from \"./data-sync/NullDataSynchronizer\";\r\nimport { IEventProcessor } from \"./events/IEventProcessor\";\r\nimport { NullEventProcessor } from \"./events/NullEventProcessor\";\r\nimport { DefaultEventProcessor } from \"./events/DefaultEventProcessor\";\r\nimport { IStore } from \"./platform/IStore\";\r\nimport { IOptions } from \"./options/IOptions\";\r\nimport { MetricEvent } from \"./events/event\";\r\nimport { DataSyncModeEnum } from \"./data-sync/DataSyncMode\";\r\nimport { IUser } from \"./options/IUser\";\r\nimport { UserValidator } from \"./options/Validators\";\r\n\r\nenum ClientState {\r\n Initializing,\r\n Initialized,\r\n Failed,\r\n}\r\n\r\nexport interface IClientCallbacks {\r\n onError: (err: Error) => void;\r\n onFailed: (err: Error) => void;\r\n onReady: () => void;\r\n // Called whenever flags change, if there are listeners.\r\n onUpdate: (keys: string[]) => void;\r\n // Method to check if event listeners have been registered.\r\n // If none are registered, then onUpdate will never be called.\r\n hasEventListeners: () => boolean;\r\n}\r\n\r\nexport class FbClientCore implements IFbClientCore {\r\n private state: ClientState = ClientState.Initializing;\r\n\r\n private store?: IStore;\r\n\r\n private dataSynchronizer?: IDataSynchronizer;\r\n\r\n private eventProcessor?: IEventProcessor;\r\n\r\n private evaluator?: Evaluator;\r\n\r\n private initResolve?: (value: IFbClientCore | PromiseLike) => void;\r\n\r\n private initReject?: (err: Error) => void;\r\n\r\n private rejectionReason: Error | undefined;\r\n\r\n private initializedPromise?: Promise;\r\n\r\n private config: Configuration;\r\n\r\n private dataSourceUpdates?: DataSourceUpdates;\r\n\r\n private onError: (err: Error) => void;\r\n\r\n private onFailed: (err: Error) => void;\r\n\r\n private onReady: () => void;\r\n\r\n logger?: ILogger;\r\n\r\n constructor(\r\n private options: IOptions,\r\n private platform: IPlatform,\r\n callbacks: IClientCallbacks\r\n ) {\r\n this.onError = callbacks.onError;\r\n this.onFailed = callbacks.onFailed;\r\n this.onReady = callbacks.onReady;\r\n\r\n const {onUpdate, hasEventListeners} = callbacks;\r\n const config = new Configuration(options);\r\n\r\n if (!config.sdkKey && !config.offline) {\r\n throw new Error('You must configure the client with an SDK key');\r\n }\r\n\r\n if (!config.user) {\r\n throw new Error('You must configure the client with a user');\r\n }\r\n\r\n this.config = config;\r\n this.logger = config.logger;\r\n\r\n this.init(platform, onUpdate, hasEventListeners);\r\n }\r\n\r\n private async init(platform: IPlatform, onUpdate: (keys: string[]) => void, hasEventListeners: () => boolean) {\r\n const clientContext = new ClientContext(this.config.sdkKey, this.config, platform);\r\n this.store = this.config.storeFactory(clientContext);\r\n await this.store.identify(this.config.user);\r\n this.dataSourceUpdates = new DataSourceUpdates(this.store, hasEventListeners, onUpdate);\r\n this.evaluator = new Evaluator(this.store);\r\n\r\n // use bootstrap provider to populate store\r\n await this.config.bootstrapProvider.populate(this.config.user.keyId, this.dataSourceUpdates);\r\n\r\n if (this.config.offline) {\r\n this.eventProcessor = new NullEventProcessor();\r\n this.dataSynchronizer = new NullDataSynchronizer();\r\n\r\n this.initSuccess();\r\n } else {\r\n this.eventProcessor = new DefaultEventProcessor(clientContext);\r\n\r\n const listeners = createStreamListeners(this.dataSourceUpdates, this.logger, {\r\n put: () => this.initSuccess(),\r\n patch: () => this.initSuccess()\r\n });\r\n\r\n const dataSynchronizer = this.config.dataSyncMode === DataSyncModeEnum.STREAMING\r\n ? new WebSocketDataSynchronizer(\r\n this.config.sdkKey,\r\n this.config.user,\r\n clientContext,\r\n platform.webSocket,\r\n () => this.store!.version,\r\n listeners,\r\n this.config.webSocketPingInterval\r\n )\r\n : new PollingDataSynchronizer(\r\n this.config,\r\n new Requestor(this.config.sdkKey, this.config, this.platform.info, this.platform.requests),\r\n () => this.store!.version,\r\n listeners,\r\n (e) => this.dataSourceErrorHandler(e),\r\n );\r\n\r\n this.dataSynchronizer = this.config.dataSynchronizerFactory?.(\r\n clientContext,\r\n this.store,\r\n this.dataSourceUpdates,\r\n () => this.initSuccess(),\r\n (e) => this.dataSourceErrorHandler(e),\r\n ) ?? dataSynchronizer;\r\n }\r\n\r\n this.start();\r\n }\r\n\r\n async identify(user: IUser) {\r\n const validator = new UserValidator();\r\n if (!validator.is(user)) {\r\n validator.messages.forEach((error: string) => {\r\n this.logger?.warn(error);\r\n });\r\n\r\n return;\r\n }\r\n\r\n this.store!.identify(user);\r\n this.dataSynchronizer!.identify(user);\r\n const [ flags ] = this.store!.all(DataKinds.Flags);\r\n if (Object.keys(flags).length === 0) {\r\n await this.config.bootstrapProvider.populate(user.keyId, this.dataSourceUpdates!);\r\n }\r\n }\r\n\r\n private start() {\r\n if (this.config.offline) {\r\n return;\r\n }\r\n\r\n this.dataSynchronizer!.start();\r\n setTimeout(() => {\r\n if (!this.initialized()) {\r\n const msg = `FbClient failed to start successfully within ${ this.config.startWaitTime } milliseconds. ` +\r\n 'This error usually indicates a connection issue with FeatBit or an invalid sdkKey.' +\r\n 'Please double-check your sdkKey and streamingUri/pollingUri configuration. ' +\r\n 'We will continue to initialize the FbClient, it still have a chance to get to work ' +\r\n 'if it\\'s a temporary network issue';\r\n\r\n const error = new Error(msg);\r\n this.state = ClientState.Failed;\r\n this.rejectionReason = error;\r\n this.initReject?.(error);\r\n\r\n return this.logger?.warn(msg);\r\n }\r\n }, this.config.startWaitTime);\r\n }\r\n\r\n initialized(): boolean {\r\n return this.state === ClientState.Initialized;\r\n }\r\n\r\n waitForInitialization(): Promise {\r\n // An initialization promise is only created if someone is going to use that promise.\r\n // If we always created an initialization promise, and there was no call waitForInitialization\r\n // by the time the promise was rejected, then that would result in an unhandled promise\r\n // rejection.\r\n\r\n // Initialization promise was created by a previous call to waitForInitialization.\r\n if (this.initializedPromise) {\r\n return this.initializedPromise;\r\n }\r\n\r\n // Initialization completed before waitForInitialization was called, so we have completed\r\n // and there was no promise. So we make a resolved promise and return it.\r\n if (this.state === ClientState.Initialized) {\r\n this.initializedPromise = Promise.resolve(this);\r\n return this.initializedPromise;\r\n }\r\n\r\n // Initialization failed before waitForInitialization was called, so we have completed\r\n // and there was no promise. So we make a rejected promise and return it.\r\n if (this.state === ClientState.Failed) {\r\n this.initializedPromise = Promise.reject(this.rejectionReason);\r\n return this.initializedPromise;\r\n }\r\n\r\n if (!this.initializedPromise) {\r\n this.initializedPromise = new Promise((resolve, reject) => {\r\n this.initResolve = resolve;\r\n this.initReject = reject;\r\n });\r\n }\r\n return this.initializedPromise;\r\n }\r\n\r\n boolVariation(\r\n key: string,\r\n defaultValue: boolean\r\n ): boolean {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.bool).value!;\r\n }\r\n\r\n boolVariationDetail(\r\n key: string,\r\n defaultValue: boolean\r\n ): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.bool);\r\n }\r\n\r\n jsonVariation(key: string, defaultValue: any): any {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.json).value!;\r\n }\r\n\r\n jsonVariationDetail(key: string, defaultValue: any): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.json);\r\n }\r\n\r\n numberVariation(key: string, defaultValue: number): number {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.number).value!;\r\n }\r\n\r\n numberVariationDetail(key: string, defaultValue: number): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.number);\r\n }\r\n\r\n stringVariation(key: string, defaultValue: string): string {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string).value!;\r\n }\r\n\r\n stringVariationDetail(key: string, defaultValue: string): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string);\r\n }\r\n\r\n variation(key: string, defaultValue: string): string {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string).value!;\r\n }\r\n\r\n variationDetail(key: string, defaultValue: string): IEvalDetail {\r\n return this.evaluateCore(key, defaultValue, ValueConverters.string);\r\n }\r\n\r\n getAllVariations(): Promise[]> {\r\n const context = Context.fromUser(this.config.user);\r\n if (!context.valid) {\r\n const error = new ClientError(\r\n `${ context.message ?? 'User not valid;' } returning default value.`,\r\n );\r\n this.onError(error);\r\n\r\n return Promise.resolve([]);\r\n }\r\n\r\n const [flags, _] = this.store!.all(DataKinds.Flags);\r\n const result = Object.keys(flags).map(flagKey => {\r\n const evalResult = this.evaluator!.evaluate(flagKey);\r\n return {flagKey, kind: evalResult.kind, reason: evalResult.reason, value: evalResult.value?.variation};\r\n });\r\n\r\n return Promise.resolve(result);\r\n }\r\n\r\n async close(): Promise {\r\n await this.eventProcessor!.close();\r\n this.dataSynchronizer?.close();\r\n this.store!.close();\r\n }\r\n\r\n track(eventName: string, metricValue?: number | undefined): void {\r\n const metricEvent = new MetricEvent(this.config.user, eventName, this.platform.info.appType, metricValue ?? 1);\r\n this.eventProcessor!.record(metricEvent);\r\n return;\r\n }\r\n\r\n async flush(callback?: (res: boolean) => void): Promise {\r\n try {\r\n await this.eventProcessor!.flush();\r\n callback?.(true);\r\n return true;\r\n } catch (err) {\r\n callback?.(false);\r\n return false;\r\n }\r\n }\r\n\r\n evaluateCore(\r\n flagKey: string,\r\n defaultValue: TValue,\r\n typeConverter: (value: string) => IConvertResult\r\n ): IEvalDetail {\r\n const context = Context.fromUser(this.config.user);\r\n if (!context.valid) {\r\n const error = new ClientError(\r\n `${ context.message ?? 'User not valid;' } returning default value.`,\r\n );\r\n this.onError(error);\r\n\r\n return {flagKey, kind: ReasonKinds.Error, reason: error.message, value: defaultValue};\r\n }\r\n\r\n const evalResult = this.evaluator!.evaluate(flagKey);\r\n\r\n if (evalResult.kind === ReasonKinds.FlagNotFound) {\r\n // flag not found, return default value\r\n const error = new ClientError(evalResult.reason!);\r\n this.onError(error);\r\n\r\n return {flagKey, kind: evalResult.kind, reason: evalResult.reason, value: defaultValue};\r\n }\r\n\r\n if (!this.initialized()) {\r\n this.logger?.warn(\r\n 'Variation called before FeatBit client initialization completed (did you wait for the' +\r\n \"'ready' event?)\",\r\n );\r\n } else {\r\n // send event\r\n this.eventProcessor!.record(evalResult.toEvalEvent(this.config.user));\r\n }\r\n\r\n const {isSucceeded, value} = typeConverter(evalResult.value?.variation!);\r\n return isSucceeded\r\n ? {flagKey, kind: evalResult.kind, reason: evalResult.reason, value}\r\n : {flagKey, kind: ReasonKinds.WrongType, reason: 'type mismatch', value: defaultValue};\r\n }\r\n\r\n private dataSourceErrorHandler(e: any) {\r\n const error =\r\n e.code === 401 ? new Error('Authentication failed. Double check your SDK key.') : e;\r\n\r\n this.onError(error);\r\n this.onFailed(error);\r\n\r\n if (!this.initialized()) {\r\n this.state = ClientState.Failed;\r\n this.rejectionReason = error;\r\n this.initReject?.(error);\r\n }\r\n }\r\n\r\n private initSuccess() {\r\n if (!this.initialized()) {\r\n this.state = ClientState.Initialized;\r\n this.logger?.info('FbClient started successfully.');\r\n this.initResolve?.(this);\r\n this.onReady();\r\n }\r\n }\r\n}\r\n","import { IBootstrapProvider } from \"./IBootstrapProvider\";\r\nimport { deserializeAll } from \"../store/serialization\";\r\nimport { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\nimport { isNullOrUndefined } from \"../utils/isNullOrUndefined\";\r\nimport { IFlag, IFlagBase } from \"../evaluation/data/IFlag\";\r\n\r\nexport class JsonBootstrapProvider implements IBootstrapProvider {\r\n private dataSet?: IStoreDataStorage;\r\n\r\n constructor(bootstrap: IFlagBase[]) {\r\n const flags: IFlag[] = (bootstrap || []).map((flag: IFlagBase) => ({...flag, variationOptions: flag.variationOptions || [{id: null, variation: flag.variation}]})) as IFlag[];\r\n\r\n const data = deserializeAll(flags);\r\n this.dataSet = {\r\n flags: data.flags,\r\n version: 0\r\n };\r\n }\r\n\r\n populate(userKeyId: string, dataSourceUpdates: IDataSourceUpdates, callback?: () => void): Promise {\r\n return new Promise((resolve, reject) => {\r\n if (isNullOrUndefined(this.dataSet)) {\r\n return resolve();\r\n }\r\n\r\n const internalCallback = () => {\r\n resolve();\r\n callback?.();\r\n }\r\n\r\n dataSourceUpdates.init(userKeyId, this.dataSet!, internalCallback);\r\n });\r\n }\r\n}","import { IBootstrapProvider } from \"./IBootstrapProvider\";\r\nimport { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\n\r\nexport class NullBootstrapProvider implements IBootstrapProvider {\r\n private dataSet?: IStoreDataStorage;\r\n\r\n constructor() {\r\n this.dataSet = {\r\n flags: {},\r\n version: 0\r\n };\r\n }\r\n\r\n populate(userKeyId: string, dataSourceUpdates: IDataSourceUpdates, callback?: () => void): Promise {\r\n return new Promise((resolve, reject) => {\r\n resolve();\r\n callback?.();\r\n });\r\n }\r\n}","export * from './IBootstrapProvider';\r\nexport * from './JsonBootstrapProvider';\r\nexport * from './NullBootstrapProvider';","export const EmptyString = '';\r\nexport const MinInt: number = 0x80000000;","import { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport {\r\n IStoreDataStorage,\r\n IStoreItem,\r\n IKeyedStoreItem\r\n} from \"../store/store\";\r\nimport { IStore } from \"../platform/IStore\";\r\nimport { IDataKind } from \"../IDataKind\";\r\nimport DataKinds from \"../store/DataKinds\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class DataSourceUpdates implements IDataSourceUpdates {\r\n\r\n constructor(\r\n private readonly store: IStore,\r\n private readonly hasEventListeners: () => boolean,\r\n private readonly onChange: (keys: string[]) => void,\r\n ) {\r\n }\r\n\r\n init(userKeyId: string, allData: IStoreDataStorage, callback?: () => void): void {\r\n if (userKeyId !== this.store.user.keyId) {\r\n callback?.();\r\n return;\r\n }\r\n\r\n const checkForChanges = this.hasEventListeners();\r\n const doInit = async (oldData?: IStoreDataStorage) => {\r\n await this.store.init(allData);\r\n Promise.resolve().then(() => {\r\n if (checkForChanges) {\r\n const updatedKeys = Object.keys(allData)\r\n .flatMap((namespace) => {\r\n const oldDataForKind = oldData?.[namespace] || {};\r\n const newDataForKind = allData[namespace];\r\n const mergedData = {...oldDataForKind, ...newDataForKind};\r\n return Object.keys(mergedData)\r\n .filter((key: string) => this.isUpdated(oldDataForKind && oldDataForKind[key], newDataForKind && newDataForKind[key]));\r\n });\r\n updatedKeys.length > 0 && this.onChange(updatedKeys);\r\n }\r\n });\r\n callback?.();\r\n };\r\n\r\n if (checkForChanges) {\r\n const [flags, version] = this.store.all(DataKinds.Flags);\r\n const oldData = {\r\n flags,\r\n version\r\n };\r\n doInit(oldData);\r\n } else {\r\n doInit();\r\n }\r\n }\r\n\r\n upsert(userKeyId: string, kind: IDataKind, data: IKeyedStoreItem, callback: () => void): void {\r\n if (userKeyId !== this.store.user.keyId) {\r\n callback?.();\r\n return;\r\n }\r\n\r\n const {key} = data;\r\n const checkForChanges = this.hasEventListeners();\r\n const doUpsert = async (oldItem?: IStoreItem) => {\r\n await this.store.upsert(kind, data);\r\n Promise.resolve().then(() => {\r\n if (checkForChanges && this.isUpdated(oldItem, data[key])) {\r\n this.onChange([key]);\r\n }\r\n });\r\n\r\n callback?.();\r\n };\r\n if (checkForChanges) {\r\n const item = this.store.get(kind, key);\r\n doUpsert(item || undefined);\r\n } else {\r\n doUpsert();\r\n }\r\n }\r\n\r\n private isUpdated(oldData?: IStoreItem, newData?: IStoreItem): boolean {\r\n return !oldData || !newData || newData.version > oldData.version\r\n }\r\n}","import { IDataSourceUpdates } from \"../store/IDataSourceUpdates\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport { VoidFunction } from \"../utils/VoidFunction\";\r\nimport {\r\n deserializeAll,\r\n deserializePatch,\r\n IPatchData,\r\n Flags\r\n} from \"../store/serialization\";\r\nimport DataKinds from \"../store/DataKinds\";\r\nimport { IStoreDataStorage } from \"../store/store\";\r\nimport { EventName, ProcessStreamResponse } from \"../data-sync/types\";\r\n\r\nexport const createPutListener = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onPutCompleteHandler: VoidFunction = () => {\r\n },\r\n) => ({\r\n deserializeData: deserializeAll,\r\n processJson: async (userKeyId: string, {flags}: Flags) => {\r\n const initData: IStoreDataStorage = {\r\n flags: flags,\r\n version: 0\r\n };\r\n\r\n logger?.debug('Initializing all data');\r\n dataSourceUpdates.init(userKeyId, initData, onPutCompleteHandler);\r\n },\r\n});\r\n\r\nexport const createPatchListener = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onPatchCompleteHandler: VoidFunction = () => {\r\n },\r\n) => ({\r\n deserializeData: deserializePatch,\r\n processJson: async (userKeyId: string, data: IPatchData[]) => {\r\n if (data?.length === 0) {\r\n onPatchCompleteHandler?.();\r\n return;\r\n }\r\n\r\n data?.forEach(item => {\r\n logger?.debug(`Updating ${ item.data.key } in ${ item.kind.namespace }`);\r\n dataSourceUpdates.upsert(userKeyId, item.kind, item.data, onPatchCompleteHandler);\r\n })\r\n },\r\n});\r\n\r\n\r\nexport const createStreamListeners = (\r\n dataSourceUpdates: IDataSourceUpdates,\r\n logger?: ILogger,\r\n onCompleteHandlers?: {\r\n put?: VoidFunction;\r\n patch?: VoidFunction;\r\n delete?: VoidFunction;\r\n },\r\n) => {\r\n const listeners = new Map();\r\n listeners.set('put', createPutListener(dataSourceUpdates, logger, onCompleteHandlers?.put));\r\n listeners.set('patch', createPatchListener(dataSourceUpdates, logger, onCompleteHandlers?.patch));\r\n return listeners;\r\n};\r\n","export * from './createStreamListeners';\r\nexport * from './DataSourceUpdates';","export enum DataSyncModeEnum {\r\n POLLING = 'polling',\r\n STREAMING = 'streaming'\r\n}","import { IDataSynchronizer } from \"./IDataSynchronizer\";\r\n\r\nexport class NullDataSynchronizer implements IDataSynchronizer {\r\n close(): void {\r\n }\r\n\r\n start(): void {\r\n }\r\n\r\n stop(): void {\r\n }\r\n\r\n identify(): void {\r\n }\r\n}","import { isHttpRecoverable, PollingError } from \"../errors\";\r\nimport { IDataSynchronizer } from \"./IDataSynchronizer\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport Configuration from \"../Configuration\";\r\nimport { EventName, PollingErrorHandler, ProcessStreamResponse, StreamResponseEventType } from \"./types\";\r\nimport Requestor from \"./Requestor\";\r\nimport { httpErrorMessage } from \"../utils/http\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\nexport default class PollingDataSynchronizer implements IDataSynchronizer {\r\n private stopped = false;\r\n\r\n private logger?: ILogger;\r\n\r\n private pollingInterval: number;\r\n\r\n private user: IUser | undefined;\r\n\r\n private timeoutHandle: any;\r\n\r\n constructor(\r\n config: Configuration,\r\n private readonly requestor: Requestor,\r\n private readonly getStoreTimestamp: () => number,\r\n private readonly listeners: Map,\r\n private readonly errorHandler?: PollingErrorHandler,\r\n ) {\r\n this.logger = config.logger;\r\n this.pollingInterval = config.pollingInterval;\r\n this.user = config.user;\r\n }\r\n\r\n private poll() {\r\n if (this.stopped) {\r\n return;\r\n }\r\n\r\n const startTime = Date.now();\r\n this.logger?.debug('Polling for feature flag and segments updates');\r\n this.requestor.requestData(this.getStoreTimestamp(), this.user, (err, body) => {\r\n const elapsed = Date.now() - startTime;\r\n const sleepFor = Math.max(this.pollingInterval - elapsed, 0);\r\n\r\n this.logger?.debug('Elapsed: %d ms, sleeping for %d ms', elapsed, sleepFor);\r\n if (err) {\r\n const {status} = err;\r\n if (status && !isHttpRecoverable(status)) {\r\n const message = httpErrorMessage(err, 'polling request');\r\n this.logger?.error(message);\r\n this.errorHandler?.(new PollingError(message, status));\r\n // It is not recoverable, return and do not trigger another\r\n // poll.\r\n return;\r\n }\r\n this.logger?.warn(httpErrorMessage(err, 'polling request', 'will retry'));\r\n } else {\r\n let featureFlags = [];\r\n let userKeyId = this.user?.keyId!;\r\n let processStreamResponse: ProcessStreamResponse | undefined = this.listeners.get('patch');\r\n\r\n if (body) {\r\n const message = JSON.parse(body);\r\n if (message.messageType === 'data-sync') {\r\n switch (message.data.eventType) {\r\n case StreamResponseEventType.patch:\r\n processStreamResponse = this.listeners.get('patch');\r\n break;\r\n case StreamResponseEventType.full:\r\n processStreamResponse = this.listeners.get('put');\r\n break;\r\n }\r\n\r\n ({featureFlags, userKeyId} = message.data);\r\n }\r\n }\r\n\r\n const data = processStreamResponse?.deserializeData?.(featureFlags);\r\n processStreamResponse?.processJson?.(userKeyId, data);\r\n }\r\n\r\n // Falling through, there was some type of error and we need to trigger\r\n // a new poll.\r\n this.timeoutHandle = setTimeout(() => {\r\n this.poll();\r\n }, sleepFor);\r\n });\r\n }\r\n\r\n identify(user: IUser) {\r\n this.user = {...user};\r\n }\r\n\r\n close(): void {\r\n this.stop();\r\n }\r\n\r\n start(): void {\r\n this.poll();\r\n }\r\n\r\n stop(): void {\r\n if (this.timeoutHandle) {\r\n clearTimeout(this.timeoutHandle);\r\n this.timeoutHandle = undefined;\r\n }\r\n this.stopped = true;\r\n }\r\n}\r\n\r\n\r\n\r\n","import { IRequestor } from \"./IRequestor\";\r\nimport Configuration from \"../Configuration\";\r\nimport { IInfo } from \"../platform/IInfo\";\r\nimport { IRequestOptions, IRequests, IResponse } from \"../platform/requests\";\r\nimport { StreamingError } from \"../errors\";\r\nimport { defaultHeaders } from \"../utils/http\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class Requestor implements IRequestor {\r\n private readonly headers: Record;\r\n\r\n private readonly uri: string;\r\n\r\n constructor(\r\n sdkKey: string,\r\n config: Configuration,\r\n info: IInfo,\r\n private readonly requests: IRequests,\r\n ) {\r\n this.headers = defaultHeaders(sdkKey, info);\r\n this.uri = config.pollingUri;\r\n }\r\n\r\n /**\r\n * Perform a request and utilize the ETag cache. The ETags are cached in the\r\n * requestor instance.\r\n */\r\n private async request(\r\n requestUrl: string,\r\n options: IRequestOptions,\r\n ): Promise<{\r\n res: IResponse;\r\n body: string;\r\n }> {\r\n const res = await this.requests.fetch(requestUrl, options);\r\n\r\n const body = await res.text();\r\n\r\n return {res, body};\r\n }\r\n\r\n async requestData(timestamp: number, payload: any, cb: (err: any, body: any) => void) {\r\n const options: IRequestOptions = {\r\n method: 'POST',\r\n headers: this.headers,\r\n body: JSON.stringify(payload)\r\n };\r\n try {\r\n const {res, body} = await this.request(`${ this.uri }?timestamp=${ timestamp ?? 0 }`, options);\r\n if (res.status !== 200 && res.status !== 304) {\r\n const err = new StreamingError(`Unexpected status code: ${ res.status }`, res.status);\r\n return cb(err, undefined);\r\n }\r\n return cb(undefined, res.status === 304 ? null : body);\r\n } catch (err) {\r\n return cb(err, undefined);\r\n }\r\n }\r\n}\r\n","import { IDataSynchronizer } from \"./IDataSynchronizer\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { EventName, ProcessStreamResponse } from \"./types\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\nimport { IWebSocketWithEvents } from \"../platform/IWebSocket\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\nclass WebSocketDataSynchronizer implements IDataSynchronizer {\r\n private socket?: IWebSocketWithEvents;\r\n private readonly logger?: ILogger;\r\n\r\n private connectionAttemptStartTime?: number;\r\n\r\n constructor(\r\n sdkKey: string,\r\n user: IUser,\r\n clientContext: ClientContext,\r\n socket: IWebSocketWithEvents,\r\n private readonly getStoreTimestamp: () => number,\r\n private readonly listeners: Map,\r\n webSocketPingInterval: number\r\n ) {\r\n const {logger, streamingUri} = clientContext;\r\n\r\n this.logger = logger;\r\n this.socket = socket;\r\n this.socket.config({\r\n sdkKey,\r\n streamingUri,\r\n pingInterval: webSocketPingInterval,\r\n user,\r\n logger,\r\n getStoreTimestamp\r\n });\r\n\r\n this.listeners.forEach(({deserializeData, processJson}, eventName) => {\r\n this.socket?.addListener(eventName, (event) => {\r\n this.logger?.debug(`Received ${ eventName } event`);\r\n\r\n if (event?.data) {\r\n const {featureFlags, userKeyId} = event.data;\r\n const data = deserializeData(featureFlags);\r\n processJson(userKeyId, data);\r\n }\r\n });\r\n })\r\n }\r\n\r\n identify(user: IUser): void {\r\n this.socket?.identify(user);\r\n }\r\n\r\n start(): void {\r\n this.logConnectionStarted();\r\n\r\n this.socket?.connect();\r\n }\r\n\r\n private logConnectionStarted() {\r\n this.connectionAttemptStartTime = Date.now();\r\n this.logger?.info(`Stream connection attempt StartTime ${ this.connectionAttemptStartTime }`);\r\n }\r\n\r\n close(): void {\r\n this.stop();\r\n }\r\n\r\n stop(): void {\r\n this.socket?.close();\r\n this.socket = undefined;\r\n }\r\n}\r\n\r\nexport default WebSocketDataSynchronizer;","export * from './DataSyncMode';\r\nexport * from './IDataSynchronizer';\r\nexport * from './IRequestor';\r\nexport * from './NullDataSynchronizer';\r\nexport * from './PollingDataSynchronizer';\r\nexport * from './Requestor';\r\nexport * from './types';\r\nexport * from './utils';\r\nexport * from './WebSocketDataSynchronizer';","import { PollingError } from \"../errors\";\r\nimport { IFlag } from \"../evaluation/data/IFlag\";\r\n\r\nexport type PollingErrorHandler = (err: PollingError) => void;\r\n\r\nexport enum StreamResponseEventType {\r\n full = 'full',\r\n patch = 'patch'\r\n}\r\n\r\nexport interface IStreamResponse {\r\n eventType: StreamResponseEventType,\r\n featureFlags: IFlag[]\r\n}\r\n\r\nexport type EventName = 'delete' | 'patch' | 'ping' | 'put';\r\nexport type ProcessStreamResponse = {\r\n deserializeData: (flags: IFlag[]) => any;\r\n processJson: (userKeyId: string, json: any) => void;\r\n};","/********************** encode text begin *****************************/\r\nconst alphabet: Record = {\r\n \"0\": \"Q\",\r\n \"1\": \"B\",\r\n \"2\": \"W\",\r\n \"3\": \"S\",\r\n \"4\": \"P\",\r\n \"5\": \"H\",\r\n \"6\": \"D\",\r\n \"7\": \"X\",\r\n \"8\": \"Z\",\r\n \"9\": \"U\",\r\n}\r\n\r\nfunction encodeNumber(param: number, length: number): string {\r\n var s = \"000000000000\" + param;\r\n const numberWithLeadingZeros = s.slice(s.length - length);\r\n return numberWithLeadingZeros.split('').map(n => alphabet[n]).join('');\r\n}\r\n\r\n// generate connection token\r\nexport function generateConnectionToken(text: string): string {\r\n text = text.replace(/=*$/, '');\r\n const timestamp = Date.now();\r\n const timestampCode = encodeNumber(timestamp, timestamp.toString().length);\r\n // get random number less than the length of the text as the start point, and it must be greater or equal to 2\r\n const start = Math.max(Math.floor(Math.random() * text.length), 2);\r\n\r\n return `${ encodeNumber(start, 3) }${ encodeNumber(timestampCode.length, 2) }${ text.slice(0, start) }${ timestampCode }${ text.slice(start) }`;\r\n}\r\n\r\n/********************** encode text end *****************************/","export class PollingError extends Error {\r\n public readonly status?: number;\r\n\r\n constructor(message: string, status?: number) {\r\n super(message);\r\n this.status = status;\r\n this.name = 'FbPollingError';\r\n }\r\n}\r\n\r\nexport class StreamingError extends Error {\r\n public readonly code?: number;\r\n\r\n constructor(message: string, code?: number) {\r\n super(message);\r\n this.code = code;\r\n this.name = 'FbStreamingError';\r\n }\r\n}\r\n\r\nexport class UnexpectedResponseError extends Error {\r\n constructor(message: string) {\r\n super(message);\r\n this.name = 'FbUnexpectedResponseError';\r\n }\r\n}\r\n\r\n\r\nexport class ClientError extends Error {\r\n constructor(message: string) {\r\n super(message);\r\n this.name = 'FbClientError';\r\n }\r\n}\r\n\r\nexport function isHttpRecoverable(status: number) {\r\n if (status >= 400 && status < 500) {\r\n return status === 400 || status === 408 || status === 429;\r\n }\r\n return true;\r\n}","import { ReasonKinds } from \"./ReasonKinds\";\r\nimport { IFlag } from \"./data/IFlag\";\r\nimport { EvalEvent } from \"../events/event\";\r\nimport { IUser } from \"../options/IUser\";\r\n\r\n/**\r\n * A class which encapsulates the result of an evaluation. It allows for differentiating between\r\n * successful and error result types.\r\n *\r\n * @internal\r\n */\r\nexport default class EvalResult {\r\n protected constructor(\r\n public kind: ReasonKinds,\r\n public value: IFlag | null,\r\n public reason?: string,\r\n ) {\r\n }\r\n\r\n static flagNotFound(flagKey: string) {\r\n return new EvalResult(ReasonKinds.FlagNotFound, null, `flag not found: ${ flagKey }`);\r\n }\r\n\r\n static matched(val: IFlag) {\r\n return new EvalResult(ReasonKinds.Match, val, 'target match');\r\n }\r\n\r\n toEvalEvent(user: IUser): EvalEvent | null {\r\n if (this.kind !== ReasonKinds.Match) {\r\n return null;\r\n }\r\n\r\n const targetedVariation = this.value?.variations.find(v => v.value === this.value?.variation);\r\n return new EvalEvent(user, this.value?.id!, targetedVariation!, this.value?.sendToExperiment!);\r\n }\r\n}","import { IFlag } from \"./data/IFlag\";\r\nimport EvalResult from \"./EvalResult\";\r\nimport { IStore } from \"../platform/IStore\";\r\nimport DataKinds from \"../store/DataKinds\";\r\n\r\n/**\r\n * @internal\r\n */\r\nexport default class Evaluator {\r\n constructor(private store: IStore) {\r\n }\r\n\r\n /**\r\n * Evaluate the given flag against the given context.\r\n * @param flagKey The key of the feature flag.\r\n */\r\n evaluate(\r\n flagKey: string,\r\n ): EvalResult {\r\n const flag = this.store.get(DataKinds.Flags, flagKey) as unknown as IFlag;\r\n if (!flag) {\r\n return EvalResult.flagNotFound(flagKey);\r\n }\r\n\r\n return EvalResult.matched(flag);\r\n }\r\n}","/**\r\n * Different kinds of error which may be encountered during evaluation.\r\n */\r\nexport enum ReasonKinds {\r\n ClientNotReady = 'ClientNotReady',\r\n Match = 'Match',\r\n WrongType = 'WrongType',\r\n FlagNotFound = 'FlagNotFound',\r\n Error = 'Error'\r\n}","export type FlagValue = any;\r\n\r\nexport enum VariationDataType {\r\n string = 'string',\r\n boolean = 'boolean',\r\n number = 'number',\r\n json = 'json',\r\n empty = ''\r\n}\r\n\r\nexport interface IVariation {\r\n id: number,\r\n value: FlagValue\r\n}\r\n\r\nexport interface IFlagBase {\r\n id: string, // the key\r\n variation: FlagValue,\r\n variationType: VariationDataType,\r\n sendToExperiment?: boolean,\r\n timestamp?: number,\r\n variationOptions?: IVariation[],\r\n}\r\n\r\nexport interface IFlag extends IFlagBase {\r\n key: string, // the same value to id\r\n variations: IVariation[],// the same value to variationOptions\r\n version: number\r\n}\r\n","export * from './IFlag';","export * from './data';\r\nexport * from './EvalResult';\r\nexport * from './Evaluator';\r\nexport * from './IEvalDetail';\r\nexport * from './ReasonKinds';","import { IEventProcessor } from \"./IEventProcessor\";\r\nimport { EventDispatcher } from \"./EventDispatcher\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { FlushEvent, IEvent, ShutdownEvent } from \"./event\";\r\nimport { isNullOrUndefined } from \"../utils/isNullOrUndefined\";\r\nimport { IEventQueue } from \"./IEventQueue\";\r\nimport { DefaultEventQueue } from \"./DefaultEventQueue\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\n\r\nexport class DefaultEventProcessor implements IEventProcessor {\r\n private readonly logger: ILogger;\r\n private readonly flushInterval: number;\r\n private readonly eventDispatcher: EventDispatcher;\r\n private readonly eventQueue: IEventQueue;\r\n private closed: boolean = false;\r\n\r\n constructor(clientContext: ClientContext) {\r\n const {logger, flushInterval, maxEventsInQueue} = clientContext;\r\n this.logger = logger!;\r\n this.flushInterval = flushInterval;\r\n this.eventQueue = new DefaultEventQueue(maxEventsInQueue, this.logger);\r\n this.eventDispatcher = new EventDispatcher(clientContext, this.eventQueue);\r\n\r\n this.flushLoop();\r\n }\r\n\r\n private flushLoop() {\r\n if (this.closed) {\r\n return;\r\n }\r\n\r\n setTimeout(async () => {\r\n try {\r\n await this.flush();\r\n } catch (err) {\r\n this.logger.error('Unexpected error while flushing events in event processor.', err);\r\n }\r\n\r\n this.flushLoop();\r\n }, this.flushInterval);\r\n }\r\n\r\n flush(): Promise {\r\n const flushEvent = new FlushEvent();\r\n this.record(flushEvent);\r\n return flushEvent.waitForCompletion();\r\n }\r\n\r\n async close(): Promise {\r\n if (this.closed) {\r\n return;\r\n }\r\n\r\n // send a shutdown event to dispatcher\r\n const shutdown = new ShutdownEvent();\r\n this.record(shutdown);\r\n\r\n try {\r\n await shutdown.waitForCompletion();\r\n } catch (err) {\r\n this.logger.error('Event processor shutdown but not complete.');\r\n }\r\n\r\n // mark the event queue as complete for adding\r\n this.eventQueue.close();\r\n this.closed = true;\r\n }\r\n\r\n record(event: IEvent | null): boolean {\r\n if (isNullOrUndefined(event)) {\r\n return false;\r\n }\r\n\r\n if (!this.eventQueue.addEvent(event!)) {\r\n if (event instanceof FlushEvent) {\r\n event.complete();\r\n }\r\n\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n}","import { IEventQueue } from \"./IEventQueue\";\r\nimport { IEvent } from \"./event\";\r\nimport { ILogger } from \"../logging/ILogger\";\r\n\r\nexport class DefaultEventQueue implements IEventQueue {\r\n private events: IEvent[];\r\n private closed: boolean = false;\r\n\r\n constructor(private readonly capacity: number, private readonly logger: ILogger) {\r\n this.events = [];\r\n }\r\n\r\n addEvent(event: IEvent): boolean {\r\n if (this.closed) {\r\n return false;\r\n }\r\n\r\n if (this.events.length >= this.capacity) {\r\n this.logger.warn(\"Events are being produced faster than they can be processed. We shouldn't see this.\");\r\n return false;\r\n }\r\n\r\n this.events.push(event);\r\n return true;\r\n }\r\n\r\n clear(): void {\r\n this.events = [];\r\n }\r\n\r\n shift(): IEvent | undefined {\r\n return this.events.shift();\r\n }\r\n\r\n close(): void {\r\n this.closed = true;\r\n }\r\n\r\n get eventsSnapshot(): IEvent[] {\r\n return [...this.events];\r\n }\r\n\r\n get length(): number {\r\n return this.events.length;\r\n }\r\n\r\n get isEmpty(): boolean {\r\n return this.length === 0;\r\n }\r\n}","import { DeliveryStatus, IEventSender, IEventSenderResult } from \"./IEventSender\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { defaultHeaders, httpErrorMessage } from \"../utils/http\";\r\nimport { IRequests } from \"../platform/requests\";\r\nimport { isHttpRecoverable, UnexpectedResponseError } from \"../errors\";\r\nimport sleep from \"../utils/sleep\";\r\n\r\nexport class DefaultEventSender implements IEventSender {\r\n private readonly defaultHeaders: {\r\n [key: string]: string;\r\n };\r\n private readonly eventsUri: string;\r\n private requests: IRequests;\r\n\r\n constructor(clientContext: ClientContext) {\r\n const {\r\n sdkKey,\r\n eventsUri,\r\n platform\r\n } = clientContext;\r\n\r\n const {info, requests} = platform;\r\n this.defaultHeaders = defaultHeaders(sdkKey, info);\r\n this.eventsUri = eventsUri;\r\n this.requests = requests;\r\n }\r\n\r\n async send(payload: string, retry: boolean): Promise {\r\n const res: IEventSenderResult = {\r\n status: DeliveryStatus.Succeeded,\r\n };\r\n\r\n const headers: Record = {\r\n ...this.defaultHeaders,\r\n 'content-type': 'application/json',\r\n }\r\n\r\n let error;\r\n try {\r\n const {status} = await this.requests.fetch(this.eventsUri, {\r\n headers,\r\n body: payload,\r\n method: 'POST',\r\n });\r\n\r\n if (status >= 200 && status <= 299) {\r\n return res;\r\n }\r\n\r\n error = new UnexpectedResponseError(\r\n httpErrorMessage({status, message: 'some events were dropped'}, 'event posting'),\r\n );\r\n\r\n if (!isHttpRecoverable(status)) {\r\n res.status = DeliveryStatus.FailedAndMustShutDown;\r\n res.error = error;\r\n return res;\r\n }\r\n } catch (err) {\r\n error = err;\r\n }\r\n\r\n // recoverable but not retrying\r\n if (error && !retry) {\r\n res.status = DeliveryStatus.Failed;\r\n res.error = error;\r\n return res;\r\n }\r\n\r\n // wait 1 second before retrying\r\n await sleep();\r\n\r\n return this.send(payload, false);\r\n }\r\n}","import { IEventSerializer } from \"./EventSerializer\";\r\nimport { EvalEvent, IEvent, MetricEvent } from \"./event\";\r\n\r\nexport class DefaultEventSerializer implements IEventSerializer {\r\n serialize(events: IEvent[]): string {\r\n const payload = events\r\n .map(event => event instanceof EvalEvent || event instanceof MetricEvent ? event.toPayload() : null)\r\n .filter(event => event !== null);\r\n\r\n return JSON.stringify(payload);\r\n }\r\n}","import { ILogger } from \"../logging/ILogger\";\r\nimport ClientContext from \"../options/ClientContext\";\r\nimport { DeliveryStatus, IEventSender } from \"./IEventSender\";\r\nimport { IEventQueue } from \"./IEventQueue\";\r\nimport { DefaultEventQueue } from \"./DefaultEventQueue\";\r\nimport { DefaultEventSender } from \"./DefaultEventSender\";\r\nimport { AsyncEvent, FlushEvent, IEvent, PayloadEvent, ShutdownEvent } from \"./event\";\r\nimport { IEventSerializer } from \"./EventSerializer\";\r\nimport { DefaultEventSerializer } from \"./DefaultEventSerializer\";\r\nimport sleep from \"../utils/sleep\";\r\n\r\nexport class EventDispatcher {\r\n private readonly logger: ILogger;\r\n private sender: IEventSender;\r\n private buffer: IEventQueue;\r\n private serializer: IEventSerializer;\r\n\r\n private maxEventPerRequest = 50;\r\n private stopped: boolean = false;\r\n\r\n constructor(clientContext: ClientContext, queue: IEventQueue) {\r\n const {logger, maxEventsInQueue} = clientContext;\r\n this.logger = logger!;\r\n\r\n this.buffer = new DefaultEventQueue(maxEventsInQueue, this.logger);\r\n this.sender = new DefaultEventSender(clientContext);\r\n this.serializer = new DefaultEventSerializer();\r\n\r\n this.dispatchLoop(queue).then();\r\n }\r\n\r\n private async dispatchLoop(queue: IEventQueue) {\r\n this.logger.debug('Start dispatch loop.');\r\n\r\n let running = true;\r\n while (running) {\r\n try {\r\n const event = queue.shift();\r\n\r\n if (event === undefined) {\r\n await sleep(1000);\r\n continue;\r\n }\r\n\r\n if (event instanceof PayloadEvent) {\r\n this.addEventToBuffer(event);\r\n } else if (event instanceof FlushEvent) {\r\n await this.triggerFlush(event);\r\n } else if (event instanceof ShutdownEvent) {\r\n await this.triggerFlush(event);\r\n this.stopped = true;\r\n running = false;\r\n }\r\n } catch (err) {\r\n this.logger.error('Unexpected error in event dispatcher.', err);\r\n }\r\n }\r\n\r\n this.logger.debug('Finish dispatch loop.');\r\n }\r\n\r\n private addEventToBuffer(event: IEvent) {\r\n if (this.stopped) {\r\n return;\r\n }\r\n\r\n if (this.buffer.addEvent(event)) {\r\n this.logger.debug('Added event to buffer.');\r\n } else {\r\n this.logger.warn('Exceeded event queue capacity, event will be dropped. Increase capacity to avoid dropping events.');\r\n }\r\n }\r\n\r\n private async triggerFlush(event: AsyncEvent) {\r\n if (this.stopped) {\r\n event.complete();\r\n return;\r\n }\r\n\r\n if (this.buffer.isEmpty) {\r\n event.complete();\r\n this.logger.debug('Flush empty buffer.');\r\n // There are no events to flush. If we don't complete the message, then the async task may never\r\n // complete (if it had a non-zero positive timeout, then it would complete after the timeout).\r\n return;\r\n }\r\n\r\n const snapshot = this.buffer.eventsSnapshot;\r\n this.buffer.clear();\r\n try {\r\n await this.flushEvents(snapshot);\r\n this.logger.debug(`${ snapshot.length } events has been flushed.`);\r\n } catch (err) {\r\n this.logger.warn('Exception happened when flushing events', err);\r\n }\r\n\r\n event.complete();\r\n }\r\n\r\n private async flushEvents(events: IEvent[]) {\r\n events = this.getUniqueEvents(events);\r\n const total = events.length;\r\n for (let i = 0; i < total; i += this.maxEventPerRequest) {\r\n const length = Math.min(this.maxEventPerRequest, total - i);\r\n const slice = events.slice(i, i + length);\r\n const payload = this.serializer.serialize(slice);\r\n\r\n const {status} = await this.sender.send(payload, true);\r\n if (status === DeliveryStatus.FailedAndMustShutDown) {\r\n this.stopped = true;\r\n }\r\n }\r\n }\r\n\r\n private getUniqueEvents(events: IEvent[]): IEvent[] {\r\n const uniqueEvents: IEvent[] = [];\r\n const hashes: string[] = [];\r\n\r\n for (const event of events) {\r\n if (!hashes.includes(event.hash)) {\r\n uniqueEvents.push(event);\r\n hashes.push(event.hash);\r\n }\r\n }\r\n\r\n return uniqueEvents;\r\n }\r\n}","export enum DeliveryStatus {\r\n Succeeded,\r\n Failed,\r\n FailedAndMustShutDown\r\n}\r\n\r\nexport interface IEventSenderResult {\r\n status: DeliveryStatus,\r\n error?: any\r\n}\r\n\r\nexport interface IEventSender {\r\n send(payload: string, retry: boolean): Promise;\r\n}","import { IEventProcessor } from \"./IEventProcessor\";\r\nimport { IEvent } from \"./event\";\r\n\r\nexport class NullEventProcessor implements IEventProcessor {\r\n flush(): Promise {\r\n return Promise.resolve();\r\n }\r\n\r\n close(): Promise {\r\n return Promise.resolve();\r\n }\r\n\r\n record(event: IEvent | null): boolean {\r\n return false;\r\n }\r\n}","import { IUser } from \"../options/IUser\";\r\nimport { IVariation } from \"../evaluation/data/IFlag\";\r\n\r\nexport interface IEvent {\r\n hash: string;\r\n}\r\n\r\nexport class AsyncEvent implements IEvent {\r\n private readonly isCompletedPromise?: Promise;\r\n private resolveFn?: (value: AsyncEvent) => void;\r\n timestamp = (new Date()).getTime();\r\n\r\n get hash(): string {\r\n return this.timestamp.toString();\r\n }\r\n\r\n constructor() {\r\n this.isCompletedPromise = new Promise((resolve) => {\r\n this.resolveFn = resolve;\r\n });\r\n }\r\n\r\n waitForCompletion(): Promise {\r\n return this.isCompletedPromise!;\r\n }\r\n\r\n complete() {\r\n this.resolveFn?.(this);\r\n }\r\n}\r\n\r\nexport class FlushEvent extends AsyncEvent {\r\n}\r\n\r\nexport class ShutdownEvent extends AsyncEvent {\r\n}\r\n\r\nexport class PayloadEvent implements IEvent {\r\n timestamp = (new Date()).getTime();\r\n\r\n get hash(): string {\r\n return this.timestamp.toString();\r\n }\r\n\r\n toPayload(): any {\r\n };\r\n}\r\n\r\nexport class MetricEvent extends PayloadEvent {\r\n constructor(\r\n public user: IUser,\r\n public eventName: string,\r\n public appType: string,\r\n public metricValue: number\r\n ) {\r\n super();\r\n }\r\n\r\n private userPayload() {\r\n return {\r\n keyId: this.user.keyId,\r\n name: this.user.name,\r\n customizedProperties: this.user.customizedProperties\r\n }\r\n }\r\n\r\n toPayload(): any {\r\n return {\r\n user: this.userPayload(),\r\n metrics: [{\r\n route: 'index/metric',\r\n timestamp: this.timestamp,\r\n numericValue: this.metricValue,\r\n appType: this.appType,\r\n eventName: this.eventName,\r\n type: 'CustomEvent'\r\n }]\r\n }\r\n }\r\n\r\n get hash(): string {\r\n const payload = this.toPayload();\r\n const hasObject = {\r\n user: payload.user,\r\n metrics: payload.metrics.map((m: any) => ({...m, timestamp: undefined}))\r\n }\r\n return JSON.stringify(hasObject);\r\n }\r\n}\r\n\r\nexport class EvalEvent extends PayloadEvent {\r\n constructor(\r\n public user: IUser,\r\n public flagKey: string,\r\n public variation: IVariation,\r\n public sendToExperiment: boolean\r\n ) {\r\n super();\r\n }\r\n\r\n private userPayload() {\r\n return {\r\n keyId: this.user.keyId,\r\n name: this.user.name,\r\n customizedProperties: this.user.customizedProperties\r\n }\r\n }\r\n\r\n toPayload(): any {\r\n return {\r\n user: this.userPayload(),\r\n variations: [{\r\n featureFlagKey: this.flagKey,\r\n sendToExperiment: this.sendToExperiment,\r\n timestamp: this.timestamp,\r\n variation: this.variation\r\n }]\r\n }\r\n }\r\n\r\n get hash(): string {\r\n const payload = this.toPayload();\r\n const hasObject = {\r\n user: payload.user,\r\n variations: payload.variations.map((m: any) => ({...m, timestamp: undefined}))\r\n }\r\n\r\n return JSON.stringify(hasObject);\r\n }\r\n}","export * from './DefaultEventProcessor';\r\nexport * from './DefaultEventQueue';\r\nexport * from './DefaultEventSender';\r\nexport * from './DefaultEventSerializer';\r\nexport * from './event';\r\nexport * from './EventDispatcher';\r\nexport * from './EventSerializer';\r\nexport * from './IEventProcessor';\r\nexport * from './IEventQueue';\r\nexport * from './IEventSender';\r\nexport * from './NullEventProcessor';\r\n","export * from './bootstrap';\r\nexport * from './data-sources';\r\nexport * from './evaluation';\r\nexport * from './events';\r\nexport * from './logging';\r\nexport * from './options';\r\nexport * from './platform';\r\nexport * from './store';\r\nexport * from './data-sync';\r\nexport * from './utils';\r\n\r\nexport * from './Configuration';\r\nexport * from './constants';\r\nexport * from './Context';\r\nexport * from './errors';\r\nexport * from './FbClientBuilder';\r\nexport * from './IContextProperty';\r\nexport * from './IDataKind';\r\nexport * from './IFbClient';\r\nexport * from './IVersionedData';\r\nexport * from './FbClientCore';\r\n\r\n","import format from './format';\r\nimport { ILogger } from \"./ILogger\";\r\nimport { IBasicLoggerOptions } from \"./IBasicLoggerOptions\";\r\n\r\nconst LogPriority = {\r\n debug: 0,\r\n info: 1,\r\n warn: 2,\r\n error: 3,\r\n none: 4,\r\n};\r\n\r\nconst LevelNames = ['debug', 'info', 'warn', 'error', 'none'];\r\n\r\n/**\r\n * A basic logger which handles filtering by level.\r\n *\r\n * With the default options it will write to `console.error`\r\n * and it will use the formatting provided by `console.error`.\r\n * If the destination is overwritten, then it will use an included\r\n * formatter similar to `util.format`.\r\n *\r\n * If a formatter is available, then that should be overridden\r\n * as well for performance.\r\n */\r\nexport class BasicLogger implements ILogger {\r\n private logLevel: number;\r\n\r\n private name: string;\r\n\r\n private destination?: (line: string) => void;\r\n\r\n private formatter?: (...args: any[]) => string;\r\n\r\n /**\r\n * This should only be used as a default fallback and not as a convenient\r\n * solution. In most cases you should construct a new instance with the\r\n * appropriate options for your specific needs.\r\n */\r\n static get() {\r\n return new BasicLogger({});\r\n }\r\n\r\n constructor(options: IBasicLoggerOptions) {\r\n this.logLevel = LogPriority[options.level ?? 'info'] ?? LogPriority.info;\r\n this.name = options.name ?? 'FeatBit';\r\n // eslint-disable-next-line no-console\r\n this.destination = options.destination;\r\n this.formatter = options.formatter;\r\n }\r\n\r\n private tryFormat(...args: any[]): string {\r\n try {\r\n if (this.formatter) {\r\n // In case the provided formatter fails.\r\n return this.formatter?.(...args);\r\n }\r\n return format(...args);\r\n } catch {\r\n return format(...args);\r\n }\r\n }\r\n\r\n private tryWrite(msg: string) {\r\n try {\r\n this.destination!(msg);\r\n } catch {\r\n // eslint-disable-next-line no-console\r\n console.error(msg);\r\n }\r\n }\r\n\r\n private log(level: number, args: any[]) {\r\n if (level >= this.logLevel) {\r\n const prefix = `${ LevelNames[level] }: [${ this.name }]`;\r\n try {\r\n if (this.destination) {\r\n this.tryWrite(`${ prefix } ${ this.tryFormat(...args) }`);\r\n } else {\r\n // `console.error` has its own formatter.\r\n // So we don't need to do anything.\r\n // eslint-disable-next-line no-console\r\n console.error(...args);\r\n }\r\n } catch {\r\n // If all else fails do not break.\r\n // eslint-disable-next-line no-console\r\n console.error(...args);\r\n }\r\n }\r\n }\r\n\r\n error(...args: any[]): void {\r\n this.log(LogPriority.error, args);\r\n }\r\n\r\n warn(...args: any[]): void {\r\n this.log(LogPriority.warn, args);\r\n }\r\n\r\n info(...args: any[]): void {\r\n this.log(LogPriority.info, args);\r\n }\r\n\r\n debug(...args: any[]): void {\r\n this.log(LogPriority.debug, args);\r\n }\r\n}\r\n","import { ILogger } from \"./ILogger\";\r\nimport { TypeValidators } from \"../options/Validators\";\r\n\r\nconst loggerRequirements = {\r\n error: TypeValidators.Function,\r\n warn: TypeValidators.Function,\r\n info: TypeValidators.Function,\r\n debug: TypeValidators.Function,\r\n};\r\n\r\n/**\r\n * The safeLogger logic exists because we allow the application to pass in a custom logger, but\r\n * there is no guarantee that the logger works correctly and if it ever throws exceptions there\r\n * could be serious consequences (e.g. an uncaught exception within an error event handler, due\r\n * to the SDK trying to log the error, can terminate the application). An exception could result\r\n * from faulty logic in the logger implementation, or it could be that this is not a logger at\r\n * all but some other kind of object; the former is handled by a catch block that logs an error\r\n * message to the SDK's default logger, and we can at least partly guard against the latter by\r\n * checking for the presence of required methods at configuration time.\r\n */\r\nexport class SafeLogger implements ILogger {\r\n private logger: ILogger;\r\n\r\n private fallback: ILogger;\r\n\r\n /**\r\n * Construct a safe logger with the specified logger.\r\n * @param logger The logger to use.\r\n * @param fallback A fallback logger to use in case an issue is encountered using\r\n * the provided logger.\r\n */\r\n constructor(logger: ILogger, fallback: ILogger) {\r\n Object.entries(loggerRequirements).forEach(([level, validator]) => {\r\n if (!validator.is((logger as any)[level])) {\r\n throw new Error(`Provided logger instance must support logger.${ level }(...) method`);\r\n // Note that the SDK normally does not throw exceptions to the application, but that rule\r\n // does not apply to FbClientNode.init() which will throw an exception if the parameters are so\r\n // invalid that we cannot proceed with creating the client. An invalid logger meets those\r\n // criteria since the SDK calls the logger during nearly all of its operations.\r\n }\r\n });\r\n this.logger = logger;\r\n this.fallback = fallback;\r\n }\r\n\r\n private log(level: 'error' | 'warn' | 'info' | 'debug', args: any[]) {\r\n try {\r\n this.logger[level](...args);\r\n } catch {\r\n // If all else fails do not break.\r\n this.fallback[level](...args);\r\n }\r\n }\r\n\r\n error(...args: any[]): void {\r\n this.log('error', args);\r\n }\r\n\r\n warn(...args: any[]): void {\r\n this.log('warn', args);\r\n }\r\n\r\n info(...args: any[]): void {\r\n this.log('info', args);\r\n }\r\n\r\n debug(...args: any[]): void {\r\n this.log('debug', args);\r\n }\r\n}","import { TypeValidators } from \"../options/Validators\";\r\n\r\n\r\n/**\r\n * Attempt to produce a string representation of a value.\r\n * The format should be roughly comparable to `util.format`\r\n * aside from object which will be JSON versus the `util.inspect`\r\n * format.\r\n * @param val\r\n * @returns A string representation of the value if possible.\r\n */\r\nfunction tryStringify(val: any) {\r\n if (typeof val === 'string') {\r\n return val;\r\n }\r\n if (val === undefined) {\r\n return 'undefined';\r\n }\r\n if (val === null) {\r\n return 'null';\r\n }\r\n if (Object.prototype.hasOwnProperty.call(val, 'toString')) {\r\n try {\r\n return val.toString();\r\n } catch {\r\n /* Keep going */\r\n }\r\n }\r\n\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n try {\r\n return JSON.stringify(val);\r\n } catch (error) {\r\n if (error instanceof TypeError && error.message.indexOf('circular') >= 0) {\r\n return '[Circular]';\r\n }\r\n return '[Not Stringifiable]';\r\n }\r\n}\r\n\r\n/**\r\n * Attempt to produce a numeric representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The numeric representation or 'NaN' if not numeric.\r\n */\r\nfunction toNumber(val: any): string {\r\n // Symbol has to be treated special because it will\r\n // throw an exception if an attempt is made to convert it.\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n return String(Number(val));\r\n}\r\n\r\n/**\r\n * Attempt to produce an integer representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The integer representation or 'NaN' if not numeric.\r\n */\r\nfunction toInt(val: any): string {\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n if (typeof val === 'bigint') {\r\n return `${ val }n`;\r\n }\r\n return String(parseInt(val, 10));\r\n}\r\n\r\n/**\r\n * Attempt to produce a float representation.\r\n * BigInts have an `n` suffix.\r\n * @param val\r\n * @returns The integer representation or 'NaN' if not numeric.\r\n */\r\nfunction toFloat(val: any): string {\r\n if (typeof val === 'symbol') {\r\n return 'NaN';\r\n }\r\n return String(parseFloat(val));\r\n}\r\n\r\n// Based on:\r\n// https://nodejs.org/api/util.html#utilformatformat-args\r\n// The result will not match browser exactly, but it should get the\r\n// right information through.\r\nconst escapes: Record string> = {\r\n s: (val: any) => tryStringify(val),\r\n d: (val: any) => toNumber(val),\r\n i: (val: any) => toInt(val),\r\n f: (val: any) => toFloat(val),\r\n j: (val: any) => tryStringify(val),\r\n o: (val: any) => tryStringify(val),\r\n O: (val: any) => tryStringify(val),\r\n c: () => '',\r\n};\r\n\r\n/**\r\n * A basic formatted for use where `util.format` is not available.\r\n * This will not be as performant, but it will produce formatted\r\n * messages.\r\n *\r\n * @internal\r\n *\r\n * @param args\r\n * @returns Formatted string.\r\n */\r\nexport default function format(...args: any[]): string {\r\n const formatString = args.shift();\r\n if (TypeValidators.String.is(formatString)) {\r\n let out = '';\r\n let i = 0;\r\n while (i < formatString.length) {\r\n const char = formatString.charAt(i);\r\n if (char === '%') {\r\n const nextIndex = i + 1;\r\n if (nextIndex < formatString.length) {\r\n const nextChar = formatString.charAt(i + 1);\r\n if (nextChar in escapes && args.length) {\r\n const value = args.shift();\r\n // This rule is for math.\r\n // eslint-disable-next-line no-unsafe-optional-chaining\r\n out += escapes[nextChar]?.(value);\r\n } else if (nextChar === '%') {\r\n out += '%';\r\n } else {\r\n out += `%${ nextChar }`;\r\n }\r\n i += 2;\r\n }\r\n } else {\r\n out += char;\r\n i += 1;\r\n }\r\n }\r\n // If there are any args left after we exhaust the format string\r\n // then just stick those on the end.\r\n if (args.length) {\r\n if (out.length) {\r\n out += ' ';\r\n }\r\n out += args.map(tryStringify).join(' ');\r\n }\r\n return out;\r\n }\r\n return args.map(tryStringify).join(' ');\r\n}\r\n","export * from './BasicLogger';\r\nexport * from './format';\r\nexport * from './IBasicLoggerOptions';\r\nexport * from './ILogger';\r\nexport * from './LogLevel';\r\nexport * from './SafeLogger';","import { ILogger } from \"../logging/ILogger\";\r\nimport { IPlatform } from \"../platform/IPlatform\";\r\nimport { IClientContext } from \"./IClientContext\";\r\nimport { IUser } from \"./IUser\";\r\n\r\n/**\r\n * The client context provides basic configuration and platform support which are required\r\n * when building SDK components.\r\n */\r\nexport default class ClientContext implements IClientContext {\r\n flushInterval: number;\r\n maxEventsInQueue: number;\r\n offline: boolean;\r\n logger: ILogger;\r\n eventsUri: string;\r\n pollingUri: string;\r\n streamingUri: string;\r\n\r\n constructor(\r\n public readonly sdkKey: string,\r\n configuration: {\r\n logger?: ILogger;\r\n offline?: boolean;\r\n flushInterval: number;\r\n maxEventsInQueue: number;\r\n streamingUri: string;\r\n pollingUri: string;\r\n eventsUri: string;\r\n },\r\n public readonly platform: IPlatform,\r\n ) {\r\n this.logger = configuration.logger!;\r\n this.offline = configuration.offline!;\r\n this.flushInterval = configuration.flushInterval;\r\n this.maxEventsInQueue = configuration.maxEventsInQueue;\r\n this.streamingUri = configuration.streamingUri;\r\n this.pollingUri = configuration.pollingUri;\r\n this.eventsUri = configuration.eventsUri;\r\n }\r\n}","/**\r\n * Messages for issues which can be encountered from processing the configuration options.\r\n */\r\nexport default class OptionMessages {\r\n static optionBelowMinimum(name: string, value: number, min: number): string {\r\n return `Config option \"${ name }\" had invalid value of ${ value }, using minimum of ${ min } instead`;\r\n }\r\n\r\n static unknownOption(name: string): string {\r\n return `Ignoring unknown config option \"${ name }\"`;\r\n }\r\n\r\n static wrongOptionType(name: string, expectedType: string, actualType: string): string {\r\n return `Config option \"${ name }\" should be of type ${ expectedType }, got ${ actualType }, using default value`;\r\n }\r\n\r\n static wrongOptionTypeBoolean(name: string, actualType: string): string {\r\n return `Config option \"${ name }\" should be a boolean, got ${ actualType }, converting to boolean`;\r\n }\r\n\r\n static partialEndpoint(name: string): string {\r\n return `You have set custom uris without specifying the ${ name } URI; connections may not work properly`;\r\n }\r\n\r\n static mandatory(name: string): string {\r\n return `${ name } is mandatory`;\r\n }\r\n\r\n static invalidOptionValue(name: string): string {\r\n return `Invalid option value: ${ name }`;\r\n }\r\n\r\n static missingKeyInBootstrapValue(key: string): string {\r\n return `Missing key \"${ key }\" in bootstrap value`;\r\n }\r\n}","import { IUser } from \"./IUser\";\r\nimport {IContextProperty} from \"../IContextProperty\";\r\n\r\n/**\r\n * Creates an instance of the FeatBit user.\r\n *\r\n * @return\r\n * The new {@link IUser} instance.\r\n */\r\nexport class UserBuilder {\r\n private _keyId: string = '';\r\n private _name: string = '';\r\n private _custom: IContextProperty[] = [];\r\n\r\n constructor(keyId: string) {\r\n this._keyId = keyId;\r\n }\r\n\r\n name(name: string): UserBuilder {\r\n this._name = name;\r\n return this;\r\n }\r\n\r\n custom(propertyName: string, value: string): UserBuilder {\r\n this._custom?.push({ name: propertyName, value: value });\r\n return this;\r\n }\r\n\r\n build(): IUser {\r\n return {\r\n name: this._name,\r\n keyId: this._keyId,\r\n customizedProperties: this._custom\r\n };\r\n }\r\n}","/* eslint-disable class-methods-use-this */\r\n/* eslint-disable max-classes-per-file */\r\n\r\n// The classes here are static, but needs to be instantiated to\r\n// support the generic functionality. Which is why we do not care about using\r\n// `this`\r\n\r\n// These validators are also of trivial complexity, so we are allowing more than\r\n// one per file.\r\n\r\nimport OptionMessages from \"./OptionMessages\";\r\nimport { IFlagBase } from \"../evaluation\";\r\n\r\n/**\r\n * Interface for type validation.\r\n */\r\nexport interface TypeValidator {\r\n // holding validation error messages\r\n messages?: string[];\r\n\r\n is(u: unknown): boolean;\r\n\r\n getType(): string;\r\n}\r\n\r\n/**\r\n * Validate a factory or instance.\r\n */\r\nexport class FactoryOrInstance implements TypeValidator {\r\n is(factoryOrInstance: unknown) {\r\n if (Array.isArray(factoryOrInstance)) {\r\n return false;\r\n }\r\n const anyFactory = factoryOrInstance as any;\r\n const typeOfFactory = typeof anyFactory;\r\n return typeOfFactory === 'function' || typeOfFactory === 'object';\r\n }\r\n\r\n getType(): string {\r\n return 'factory method or object';\r\n }\r\n}\r\n\r\n/**\r\n * Validate a basic type.\r\n */\r\nexport class Type implements TypeValidator {\r\n private typeName: string;\r\n\r\n protected typeOf: string;\r\n\r\n constructor(typeName: string, example: T) {\r\n this.typeName = typeName;\r\n this.typeOf = typeof example;\r\n }\r\n\r\n is(u: unknown): u is T {\r\n if (Array.isArray(u)) {\r\n return false;\r\n }\r\n return typeof u === this.typeOf;\r\n }\r\n\r\n getType(): string {\r\n return this.typeName;\r\n }\r\n}\r\n\r\n/**\r\n * Validate an array of the specified type.\r\n *\r\n * This does not validate instances of types. All class instances\r\n * of classes will simply objects.\r\n */\r\nexport class TypeArray implements TypeValidator {\r\n private typeName: string;\r\n\r\n protected typeOf: string;\r\n\r\n constructor(typeName: string, example: T) {\r\n this.typeName = typeName;\r\n this.typeOf = typeof example;\r\n }\r\n\r\n is(u: unknown): u is T {\r\n if (Array.isArray(u)) {\r\n if (u.length > 0) {\r\n return u.every((val) => typeof val === this.typeOf);\r\n }\r\n return true;\r\n }\r\n return false;\r\n }\r\n\r\n getType(): string {\r\n return this.typeName;\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a number and is greater or eval than a minimum.\r\n */\r\nexport class NumberWithMinimum extends Type {\r\n readonly min: number;\r\n\r\n constructor(min: number) {\r\n super(`number with minimum value of ${ min }`, 0);\r\n this.min = min;\r\n }\r\n\r\n override is(u: unknown): u is number {\r\n return typeof u === this.typeOf && (u as number) >= this.min;\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a string and it matches the given expression.\r\n */\r\nexport class StringMatchingRegex extends Type {\r\n readonly expression: RegExp;\r\n\r\n constructor(expression: RegExp) {\r\n super(`string matching ${ expression }`, '');\r\n this.expression = expression;\r\n }\r\n\r\n override is(u: unknown): u is string {\r\n return !!(u as string).match(this.expression);\r\n }\r\n}\r\n\r\n/**\r\n * Validate a value is a function.\r\n */\r\nexport class Function implements TypeValidator {\r\n is(u: unknown): u is (...args: any[]) => void {\r\n // We cannot inspect the parameters and there isn't really\r\n // a generic function type we can instantiate.\r\n // So the type guard is here just to make TS comfortable\r\n // calling something after using this guard.\r\n return typeof u === 'function';\r\n }\r\n\r\n getType(): string {\r\n return 'function';\r\n }\r\n}\r\n\r\nexport class NullableBoolean implements TypeValidator {\r\n is(u: unknown): boolean {\r\n return typeof u === 'boolean' || typeof u === 'undefined' || u === null;\r\n }\r\n\r\n getType(): string {\r\n return 'boolean | undefined | null';\r\n }\r\n}\r\n\r\nexport class BootstrapValidator implements TypeValidator {\r\n messages: string[] = [];\r\n\r\n is(u: unknown): boolean {\r\n if (typeof u !== 'object' || u === null) {\r\n this.messages.push(OptionMessages.invalidOptionValue('bootstrap'));\r\n return false;\r\n }\r\n\r\n try {\r\n const bootstrap = u as IFlagBase[];\r\n for (let flag of bootstrap) {\r\n const hasMandatoryKeys = ['id', 'variation'].every((key) => Object.keys(flag).includes(key));\r\n const keys = Object.keys(flag);\r\n\r\n if (keys.includes('id')) {\r\n this.messages.push(OptionMessages.missingKeyInBootstrapValue('id'));\r\n }\r\n\r\n if (keys.includes('variation')) {\r\n this.messages.push(OptionMessages.missingKeyInBootstrapValue('variation'));\r\n }\r\n\r\n if (this.messages.length > 0) {\r\n return false;\r\n }\r\n }\r\n } catch (_) {\r\n this.messages.push(OptionMessages.wrongOptionType('bootstrap', this.getType(), typeof u));\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n\r\n getType(): string {\r\n return 'IFlagBase[]';\r\n }\r\n}\r\n\r\nexport class UserValidator implements TypeValidator {\r\n messages: string[] = [];\r\n\r\n is(u: unknown): boolean {\r\n if (typeof u !== 'object' || u === null) {\r\n this.messages.push(OptionMessages.mandatory('user'));\r\n return false;\r\n }\r\n\r\n const user = u as any;\r\n\r\n if (typeof user.keyId !== 'string' || user.keyId.trim() === '') {\r\n this.messages.push(OptionMessages.mandatory('user.keyId'));\r\n return false;\r\n }\r\n\r\n if (typeof user.name !== 'string' || user.name.trim() === '') {\r\n this.messages.push(OptionMessages.mandatory('user.name'));\r\n return false;\r\n }\r\n\r\n return true;\r\n }\r\n\r\n getType(): string {\r\n return 'user';\r\n }\r\n}\r\n\r\n// Our reference SDK, Go, parses date/time strings with the time.RFC3339Nano format.\r\n// This regex should match strings that are valid in that format, and no others.\r\n// Acceptable:\r\n// 2019-10-31T23:59:59Z, 2019-10-31T23:59:59.100Z,\r\n// 2019-10-31T23:59:59-07, 2019-10-31T23:59:59-07:00, etc.\r\n// Unacceptable: no \"T\", no time zone designation\r\nconst DATE_REGEX = /^\\d\\d\\d\\d-\\d\\d-\\d\\dT\\d\\d:\\d\\d:\\d\\d(\\.\\d\\d*)?(Z|[-+]\\d\\d(:\\d\\d)?)/;\r\n\r\n/**\r\n * Validate a value is a date. Values which are numbers are treated as dates and any string\r\n * which if compliant with `time.RFC3339Nano` is a date.\r\n */\r\nexport class DateValidator implements TypeValidator {\r\n is(u: unknown): boolean {\r\n return typeof u === 'number' || (typeof u === 'string' && DATE_REGEX.test(u));\r\n }\r\n\r\n getType(): string {\r\n return 'date';\r\n }\r\n}\r\n\r\n/**\r\n * Validates that a string is a valid kind.\r\n */\r\nexport class KindValidator extends StringMatchingRegex {\r\n constructor() {\r\n super(/^(\\w|\\.|-)+$/);\r\n }\r\n\r\n override is(u: unknown): u is string {\r\n return super.is(u) && u !== 'kind';\r\n }\r\n}\r\n\r\n/**\r\n * A set of standard type validators.\r\n */\r\nexport class TypeValidators {\r\n static readonly String = new Type('string', '');\r\n\r\n static readonly Number = new Type('number', 0);\r\n\r\n static readonly ObjectOrFactory = new FactoryOrInstance();\r\n\r\n static readonly Object = new Type('object', {});\r\n\r\n static readonly StringArray = new TypeArray('string[]', '');\r\n\r\n static readonly Boolean = new Type('boolean', true);\r\n\r\n static readonly User = new Type('object', {});\r\n\r\n static readonly Bootstrap = new Type('object', {});\r\n\r\n static readonly Function = new Function();\r\n\r\n static createTypeArray(typeName: string, example: T) {\r\n return new TypeArray(typeName, example);\r\n }\r\n\r\n static numberWithMin(min: number): NumberWithMinimum {\r\n return new NumberWithMinimum(min);\r\n }\r\n\r\n static stringMatchingRegex(expression: RegExp): StringMatchingRegex {\r\n return new StringMatchingRegex(expression);\r\n }\r\n\r\n static readonly Date = new DateValidator();\r\n\r\n static readonly Kind = new KindValidator();\r\n static readonly NullableBoolean = new NullableBoolean();\r\n}","export * from './ClientContext';\r\nexport * from './IClientContext';\r\nexport * from './IOptions';\r\nexport * from './IUser';\r\nexport * from './IValidatedOptions';\r\nexport * from './OptionMessages';\r\nexport * from './UserBuilder';\r\nexport * from './Validators';","import { IInfo, IPlatformData, ISdkData } from \"../IInfo\";\r\nimport { name, version } from '../../version';\r\n\r\n\r\nexport default class BrowserInfo implements IInfo {\r\n get appType(): string {\r\n return 'Browser-Client-SDK';\r\n }\r\n\r\n platformData(): IPlatformData {\r\n return {\r\n os: {},\r\n name: 'Browser',\r\n additional: {},\r\n };\r\n }\r\n\r\n sdkData(): ISdkData {\r\n return {\r\n name: name,\r\n version: version,\r\n userAgentBase: this.appType\r\n };\r\n }\r\n}","import { IPlatform } from \"../IPlatform\";\r\nimport { IInfo } from \"../IInfo\";\r\nimport { IRequests } from \"../requests\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport BrowserInfo from \"./BrowserInfo\";\r\nimport { BrowserRequests } from \"./BrowserRequests\";\r\nimport { IWebSocketWithEvents } from \"../IWebSocket\";\r\nimport BrowserWebSocket from \"./BrowserWebSocket\";\r\n\r\nexport default class BrowserPlatform implements IPlatform {\r\n info: IInfo = new BrowserInfo();\r\n\r\n requests: IRequests;\r\n webSocket: IWebSocketWithEvents;\r\n\r\n constructor(options: IOptions) {\r\n this.requests = new BrowserRequests();\r\n this.webSocket = new BrowserWebSocket();\r\n }\r\n}","import { IRequestOptions, IRequests } from \"../requests\";\r\n\r\nexport class BrowserRequests implements IRequests {\r\n fetch(url: string, options: IRequestOptions = {}): Promise {\r\n return fetch(url, options);\r\n }\r\n}","import { IWebSocket, IWebSocketConfig } from \"../IWebSocket\";\r\nimport { Emits } from \"../../utils/Emits\";\r\nimport { IEventEmitter } from \"../../utils/IEventEmitter\";\r\nimport { EventEmitter } from \"../../utils/EventEmitter\";\r\nimport { generateConnectionToken } from \"../../data-sync/utils\";\r\nimport { StreamResponseEventType } from \"../../data-sync/types\";\r\nimport { IUser } from \"../../options/IUser\";\r\n\r\nconst socketConnectionIntervals = [1000, 3000, 5000, 7000, 11000, 13000, 30000, 60000];\r\n\r\nclass BrowserWebSocket implements IWebSocket {\r\n emitter: IEventEmitter;\r\n private ws?: WebSocket;\r\n private retryCounter = 0;\r\n private closed: boolean = false;\r\n\r\n private _config: IWebSocketConfig = {} as IWebSocketConfig;\r\n\r\n constructor() {\r\n this.emitter = new EventEmitter();\r\n }\r\n\r\n identify(user: IUser) {\r\n this._config.user = user;\r\n this.doDataSync();\r\n }\r\n\r\n connect() {\r\n let that = this;\r\n const startTime = Date.now();\r\n const url = this._config.streamingUri.replace(/^http/, 'ws') + `?type=client&token=${ generateConnectionToken(this._config.sdkKey) }`;\r\n this.ws = new WebSocket(url);\r\n\r\n // Connection opened\r\n that.ws?.addEventListener('open', function (this: WebSocket, event) {\r\n // this is the websocket instance to which the current listener is binded to, it's different from that.socket\r\n that._config.logger.info(`WebSocket connection succeeded, connection time: ${ Date.now() - startTime } ms`);\r\n that.doDataSync();\r\n that.sendPingMessage();\r\n });\r\n\r\n // Connection closed\r\n that.ws?.addEventListener('close', function (event) {\r\n that._config.logger.warn('WebSocket closed');\r\n if (event.code === 4003) { // do not reconnect when 4003\r\n return;\r\n }\r\n\r\n that.reconnect();\r\n });\r\n\r\n // Connection error\r\n that.ws?.addEventListener('error', function (event) {\r\n // reconnect\r\n that._config.logger.debug('error');\r\n });\r\n\r\n // Listen for messages\r\n that.ws?.addEventListener('message', function (event) {\r\n const message = JSON.parse(event.data as string);\r\n if (message.messageType === 'data-sync') {\r\n switch (message.data.eventType) {\r\n case StreamResponseEventType.patch:\r\n that.emitter.emit('patch', message);\r\n break;\r\n case StreamResponseEventType.full:\r\n that.emitter.emit('put', message);\r\n break;\r\n }\r\n }\r\n });\r\n }\r\n\r\n close() {\r\n this.closed = true;\r\n this.ws?.close(4003, 'The client is closed by user');\r\n this.ws = undefined;\r\n }\r\n\r\n config(param: IWebSocketConfig) {\r\n if (param.emitter) {\r\n this.emitter = param.emitter;\r\n }\r\n\r\n this._config = {...param};\r\n }\r\n\r\n private sendPingMessage() {\r\n const payload = {\r\n messageType: 'ping',\r\n data: null\r\n };\r\n\r\n setTimeout(() => {\r\n try {\r\n if (this.ws?.readyState === WebSocket.OPEN) {\r\n this._config.logger.debug('sending ping')\r\n this.ws.send(JSON.stringify(payload));\r\n this.sendPingMessage();\r\n } else {\r\n this._config.logger.debug(`socket closed at ${ new Date() }`);\r\n }\r\n } catch (err) {\r\n this._config.logger.debug(err);\r\n }\r\n }, this._config.pingInterval);\r\n }\r\n\r\n private doDataSync() {\r\n const payload = {\r\n messageType: 'data-sync',\r\n data: {\r\n timestamp: this._config.getStoreTimestamp(),\r\n user: this._config.user\r\n }\r\n };\r\n\r\n try {\r\n if (this.ws?.readyState === WebSocket.OPEN) {\r\n this._config.logger.debug('requesting data');\r\n this.ws?.send(JSON.stringify(payload));\r\n } else {\r\n this._config.logger.error(`not requesting data because socket not open`);\r\n }\r\n } catch (err) {\r\n this._config.logger.debug(err);\r\n }\r\n }\r\n\r\n private reconnect() {\r\n if (!this.closed) {\r\n this.ws = undefined;\r\n const waitTime = socketConnectionIntervals[Math.min(this.retryCounter++, socketConnectionIntervals.length - 1)];\r\n this._config.logger.info(`The client will try to reconnect in ${ waitTime } milliseconds.`);\r\n setTimeout(() => {\r\n this._config.logger.info(`The client is trying to reconnect, flag evaluation results may be stale until reconnected, waited for: ${ waitTime } milliseconds`);\r\n this.connect();\r\n }, waitTime);\r\n }\r\n }\r\n}\r\n\r\nexport default Emits(BrowserWebSocket);","import { FbClientCore } from \"../../FbClientCore\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport { BasicLogger } from \"../../logging/BasicLogger\";\r\nimport { EventEmitter } from \"../../utils/EventEmitter\";\r\nimport { SafeLogger } from \"../../logging/SafeLogger\";\r\nimport { Emits } from \"../../utils/Emits\";\r\nimport { IEventEmitter } from \"../../utils/IEventEmitter\";\r\nimport BrowserPlatform from \"./BrowserPlatform\";\r\nimport LocalStorageStore from \"./LocalStorageStore\";\r\nimport { IPlatform } from \"../IPlatform\";\r\n\r\n/**\r\n * @ignore\r\n */\r\nclass FbClient extends FbClientCore {\r\n emitter: IEventEmitter;\r\n\r\n constructor(options: IOptions, platform: IPlatform | undefined = undefined) {\r\n const fallbackLogger = new BasicLogger({\r\n level: 'none',\r\n destination: console.log\r\n });\r\n\r\n const logger = options.logger ? new SafeLogger(options.logger, fallbackLogger) : fallbackLogger;\r\n\r\n const emitter = new EventEmitter(logger);\r\n\r\n let { store } = options;\r\n if (!store) {\r\n store = new LocalStorageStore(options);\r\n }\r\n\r\n super(\r\n {...options, logger, store },\r\n platform ?? new BrowserPlatform({...options, logger}),\r\n {\r\n onError: (err: Error) => {\r\n if (emitter.listenerCount('error')) {\r\n emitter.emit('error', err);\r\n }\r\n },\r\n onFailed: (err: Error) => {\r\n emitter.emit('failed', err);\r\n },\r\n onReady: () => {\r\n emitter.emit('ready');\r\n },\r\n onUpdate: (keys: string[]) => {\r\n emitter.emit('update', [keys]);\r\n keys.forEach((key) => emitter.emit(`update:${ key }`, key));\r\n },\r\n hasEventListeners: () =>\r\n emitter\r\n .eventNames()\r\n .some(\r\n (name) =>\r\n name === 'update' || (typeof name === 'string' && name.startsWith('update:')),\r\n ),\r\n },\r\n );\r\n\r\n this.emitter = emitter;\r\n }\r\n}\r\n\r\nexport default Emits(FbClient);","import {\r\n StoreStorageKey,\r\n IStoreDataStorage, CurrentUserStorageKey\r\n} from \"../../store/store\";\r\nimport { IOptions } from \"../../options/IOptions\";\r\nimport { BaseStore } from \"../../store/BaseStore\";\r\nimport { ILogger } from \"../../logging\";\r\nimport { serializeUser } from \"../../utils/serializeUser\";\r\n\r\nexport default class LocalStorageStore extends BaseStore {\r\n private logger: ILogger;\r\n\r\n constructor(options: IOptions) {\r\n super();\r\n\r\n this.logger = options.logger!;\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get description(): string {\r\n return 'local-storage-store'\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async saveUser(): Promise {\r\n localStorage.setItem(CurrentUserStorageKey, serializeUser(this._user));\r\n }\r\n\r\n protected override async dumpStoreToStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n localStorage.setItem(storageKey, JSON.stringify(this.store));\r\n }\r\n\r\n protected override async loadStoreFromStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n const dataStoreStr = localStorage.getItem(storageKey);\r\n let store: IStoreDataStorage | null = null;\r\n\r\n try {\r\n if (dataStoreStr && dataStoreStr.trim().length > 0) {\r\n store = JSON.parse(dataStoreStr);\r\n }\r\n } catch (err) {\r\n this.logger.error(`error while loading local data store: ${storageKey}`, err);\r\n }\r\n\r\n if (!!store) {\r\n this.store = store;\r\n } else {\r\n this.store = {\r\n flags: {},\r\n version: 0\r\n };\r\n }\r\n }\r\n}","export * from './IInfo';\r\nexport * from './IStore';\r\nexport * from './IPlatform';\r\nexport * from './IWebSocket';\r\nexport * from './requests';\r\nexport * from './browser/BrowserRequests';\r\n\r\nimport BrowserWebSocket from './browser/BrowserWebSocket';\r\n\r\nexport {\r\n BrowserWebSocket\r\n};","import { IStore } from \"../platform\";\r\nimport { IKeyedStoreItem, IStoreDataStorage, IStoreItem, IStoreKindData } from \"./store\";\r\nimport { IUser } from \"../options\";\r\nimport { IDataKind } from \"../IDataKind\";\r\n\r\nexport class BaseStore implements IStore {\r\n protected store: IStoreDataStorage = {} as IStoreDataStorage;\r\n\r\n protected initCalled = false;\r\n\r\n protected _user: IUser = {} as IUser;\r\n\r\n constructor() {\r\n }\r\n\r\n async identify(user: IUser) {\r\n this._user = {...user};\r\n\r\n await this.saveUser();\r\n await this.loadStoreFromStorage();\r\n }\r\n\r\n get user(): IUser {\r\n return this._user;\r\n }\r\n\r\n protected async addItem(kind: IDataKind, key: string, item: IStoreItem) {\r\n let items = this.store[kind.namespace];\r\n if (!items) {\r\n items = {};\r\n this.store[kind.namespace] = items;\r\n }\r\n if (Object.hasOwnProperty.call(items, key)) {\r\n const old = items[key];\r\n if (!old || old.version < item.version) {\r\n items[key] = item;\r\n }\r\n } else {\r\n items[key] = item;\r\n }\r\n\r\n if (item.version > this.store.version) {\r\n this.store.version = item.version;\r\n }\r\n\r\n await this.dumpStoreToStorage();\r\n }\r\n\r\n get(kind: IDataKind, key: string): IStoreItem | null {\r\n const items = this.store[kind.namespace];\r\n if (items) {\r\n if (Object.prototype.hasOwnProperty.call(items, key)) {\r\n const item = items[key];\r\n if (item) {\r\n return item;\r\n }\r\n }\r\n }\r\n return null;\r\n }\r\n\r\n all(kind: IDataKind): [IStoreKindData, number] {\r\n const result: IStoreKindData = {};\r\n const items = this.store[kind.namespace] ?? {};\r\n Object.entries(items).forEach(([key, item]) => {\r\n if (item) {\r\n result[key] = item;\r\n }\r\n });\r\n\r\n return [result, this.store.version];\r\n }\r\n\r\n async init(allData: IStoreDataStorage) {\r\n this.store = allData as IStoreDataStorage;\r\n\r\n Object.keys(allData).map(namespace => {\r\n Object.entries(allData[namespace]).forEach(([_, item]) => {\r\n const ele = item as IStoreItem;\r\n if (ele.version > this.store.version) {\r\n this.store.version = ele.version;\r\n }\r\n })\r\n });\r\n\r\n await this.dumpStoreToStorage();\r\n this.initCalled = true;\r\n }\r\n\r\n async upsert(kind: IDataKind, data: IKeyedStoreItem) {\r\n await this.addItem(kind, data.key, data);\r\n }\r\n\r\n initialized(): boolean {\r\n return this.initCalled;\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get version(): number {\r\n return this.store.version;\r\n }\r\n\r\n // This getter needs to be overridden in the child class\r\n get description(): string {\r\n return '';\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async saveUser(): Promise {\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async loadStoreFromStorage(): Promise {\r\n }\r\n\r\n // This method needs to be overridden in the child class\r\n protected async dumpStoreToStorage(): Promise {\r\n }\r\n}","import { IDataKind } from \"../IDataKind\";\r\n\r\nexport default class DataKinds {\r\n static readonly Flags: IDataKind = {\r\n namespace: 'flags'\r\n };\r\n}","import {\r\n StoreStorageKey,\r\n IStoreDataStorage\r\n} from \"./store\";\r\nimport { BaseStore } from \"./BaseStore\";\r\n\r\nexport default class InMemoryStore extends BaseStore {\r\n private allStores: { [DataStoreStorageKey: string]: IStoreDataStorage } = {};\r\n\r\n constructor() {\r\n super();\r\n }\r\n\r\n /* eslint-disable class-methods-use-this */\r\n close(): void {\r\n // For the LocalStorage store this is a no-op.\r\n }\r\n\r\n get description(): string {\r\n return 'in-memory-store'\r\n }\r\n\r\n protected async saveUser(): Promise {\r\n // For in-memory store, this is a no-op.\r\n }\r\n\r\n protected override async dumpStoreToStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n this.allStores[storageKey] = {...this.store};\r\n }\r\n\r\n protected override async loadStoreFromStorage() {\r\n const storageKey = `${StoreStorageKey}-${this._user.keyId}`;\r\n\r\n this.store = this.allStores[storageKey] ?? { flags: {}, version: 0 };\r\n }\r\n}","export * from './DataKinds';\r\nexport * from './IDataSourceUpdates';\r\nexport * from './InMemoryStore';\r\nexport * from './serialization';\r\nexport * from './store';\r\nexport * from './BaseStore';","import { IFlag } from \"../evaluation/data/IFlag\";\r\nimport DataKinds from \"./DataKinds\";\r\nimport { IVersionedData } from \"../IVersionedData\";\r\nimport { IDataKind } from \"../IDataKind\";\r\n\r\nexport interface Flags {\r\n flags: { [name: string]: IFlag };\r\n}\r\n\r\ntype VersionedFlag = IVersionedData & IFlag;\r\n\r\nexport interface IPatchData {\r\n data: VersionedFlag;\r\n kind: IDataKind;\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport function deserializeAll(flags: IFlag[]): Flags {\r\n const result = {\r\n [DataKinds.Flags.namespace]: {}\r\n };\r\n\r\n if (flags?.length) {\r\n result[DataKinds.Flags.namespace] = flags.reduce((acc: any, cur: any) => {\r\n acc[cur.id] = {...cur, version: cur.timestamp || 0, key: cur.id, variations: cur.variationOptions};\r\n return acc;\r\n }, {});\r\n }\r\n\r\n return result as any as Flags;\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport function deserializePatch(flags: IFlag[]): IPatchData[] {\r\n const result = [\r\n ...flags?.map(item => ({\r\n data: {\r\n ...item,\r\n version:item.timestamp,\r\n key: item.id,\r\n variations: item.variationOptions\r\n },\r\n kind: DataKinds.Flags\r\n })) || []\r\n ];\r\n\r\n return result as any as IPatchData[];\r\n}\r\n","export const StoreStorageKey = 'fb-datastore';\r\n\r\nexport const CurrentUserStorageKey = 'fb-user';\r\n\r\n/**\r\n * Represents an item which can be stored in the feature store.\r\n */\r\nexport interface IStoreItem {\r\n version: number;\r\n\r\n // The actual data associated with the item.\r\n [attribute: string]: any;\r\n}\r\n\r\n/**\r\n * When upserting an item it must contain a key.\r\n */\r\nexport interface IKeyedStoreItem extends IStoreItem {\r\n key: string;\r\n}\r\n\r\n/**\r\n * Represents the storage for a single kind of data. e.g. 'flag' or 'segment'.\r\n */\r\nexport interface IStoreKindData {\r\n [key: string]: IStoreItem;\r\n}\r\n\r\n/**\r\n * Represents the storage for the full data store.\r\n */\r\nexport interface IStoreDataStorage {\r\n flags: IStoreKindData;\r\n version: number;\r\n\r\n // This attribute is to ingore the type check error\r\n [attribute: string]: any;\r\n}","import { IEventEmitter } from \"./IEventEmitter\";\r\n\r\nexport type EventableConstructor = new (...args: any[]) => T;\r\nexport type Eventable = EventableConstructor<{ emitter: IEventEmitter }>;\r\n\r\n/**\r\n * Adds the implementation of an event emitter to something that contains\r\n * a field of `emitter` with type `EventEmitter`.\r\n * @param Base The class to derive the mixin from.\r\n * @returns A class extending the base with an event emitter.\r\n */\r\nexport function Emits(Base: TBase) {\r\n return class WithEvents extends Base implements IEventEmitter {\r\n on(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.on(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n addListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.addListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n once(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.once(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n removeListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.removeListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n off(eventName: string | symbol, listener: (...args: any) => void, context?: any): this {\r\n this.emitter.off(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n removeAllListeners(event?: string | symbol): this {\r\n this.emitter.removeAllListeners(event);\r\n return this;\r\n }\r\n\r\n listeners(eventName: string | symbol): Function[] {\r\n return this.emitter.listeners(eventName);\r\n }\r\n\r\n emit(eventName: string | symbol, ...args: any[]): this {\r\n this.emitter.emit(eventName, args);\r\n return this;\r\n }\r\n\r\n listenerCount(eventName: string | symbol): number {\r\n return this.emitter.listenerCount(eventName);\r\n }\r\n\r\n prependListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.prependListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n prependOnceListener(eventName: string | symbol, listener: (...args: any[]) => void, context?: any): this {\r\n this.emitter.prependOnceListener(eventName, listener, context);\r\n return this;\r\n }\r\n\r\n eventNames(): (string | symbol)[] {\r\n return this.emitter.eventNames();\r\n }\r\n\r\n maybeReportError (error: any): this {\r\n this.emitter.maybeReportError(error);\r\n return this;\r\n }\r\n };\r\n}","import { ILogger } from \"../logging/ILogger\";\r\nimport { IEventEmitter } from \"./IEventEmitter\";\r\n\r\ninterface Events {\r\n [key: string | symbol]: {\r\n handler: (...args: any[]) => void;\r\n context: any;\r\n }[];\r\n}\r\n\r\nexport class EventEmitter implements IEventEmitter {\r\n private events: Events = {};\r\n\r\n constructor(private logger?: ILogger) {}\r\n\r\n private listeningTo (event: string) {\r\n return !!this.events[event];\r\n }\r\n\r\n on (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n this.events[event] = this.events[event] || [];\r\n this.events[event] = this.events[event].concat({\r\n handler: handler,\r\n context: context,\r\n });\r\n\r\n return this;\r\n }\r\n\r\n addListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n return this.on(event, handler, context);\r\n }\r\n\r\n once (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n const onceHandler = (...args: any[]) => {\r\n this.off(event, onceHandler, context);\r\n handler.apply(context, args);\r\n };\r\n return this.on(event, onceHandler, context);\r\n }\r\n\r\n off (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n if (!this.events[event]) {\r\n return this;\r\n }\r\n for (let i = 0; i < this.events[event].length; i++) {\r\n if (this.events[event][i].handler === handler && this.events[event][i].context === context) {\r\n this.events[event] = this.events[event].slice(0, i).concat(this.events[event].slice(i + 1));\r\n }\r\n }\r\n\r\n return this;\r\n }\r\n\r\n removeListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n return this.off(event, handler, context);\r\n }\r\n\r\n removeAllListeners (event?: string | symbol): this {\r\n if (event) {\r\n delete this.events[event];\r\n } else {\r\n this.events = {};\r\n }\r\n\r\n return this;\r\n }\r\n\r\n listeners (event: string | symbol): Function[] {\r\n return this.events[event] ? this.events[event].map((event) => event.handler) : [];\r\n }\r\n\r\n emit (event: string | symbol, ...args: any[]): this {\r\n if (!this.events[event]) {\r\n return this;\r\n }\r\n // Copy the list of handlers before iterating, in case any handler adds or removes another handler.\r\n // Any such changes should not affect what we do here-- we want to notify every handler that existed\r\n // at the moment that the event was fired.\r\n const copiedHandlers = [...this.events[event]];\r\n for (let i = 0; i < copiedHandlers.length; i++) {\r\n copiedHandlers[i].handler.apply(copiedHandlers[i].context, Array.prototype.slice.call(arguments, 1));\r\n }\r\n\r\n return this;\r\n }\r\n\r\n listenerCount (event: string | symbol): number {\r\n return this.events[event] ? this.events[event].length : 0;\r\n }\r\n\r\n prependListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n this.events[event] = this.events[event] || [];\r\n this.events[event] = [\r\n {\r\n handler: handler,\r\n context: context,\r\n },\r\n ...this.events[event]\r\n ];\r\n\r\n return this;\r\n }\r\n\r\n prependOnceListener (event: string | symbol, handler: (...args: any[]) => void, context?: any): this {\r\n const onceHandler = (...args: any[]) => {\r\n this.off(event, onceHandler, context);\r\n handler.apply(context, args);\r\n };\r\n return this.prependListener(event, onceHandler, context);\r\n }\r\n\r\n eventNames (): (string | symbol)[] {\r\n return Object.keys(this.events);\r\n }\r\n\r\n maybeReportError (error: any): this {\r\n if (!error) {\r\n return this;\r\n }\r\n if (this.listeningTo('error')) {\r\n this.emit('error', error);\r\n } else {\r\n this.logger?.error(error);\r\n }\r\n\r\n return this;\r\n }\r\n}","import { Regex } from \"./Regex\";\r\n\r\nexport interface IConvertResult {\r\n isSucceeded: boolean,\r\n value?: TValue\r\n}\r\n\r\nexport class ValueConverters {\r\n static bool(value: string): IConvertResult {\r\n if (value?.toUpperCase() === 'TRUE') {\r\n return ValueConverters.success(true);\r\n }\r\n\r\n if (value?.toUpperCase() === 'FALSE') {\r\n return ValueConverters.success(false);\r\n }\r\n\r\n return ValueConverters.error();\r\n }\r\n\r\n static number(value: string): IConvertResult {\r\n const num = Number(value);\r\n\r\n if (Number.isNaN(num)) {\r\n return ValueConverters.error();\r\n }\r\n\r\n return ValueConverters.success(num);\r\n }\r\n\r\n static string(value: string): IConvertResult {\r\n return ValueConverters.success(value);\r\n }\r\n\r\n static json(value: string): IConvertResult {\r\n try {\r\n const val = JSON.parse(value);\r\n return ValueConverters.success(val);\r\n } catch (err) {\r\n return ValueConverters.error();\r\n }\r\n }\r\n\r\n private static success(value: TValue): IConvertResult {\r\n return {\r\n isSucceeded: true,\r\n value: value\r\n }\r\n }\r\n\r\n private static error(): IConvertResult {\r\n return {\r\n isSucceeded: false\r\n }\r\n }\r\n}","// This function is designed to remove any trailing forward slashes at the end of the provided URI string\r\nexport function canonicalizeUri(uri: string): string {\r\n return uri.replace(/\\/+$/, '');\r\n}","/**\r\n * Wait before calling the same function. Useful for expensive calls.\r\n * Adapted from https://amitd.co/code/typescript/debounce.\r\n *\r\n * @return The debounced function.\r\n *\r\n * @example\r\n *\r\n * ```js\r\n * const debouncedFunction = debounce(e => {\r\n * console.log(e);\r\n * }, 5000);\r\n *\r\n * // Console logs 'Hello world again ' after 5 seconds\r\n * debouncedFunction('Hello world');\r\n * debouncedFunction('Hello world again');\r\n * ```\r\n * @param fn The function to be debounced.\r\n * @param delayMs Defaults to 5 seconds.\r\n */\r\nexport const debounce = ReturnType>(\r\n fn: T,\r\n delayMs: number = 5000,\r\n): ((...args: Parameters) => void) => {\r\n let timer: ReturnType;\r\n\r\n return (...args: Parameters) => {\r\n clearTimeout(timer);\r\n timer = setTimeout(() => {\r\n fn(...args);\r\n }, delayMs);\r\n };\r\n};\r\n","import { IInfo } from \"../platform/IInfo\";\r\n\r\nexport type Headers = {\r\n Authorization: string;\r\n 'User-Agent': string;\r\n 'Content-Type': string;\r\n};\r\n\r\nexport function defaultHeaders(\r\n sdkKey: string,\r\n info: IInfo\r\n): Headers {\r\n const {userAgentBase, version} = info.sdkData();\r\n\r\n const headers: Headers = {\r\n 'Content-Type': 'application/json',\r\n 'User-Agent': `${ userAgentBase ?? info.appType }/${ version }`,\r\n 'Authorization': sdkKey\r\n };\r\n\r\n return headers;\r\n}\r\n\r\nexport function httpErrorMessage(\r\n err: {\r\n status: number;\r\n message: string;\r\n },\r\n context: string,\r\n retryMessage?: string,\r\n): string {\r\n let desc;\r\n if (err.status) {\r\n desc = `error ${ err.status }${ err.status === 401 ? ' (invalid SDK key)' : '' }`;\r\n } else {\r\n desc = `I/O error (${ err.message || err })`;\r\n }\r\n const action = retryMessage ?? 'giving up permanently';\r\n return `Received ${ desc } for ${ context } - ${ action }`;\r\n}\r\n","export * from './isNullOrUndefined';\r\nexport * from './sleep';\r\nexport * from './ValueConverters';\r\nexport * from './VoidFunction';\r\nexport * from './serializeUser';\r\nexport * from './debounce';","export function isNullOrUndefined(val: any) {\r\n return val === null || val === undefined;\r\n}","import { IUser } from \"../options/IUser\";\r\n\r\nexport function serializeUser(user: IUser | undefined): string {\r\n if (!user) {\r\n return '';\r\n }\r\n\r\n const builtInProperties = `${user.keyId},${user.name}`;\r\n\r\n const customizedProperties = user.customizedProperties\r\n ?.sort((a, b) => {\r\n const nameA = a.name.toLowerCase();\r\n const nameB = b.name.toLowerCase();\r\n if (nameA < nameB) {\r\n return -1;\r\n }\r\n\r\n if (nameA > nameB) {\r\n return 1;\r\n }\r\n\r\n return 0;\r\n })\r\n .map(p => `${p.name}:${p.value}`)\r\n .join(',');\r\n\r\n return `${builtInProperties},${customizedProperties}`;\r\n}","const sleep = async (delayMillis: number = 1000) =>\r\n new Promise((resolve) => {\r\n setTimeout(resolve, delayMillis);\r\n });\r\n\r\nexport default sleep;","export const version = \"3.0.3\"; export const name = \"@featbit/js-client-sdk\";\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// startup\n// Load entry module and return exports\n// This entry module is referenced by other modules so it can't be inlined\nvar __webpack_exports__ = __webpack_require__(9872);\n"],"names":["root","factory","exports","module","define","amd","a","i","this","validations","startWaitTime","TypeValidators","Number","sdkKey","String","pollingUri","streamingUri","eventsUri","webSocketPingInterval","logger","Object","store","ObjectOrFactory","dataSynchronizer","flushInterval","maxEventsInQueue","pollingInterval","offline","Boolean","dataSyncMode","bootstrap","Bootstrap","user","User","defaultValues","DataSyncModeEnum","STREAMING","sendEvents","options","undefined","constructor","bootstrapProvider","NullBootstrapProvider","errors","validatedOptions","keys","forEach","optionName","optionValue","validator","is","getType","push","wrongOptionTypeBoolean","NumberWithMinimum","min","optionBelowMinimum","UserValidator","messages","wrongOptionType","warn","unknownOption","validateTypesAndNames","error","streamingUriMissing","isNullOrUndefined","EmptyString","pollingUriMissing","eventsUriMissing","partialEndpoint","POLLING","validateEndpoints","canonicalizeUri","length","JsonBootstrapProvider","_","info","Function","dataSynchronizerFactory","storeFactory","Context","valid","message","fromUser","contextForError","keyId","name","trim","context","_user","value","property","customizedProperties","find","x","_options","build","platform","_platform","mode","flags","ClientState","callbacks","state","Initializing","onError","onFailed","onReady","onUpdate","hasEventListeners","config","Error","init","clientContext","identify","dataSourceUpdates","evaluator","populate","eventProcessor","NullEventProcessor","NullDataSynchronizer","initSuccess","DefaultEventProcessor","listeners","createStreamListeners","put","patch","webSocket","version","requests","e","dataSourceErrorHandler","start","all","Flags","setTimeout","initialized","msg","Failed","rejectionReason","initReject","Initialized","waitForInitialization","initializedPromise","Promise","resolve","reject","initResolve","boolVariation","key","defaultValue","evaluateCore","ValueConverters","bool","boolVariationDetail","jsonVariation","json","jsonVariationDetail","numberVariation","number","numberVariationDetail","stringVariation","string","stringVariationDetail","variation","variationDetail","getAllVariations","ClientError","result","map","flagKey","evalResult","evaluate","kind","reason","close","track","eventName","metricValue","metricEvent","MetricEvent","appType","record","flush","callback","err","typeConverter","ReasonKinds","FlagNotFound","toEvalEvent","isSucceeded","WrongType","code","flag","variationOptions","id","data","deserializeAll","dataSet","userKeyId","MinInt","onChange","allData","checkForChanges","doInit","oldData","then","updatedKeys","flatMap","namespace","oldDataForKind","newDataForKind","mergedData","filter","isUpdated","upsert","doUpsert","oldItem","get","newData","createPutListener","onPutCompleteHandler","deserializeData","processJson","initData","debug","createPatchListener","onPatchCompleteHandler","deserializePatch","item","onCompleteHandlers","Map","set","stop","requestor","getStoreTimestamp","errorHandler","stopped","poll","startTime","Date","now","requestData","body","elapsed","sleepFor","Math","max","status","isHttpRecoverable","httpErrorMessage","PollingError","featureFlags","processStreamResponse","JSON","parse","messageType","eventType","StreamResponseEventType","full","timeoutHandle","clearTimeout","headers","defaultHeaders","uri","request","requestUrl","res","fetch","text","timestamp","payload","cb","method","stringify","StreamingError","socket","pingInterval","addListener","event","logConnectionStarted","connect","connectionAttemptStartTime","alphabet","encodeNumber","param","s","slice","split","n","join","replace","timestampCode","toString","floor","random","super","UnexpectedResponseError","EvalResult","flagNotFound","matched","val","Match","targetedVariation","variations","v","EvalEvent","sendToExperiment","VariationDataType","closed","eventQueue","DefaultEventQueue","eventDispatcher","EventDispatcher","flushLoop","flushEvent","FlushEvent","waitForCompletion","shutdown","ShutdownEvent","addEvent","complete","capacity","events","clear","shift","eventsSnapshot","isEmpty","send","retry","DeliveryStatus","Succeeded","FailedAndMustShutDown","serialize","toPayload","queue","maxEventPerRequest","buffer","sender","DefaultEventSender","serializer","DefaultEventSerializer","dispatchLoop","running","PayloadEvent","addEventToBuffer","triggerFlush","snapshot","flushEvents","total","getUniqueEvents","uniqueEvents","hashes","includes","hash","AsyncEvent","getTime","isCompletedPromise","resolveFn","userPayload","metrics","route","numericValue","type","hasObject","m","featureFlagKey","LogPriority","none","LevelNames","BasicLogger","logLevel","level","destination","formatter","tryFormat","args","tryWrite","console","log","prefix","loggerRequirements","fallback","entries","tryStringify","prototype","hasOwnProperty","call","TypeError","indexOf","escapes","d","toNumber","parseInt","toInt","f","parseFloat","toFloat","j","o","O","c","formatString","out","char","charAt","nextChar","configuration","expectedType","actualType","mandatory","invalidOptionValue","missingKeyInBootstrapValue","_keyId","_name","_custom","custom","propertyName","FactoryOrInstance","factoryOrInstance","Array","isArray","typeOfFactory","Type","typeName","example","typeOf","u","TypeArray","every","StringMatchingRegex","expression","match","NullableBoolean","DATE_REGEX","DateValidator","test","KindValidator","createTypeArray","numberWithMin","stringMatchingRegex","StringArray","Kind","platformData","os","additional","sdkData","userAgentBase","BrowserRequests","url","socketConnectionIntervals","Emits","retryCounter","_config","emitter","EventEmitter","doDataSync","that","generateConnectionToken","ws","WebSocket","addEventListener","sendPingMessage","reconnect","emit","readyState","OPEN","waitTime","FbClient","FbClientCore","fallbackLogger","SafeLogger","listenerCount","eventNames","some","startsWith","LocalStorageStore","BaseStore","description","saveUser","localStorage","setItem","CurrentUserStorageKey","serializeUser","dumpStoreToStorage","storageKey","StoreStorageKey","loadStoreFromStorage","dataStoreStr","getItem","BrowserWebSocket","initCalled","addItem","items","old","ele","DataKinds","InMemoryStore","allStores","reduce","acc","cur","Base","on","listener","once","removeListener","off","removeAllListeners","prependListener","prependOnceListener","maybeReportError","listeningTo","handler","concat","onceHandler","apply","copiedHandlers","arguments","toUpperCase","success","num","isNaN","debounce","fn","delayMs","timer","retryMessage","desc","sort","b","nameA","toLowerCase","nameB","p","delayMillis","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__"],"sourceRoot":""} \ No newline at end of file diff --git a/package.json b/package.json index 5044732..364efc4 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@featbit/js-client-sdk", - "version": "3.0.2", + "version": "3.0.3", "description": "https://github.com/featbit/featbit-js-client-sdk", "main": "./dist/esm/index.js", "module": "./dist/esm/index.js", diff --git a/src/FbClientBuilder.ts b/src/FbClientBuilder.ts index c647b6b..ebff296 100644 --- a/src/FbClientBuilder.ts +++ b/src/FbClientBuilder.ts @@ -41,7 +41,7 @@ export class FbClientBuilder { return new FbClient(this._options); } - platform(platform: IPlatform): FbClientBuilder { + platform(platform: IPlatform | undefined): FbClientBuilder { this._platform = platform; return this; } diff --git a/src/version.ts b/src/version.ts index 099ca77..2135ec2 100644 --- a/src/version.ts +++ b/src/version.ts @@ -1 +1 @@ -export const version = "3.0.2"; export const name = "@featbit/js-client-sdk"; +export const version = "3.0.3"; export const name = "@featbit/js-client-sdk";