diff --git a/packages/core/test/TestCaseResult.types.ts b/packages/core/test/TestCaseResult.types.ts index 60420819..d7d6daf3 100644 --- a/packages/core/test/TestCaseResult.types.ts +++ b/packages/core/test/TestCaseResult.types.ts @@ -13,6 +13,8 @@ export interface TestCase { value: FlagValue reason: string errorCode?: string + serialId?: number | null + doLog?: boolean variant?: string flagMetadata?: PrecomputedFlagMetadata } diff --git a/packages/core/test/evaluation/flags-v1.spec.ts b/packages/core/test/evaluation/flags-v1.spec.ts index 67875377..b5bcd6ca 100644 --- a/packages/core/test/evaluation/flags-v1.spec.ts +++ b/packages/core/test/evaluation/flags-v1.spec.ts @@ -26,6 +26,17 @@ describe('Universal Flag Configuration V1', () => { const ufcJson = fs.readFileSync(path.join(fixtureDirectory, 'ufc-config.json'), 'utf8') return JSON.parse(ufcJson) as UniversalFlagConfigurationV1 } + // Keep ordered repeated cases on the same prepared configuration. + const configuration = getUFC() + + const expectMetadata = (details: ResolutionDetails, expected: TestCase['result']) => { + if (expected.serialId !== undefined) { + expect(details.flagMetadata?.__dd_split_serial_id ?? null).toBe(expected.serialId) + } + if (expected.doLog !== undefined) { + expect(details.flagMetadata?.__dd_do_log).toBe(expected.doLog) + } + } const getTestCaseFileNames = (): string[] => { const fixtureFiles = fs.readdirSync(path.join(fixtureDirectory, 'evaluation-cases')).sort() @@ -45,7 +56,6 @@ describe('Universal Flag Configuration V1', () => { context: EvaluationContext, immediate: ExperimentationOptOutOption = false ): ResolutionDetails => { - const configuration = getUFC() if (testCase.variationType === 'BOOLEAN') { return evaluateRulesBasedConfiguration( configuration, @@ -94,7 +104,7 @@ describe('Universal Flag Configuration V1', () => { } it.each(['constructor', '__proto__'])('treats inherited JSON flag key %s as missing', (flagKey) => { - expect(evaluateRulesBasedConfiguration(getUFC(), 'boolean', flagKey, false, {}, logger)).toMatchObject({ + expect(evaluateRulesBasedConfiguration(configuration, 'boolean', flagKey, false, {}, logger)).toMatchObject({ value: false, reason: 'ERROR', errorCode: 'FLAG_NOT_FOUND', @@ -119,6 +129,7 @@ describe('Universal Flag Configuration V1', () => { if (testCase.result.errorCode !== undefined || testCase.result.reason !== 'ERROR') { expect(details.errorCode).toEqual(testCase.result.errorCode) } + expectMetadata(details, testCase.result) }) for (const [capability, mode] of [ @@ -134,6 +145,7 @@ describe('Universal Flag Configuration V1', () => { expect(details.value).toStrictEqual(expected.value) expect(details.reason).toEqual(expected.reason) expect(details.errorCode).toEqual(expected.errorCode) + expectMetadata(details, expected) }) } } diff --git a/packages/core/test/ffe-system-test-data b/packages/core/test/ffe-system-test-data index 1c831fed..b2887620 160000 --- a/packages/core/test/ffe-system-test-data +++ b/packages/core/test/ffe-system-test-data @@ -1 +1 @@ -Subproject commit 1c831fed02a428a1b0a4ac412da9b773e22df257 +Subproject commit b28876200152f00c7d5eb04616f721afa5955c1d diff --git a/packages/node-server/test/ffe-system.spec.ts b/packages/node-server/test/ffe-system.spec.ts index 81d3657a..054b7c62 100644 --- a/packages/node-server/test/ffe-system.spec.ts +++ b/packages/node-server/test/ffe-system.spec.ts @@ -15,6 +15,8 @@ type SystemTestCase = { result: { value: FlagValue reason: string + serialId?: number | null + doLog?: boolean } } @@ -52,10 +54,10 @@ function getTestCases(testCaseFileName: string): SystemTestCase[] { ) as SystemTestCase[] } -async function evaluateTestCase(testCase: SystemTestCase): Promise> { - const provider = new DatadogNodeServerProvider({ exposureChannel }) - provider.setConfiguration(configuration) - +async function evaluateTestCase( + provider: DatadogNodeServerProvider, + testCase: SystemTestCase +): Promise> { const context = { ...(testCase.targetingKey === null ? {} : { targetingKey: testCase.targetingKey }), ...testCase.attributes, @@ -77,12 +79,25 @@ async function evaluateTestCase(testCase: SystemTestCase): Promise { describe.each(getTestCaseFileNames())('should evaluate for %s', (testCaseFileName) => { const testCases = getTestCases(testCaseFileName) + let provider: DatadogNodeServerProvider + + beforeAll(() => { + // Repeated cases must exercise the same provider in fixture order. + provider = new DatadogNodeServerProvider({ exposureChannel }) + provider.setConfiguration(configuration) + }) it.each(testCases)('with context $targetingKey and flag $flag', async (testCase) => { - const details = await evaluateTestCase(testCase) + const details = await evaluateTestCase(provider, testCase) expect(details.value).toEqual(testCase.result.value) expect(details.reason).toEqual(testCase.result.reason) + if (testCase.result.serialId !== undefined) { + expect(details.flagMetadata?.__dd_split_serial_id ?? null).toBe(testCase.result.serialId) + } + if (testCase.result.doLog !== undefined) { + expect(details.flagMetadata?.__dd_do_log).toBe(testCase.result.doLog) + } }) }) })