ابرووا
شروع رایگان
☰ فهرست مستندات · endpointهای عمومی SDK
به‌زودی. Abrova Flags به‌زودی فعال می‌شود. این صفحه توضیح می‌دهد چطور کار خواهد کرد؛ هنوز قابل استفاده نیست.
این صفحه هنوز ترجمه نشده — نسخه‌ی انگلیسی نمایش داده می‌شود. English

Public SDK Endpoints

The REST API behind the Abrova Flags SDKs. Client SDKs ask the service for evaluated values with the public key; server SDKs download the rules with the server secret and evaluate locally.

به‌روزرسانی: ۵ آبان ۱۴۰۵
Public SDK Endpoints.

These are the endpoints the 0.2.0 SDKs call. You only need this page if you call Abrova Flags over HTTP yourself, for example from a platform without an SDK. Base URL: https://flags.abrova.ir. All bodies are JSON.

Who calls what#

Client SDKs

Flutter, React Native, Android, iOS, Next.js client

  • Public API key only
  • POST /public/v2/evaluate
  • The service evaluates and returns values for one user
  • Rules, segments and variant weights are never returned
Server SDKs

Node.js, Next.js server

  • API key and server secret
  • GET /server/v2/flags
  • The SDK downloads the rules and evaluates locally
  • Optional POST /server/v2/usage for the Console charts

Authentication#

OptionTypeRequiredDescription
x-api-keyHeaderYesYour project API key (ab_live_xxx)
x-server-secretHeaderNoServer secret (ab_srv_xxx). Required on every /server route. Never send it from an app or a browser
x-abrova-sdkHeaderNoPlatform and version of the caller, for example node/0.2.0. Informational
If-None-MatchHeaderNoThe ETag of your last answer for the same request. The service answers 304 when nothing changed

A public API key cannot read targeting rules. A /server route called without the server secret answers 403 with code server_secret_required. If the server secret has an IP allow-list, calls from other addresses are refused.

POST /public/v2/evaluate#

Evaluates the flags of the project for one user context and returns the values. Used by all client SDKs.

Request

bash
curl -X POST "https://flags.abrova.ir/public/v2/evaluate" \
  -H "x-api-key: ab_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "environment": "production",
    "context": {
      "userId": "user-123",
      "anonymousId": "3f1c2b8e-9d0a-4c51-a1f2-6f0b7e2d9c11",
      "attributes": { "plan": "pro", "country": "IR", "beta": true, "age": 31 }
    },
    "flagKeys": ["new-checkout", "theme"]
  }'

Request Body

OptionTypeRequiredDescription
environmentstringNoEnvironment key (production, staging, development or your own). Leave out to use the Default values. An unknown or inactive key answers 404
contextobjectYesWho the flags are evaluated for
context.userIdstringNoThe signed-in user id, 1 to 256 characters
context.anonymousIdstringNoAn id for a signed-out install or visitor, 1 to 256 characters. The SDKs always send it
context.attributesobjectNoAt most 100 attributes. A value is a string (at most 1,024 characters), a number, a boolean, null, or an array of at most 100 of those. No nested objects
flagKeysstring[]NoOnly evaluate these flags, at most 500. Leave out to evaluate every flag

At least one of context.userId and context.anonymousId is required. Attributes named userId or anonymousId are ignored; the context fields are used instead.

Response

json
{
  "environment": "production",
  "evaluatedAt": "2026-10-01T12:00:00.000Z",
  "flags": {
    "new-checkout": {
      "key": "new-checkout",
      "valueType": "boolean",
      "enabled": true,
      "value": true,
      "variant": null,
      "reason": "ON",
      "version": 7
    },
    "theme": {
      "key": "theme",
      "valueType": "string",
      "enabled": true,
      "value": "dark",
      "variant": "dark",
      "reason": "VARIANT",
      "version": 3
    }
  }
}
FieldTypeDescription
environmentstring | nullThe environment that was evaluated. null for the Default values
evaluatedAtstringTime of the evaluation (ISO 8601)
flagsobjectOne entry per flag, by key. Flags that are off are included with their off value. Keys that do not exist are left out
flags.*.valueTypestringboolean, string, number or json
flags.*.enabledbooleantrue when the flag is served on for this context
flags.*.valueanyThe value to use, already of the flag type
flags.*.variantstring | nullKey of the served variant, if any
flags.*.reasonstringWhy: ON, VARIANT, DISABLED, PREREQUISITE_FAILED, NOT_TARGETED, OUTSIDE_ROLLOUT, NO_BUCKETING_ID or ERROR
flags.*.versionnumberVersion of the flag

The response carries an ETag header. Send it back as If-None-Match with the same body to get 304 Not Modified when the values did not change.

Counted as one evaluation per request.

Each call to this endpoint is counted as one flag evaluation, whatever the number of flags it returns, and also when the answer is 304 (100,000 evaluations are free every month; the price above that is set at launch). Cache the values and call again only when the user or the attributes change.

GET /server/v2/flags#

Returns every flag of the project with its rules, for local evaluation. Used by the Node.js and Next.js server SDKs. Requires the server secret. Not counted as evaluations.

Request

bash
curl -X GET "https://flags.abrova.ir/server/v2/flags?environment=production" \
  -H "x-api-key: ab_live_xxx" \
  -H "x-server-secret: ab_srv_xxx"

Query Parameters

OptionTypeRequiredDescription
environmentstringNoEnvironment key. Leave out to use the Default values. An unknown or inactive key answers 404

Response

json
{
  "schemaVersion": 2,
  "environment": "production",
  "generatedAt": "2026-10-01T12:00:00.000Z",
  "flags": [
    {
      "key": "theme",
      "valueType": "string",
      "enabled": true,
      "rolloutPercentage": 100,
      "salt": "a1b2c3d4e5f6",
      "rules": {
        "operator": "AND",
        "rules": [
          { "attribute": "plan", "operator": "in", "value": ["pro", "business"] }
        ]
      },
      "variants": [
        { "key": "dark", "value": "dark", "weight": 50 },
        { "key": "light", "value": "light", "weight": 50 }
      ],
      "offValue": "light",
      "prerequisites": [{ "flagKey": "new-ui" }],
      "version": 3
    }
  ],
  "segments": [
    {
      "key": "beta-testers",
      "rules": {
        "operator": "OR",
        "rules": [
          { "attribute": "email", "operator": "ends_with", "value": "@example.com" }
        ]
      }
    }
  ]
}

Environment overrides are already merged into each flag. offValue is the value served when the user does not get the flag. The response carries an ETag header; send it back as If-None-Match to get 304 when nothing changed. The server SDKs do this every 30 seconds.

Use a server SDK when you can.

Evaluating these rules yourself means implementing the whole evaluation flow, including bucketing. The Node.js and Next.js server SDKs already do it and give the same results as the service.

POST /server/v2/usage#

Optional. Reports how often a server evaluated each flag, so the evaluation charts in Abrova Console include server-side evaluations. The server SDKs send it when sendUsage is true. Requires the server secret. Not billed, and it contains no user ids.

Request

bash
curl -X POST "https://flags.abrova.ir/server/v2/usage" \
  -H "x-api-key: ab_live_xxx" \
  -H "x-server-secret: ab_srv_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "environment": "production",
    "periodStart": "2026-10-01T12:00:00.000Z",
    "periodEnd": "2026-10-01T12:01:00.000Z",
    "counts": [
      { "flagKey": "theme", "variant": "dark", "enabled": true, "count": 1520 },
      { "flagKey": "theme", "variant": null, "enabled": false, "count": 40 }
    ]
  }'

Request Body

OptionTypeRequiredDescription
environmentstringNoEnvironment key the counts belong to
periodStartstringYesStart of the period (ISO 8601)
periodEndstringYesEnd of the period. Not before periodStart, at most one hour after it
countsarrayYesAt most 1,000 entries
counts[].flagKeystringYesThe flag key. Unknown keys are ignored
counts[].variantstring | nullNoThe served variant key
counts[].enabledbooleanYesWhether the flag was served on
counts[].countnumberYesWhole number from 1 to 10,000,000

Response

202 Accepted

json
{ "accepted": 2 }

Errors#

Errors are JSON. Act on the HTTP status; code and message are for your logs.

json
{
  "statusCode": 403,
  "error": "Forbidden",
  "code": "server_secret_required",
  "message": "This route returns targeting rules and needs the server secret (x-server-secret)."
}
StatusWhenWhat to do
304If-None-Match matchedKeep the values or rules you have
400Invalid body (code invalid_request): no user id and no anonymous id, too many attributes, a nested attributeFix the request. Do not send the same body again
401Missing or invalid API key, invalid server secret, or Flags is not set up for the projectCheck the keys. Do not retry automatically
403A /server route without the server secret, or a caller outside the server secret IP allow-listDo not retry automatically
404The environment does not exist or is inactive (code environment_not_found)Check the environment key. Do not retry automatically
429Rate limitedWait the number of seconds in the Retry-After header, then retry with a growing delay
5xxServer errorKeep the last values and retry with a growing delay

Requests are rate limited per key and per address. Server-secret calls have higher limits than public-key calls. Do not hard-code the limits: follow Retry-After.

Older endpoints (upgrading from 0.1.x)#

Two endpoints from the 0.1.x SDKs still answer. Use the endpoints above for new code.

EndpointStatus
POST /public/flag-evaluationDeprecated. Evaluates one flag for one user with the public key. Body: flagKey and userId (required), userAttributes and environment (optional). Answers flagKey, enabled, value and, when a variant was served, variant. An unknown flag answers enabled false with reason flag_not_found. Counted as one evaluation per call. Use POST /public/v2/evaluate instead
GET /public/flagsDeprecated; needs the server secret. Use `GET /server/v2/flags`.
Request Volume.

The client SDKs call the service on start, when the user context changes and when the app or tab comes back after 15 minutes. The server SDKs never call the service per evaluation. If you call the API yourself, follow the same pattern.

این صفحه مفید بود؟
گزارش مشکل