Number Flags

Numeric values for rate limits, timeouts, batch sizes, thresholds, and runtime tuning without redeploys.

Introduction

Number flags store a numeric value — integers, decimals, and percentages. Use them when behavior depends on a quantity that operators may need to adjust at runtime.

Applications read Number flags locally from an in-memory snapshot. Evaluation is synchronous — no network request occurs on the read path.

SOASAP stores a single Number type. SDKs map it to a floating-point numeric type (double in .NET and Kotlin, float in Python, number in JavaScript). Whole-number values such as batch sizes and retry counts are stored and returned as numbers — cast or round in application code when you need an integer.

Common use cases:

  • Rate limits — requests per second, concurrent connections, or API quotas
  • Timeouts — HTTP, cache, or job execution timeouts in seconds or milliseconds
  • Batch sizes — records per page, queue batch size, or upload chunk size
  • Retry and backoff — maximum retry attempts or delay multipliers
  • Thresholds — error rates, latency cutoffs, or scoring limits
  • Capacity tuning — pool sizes, buffer limits, or max items per order

When to use Number flags

Use a Number flag when configuration is a single numeric value that may change independently of code deploys.

Scenario Example key Example value Typical default
Rate limit rate-limit-rps 200 100
Request timeout http-timeout-ms 5000 3000
Batch size job-batch-size 50 25
Error threshold error-rate-threshold 0.05 0.01

Rate limit — tune throughput caps per environment. Default to a conservative production-safe limit so a missing flag never opens unlimited traffic.

Request timeout — adjust latency budgets without redeploying. Include the unit in the key name (-ms, -seconds).

Batch size — control worker or query batch sizes. Validate minimum and maximum bounds in code after reading the flag.

Error threshold — trigger alerts or circuit-breaking logic from a fractional rate. Use decimal values where fine-grained tuning matters.

For on/off gates, use Boolean flags. For named variants, use String flags. For multiple related numeric fields or nested options, use JSON flags.

Create a Number flag

Create flags in the SOASAP dashboard. If you have not set up a project yet, start with Create Your First Flag.

  1. Open your project

    Sign in to the dashboard, select your project, and open the environment where you want to configure the initial value — typically Development for local work.

  2. Create the flag

    Add a new flag with the following properties:

    Key rate-limit-rps
    Type Number
    Initial value 100
  3. Save and verify

    Save the flag. Connected SDKs receive the update over SSE. Read the flag in your application to confirm the value matches the dashboard for that environment.

Project vs environment. The flag definition (key and type) belongs to the project — defined once, shared across all environments. The flag value belongs to each environment. The same key can hold different values per environment.

Example configuration for rate-limit-rps:

EnvironmentValue
Development1000
Staging500
Production200

Each environment uses its own API key. The SDK bound to the Production key reads Production values only.

Evaluate a Number flag

SDKs evaluate Number flags locally from an in-memory snapshot. The getter returns a numeric value synchronously — no HTTP request, no disk I/O, and no dependency on SOASAP Cloud availability at read time.

If the stored value is not a number, the SDK returns your explicit default. Getters never throw.

Method names vary by SDK; the semantics are identical.

.NET

var limit = client.GetNumber(
    "rate-limit-rps",
    defaultValue: 100);

var maxItems = (int)client.GetNumber("max-items", defaultValue: 10);

Node.js

const limit = flags.getNumber(
    "rate-limit-rps",
    100,
);

const maxItems = Math.trunc(flags.getNumber("max-items", 10));

Python

limit = flags.get_number(
    "rate-limit-rps",
    100,
)

max_items = int(flags.get_number("max-items", 10))

Kotlin

val limit = client.getNumber(
    "rate-limit-rps",
    defaultValue = 100.0,
)

val maxItems = client.getNumber("max-items", defaultValue = 10.0).toInt()

React / React Native

const limit = useSoasapNumber("rate-limit-rps", 100);

Angular

readonly limit = this.soasap.number("rate-limit-rps", 100);

Flag evaluation never performs network requests. Values are read from the local SDK snapshot. Background synchronization (SSE) updates the snapshot; subsequent reads return the new value without a redeploy. See Local Evaluation.

Explicit defaults

Always provide a default value on every Number read:

client.GetNumber("rate-limit-rps", defaultValue: 100);

The default is returned when:

  • The flag key does not exist in the synchronized snapshot
  • The flag was deleted or disabled in the dashboard for this environment
  • Synchronization has not completed and no cached snapshot is available
  • The restored disk or browser cache is empty or invalid
  • The stored value is not a number (type mismatch — for example, a String flag read with GetNumber)

Explicit defaults are your production safety net. They define application behavior when configuration is missing, stale, or not yet synchronized — without try/catch on the hot path.

Recommendation. Default to the safest operational value — a conservative rate limit, a shorter timeout, or a smaller batch size. SOASAP does not enforce min/max bounds; validate ranges in application code after reading the flag.

Details: Default Values.

Common usage patterns

Rate limiting

Apply a requests-per-second cap from the dashboard. Clamp the value to acceptable bounds in code.

var rps = client.GetNumber("rate-limit-rps", defaultValue: 100);
var effectiveRps = Math.Clamp(rps, min: 1, max: 10_000);

ApplyRateLimit(effectiveRps);

Timeout configuration

Adjust outbound or handler timeouts per environment. Document the unit in the flag key.

var timeoutMs = (int)client.GetNumber("http-timeout-ms", defaultValue: 3000);
var effectiveTimeout = Math.Clamp(timeoutMs, 500, 30_000);

httpClient.Timeout = TimeSpan.FromMilliseconds(effectiveTimeout);

Batch processing

Control how many records a worker processes per iteration.

var batchSize = (int)client.GetNumber("job-batch-size", defaultValue: 25);
var effectiveBatch = Math.Clamp(batchSize, 1, 500);

await ProcessBatch(effectiveBatch);

Threshold-based behavior

Compare a metric against a fractional threshold configured from the dashboard.

var threshold = client.GetNumber("error-rate-threshold", defaultValue: 0.01);

if (currentErrorRate > threshold)
{
    EnterDegradedMode();
}

Runtime behavior

  1. An operator changes a flag value in the dashboard for a specific environment
  2. SOASAP Cloud pushes the update to connected SDKs over Server-Sent Events (SSE)
  3. The SDK validates the payload and atomically replaces its in-memory snapshot
  4. Subsequent getNumber / GetNumber calls return the new value

No redeploy is required. No network requests occur during evaluation — only during background synchronization. Propagation is typically sub-second on healthy networks; reads during disconnect continue using the last known snapshot.

See Real-Time Synchronization and Offline Operation.

Production recommendations

  • Use explicit defaults — every read must pass a code-defined fallback that represents safe behavior when the flag is missing or unsynced.
  • Validate ranges in application code — clamp or reject out-of-range dashboard values; SOASAP stores the number but does not enforce business rules.
  • Include units in flag keyshttp-timeout-ms, rate-limit-rps, cache-ttl-seconds prevent ambiguity across teams.
  • Cast intentionally for integers — SDKs return floating-point types; use (int), Math.trunc, or toInt() for counts and sizes, then validate > 0.
  • Default conservatively — lower limits, shorter timeouts, and smaller batches are safer when configuration is absent.
  • Use JSON for grouped numeric config — multiple related limits belong in a JSON flag, not a set of loosely named Number flags.

Common mistakes

Storing numbers as strings

Avoid:

var raw = client.GetString("rate-limit", defaultValue: "100");
var limit = int.Parse(raw);

Prefer:

var limit = (int)client.GetNumber("rate-limit-rps", defaultValue: 100);

String parsing adds failure modes on the hot path and bypasses SDK type checking. Use Number flags for numeric configuration.

Using numbers for Boolean logic

Avoid GetNumber("feature-enabled", 0) == 1 or similar patterns. Use Boolean flags for on/off behavior.

Skipping range validation

A dashboard typo can set rate-limit-rps to 999999 or -1. Always clamp or validate after read — never trust raw values for safety-critical limits.

Unclear units

Avoid:

client.GetNumber("timeout", defaultValue: 30);

Prefer:

client.GetNumber("http-timeout-seconds", defaultValue: 30);

Ambiguous keys cause production incidents when one team assumes seconds and another assumes milliseconds.

Using Number flags for structured configuration

Multiple related values — min-items, max-items, default-items — are easier to manage as a single JSON flag with typed deserialization than as scattered Number flags.

Related documentation