Creating a number flag

4 minute read

This section describes how to define a number flag.

Understanding number flags

Number flags are flags that can have multiple number values. When you create a number flag in your application, you define the default value and all the other values this flag can have. Like simple boolean flags, the number flag name is derived from the flag variable name.

Creating a container class and defining a feature flag

To add a number flag, you need two things:

  • A container class for your flags

  • A defined flag inside the container class

In the example below, a number flag is defined with the name titleSize. The flag name is derived from the flag variable name. The titleSize flag has a default value of 12.

If you need a number flag to be more dynamic with regards to value, you can define a number flag in the code with only one value (which is also the default value). This will result in a Free Text input field when configuring the flag’s through the CloudBees Feature Management dashboard.

In the example below, the title size can be any one of 12, 14, 18 and 24. By default, it will be 12.

React Native
JavaScript
Node.js
JavaScript SSR
.NET
Python
Android
JDK
C
C Client Side
C++
C++ Client Side
Go
Ruby
Objective C
Swift
const flags = {
  titleSize: new Rox.RoxNumber(12, [12, 14, 18, 24]),
};
const flags = {
  titleSize: new Rox.RoxNumber(12, [12, 14, 18, 24]),
};
const flags = {
  titleSize: new Rox.RoxNumber(12, [12, 14, 18, 24]),
};
import {RoxNumber} from 'rox-ssr';
const flags = {
  titleSize: new Rox.RoxNumber(12, [12, 14, 18, 24]),
};
using Io.Rollout.Rox.Server.Flags;

public class Container : IRoxContainer
{
    public RoxInt titleSize = new RoxInt(5, new List<int>() { 8, 13 });
    public RoxDouble specialNumber = new RoxDouble(3.14, new List<int>() { 2.71, 0.577 });
}
from rox.core.entities.rox_int import RoxInt
from rox.core.entities.rox_double import RoxDouble

class MyContainer:
  def __init__(self):
    self.title_size = RoxInt(5, [8, 13])
    self.special_number = RoxDouble(3.14, [2.71, 0.577])
import io.rollout.configuration.RoxContainer;
import io.rollout.flags.Freeze;
import io.rollout.flags.RoxDouble;
import io.rollout.flags.RoxInt;

public class Container implements RoxContainer {
    public final RoxInt titleSize = new RoxInt(5, new int[]{ 8, 13 }, Freeze.UntilLaunch);
    public final RoxDouble specialNumber = new RoxDouble(3.14, new double[]{ 2.71, 0.577 }, Freeze.UntilLaunch);
}
import io.rollout.configuration.RoxContainer;
import io.rollout.flags.RoxDouble;
import io.rollout.flags.RoxInt;

public class Container implements RoxContainer {
    public final RoxInt titleSize = new RoxInt(5, new int[]{ 8, 13 });
    public final RoxDouble specialNumber = new RoxDouble(3.14, new double[]{ 2.71, 0.577 });
}
#import <rox/server.h>

RoxStringBase* titleSize = rox_add_int_with_options("titleSize", 5, ROX_INT_LIST(8, 13));

RoxStringBase* specialNumber = rox_add_double_with_options("specialNumber", 3.14, ROX_DBL_LIST(2.71, 0.577));
#import <rox/client.h>

RoxStringBase* titleSize = rox_add_int_with_freeze_and_options("titleSize", 5, ROX_INT_LIST(8, 13), RoxFreezeUntilLaunch);

RoxStringBase* specialNumber = rox_add_double_with_freeze_and_options("specialNumber", 3.14, ROX_DBL_LIST(2.71, 0.577), RoxFreezeUntilLaunch);
#import <roxx/server.h>

using namespace Rox;

auto titleSize = Int::Create("titleSize", 5, {8, 13});
auto specialNumber = Double::Create("specialNumber", 3.14, {2.71, 0.577});
#import <roxx/client.h>

using namespace Rox::Client;

auto titleSize = Int::Create("titleSize", 5, {8, 13}, RoxFreezeUntilLaunch);
auto specialNumber = Double::Create("specialNumber", 3.14, {2.71, 0.577}, RoxFreezeUntilLaunch);
import "github.com/rollout/rox-go/server"

type Flags struct {
        EnableTutorial server.RoxFlag
        TitleColors server.RoxString
        Page server.RoxInt
        Percentage server.RoxDouble
}

var flags = & Flags {
        // Define the feature flags
        EnableTutorial: server.NewRoxFlag(false),
        TitleColors: server.NewRoxString("Green", [] string {"White", "Blue", "Green", "Yellow"}),
        Page: sever.NewRoxInt(1, [1, 2, 3]),
        Percentage: server.NewRoxDouble(99.9, [10.5, 50.0, 99.9]),
}
require 'rox/server/rox_server'

class MyContainer:
  attr_reader :title_size, :special_number

  def initialize
    @title_size = Rox::Server::RoxInt.new(5, [8, 13])
    @special_number = Rox::Server::RoxDouble.new(3.14, [2.71, 0.577])
  end
end
#import <ROXCore/ROXCore.h>

@interface Flags : ROXBaseContainer
@property (nonatomic) ROXInt* titleSize;
@property (nonatomic) ROXDouble* specialNumber;
@end

@implementation Flags

- (instancetype)init {
  self = [super init];
  if (self) {
    self.titleSize = [[ROXInt alloc] initWithDefault:5 variations:@[8, 13]];
    self.specialNumber = [[ROXDouble alloc] initWithDefault:3.14 variations:@[2.71, 0.577]];
  }
  return self;
}
public class Flags : RoxContainer {
  let titleSize = RoxInt(withDefault: 5, variations: [8, 13])
  let specialNumber = RoxDouble(withDefault: 3.14, variations: [2.71, 0.577])
}

Registering the container class

Once you have the container class, you need to register its instance to the CloudBees Feature Management SDK. This is done with the Rox.register SDK function.

The namespace parameter is a logical separation between containers and can be used to find flags on the dashboard.

  • A namespace can only be registered once.

React Native
JavaScript
Node.js
JavaScript SSR
.NET
Python
Android
JDK
Go
Ruby
Objective C
Swift
const flags = {
  // define Rox entities here
}
Rox.register('<namespace>', flags);
await Rox.setup('<ROLLOUT_KEY>');
const flags = {
  // define Rox entities here
}
Rox.register('<namespace>', flags);
Rox.setup('<ROLLOUT_KEY>');
const flags = {
  // define Rox entities here
}
Rox.register('<namespace>', flags);
await Rox.setup('<ROLLOUT_KEY>');
import {Rox} from 'rox-ssr';
const flags = {
  // define Rox entities here
}
Rox.register('<namespace>', flags);
Rox.setup('<ROLLOUT_KEY>');
Container flags = new Container();
Rox.Register("<namespace>", flags);
await Rox.Setup(<ROLLOUT_KEY>);
flags = Container()
Rox.register(flags)
Rox.setup(<ROLLOUT_KEY>)
public class App extends Application {

  @Override
  public void onCreate() {
    super.onCreate();

    Container flags = new Container();
    Rox.register("<namespace>", flags);
    Rox.setup(this);

    // This can also be done in the MainActivity if your app doesn't extends the Application class
  }
}
Container flags = new Container();
Rox.register("<namespace>", flags);
Rox.setup("<ROLLOUT_KEY>");
rox := server.NewRox()
rox.Register(flags)
<-rox.Setup("<ROLLOUT_KEY>")
flags = Container.new()
Rox::Server::RoxServer.register(flags)
Rox::Server::RoxServer.setup(<ROLLOUT_KEY>)
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

    [ROX register:[[Flags alloc] init]];
    [ROX setupWithKey:@<ROLLOUT_KEY>];

    return YES;
}
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

  ROX.register("<namespace>", container: Flags())
  ROX.setup(withKey: ROLLOUT_KEY)
  return true
}

Using a number flag

React Native
JavaScript
Node.js
JavaScript SSR
.NET
Python
Android
JDK
C
C++
Go
Ruby
Objective C
Swift
  console.log('Title size is ' + flags.titleColors.getValue());
  console.log('Title size is ' + flags.titleColors.getValue());
  console.log('Title size is ' + flags.titleColors.getValue());
  console.log('Title size is ' + flags.titleColors.getValue());
  Console.WriteLine("Title size is {0}", flags.titleSize.GetValue());
  Console.WriteLine("The special number is {0}, flags.specialNumber.GetValue());
  print('Title size is {}'.format(flags.title_size.get_value()))
  print('The special number is {}'.format(flags.special_number.get_value()))
  System.out.println("Title size is " + flags.titleSize.getValue());
  System.out.println("The special number is " + flags.specialNumber.getValue());
  System.out.println("Title size is " + flags.titleSize.getValue());
  System.out.println("The special number is " + flags.specialNumber.getValue());
  printf("Title size is %d\n", rox_get_int(titleSize));
  printf("The special number is %f\n", rox_get_double(specialNumber));
  std::cout << "Title size is " << titleSize.GetValue() << std::endl;
  std::cout << "The special number is " << specialNumber.GetValue() << std::endl);
  fmt.Println("Page is " + flags.Page.GetValue())
  fmt.Println("Percentage is " + flags.Percentage.GetValue())
  puts("Title size is #{flags.title_size.value}")
  puts("The special number is #{flags.special_number.value}")
  NSLog(@"Title size is %i", flags.titleSize.value);
  NSLog(@"The special number is %f", flags.specialNumber.value);
  print("Title size is " + flags.titleSize.value)
  print("The special number is " + flags.specialNumber.value)

Flag freeze level Flag freeze is available on client side SDKs by default.

  • SDK version 4.x the default is set to untilForeground

  • SDK version 5.0 or later the default is set to none

See Understanding a flag freeze for more information.