Skip to content
API referenceAffiliates

API reference · App API

Affiliates

Your users as affiliates: their own code and results, codes they enter, and how your program is configured.

Claim an invite code

POST/v1/affiliates/claim

Binds an invite code to one of your users who already has an account: a code typed in, pasted or carried by a universal link. Before sign-up, ask with POST /v1/attributions instead.

Safe to repeat. A registration that arrived earlier without a code is attributed again when the claim arrives. Pass the clickId and platform you have, so the claim can be tied to the click that led to it.

AuthSigned request with an app key, fg_live_… or fg_test_…

Request body

appUserIdstringrequired≤ 200 chars

Your pseudonymous id for the user. Never an email address or phone number.

codestringrequired≤ 100 chars

The invite code the user typed, pasted or opened. Case and surrounding spaces do not matter.

sourcestringdefault code_entry

universal_link when the code came from the link that opened the app, code_entry when the user typed or pasted it.

One of code_entry universal_link

clickIdstringuuid

fg_click from the link that opened the app. A value that is not a click id is ignored, never refused.

platformstring

The platform the app runs on. Any other value is ignored.

One of ios android

Returns · 200

touchIdstringrequireduuid
attributedbooleanrequired

Whether the user’s registration is now attributed to this code. False until user.registered has been sent and processed.

attributionKeystringrequired

The claim’s attribution key, bound to this user. Events may carry it instead of appUserId.

Errors

400validation_error

The request does not match the schema. details says which fields failed and why.

401missing_signature

One of x-fg-key, x-fg-timestamp and x-fg-signature is missing.

401invalid_timestamp

x-fg-timestamp is not Unix time in seconds.

401stale_timestamp

x-fg-timestamp is more than 300 seconds from the server clock. Sign each attempt again, and keep your clock in sync.

401invalid_key

The key id is unknown or revoked, or the app is archived.

401invalid_signature

The signature does not match. Sign the exact bytes you send.

404not_found

No code like this belongs to your app.

409code_inactive

The code was deactivated or has expired.

409already_attributed

The user is already attributed to another referrer.

429too_many_attempts

Too many requests with this key in the last minute. Wait Retry-After seconds.

Request
BODY='{"appUserId":"u_8F2K","code":"k7qxa2mp","source":"code_entry","platform":"ios"}'
TS=$(date +%s)
SIG=$(printf '%s.%s' "$TS" "$BODY" | openssl dgst -sha256 -hmac "$FG_SECRET" | sed 's/^.*= //')

curl -X POST "https://api.flowgroup.se/v1/affiliates/claim" \
  -H "content-type: application/json" \
  -H "x-fg-key: $FG_KEY_ID" \
  -H "x-fg-timestamp: $TS" \
  -H "x-fg-signature: $SIG" \
  --data-raw "$BODY"
200 OK
{
  "touchId": "6b0f2a51-3c4d-4e8f-9a1b-2c3d4e5f6a7b",
  "attributed": true,
  "attributionKey": "fga_k7qxa2mpw4ht9bvc3rnd8ezj"
}

Record the first app open

POST/v1/affiliates/app-open

Reports the first open of the app after an install, with the click id or code it came with, so the funnel shows how many clicks became installs. Measurement only: it never attributes or pays. An open with neither a click id nor a code is not counted, and a sandbox key gets the same answer without recording anything.

AuthSigned request with an app key, fg_live_… or fg_test_…

Request body

clickIdstringuuid

fg_click from the link that opened the app. A value that is not a click id is ignored, never refused.

codestring≤ 100 chars

fg_ref, or the code the app opened with, when there is no click id.

platformstring

The platform the app runs on. Any other value is ignored.

One of ios android

Returns · 200

matchedbooleanrequired

Whether the open was tied to a click on one of your links.

matchstringrequirednullable

click_id: the click id named it. nearest_click: the code led to its most recent click on this platform.

One of click_id nearest_click

Errors

400validation_error

The request does not match the schema. details says which fields failed and why.

401missing_signature

One of x-fg-key, x-fg-timestamp and x-fg-signature is missing.

401invalid_timestamp

x-fg-timestamp is not Unix time in seconds.

401stale_timestamp

x-fg-timestamp is more than 300 seconds from the server clock. Sign each attempt again, and keep your clock in sync.

401invalid_key

The key id is unknown or revoked, or the app is archived.

401invalid_signature

The signature does not match. Sign the exact bytes you send.

429too_many_attempts

Too many requests with this key in the last minute. Wait Retry-After seconds.

Request
BODY='{"clickId":"1d4f9c5e-7a8b-4c2d-9e1f-0a1b2c3d4e5f","platform":"android"}'
TS=$(date +%s)
SIG=$(printf '%s.%s' "$TS" "$BODY" | openssl dgst -sha256 -hmac "$FG_SECRET" | sed 's/^.*= //')

curl -X POST "https://api.flowgroup.se/v1/affiliates/app-open" \
  -H "content-type: application/json" \
  -H "x-fg-key: $FG_KEY_ID" \
  -H "x-fg-timestamp: $TS" \
  -H "x-fg-signature: $SIG" \
  --data-raw "$BODY"
200 OK
{
  "matched": true,
  "match": "click_id"
}

Get a user’s affiliate summary

GET/v1/affiliates/me

The user’s own invite code and link, how many people signed up with it, and what they have earned. Creates their referrer account on first use, so call it when the user opens your referral screen.

AuthSigned request with an app key, fg_live_… or fg_test_…

Query parameters

appUserIdstringrequired≤ 200 chars

Your pseudonymous id for the user. Never an email address or phone number.

codestring

The code the user already shares in your app (3 to 24 letters and digits), kept as theirs here.

Matches ^[A-Za-z0-9]{3,24}$

Returns · 200

One of your users as an affiliate.

codestringrequired

The user’s own invite code.

urlstringrequireduri

Their shareable link for the code.

programIdstringrequireduuid
statusstringrequired

One of active inactive

countsobjectrequired
Child attributes
registeredintegerrequired

Users who signed up with their code or link.

qualifiedintegerrequired
rejectedintegerrequired

Rejected or reversed.

earnedarray of objectsrequired

Per currency.

Child attributes
currencystringrequired
amountintegerrequired

Everything earned, in minor units.

pendingintegerrequired

Not delivered to the user yet.

deliveredintegerrequired

Delivered through your reward webhook.

Errors

400validation_error

The request does not match the schema. details says which fields failed and why.

401missing_signature

One of x-fg-key, x-fg-timestamp and x-fg-signature is missing.

401invalid_timestamp

x-fg-timestamp is not Unix time in seconds.

401stale_timestamp

x-fg-timestamp is more than 300 seconds from the server clock. Sign each attempt again, and keep your clock in sync.

401invalid_key

The key id is unknown or revoked, or the app is archived.

401invalid_signature

The signature does not match. Sign the exact bytes you send.

404not_found

Your app has no active friend-referral program.

429too_many_attempts

Too many requests with this key in the last minute. Wait Retry-After seconds.

Request
TS=$(date +%s)
SIG=$(printf '%s.' "$TS" | openssl dgst -sha256 -hmac "$FG_SECRET" | sed 's/^.*= //')

curl "https://api.flowgroup.se/v1/affiliates/me?appUserId=u_1042" \
  -H "x-fg-key: $FG_KEY_ID" \
  -H "x-fg-timestamp: $TS" \
  -H "x-fg-signature: $SIG"
200 OK
{
  "code": "k7qxa2mp",
  "url": "https://go.affiliate.yflow.io/a/k7qxa2mp",
  "programId": "0c9e6f3a-1b2d-4c5e-8f7a-9b0c1d2e3f4a",
  "status": "active",
  "counts": {
    "registered": 3,
    "qualified": 2,
    "rejected": 0
  },
  "earned": [
    {
      "currency": "USD",
      "amount": 400,
      "pending": 200,
      "delivered": 200
    }
  ]
}

Get the program’s mode and rules

GET/v1/affiliates/config

Which mode your friend-referral program is in for a market, and under which rules, so the app can show the right terms and knows whether to credit referral rewards itself.

AuthSigned request with an app key, fg_live_… or fg_test_…

Query parameters

countrystring2 chars

ISO 3166 alpha-2 country of the new user. Without it, the program’s default market applies.

Returns · 200

Your friend-referral program as it applies to new users in one country. Cache it for a minute.

modestringrequired

off: Flow Affiliate is not involved, run your own scheme. shadow: keep your scheme; Flow Affiliate works out what it would pay, for comparison. live: Flow Affiliate decides; credit exactly what the reward webhook says.

One of off shadow live

programIdstringrequireduuidnullable
campaignIdstringrequireduuidnullable
currencystringrequirednullable
rulesarray of objectsrequired

The rules in force, to show the terms to your users. Empty when mode is off.

Child attributes
idstringrequireduuid
namestringrequired
triggerEventstringrequired

The event type that earns it, e.g. purchase.completed.

modelstringrequired

One of fixed percentage

amountintegerrequirednullable

Minor units, for fixed rules.

percentBpsintegerrequirednullable

Basis points of the event’s amount, for percentage rules.

maxAmountintegerrequirednullable

Ceiling on one payout of a percentage rule, minor units.

currencystringrequired
beneficiarystringrequired

partner: whoever referred the user. referred_user: the new user themselves.

One of partner referred_user

recurringbooleanrequired

Pays on every matching event, not just the first.

holdDaysintegerrequired
qualificationobjectrequired

Conditions the event must meet, e.g. withinDays.

updatedAtstringrequireddate-time

Errors

400validation_error

The request does not match the schema. details says which fields failed and why.

401missing_signature

One of x-fg-key, x-fg-timestamp and x-fg-signature is missing.

401invalid_timestamp

x-fg-timestamp is not Unix time in seconds.

401stale_timestamp

x-fg-timestamp is more than 300 seconds from the server clock. Sign each attempt again, and keep your clock in sync.

401invalid_key

The key id is unknown or revoked, or the app is archived.

401invalid_signature

The signature does not match. Sign the exact bytes you send.

429too_many_attempts

Too many requests with this key in the last minute. Wait Retry-After seconds.

Request
TS=$(date +%s)
SIG=$(printf '%s.' "$TS" | openssl dgst -sha256 -hmac "$FG_SECRET" | sed 's/^.*= //')

curl "https://api.flowgroup.se/v1/affiliates/config" \
  -H "x-fg-key: $FG_KEY_ID" \
  -H "x-fg-timestamp: $TS" \
  -H "x-fg-signature: $SIG"
200 OK
{
  "mode": "live",
  "programId": "0c9e6f3a-1b2d-4c5e-8f7a-9b0c1d2e3f4a",
  "campaignId": "5a6b7c8d-9e0f-4a1b-8c2d-3e4f5a6b7c8d",
  "currency": "USD",
  "rules": [
    {
      "id": "9f8e7d6c-5b4a-4392-8170-6f5e4d3c2b1a",
      "name": "Friend makes a first purchase",
      "triggerEvent": "purchase.completed",
      "model": "fixed",
      "amount": 200,
      "percentBps": null,
      "maxAmount": null,
      "currency": "USD",
      "beneficiary": "partner",
      "recurring": false,
      "holdDays": 14,
      "qualification": {
        "withinDays": 30
      }
    }
  ],
  "updatedAt": "2026-11-01T08:00:00.000Z"
}

Import your users’ existing codes

POST/v1/affiliates/codes

Hands over the invite codes your users already share in your own scheme, so each code stays theirs and keeps working here. Safe to repeat. Codes are real identities, so a sandbox key changes nothing and answers sandbox: true.

AuthSigned request with an app key, fg_live_… or fg_test_…

Request body

codesarray of objectsrequired1–500 items
Child attributes
appUserIdstringrequired≤ 200 chars

Your pseudonymous id for the user. Never an email address or phone number.

codestringrequired≤ 100 chars

The code the user shares in your app today.

Returns · 200

importedintegerrequired
existingintegerrequired

Already theirs.

conflictsarray of objectsrequired
Child attributes
appUserIdstringrequired
codestringrequired
reasonstringrequired

code_taken: another user holds it here. invalid_code: not 3 to 24 letters and digits.

sandboxboolean

Sent with a sandbox key: nothing was imported.

Errors

400validation_error

The request does not match the schema. details says which fields failed and why.

401missing_signature

One of x-fg-key, x-fg-timestamp and x-fg-signature is missing.

401invalid_timestamp

x-fg-timestamp is not Unix time in seconds.

401stale_timestamp

x-fg-timestamp is more than 300 seconds from the server clock. Sign each attempt again, and keep your clock in sync.

401invalid_key

The key id is unknown or revoked, or the app is archived.

401invalid_signature

The signature does not match. Sign the exact bytes you send.

404not_found

Your app has no active friend-referral program.

429too_many_attempts

Too many requests with this key in the last minute. Wait Retry-After seconds.

Request
BODY='{"codes":[{"appUserId":"41","code":"K7QXA"}]}'
TS=$(date +%s)
SIG=$(printf '%s.%s' "$TS" "$BODY" | openssl dgst -sha256 -hmac "$FG_SECRET" | sed 's/^.*= //')

curl -X POST "https://api.flowgroup.se/v1/affiliates/codes" \
  -H "content-type: application/json" \
  -H "x-fg-key: $FG_KEY_ID" \
  -H "x-fg-timestamp: $TS" \
  -H "x-fg-signature: $SIG" \
  --data-raw "$BODY"
200 OK
{
  "imported": 1,
  "existing": 0,
  "conflicts": [
    {
      "appUserId": "42",
      "code": "k7qxa",
      "reason": "code_taken"
    }
  ]
}