Skip to content
Draft
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
148 changes: 148 additions & 0 deletions test/OpenFeature.E2ETests/Features/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@
# Test Assets

This directory contains test assets for the OpenFeature specification, including Gherkin test scenarios and structured JSON test data for comprehensive implementation validation.

## Overview

The test assets improve the existing Gherkin test suite by providing structured JSON test data that eliminates the need for manual test data creation. The data includes various flag types with different targeting scenarios to test edge cases and standard behavior.

## Test Data Structure (`test-flags.json`)

The [JSON test data](./test-flags.json) contains flags organized into several categories based on their behavior and purpose:

### Standard Flags
Basic feature flags with straightforward evaluation:
- `boolean-flag`: Boolean flag with variants `on` (true) and `off` (false), defaults to `on`
- `string-flag`: String flag with variants `greeting` ("hi") and `parting` ("bye"), defaults to `greeting`
- `integer-flag`: Integer flag with variants `one` (1) and `ten` (10), defaults to `ten`
- `float-flag`: Float flag with variants `tenth` (0.1) and `half` (0.5), defaults to `half`
- `object-flag`: Object flag with `empty` ({}) and `template` variants, defaults to `template`

### Zero Value Flags
Flags specifically designed to test zero/empty value handling:
- `boolean-zero-flag`: Boolean flag that defaults to `zero` variant (false)
- `string-zero-flag`: String flag that defaults to `zero` variant (empty string "")
- `integer-zero-flag`: Integer flag that defaults to `zero` variant (0)
- `float-zero-flag`: Float flag that defaults to `zero` variant (0.0)
- `object-zero-flag`: Object flag that defaults to `zero` variant (empty object {})

### Targeted Zero Flags
Flags with CEL expressions that can evaluate to zero values based on context:
- `boolean-targeted-zero-flag`: Uses CEL targeting, defaults to `zero` (false)
- `string-targeted-zero-flag`: Uses CEL targeting, defaults to `zero` (empty string)
- `integer-targeted-zero-flag`: Uses CEL targeting, defaults to `zero` (0)
- `float-targeted-zero-flag`: Uses CEL targeting, defaults to `zero` (0.0)
- `object-targeted-zero-flag`: Uses CEL targeting, defaults to `zero` (empty object)

### Disabled Flags
Flags that are statically disabled:
- `boolean-disabled-flag`: Disabled Flag
- `string-disabled-flag`: Disabled Flag
- `integer-disabled-flag`: Disabled Flag
- `float-disabled-flag`: Disabled Flag
- `object-disabled-flag`: Disabled Flag

### Special Testing Flags
Flags for testing edge cases and metadata:
- `metadata-flag`: Boolean flag with rich metadata including string, integer, boolean, and float values
- `complex-targeted`: String flag with complex CEL expression for internal/external user distinction
- `null-default-flag`: Flag with explicitly null default variant
- `undefined-default-flag`: Flag with no default variant defined
- `wrong-flag`: Flag for testing error scenarios

## CEL Expression Variables

The test data uses Common Expression Language (CEL) expressions in the `contextEvaluator` field. Based on the expressions in the test data, the following context variables are expected:

### Available Context Variables
- `email`: User's email address (string)
- `customer`: Boolean flag indicating customer status
- `age`: User's age (integer)

### CEL Expressions Used

#### Simple Email Targeting
```cel
email == 'ballmer@macrosoft.com' ? 'zero' : ''
```
Used in: `boolean-targeted-zero-flag`, `string-targeted-zero-flag`, `integer-targeted-zero-flag`, `float-targeted-zero-flag`, `object-targeted-zero-flag`

#### Complex Multi-Condition Targeting
```cel
!customer && email == 'ballmer@macrosoft.com' && age > 10 ? 'internal' : ''
```
Used in: `complex-targeted`

## Flag Structure Schema

Each flag in the test data follows this structure:

```json
{
"flag-name": {
"variants": {
"variant-key": "variant-value"
},
"defaultVariant": "variant-key-or-null",
"contextEvaluator": "CEL-expression", // Optional
"flagMetadata": {} // Optional
}
}
```

### Key Components
- **variants**: Object containing all possible flag values mapped to variant keys
- **defaultVariant**: The variant key to use when no targeting rules match (can be null or omitted)
- **contextEvaluator**: Optional CEL expression for dynamic targeting
- **flagMetadata**: Optional metadata object containing additional flag information

## Usage

1. **Test Implementation**: Parse the JSON file with your preferred JSON library
2. **Context Setup**: Ensure your test contexts include the required variables (`email`, `customer`, `age`)
3. **CEL Evaluation**: Implement CEL expression evaluation for flags with `contextEvaluator`
4. **Edge Case Testing**: Use the zero flags and special flags to test boundary conditions

## Test Context Examples

For comprehensive testing, use these context combinations:

```json
// Triggers targeted zero variants
{
"targetingKey": "user1",
"email": "ballmer@macrosoft.com",
"customer": false,
"age": 25
}

// Triggers complex targeting
{
"targetingKey": "user2",
"email": "ballmer@macrosoft.com",
"customer": false,
"age": 15
}

// Triggers alternative targeting
{
"targetingKey": "user3",
"email": "jobs@orange.com"
}

// Default behavior (no targeting matches)
{
"targetingKey": "user4",
"email": "test@example.com",
"customer": true,
"age": 30
}
```

## Contributing

When modifying test data:
1. Maintain the category structure (standard, zero, targeted-zero, disabled)
2. Validate CEL expressions for syntax correctness
3. Ensure all required context variables are documented
4. Test both matching and non-matching targeting scenarios
221 changes: 221 additions & 0 deletions test/OpenFeature.E2ETests/Features/test-flags.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,221 @@
{
"boolean-flag": {
"variants": {
"on": true,
"off": false
},
"defaultVariant": "on",
"flagMetadata": null
},
"boolean-disabled-flag": {
"disabled": true,
"variants": {
"on": true,
"off": false
},
"defaultVariant": "on",
"flagMetadata": null
},
"boolean-targeted-zero-flag": {
"variants": {
"zero": false,
"non-zero": true
},
"defaultVariant": "zero",
"contextEvaluator": "email == 'ballmer@macrosoft.com' ? 'zero' : ''"
},
"boolean-zero-flag": {
"variants": {
"zero": false,
"non-zero": true
},
"defaultVariant": "zero"
},
"complex-targeted": {
"variants": {
"internal": "INTERNAL",
"external": "EXTERNAL"
},
"defaultVariant": "external",
"flagMetadata": null,
"contextEvaluator": "!customer && email == 'ballmer@macrosoft.com' && age > 10 ? 'internal' : ''"
},
"float-flag": {
"variants": {
"tenth": 0.1,
"half": 0.5
},
"defaultVariant": "half",
"flagMetadata": null
},
"float-disabled-flag": {
"disabled": true,
"variants": {
"tenth": 0.1,
"half": 0.5
},
"defaultVariant": "half",
"flagMetadata": null
},
"float-targeted-zero-flag": {
"variants": {
"zero": 0.0,
"non-zero": 1.0
},
"defaultVariant": "zero",
"contextEvaluator": "email == 'ballmer@macrosoft.com' ? 'zero' : ''"
},
"float-zero-flag": {
"variants": {
"zero": 0.0,
"non-zero": 1.0
},
"defaultVariant": "zero"
},
"integer-flag": {
"variants": {
"one": 1,
"ten": 10
},
"defaultVariant": "ten",
"flagMetadata": null
},
"integer-disabled-flag": {
"disabled": true,
"variants": {
"one": 1,
"ten": 10
},
"defaultVariant": "ten",
"flagMetadata": null
},
"integer-targeted-zero-flag": {
"variants": {
"zero": 0,
"non-zero": 1
},
"defaultVariant": "zero",
"contextEvaluator": "email == 'ballmer@macrosoft.com' ? 'zero' : ''"
},
"integer-zero-flag": {
"variants": {
"zero": 0,
"non-zero": 1
},
"defaultVariant": "zero"
},
"metadata-flag": {
"variants": {
"on": true,
"off": false
},
"defaultVariant": "on",
"flagMetadata": {
"string": "1.0.2",
"integer": 2,
"boolean": true,
"float": 0.1
}
},
"null-default-flag": {
"variants": {
"on": true,
"off": false
},
"defaultVariant": null
},
"object-flag": {
"variants": {
"empty": {},
"template": {
"showImages": true,
"title": "Check out these pics!",
"imagesPerPage": 100
}
},
"defaultVariant": "template",
"flagMetadata": null
},
"object-disabled-flag": {
"disabled": true,
"variants": {
"empty": {},
"template": {
"showImages": true,
"title": "Check out these pics!",
"imagesPerPage": 100
}
},
"defaultVariant": "template",
"flagMetadata": null
},
"object-targeted-zero-flag": {
"variants": {
"zero": {},
"non-zero": {
"showImages": true,
"title": "Check out these pics!",
"imagesPerPage": 100
}
},
"defaultVariant": "zero",
"contextEvaluator": "email == 'ballmer@macrosoft.com' ? 'zero' : ''"
},
"object-zero-flag": {
"variants": {
"zero": {},
"non-zero": {
"showImages": true,
"title": "Check out these pics!",
"imagesPerPage": 100
}
},
"defaultVariant": "zero"
},
"string-flag": {
"variants": {
"greeting": "hi",
"parting": "bye"
},
"defaultVariant": "greeting",
"flagMetadata": null
},
"string-disabled-flag": {
"disabled": true,
"variants": {
"greeting": "hi",
"parting": "bye"
},
"defaultVariant": "greeting",
"flagMetadata": null
},
"string-targeted-zero-flag": {
"variants": {
"zero": "",
"non-zero": "str"
},
"defaultVariant": "zero",
"contextEvaluator": "email == 'ballmer@macrosoft.com' ? 'zero' : ''"
},
"string-zero-flag": {
"variants": {
"zero": "",
"non-zero": "str"
},
"defaultVariant": "zero"
},
"undefined-default-flag": {
"variants": {
"small": 10,
"big": 1000
}
},
"wrong-flag": {
"variants": {
"one": "uno",
"two": "dos"
},
"defaultVariant": "one",
"flagMetadata": null
}
}
Loading
Loading