Create flag variations
Describes flag variations and how to create them in Optimizely Feature Experimentation.
A flag variation is a reusable group of flag variable values (also called remote feature configuration or remote variables) that let you avoid hard coding values in your code. Instead of waiting for a deployment, you can group them in a flag variation and then update them remotely in the Optimizely Experimentation application.
Optimizely Feature Experimentation dynamically assigns those variable values to your flag based on your flag rules. For information, see Flag variations.
Create flag variations
You can create flag variations using the Feature Experimentation UI or the Feature Experimentation REST API.
Prerequisites
You must create variables in the flag before assigning them to a variation.
Use the Feature Experimentation UI
-
Go to Flags > select a Flag > Variations.
-
Click Add variations.
-
Configure the variation.
- Enter a Name.
- Enter a Key
Note
You cannot change the Key after Save the variation.
- (Optional) Enter a Description.
- Configure the Variables for the variation.
-
Click Save.
Note
When a flag is created, the default variations, On and Off, are automatically generated.
You cannot delete the Off variation.
Use the Optimizely Feature Experimentation REST API
You can use the Optimizely Feature Experimentation REST API Variation endpoints to manage your variations. See the Create a new Variation endpoint for information.
Brainstorm variation ideas with Opal
You can brainstorm with Opal to automatically create variations.
-
Go to Flags > Variations.
-
Click Brainstorm.
-
Enter the hypothesis you want to test and click send (or press Enter). Opal returns suggestions for variations. See Design an effective hypothesis.
-
(Optional) When reviewing Opal's variation suggestions, you can
- Hover over the variation and click Like response or Dislike response to provide feedback on the suggested variations.
- Click Add All to add all the suggestions as variations.
- Click Regenerate for Opal to create variation ideas.
- Click Exit Chat & Configure to close the Opal chat tab and configure your variations.
-
Click on a variation to add it. Click Exit Chat & Configure.
-
Review the new variation and update any suggested configurations, including the suggested default variable values.
-
(Optional) Click Return to chat to brainstorm more variations and repeat steps 4 and 5.
-
Click Save to add your variations.
Implement flag variations
You deliver flag variations through flag rules to control the end-user's experiences. Flag rules can be a targeted delivery, an A/B test, or a Multi-armed bandit optimization.
In the Optimizely Experimentation application, you see flag variations, which let you group and reuse variable values.
In your code implementation, you can use the returned OptimizelyDecision's
variation key to execute code conditionally. But, to take full advantage of variables, you must get the values of the variation's variables directly.
The following code sample shows how you would use flag variables:
Note
This code is indifferent about what type of flag rule the user is in (targeted delivery, A/B test, or Multi-armed bandit), so you can re-use the same code to run different rules.
/**
* Fetch enabled state for the "product_sort" flag.
* Then use flag variations to expose different sorting methods and pagation.
*/
// Define flag variable defaults (if the flag is disabled, you fall back to these values)
var sortMethod = "alphabetical";
var pageLimit = 10;
// Is the flag enabled for the user?
var user = optimizely.CreateUserContext("userId");
var decision = user.Decide("product_sort");
var enabled = decision.Enabled;
/**
* In the online Optimizely app, go define flag variations using
* sort_method and page_limit variables.
* For example, variation_1 might sort by popularity and limit results to 15 pages.
*/
if (enabled)
{
// get flag variable values depending on the variation the user bucketed into
sortMethod = decision.Variables.GetValue<string>("sort_method");
pageLimit = decision.Variables.GetValue<int>("page_limit");
}
// Fetch products using the flag variables, using something like this pseudocode:
var products = productProvider.Get(sortMethod, pageLimit);
// Fetch enabled state for the "product_sort" flag.
// Then use flag variations to expose different sorting methods and pagination.
// Define flag variable defaults (if the flag is disabled, you fall back to these values)
var sort_method = "alphabetical";
var page_limit = 10;
// Is the flag enabled for the user?
var user = await flutterSDK.createUserContext(userId: "user123");
var decisionResponse = await user!.decide(sort_method);
var decision = decisionResponse.decision;
var enabled = decision!.enabled;
// In the online Optimizely app, go define flag variations using sort_method and page_limit variables.
// For example, variation_1 might sort by popularity and limit results to 15 pages.
if (enabled) {
// get flag variable values depending on the variation the user bucketed into
var sort_method = decision.variables["sort_method"];
var page_limit = decision.variables["page_limit"];
}
// Fetch products using the flag variables, using something like this pseudocode:
var products = ProductProvider.get(sort_method, page_limit);
// Fetch enabled state for the "product_sort" flag.
// Then use flag variations to expose different sorting methods and pagation.
//Define flag variable defaults (if the flag is disabled, you fall back to these values)
sortMethod := "alphabetical"
pageLimit := 10
// Is the flag enabled for the user?
user := optimizely.CreateUserContext(userId, nil)
decision := user.Decide("product_sort", nil)
enabled := decision.Enabled
// In the online Optimizely app, go define flag variations using
// sort_method and page_limit variables.
// For example, variation_1 might sort by popularity and limit results to 15 pages.
if enabled {
// get flag variable values depending on the variation the user bucketed into
err1 := decision.Variables.GetValue("sort_method", &sortMethod)
err2 := decision.Variables.GetValue("page_limit", &pageLimit)
}
// Fetch products using the flag variables, using something like this pseudocode:
products := productProvider.get(sortMethod, pageLimit)
/**
* Fetch enabled state for the "product_sort" flag.
* Then use flag variations to expose different sorting methods and pagation.
*/
// Define flag variable defaults (if the flag is disabled, you fall back to these values)
String sortMethod = "alphabetical";
int pageLimit = 10;
// Is the flag enabled for the user?
OptimizelyUserContext user = optimizely.createUserContext("userId");
OptimizelyDecision decision = user.decide("product_sort");
Boolean enabled = decision.getEnabled();
/**
* In the online Optimizely app, go define flag variations using
* sort_method and page_limit variables.
* For example, variation_1 might sort by popularity and limit results to 15 pages.
*/
if (enabled)
{
// get flag variable values depending on the variation the user bucketed into
try {
sortMethod = decision.getVariables().getValue("sort_method", String.class);
pageLimit = decision.getVariables().getValue("page_limit", Integer.class);
} catch (JsonParseException e) {
e.printStackTrace();
}
}
// Fetch products using the flag variables, using something like this pseudocode:
List products = productProvider.get(sortMethod, pageLimit);
// Fetch enabled state for the "product_sort" flag.
// Then use flag variations to expose different sorting methods and pagination.
// Define flag variable defaults (if the flag is disabled, you fall back to these values)
let sortMethod = 'alphabetical';
let pageLimit = 10;
// Is the flag enabled for the user?
const userId = 'user123'
const user = optimizely.createUserContext(userId);
const decision = user.decide('product_sort');
const enabled = decision.enabled;
//In the online Optimizely app, go define flag variations using
// sort_method and page_limit variables.
// For example, variation_1 might sort by popularity and limit results to 15 pages.
if (enabled) {
// get flag variable values depending on the variation the user bucketed into
sortMethod = decision.variables['sort_method'];
pageLimit = decision.variables['page_limit'];
}
// Fetch products using the flag variables, using something like this pseudocode:
const products = productProvider.get(sortMethod, pageLimit);
/*
* Fetch enabled state for the "product_sort" flag.
* Then use flag variations to expose different sorting methods and pagination.
*/
// Define flag variable defaults (if the flag is disabled, you fall back to these values)
$sortMethod = 'alphabetical';
$pageLimit = 10;
// Is the flag enabled for the user?
$userId = "user123";
$user = $optimizely->createUserContext($userId);
$decision = $user->decide('product_sort');
$enabled = $decision->getEnabled();
/**
* In the online Optimizely app, go define flag variations using
* sort_method and page_limit variables.
* For example, variation_1 might sort by popularity and limit results to 15 pages.
*/
if ($enabled) {
// get flag variable values depending on the variation the user bucketed into
$sortMethod = (string) $decision->getVariables()['sort_method'];
$pageLimit = (int) $decision->getVariables()['page_limit'];
}
// Fetch products using the flag variables, using something like this pseudocode:
$products = $productProvider->get($sortMethod, $pageLimit);
"""
Fetch enabled state for the "product_sort" flag.
Then use flag variations to expose different sorting methods and pagination.
"""
# Define flag variable defaults (if the flag is disabled, you fall back to these values)
sort_method = "alphabetical"
page_limit = 10
# Is the flag enabled for the user?
user = optimizely.create_user_context("user123")
decision = user.decide("product_sort")
enabled = decision.enabled
"""
In the online Optimizely app, go define flag variations using
sort_method and page_limit variables.
For example, variation_1 might sort by popularity and limit results to 15 pages.
"""
if enabled:
# get flag variable values depending on the variation the user bucketed into
sort_method = decision.variables["sort_method"]
page_limit = decision.variables["page_limit"]
# Fetch products using the flag variables, using something like this pseudocode:
products = ProductProvider.get(sort_method, page_limit)
// Fetch enabled state for the "product_sort" flag.
// Then use flag variations to expose different sorting methods and pagination.
// Define flag variable defaults (if the flag is disabled, you fall back to these values)
let sort_method = 'alphabetical';
let page_limit = 10;
// Is the flag enabled for the user?
const decision = useDecision('product_sort');
const enabled = decision.enabled;
//In the online Optimizely app, go define flag variations using
// sort_method and page_limit variables.
// For example, variation_1 might sort by popularity and limit results to 15 pages.
if (enabled) {
// get flag variable values depending on the variation the user bucketed into
sortMethod = decision.variables['sort_method'];
pageLimit = decision.variables['page_limit'];
}
// Fetch products using the flag variables, using something like this pseudocode:
const products = productProvider.get(sortMethod, pageLimit);
# frozen_string_literal: true
# Fetch enabled state for the "product_sort" flag.
# Then use flag variations to expose different sorting methods and pagination.
# Define flag variable defaults (if the flag is disabled, you fall back to these values)
sort_method = 'alphabetical'
page_limit = 10
# Is the flag enabled for the user?
user = optimizely.create_user_context(userId)
decision = user.decide('product_sort')
enabled = decision.enabled
# In the online Optimizely app, go define flag variations using
# sort_method and page_limit variables.
# For example, variation_1 might sort by popularity and limit results to 15 pages.
if enabled
# get flag variable values depending on the variation the user bucketed into
sort_method = decision.variables['sort_method']
page_limit = decision.variables['page_limit']
end
# Fetch products using the flag variables, using something like this pseudocode:
products = productProvider.get(sort_method, page_limit)
/**
* Fetch enabled state for the "product_sort" flag.
* Then use flag variations to expose different sorting methods and pagation.
*/
//Define flag variable defaults (if the flag is disabled, you fall back to these values)
var sort_method = "alphabetical"
var page_limit = 10
// Is the flag enabled for the user?
let user = optimizely.createUserContext(userId: userId)
let decision = user.decide(key: "product_sort")
let enabled = decision.enabled
/**
* In the online Optimizely app, go define flag variations using
* sort_method and page_limit variables.
* For example, variation_1 might sort by popularity and limit results to 15 pages.
*/
if enabled {
// get flag variable values depending on the variation the user bucketed into
let sortMethod: String? = decision.variables.getValue(jsonPath: "sort_method")
let pageLimit: Int? = decision.variables.getValue(jsonPath: "page_limit")
}
// Fetch products using the flag variables, using something like this pseudocode:
let products = productProvider.get(sort_method, page_limit)
For more, see the following example usage documentation:
- Android SDK
- Go SDK
- C# SDK
- Flutter SDK
- Java SDK
- Javascript (Browser) SDK
- JavaScript (Node) SDK
- PHP SDK
- Python SDK
- React SDK
- Ruby SDK
- Swift SDK
Delete variation
To delete a variation, go to Flags > select a Flag > Variations. For the variation you want to remove, click Delete variation. Click Save.

You can also delete a variation by clicking Delete variation on the Configure Variation page. Click Save.

Click Undo on each variation before clicking Save to undo the delete. You can click Revert to undo all changes.
Note
You cannot delete the Off variation.
Updated 10 days ago
Use flag variations to build flag delivery rules or experiment rules: