# Throttling

Liberator throttles updates to clients from [records](../datasource/datasource-records.md) and [generic objects](../datasource/datasource-generic-data.md) (Liberator 7.1.24+) by default. Throttling client updates reduces the performance impact of high update rates from adapters by merging updates over a period of time called 'throttle time' (default 1 second).

The default throttling settings are not suitable for all purposes and it is common practice to change them on a subject-by-subject basis. For example, executable pricing streams may require a shorter throttle time, and [messaging channels](../platform-architecture/channels.md#control-channels) require throttling to be disabled.

This page provides an overview of throttling, how to configure it, and how to disable it. For information on a related performance feature that _batches_ rather than merges client updates, see [Bursting](liberator-bursting.md). 

**❗ IMPORTANT**\
From version **7.1.24**, in addition to throttling updates from records, Liberator now throttles updates from  [generic objects](../datasource/datasource-generic-data.md) too. Review your configuration before upgrading to Liberator 7.1.24, and disable throttling for generic objects for which throttling is inappropriate (for example, messaging channels). For more details, see [Disabling throttling](#disabling-throttling), below.

## Overview

In a fast moving market, data updates can be generated more frequently than the end-user can actually notice them. For example, the user can’t actually see every update for an item that is updating at ten times a second. Additionally, having to feed such high update rates through to client applications can adversely impact system resources, performance, and the network.

When throttling is enabled (the default), Liberator conflates all the updates for a data item during an interval called the throttle time (default 1 second). At the end of this interval, Liberator sends an update to the client.

## Throttling of records

At the end of the throttle time for a record, by default Liberator sends the client all _updated_ fields regardless of whether their value has changed since the last update was sent to the client. If no fields were updated in the throttle time, then no update is sent to the client

**Records (default behaviour)**

Three updates are received by a [type 1](../datasource/datasource-type-1-data.md) record `/ABC` during throttle time. At the end of throttle time, the object’s bid and ask fields have both received updates, but only the bid field has changed in value since the last update was sent to the client. Liberator sends the client an update containing both fields.

```plantuml
@startuml
hide footbox
skinparam participantpadding 40
hide footbox

Participant Client
Participant Liberator [
    Liberator object cache
    ----
    ""/ABC""
]
Participant Adapter

Client -> Liberator : Subscribe /ABC
Liberator -> Adapter : Request /ABC
Liberator <- Adapter : bid=51.160, ask=52.032
Client <- Liberator : bid=51.160, ask=52.032

note over Liberator : bid=51.160, ask=52.032
group Throttle time
Adapter -> Liberator : bid=51.162, ask=52.032
Adapter -> Liberator : bid=51.155, ask=52.032
Adapter -> Liberator : bid=51.158, ask=52.032
end
note over Liberator : bid=51.158, ask=52.032
Client <- Liberator : bid=51.158, ask=52.032
@enduml
```

By default, throttled record updates to clients include all fields that have been updated in the throttle time, even if the updated fields have not changed in value. To configure throttled record updates to include only the updated fields that have changed in value, see configuration option [`add-object::only-changed-fields`](liberator-object-configuration-part-1.md#only-changed-fields). 

**Records (`only-changed-fields TRUE`)**

A [type 1](../datasource/datasource-type-1-data.md) object, `/ABC`, has been configured to send only changed fields in client updates:

```
add-object
    name /ABC
    type record
    only-changed-fields TRUE
end-object
```

Three updates are received by the type 1 object `/ABC` during throttle time. At the end of throttle time, the object’s bid and ask fields have both received updates, but only the bid field has changed in value since the last update was sent to the client. Liberator sends the client an update containing only the bid field.

```plantuml
@startuml
hide footbox
skinparam participantpadding 40
Participant Client
Participant Liberator [
    Liberator object cache
    ----
    ""/ABC""
]
Participant Adapter

Client -> Liberator : Subscribe /ABC
Liberator -> Adapter : Request /ABC
Liberator <- Adapter : bid=51.160, ask=52.032
Client <- Liberator : bid=51.160, ask=52.032

note over Liberator : bid=51.160, ask=52.032
group Throttle time
Adapter -> Liberator : bid=51.162, ask=52.032
Adapter -> Liberator : bid=51.155, ask=52.032
Adapter -> Liberator : bid=51.158, ask=52.032
end
note over Liberator : bid=51.158, ask=52.032
Client <- Liberator : bid=51.158

@enduml
```

## Throttling of generic objects

**Available from:** Liberator 7.1.24

From version 7.1.24, Liberator throttles updates from generic objects by default. To restore throttling behaviour for all generic objects to pre 7.1.24 behaviour, set the [`object-disable-generic-throttling`](liberator-throttling-configuration.md#object-disable-generic-throttling) item to `true`.

At the end of the throttle interval for a generic object, Liberator sends the client an update containing only the updated fields that have _changed_ in value. If no fields have changed in value, then no update is sent to the client.

**Generic objects**

Three updates are received by a [generic](../datasource/datasource-generic-data.md) object `/ABC` during throttle time. At the end of throttle time, the object’s bid and ask fields have both received updates, but only the bid field has changed in value since the last update was sent to the client. Liberator sends the client an update containing only the bid field.

```plantuml
@startuml
hide footbox
skinparam participantpadding 40
Participant Client
Participant Liberator [
    Liberator object cache
    ----
    ""/ABC""
]
Participant Adapter

Client -> Liberator : Subscribe /ABC
Liberator -> Adapter : Request /ABC
Liberator <- Adapter : bid=51.160, ask=52.032
Client <- Liberator : bid=51.160, ask=52.032

note over Liberator : bid=51.160, ask=52.032
group Throttle time
Adapter -> Liberator : bid=51.162, ask=52.032
Adapter -> Liberator : bid=51.155, ask=52.032
Adapter -> Liberator : bid=51.158, ask=52.032
end
note over Liberator : bid=51.158, ask=52.032
Client <- Liberator : bid=51.158

@enduml
```

There are some differences between the throttling of generic objects and the throttling of records:

* **Throttle times**\
**Records:** all throttle times in [`object-throttle-times`](liberator-throttling-configuration.md#object-throttle-times) and [`add-object::throttle-times`](liberator-object-configuration-part-1.md#throttle-times) can be used.

  **Generic objects:** only the first throttle time in [`object-throttle-times`](liberator-throttling-configuration.md#object-throttle-times) and [`add-object::throttle-times`](liberator-object-configuration-part-1.md#throttle-times) is used.
* **Fields in updates sent to clients**\
**Records:** regardless of whether throttling is enabled or disabled, you can configure whether updates sent to clients contain all updated fields, or only updated fields that have changed in value. See [`add-object::only-changed-fields`](liberator-object-configuration-part-1.md#only-changed-fields).

  **Generic objects:** when throttling is disabled, updates sent to clients contain all updated fields. When throttling is enabled, updates sent to clients contain only updated fields that have changed in value. This behaviour is non-configurable.

## Configuring throttling

Client applications can change the level of throttling for specified items, groups of items, or all items globally.

### Global-level configuration

Global throttling configuration applies to all records and generic objects, unless overridden at object level.

* [`object-throttle-off`](liberator-throttling-configuration.md#object-throttle-off): when set to TRUE, disables throttling for all objects. This item cannot be overridden at object level.
* [`object-throttle-times`](liberator-throttling-configuration.md#object-throttle-times): an array (space-separated values) of throttle times. When an array is provided, clients begin with the value indicated by `object-throttle-default-level`, and can switch to any of the other values in the array. For most scenarios, one value is sufficient.

  For throttled generic objects, only the first value in the array is used.
* [`object-throttle-default-level`](liberator-throttling-configuration.md#object-throttle-default-level): an index (0 based) to the array specified in `object-throttle-times`. Defaults to 0 (the first value in the array).

  For throttled generic objects, only the first value (0) in the `object-throttle-times` array is used.
* [`object-disable-generic-throttling`](liberator-throttling-configuration.md#object-disable-generic-throttling): when set to TRUE, disables throttling for all generic objects.

### Object-level configuration

You can use the [`add-object`](liberator-object-configuration-part-1.md#add-object) configuration item to configure throttling at the object level for records and generic objects. You can also configure throttling at the directory level (objects of type directory), and records and generic objects under that directory will inherit the configuration.

[`add-object`](liberator-object-configuration-part-1.md#add-object):

* [`name`](liberator-object-configuration-part-1.md#name) option: the name of the object.
* [`type`](liberator-object-configuration-part-1.md#type) option: the type of the object. Set to `record` or `generic` for a specific object (for example, `/FX/EURUSD`) or `directory` for a namespace containing objects of type `record` and `generic` (for example, `/FX`).
* [`throttle-times`](liberator-object-configuration-part-1.md#throttle-times) option: overrides [`object-throttle-times`](liberator-throttling-configuration.md#object-throttle-times). Set to 0 to disable throttling for this subject.
* [`only-changed-fields`](liberator-object-configuration-part-1.md#only-changed-fields) option: [type 'record' only] determines which fields are sent to clients in updates. Set to FALSE (default) to send clients all _updated_ fields, and set to TRUE to send clients only updated fields that have _changed_ in value.

  This option is ignored by generic objects. When throttling is disabled, generic objects send clients all _updated_ fields. From Liberator 7.1.24, when throttling is enabled, generic objects send clients only updated fields that have changed in value.
* [`disable-generic-throttling`](liberator-object-configuration-part-1.md#disable-generic-throttling) option: disables throttling of generic objects in a directory.

**Subject-level configuration**

The configuration below sets the throttle time to 0.25s for objects under the /FX namespace. Subscriptions to type 1 records under the /FX namespace will receive a maximum of 4 updates a second.

```
add-object
    name /FX
    type directory
    throttle-times 0.25
end-object
```

## Disabling throttling

By default, throttling is enabled for records (and generic objects, since Liberator 7.1.24) with a throttle time of 1 second.

Throttling updates is not appropriate for all objects. Updates in [messaging channels](../platform-architecture/channels.md#channel-subscription), such as those used by [FX Integration API](../../../fx-integration-api/index.md) trade-models, must not be throttled. Throttling message channels may delay message transmission, and, if only _changed_ fields are sent, throttling breaks message specifications that guarantee the presence of specific fields.

### Disabling throttling for all namespaces

Before disabling throttling globally, consider whether some objects would benefit from some level of throttling (highly volatile pricing streams, for example).

Choose the most appropriate option below:

* To disable throttling of all records and generic objects, set the configuration item [`object-throttle-off`](liberator-throttling-configuration.md#object-throttle-off) to `TRUE`.
* To disable throttling for all generic objects, set the configuration item [`object-disable-generic-throttling`](liberator-throttling-configuration.md#object-disable-generic-throttling) to `TRUE`.

### Disabling throttling for a specific namespace

Choose the most appropriate option below:

* To disable throttling of records and generic objects under a specific namespace, use an [`add-object`](liberator-object-configuration-part-1.md#add-object) item with option `type` set to `directory` and option [`throttle-times`](liberator-object-configuration-part-1.md#throttle-times) set to `0`.

  **Disabling throttling of records and generic objects in a namespace**

  To disable throttling of records and generic objects under the `/PRIVATE` namespace, use the configuration below:

  ```
  add-object
      name /PRIVATE
      type directory
      throttle-times 0
  end-object
  ```
* To disable throttling of generic objects under a specific namespace, use an [`add-object`](liberator-object-configuration-part-1.md#add-object) item with option `type` set to `directory` and option [`disable-generic-throttling`](liberator-object-configuration-part-1.md#disable-generic-throttling) set to `TRUE`.

  **Disabling throttling of generic objects in a namespace**

  To disable throttling of generic objects under the `/PRIVATE` namespace, use the configuration below:

  ```
  add-object
      name /PRIVATE
      type directory
      disable-generic-throttling TRUE
  end-object
  ```

---

**See also:**

* [Throttling configuration](liberator-throttling-configuration.md)
* [Bursting](liberator-bursting.md)
* [Threading](liberator-threading.md)
* [Liberator configuration and blades](liberator-configuration-and-blades.md)
