# Querying the API

{% hint style="info" %}
This documentation is about an Early Adopter feature and the instructions detailled here are subject to changes. Please contact your usual AB Tasty contact if some instructions are unclear or if something is missing.
{% endhint %}

{% hint style="info" %}
This page is a description of each object that structure the final payload. For a more guided version of the documentation, visit the [walkthrough](/client-side/data-apis/data-explorer/de-walkthrough.md).
{% endhint %}

### Sending the query

`POST https://api-data-explorer.abtasty.com/v2/clients/{{account_identifier}}/query`

**Arguments**

| Parameter           | Type   | Required | Format           | Description                                        |
| ------------------- | ------ | -------- | ---------------- | -------------------------------------------------- |
| account\_identifier | string | true     | Example: "37976" | Your account ID (or environmentId for server-side) |

**Headers**

| Name          | Required                | Value                  |
| ------------- | ----------------------- | ---------------------- |
| Content-Type  | true                    | `application/json`     |
| Authorization | true                    | Bearer {{your\_token}} |
| x-source      | true (server-side only) | `flagship`             |

### Building the payload

The payload must be inserted in the body of the request.

Example of payload:

```
{
    "timeIntervals": [
        {
            "start": "1640991600",
            "end": "1646290561"
        }
    ],
    "filters": {
        "single": {
            "field": "device",
            "operator": "EQUAL",
            "value": "Desktop"
        },
        "filteringStrategy": "PER_USER"
    },
    "dimensions": [
        "campaignId",
        "variationId"
    ],
    "metrics": [
        {
            "key": "users",
            "name": "",
            "filter": null,
            "type": "COMMON"
        },
        {
            "key": "npsCount",
            "name": "npsPromoters",
            "filter": {
                "single": {
                    "field": "npsScore",
                    "operator": "GREATER",
                    "value": "8"
                },
                "filteringStrategy": "PER_USER"
            },
            "type": "COMMON"
        }
    ],
    "orderBy": [
        {
            "field": "users",
            "direction": "DESC"
        }
    ],
    "limit": 100
}
```

### Setting up the dates

You will need a timeframe for your query. Select the two [epochs](https://en.wikipedia.org/wiki/Unix_time) (timestamps but in seconds) that will bound your request.

```
"timeIntervals": [
    {
        "start": "1640991600",
        "end": "1646290561"
    }
]
```

Remember that the larger the window, the longer it will take for our engine to process it or the biggest part of your fair-use it will consume.

### Choosing your dimensions

Choose which dimensions you want to get in the answer.

```
dimensions": [
      "campaignId",
      "variationId"
  ]
```

It must be a array of dimensions. Dimensions are enumerative values that are being collected by our tool, automatically or through specific parameters you have set up. Examples: campaignId, device name, event action, transaction revenue, etc…

The list of dimensions can be found [here](/client-side/data-apis/data-explorer/de-metrics-dimensions.md#dimensions-list).

### Choosing your metrics

Choose which metrics you want to get in the answer.

```
"metrics": [        
  {
      "key": "users",
      "name": "users",
      "filter": null,
      "type": "COMMON"
  },
  {
      "key": "sessions",
      "name": "sessions",
      "filter": null,
      "type": "COMMON"
  }
]
```

It must be a tab of objects, one object per metric. Metrics are counters that will be computed and filtered out depending on the dimensions you chose. For example, if you want to get the amount of UVs per browser, you will put “users” as a metric and “browser name” as a dimension.

`key` is the exact name of the metric.

The list of metrics can be found [here](/client-side/data-apis/data-explorer/de-metrics-dimensions.md#metrics-list).

`name` is optional (can be replaced by an empty String) and will only affect the result. It is used to give a custom name to a metric.

`filter` is optional and used to filter the metric, can be set to null

`type` must be set to “COMMON”

### Ordering the result

You can simply add an order instruction for the result.

```
"orderBy": [
    {
        "field": "users",
        "direction": "DESC"
    }
]
```

This won’t affect the content of the result.

`field` must be the exact name of the metric.

`direction` can either be `DESC` or `ASC`

### Limiting the result

You can add a limit to the number of lines that will be returned.

```
  "limit": 100
```

{% hint style="warning" %}
This will not change the amount of data that will be parsed!
{% endhint %}

### Filters

There are three levels of filters:

* selecting the population you will be using for this request,
* filtering the metrics you will be receiving,
* filtering on campaign history

#### Selecting your population

The first level of filter you will want to set in the population you will get data from. This allows you to narrow your request to remove all the unnecessary population.

Examples of populations you want to filter on:

> Only the visitors that have seen campaign #362412

> Only the visitors that have sent an “Add to cart” EVENT

This is achieved by adding a root `filters` argument in the payload. For example:

```
{
    "timeIntervals": [
        {
            "start": "1657707046",
            "end": "1658916646"
        }
    ],
    "filters": {
        "single": {
            "field": "campaignId",
            "value": "871873"
        },
        "filteringStrategy": "PER_SESSION"
    },
    "dimensions": [
        "date"
    ],
    "metrics": [
        {
            "key": "users",
            "name": "users",
            "type":"COMMON"
        },
        {
            "key": "uniqueEvents",
            "name": "uniqueEvents",
            "type": "COMMON"
        }
    ],
    "limit": 100
}
```

#### Single filter condition

When the population is only filtered on one condition, the syntax is pretty simple:

```
"filters": {
    "single": {
        "field": "campaignId",
        "value": "871873"
    },
    "filteringStrategy": "PER_SESSION"
}
```

In this example, the population will be filtered on the campaign ID. All the visitors that haven’t been exposed to campaign #871873 won’t be parsed.

The `field` argument is selecting the dimension and the `value` argument the expected value. By default, the request will be made on an `EQUAL` match, but you can add an `operator` parameter to change that.

Possible values are:

* EQUAL
* NOT\_EQUAL
* GREATER
* GREATER\_OR\_EQUAL
* LESS
* LESS\_OR\_EQUAL
* CONTAINS
* NOT\_CONTAINS
* REGEXP
* IS\_NULL
* IS\_NOT\_NULL

The `filteringStrategy` argument is used to decide if the population must validate the criterion at the session level or user-wide.

The two possible values are `PER_SESSION` or `PER_USER`.

For example, if one visitor has made two visits but only one transaction (let's say on visit #2), getting the metric `sessions` with a filter on the transaction will return `2` with the `PER_USER` value and only `1` with `PER_SESSION`.

#### Excluding filter condition

The same logic as above applies but with a global exclusion. Only the keyword needs to be changed:

```
"excludeFilters": {
    "single": {
        "field": "campaignId",
        "value": "871873"
    },
    "filteringStrategy": "PER_SESSION"
}
```

In this example, the population will be excluded based on the campaign ID. All the visitors that have been exposed to campaign #871873 won't be selected.

#### Multiple filters condition

You can add multiple filters and combine them. You will achieve that by adding a “composite” filter.

```
"filters": {
    "composite": {
        "singleHitCondition":true,
        "operator": "OR",
        "filters": [
            {
                "single": {
                    "field": "campaignId",
                    "operator": "EQUAL",
                    "value": "885397"
                },
                "filteringStrategy": "PER_USER"
            },
            {
                "single": {
                    "field": "campaignId",
                    "operator": "EQUAL",
                    "value": "883918"
                },
                "filteringStrategy": "PER_USER"
            }
        ]
    }
}
```

In this example, the population will be also filtered on the campaign ID. However, this time, we want to have visitors that have seen campaign #885397 **OR** campaign #883918.

The `composite` filter is composed of two `single` filters (exclusion is possible).

The `singleHitCondition` is set to `true`, which means that the two filters will be matched on the same hit. When evaluating the filter on the specific arguments of different type of hits (for example a transaction revenue and an event action), this parameter must be set to `false` as the condition would be impossible if set to `true`.

This syntax would also work:

```
"filters": {
    "single": {
        "field": "campaignId",
        "operator": "REGEX",
        "value": "(^885397$)|(^883918$)"
    },
    "filteringStrategy": "PER_USER"
}
```

#### Nested filters

It is possible to nest another composite filter inside a composite filter. For example:

```
"filters": {
  // root composite
  "composite": {
    "singleHitCondition": true,
    "filters": [
      {
        "single": {
          "field": "device",
          "operator": "EQUAL",
          "value": "Mobile"
        }
      },
      {
        // nested composite
        "composite": {
          "singleHitCondition": false,
          "filters": [
            {
              "single": {
                "field": "browser",
                "operator": "EQUAL",
                "value": "Chrome"
              }
            },
            {
              "single": {
                "field": "country",
                "operator": "NOT_EQUAL",
                "value": "Spain"
              }
            }
          ]
        }
      }
    ]
  }
}
```

#### Refining your metrics

After you selected your population, you can add a filter directly to your metrics.

```
{
    "timeIntervals": [
        {
            "start": "1657707046",
            "end": "1658916646"
        }
    ],
    "filters": {
        "single": {
            "field": "eventAction",
            "value": "Click productss"
        },
        "filteringStrategy": "PER_USER"
    },
    "metrics": [
        {
            "key": "transactions",
            "name": "transactions",
            "type": "COMMON",
            "filter":{
                "single": {
                    "field":"affiliation",
                    "operator":"EQUAL",
                    "value":"Purchase"
                }
            }
        }
    ],
    "limit": 100
}
```

In this example, we select all the visitors that have sent a “Click products” `EVENT` and want to have the number of transactions but only for the `affiliation` (transaction goal name) “Purchase”. Not adding the filter would have displayed the number of transactions for all existing transaction goals.

The syntax is the same as for a population filter. However, the `field` you are filtering on must be relative to the metric this filter is nested on.

#### Filtering on campaign history

As exposed in the [data schema documentation](/client-side/data-apis/universal-collect/uc-data-schema.md), the campaign history determines if a hit has been done after being exposed to a specific campaign. You might want to only get data from hits that happen after a visitor has been exposed to a campaign.

For this, you would use the `campaignFilter` parameter. The syntax is exactly the same as the `filters` but it will only return hits that has the specified campaignId in the campaign history.

The main difference is that a `filters` parameter would always return if a transaction has been made during the visitor's session while `campaignFilter` will only return this transaction **IF** the visitor has seen the campaign before.

```
"campaignFilter": {
    "single": {
        "field": "campaignId",
        "value": "871873"
    }
}
```

### Examples library

In this section you will find several examples with their description.

***

Getting the amount of users / sessions / transactions grouped by browser and browser version for all visitors that have seen at least one URL that contains the keyword “/how” in the time range.

```
{
    "timeIntervals": [
        {
            "start": "1667059200",
            "end": "1667980740"
        }
    ],
    "filters": {
        "single": {
            "field": "url",
            "operator": "CONTAINS",
            "value": "/how"
        }
    },
    "dimensions": [
        "browser",
        "browserVersion"
    ],
    "metrics": [
        {
            "key": "users"
        },
        {
            "key": "sessions"
        },
        {
            "key": "transactions"
        }
    ],
    "limit": 100
}
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.abtasty.com/client-side/data-apis/data-explorer/de-query.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
