Reporting

The POST/report endpoint allows you to report usage data to Tggl from your server, proxy, and clients. You can then find this data directly in the Tggl dashboard to track which flags are being used, how often, by which client...

curl 'https://api.tggl.io/report' \
  -H 'Content-Type: application/json' \
  -H 'x-tggl-api-key: <api key>' \
  --data-raw '{}'

The body should be a JSON object with the properties you want to report as described in the following sections. When successful, the response will be a 200 OK with a JSON body:

Response
{
  "success": true
}

Flag evaluation

Both client and server keys can be used to report flag evaluation metrics. You can add a clients array to the body to report metrics:

JSON
cURL
Request body
{
  "clients": [
    {
      "flags": {}
    }
  ]
}

You may pass multiple clients at once and add an id for each client to identify them in the dashboard:

Request body
{
  "clients": [
    {
      "id": "react-client:1.3.2",
      "flags": {}
    },
    {
      "id": "php-client:2.1.0",
      "flags": {}
    }
  ]
}

For each client, you can specify which flags were evaluated and the result of those evaluations. The flags object should contain the flag key as the key and an array of evaluation results as the value:

Request body
{
  "clients": [
    {
      "id": "react-client:1.3.2",
      "flags": {
        "new-button-color": [
          { "value": "#ff0000", "active": true, "count": 3 },
          { "value": "#00ff00", "active": true, "count": 7 },
          { "active": false, "count": 42 }
        ],
        "analytics-panel-beta": [
          { "active": true, "count": 11 },
          { "active": false, "count": 35 }
        ]
      }
    }
  ]
}

Each flag evaluation result is an object where all keys are optional and follows the following schema:

Schema
YAML
JSON
TypeScript
FlagEvaluationResult object
active boolean

The only require key, true when the flag was evaluated as active.

value any

The value the flag was evaluated to. Can by any type. Should be omitted if the flag was evaluated as inactive.

default any

The default value that was used in the code. Can by any type. Can be omitted if the flag was simply checked for its active state and not its value.

count integer

The number of times the flag was evaluated to that specific value. Default to 1 if not specified.

Context

Only the server API key can be used to report context related metrics. You can report both the properties you received for each context, and the values each of those properties had.

Received properties

You can add a receivedProperties object to the body of the request to report the properties you received for each context:

JSON
cURL
Request body
{
  "receivedProperties": {
    "userId": [1721461881, 1721461898],
    "email": [1721461881, 1721461898]
  }
}

The keys of the receivedProperties object are the properties you received, and the values are a tuple of two timestamps in seconds (not milliseconds) that represent the first and last time each property was received.

Received values

You can add a receivedValues object to the body of the request to report the values you received for each property:

JSON
cURL
Request body
{
  "receivedValues": {
    "email": [
      ["elon@gmail.com"],
      ["jeff@gmail.com"]
    ]
  }
}

The keys of the receivedValues object are the properties, and the values are an array of received values. Each received value is a tuple of the value itself, and an optional label associated.

For instance, if you want to associate a user's name to its user ID, you can do so like this:

Request body
{
  "receivedValues": {
    "userId": [
      ["U4zZSgiR", "Elon Musk"],
      ["Be6QkIjN", "Jeff Bezos"]
    ]
  }
}

To match a value with a label, the SDKs looks for keys that end with "Id" and "Name" and automatically associate them. For instance, if you have a userId and a userName property, the SDK will automatically associate the values. This also works with company_id and company_name, product-id and product-name, etc.

Reporting everything at once

You can report as much data as you want in a single API call. Here is an example of a complete request body:

Example
Schema
YAML
JSON
TypeScript
{
  "clients": [
    {
      "id": "php-client:1.5.1",
      "flags": {
        "analytics-panel-beta": [
          { "active": true, "count": 11 },
          { "active": false, "count": 35 }
        ]
      }
    }
  ],
  "receivedProperties": {
    "userId": [1721461881, 1721461898],
    "userName": [1721461881, 1721461898]
  },
  "receivedValues": {
    "userId": [
      ["U4zZSgiR", "Elon Musk"],
      ["Be6QkIjN", "Jeff Bezos"]
    ],
    "userName": [["Elon Musk"], ["Jeff Bezos"]]
  }
}

Error handling

If you API key is invalid or missing, you will receive a 401 Unauthorized response.

401 Unauthorized
{
  "error": "Invalid API key"
}

If the request body is invalid, you will receive a 400 Bad Request response with either an error or errors key.

400 Bad Request
{
  "error": "Unexpected end of JSON input"
}
400 Bad Request
{
  "errors": [
    {
      "code": "invalid_type",
      "expected": "object",
      "received": "undefined",
      "path": [
        "clients",
        0,
        "flags"
      ],
      "message": "Required"
    }
  ]
}