Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@eppo/js-client-sdk-common",
"version": "4.14.2",
"version": "4.14.3",
"description": "Common library for Eppo JavaScript SDKs (web, react native, and node)",
"main": "dist/index.js",
"files": [
Expand Down
68 changes: 19 additions & 49 deletions src/client/eppo-client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,7 @@ export type EppoClientParameters = {
flagConfigurationStore: IConfigurationStore<Flag | ObfuscatedFlag>;
banditVariationConfigurationStore?: IConfigurationStore<BanditVariation[]>;
banditModelConfigurationStore?: IConfigurationStore<BanditParameters>;
overrideStore?: ISyncStore<Variation>;
configurationRequestParameters?: FlagConfigurationRequestParameters;
/**
* Setting this value will have no side effects other than triggering a warning when the actual
Expand Down Expand Up @@ -131,40 +132,33 @@ export default class EppoClient {
private assignmentCache?: AssignmentCache;
// whether to suppress any errors and return default values instead
private isGracefulFailureMode = true;
private expectObfuscated: boolean;
private obfuscationMismatchWarningIssued = false;
private configObfuscatedCache?: boolean;
private requestPoller?: IPoller;
private readonly evaluator = new Evaluator();
private configurationRequestor?: ConfigurationRequestor;
private readonly overrideValidator = new OverrideValidator();

constructor({
eventDispatcher = new NoOpEventDispatcher(),
isObfuscated = false,
isObfuscated,
flagConfigurationStore,
banditVariationConfigurationStore,
banditModelConfigurationStore,
overrideStore,
configurationRequestParameters,
}: {
// Dispatcher for arbitrary, application-level events (not to be confused with Eppo specific assignment
// or bandit events). These events are application-specific and captures by EppoClient#track API.
eventDispatcher?: EventDispatcher;
flagConfigurationStore: IConfigurationStore<Flag | ObfuscatedFlag>;
banditVariationConfigurationStore?: IConfigurationStore<BanditVariation[]>;
banditModelConfigurationStore?: IConfigurationStore<BanditParameters>;
overrideStore?: ISyncStore<Variation>;
configurationRequestParameters?: FlagConfigurationRequestParameters;
isObfuscated?: boolean;
}) {
}: EppoClientParameters) {
this.eventDispatcher = eventDispatcher;
this.flagConfigurationStore = flagConfigurationStore;
this.banditVariationConfigurationStore = banditVariationConfigurationStore;
this.banditModelConfigurationStore = banditModelConfigurationStore;
this.overrideStore = overrideStore;
this.configurationRequestParameters = configurationRequestParameters;
this.expectObfuscated = isObfuscated;

if (isObfuscated !== undefined) {
logger.warn(
'[Eppo SDK] specifying isObfuscated no longer has an effect and will be removed in the next major release; obfuscation ' +
'is now inferred from the configuration, so you can safely remove the option.',
);
}
}

private getConfiguration(): IConfiguration {
Expand All @@ -177,32 +171,6 @@ export default class EppoClient {
);
}

private maybeWarnAboutObfuscationMismatch(configObfuscated: boolean) {
// Don't warn again if we did on the last check.
if (configObfuscated !== this.expectObfuscated && !this.obfuscationMismatchWarningIssued) {
this.obfuscationMismatchWarningIssued = true;
logger.warn(
`[Eppo SDK] configuration obfuscation [${configObfuscated}] does not match expected [${this.expectObfuscated}]`,
);
} else if (configObfuscated === this.expectObfuscated) {
// Reset the warning to false in case the client configuration (re-)enters a mismatched state.
this.obfuscationMismatchWarningIssued = false;
}
}

/**
* This method delegates to the configuration to determine whether it is obfuscated, then caches the actual
* obfuscation state and issues a warning if it hasn't already.
* This method can be removed with the next major update when the @deprecated setIsObfuscated is removed
*/
private isObfuscated(config: IConfiguration) {
if (this.configObfuscatedCache === undefined) {
this.configObfuscatedCache = config.isObfuscated();
}
this.maybeWarnAboutObfuscationMismatch(this.configObfuscatedCache);
return this.configObfuscatedCache;
}

/**
* Validates and parses x-eppo-overrides header sent by Eppo's Chrome extension
*/
Expand Down Expand Up @@ -241,7 +209,6 @@ export default class EppoClient {
// noinspection JSUnusedGlobalSymbols
setFlagConfigurationStore(flagConfigurationStore: IConfigurationStore<Flag | ObfuscatedFlag>) {
this.flagConfigurationStore = flagConfigurationStore;
this.configObfuscatedCache = undefined;
}

// noinspection JSUnusedGlobalSymbols
Expand Down Expand Up @@ -287,8 +254,12 @@ export default class EppoClient {
* @deprecated The client determines whether the configuration is obfuscated by inspection
* @param isObfuscated
*/
// eslint-disable-next-line @typescript-eslint/no-unused-vars
setIsObfuscated(isObfuscated: boolean) {
this.expectObfuscated = isObfuscated;
logger.warn(
'[Eppo SDK] setIsObfuscated no longer has an effect and will be removed in the next major release; obfuscation ' +
'is now inferred from the configuration, so you can safely remove the call to this method.',
);
}

setOverrideStore(store: ISyncStore<Variation>): void {
Expand Down Expand Up @@ -354,7 +325,6 @@ export default class EppoClient {

const pollingCallback = async () => {
if (await configurationRequestor.isFlagConfigExpired()) {
this.configObfuscatedCache = undefined;
return configurationRequestor.fetchAndStoreConfigurations();
}
};
Expand Down Expand Up @@ -977,7 +947,7 @@ export default class EppoClient {
configDetails,
subjectKey,
subjectAttributes,
this.isObfuscated(config),
config.isObfuscated(),
);

// allocationKey is set along with variation when there is a result. this check appeases typescript below
Expand Down Expand Up @@ -1130,7 +1100,7 @@ export default class EppoClient {
);
}

const isObfuscated = this.isObfuscated(config);
const isObfuscated = config.isObfuscated();
const result = this.evaluator.evaluateFlag(
flag,
configDetails,
Expand Down Expand Up @@ -1182,7 +1152,7 @@ export default class EppoClient {
}

private getNormalizedFlag(config: IConfiguration, flagKey: string): Flag | null {
return this.isObfuscated(config)
return config.isObfuscated()
? this.getObfuscatedFlag(config, flagKey)
: config.getFlag(flagKey);
}
Expand Down Expand Up @@ -1349,7 +1319,7 @@ export default class EppoClient {

private buildLoggerMetadata(): Record<string, unknown> {
return {
obfuscated: this.isObfuscated(this.getConfiguration()),
obfuscated: this.getConfiguration().isObfuscated(),
sdkLanguage: 'javascript',
sdkLibVersion: LIB_VERSION,
};
Expand Down
Loading