NAUTILUS / RUST source 3eb18933
Pages

Rust edition: this page follows the live DeepWiki structure but treats the current Rust crates as implementation authority. Non-Rust surfaces are identified at their boundary and are not presented as Rust APIs.

Bar Aggregation System

Relevant Rust source files

  • crates/data/src/aggregation.rs

Purpose and Scope

The Bar Aggregation System provides the infrastructure for transforming tick-level market data (quotes and trades) into higher-level bar/candlestick data through various aggregation methods. This system handles time-based, tick-based, volume-based, value-based, imbalance, runs, and Renko bar aggregation. It features both a high-performance legacy implementation for the binding-side DataEngine and a native Rust implementation for the Rust-native components.

System Overview

The bar aggregation system is built on two core abstractions: BarBuilder maintains the state of a bar being constructed (open, high, low, close, volume), while BarAggregator subclasses implement specific triggering logic to determine when a bar should be completed and emitted. Aggregators receive tick-level updates, update the builder, and emit completed bars through registered handler callbacks.

The system integrates with the DataEngine which manages aggregator lifecycles, routes incoming tick data to appropriate aggregators, and publishes completed bars to subscribers via the MessageBus.

Code Entity Space Mapping

The following diagram bridges the natural language concepts to the specific code entities used in the aggregation system.

Databento ticks and quotes entering DataEngine, where internal aggregation can construct and publish canonical bars.

BarBuilder Implementation

The BarBuilder class maintains the state required to construct a bar as updates arrive. It tracks the open, high, low, and close prices, along with accumulated volume and an update count. It also handles price adjustments for continuous futures.

Properties and State

Property Type Description
price_precision uint8_t Price precision from instrument
size_precision uint8_t Size precision from instrument
initialized bint Whether first update received
ts_last uint64_t Timestamp of last update (nanoseconds)
count int Number of updates applied
volume Quantity Accumulated volume

Continuous Future Adjustments

The BarBuilder supports four adjustment modes for continuous futures via ContinuousFutureAdjustmentType:

  • BACKWARD_SPREAD: Adjusts historical prices by adding a fixed spread.
  • FORWARD_SPREAD: Adjusts future prices by adding a fixed spread.
  • BACKWARD_RATIO: Adjusts historical prices by multiplying by a ratio.
  • FORWARD_RATIO: Adjusts future prices by multiplying by a ratio.

Key Functions

  • update(price, size, ts_init): Updates bar state. First update initializes OHLC. Subsequent updates adjust high/low and set close. Volume accumulates.
  • update_bar(bar, volume, ts_init): Updates state from another bar, used for building composite bars.
  • set_adjustment(adjustment, mode): Configures price adjustment parameters for the builder.
  • build(ts_event, ts_init): Constructs final Bar object and resets builder state.

Aggregation Types

Standard Aggregators

  • TickBarAggregator: Completes a bar after a fixed number of ticks (steps).
  • VolumeBarAggregator: Completes a bar when accumulated volume reaches a threshold.
  • ValueBarAggregator: Completes a bar when cumulative value (price × size) reaches a threshold.
  • TimeBarAggregator: Completes bars at regular time intervals using clock-based timers and TimeEvent callbacks.

Advanced Aggregators (Imbalance and Runs)

These aggregators track the "aggressiveness" of market participants using AggressorSide.

  • TickImbalanceBarAggregator: Tracks the cumulative imbalance of tick directions.
  • TickRunsBarAggregator: Completes bars when a specific run of tick directions is achieved.
  • VolumeImbalanceBarAggregator: Tracks the difference between buy and sell volume.
  • VolumeRunsBarAggregator: Completes bars when a specific run of volume on one side is achieved.
  • RenkoBarAggregator: Completes bars based on price movement "bricks" of a fixed size.

Rust Implementation (crates/data/src/aggregation.rs)

The Rust core provides a high-performance alternative to the legacy implementation, utilized by native components.

BarAggregator Trait

The Rust implementation defines a trait that all aggregators must implement:

  • bar_type(): Returns the associated BarType.
  • update(price, size, ts_init): Primary entry point for tick data.
  • handle_quote(quote) and handle_trade(trade): Helper methods that extract relevant price/size and call update.
  • start_timer(): Specifically for TimeBarAggregator to initialize its scheduling logic.

BarBuilder (Rust)

The Rust BarBuilder uses typed prices, quantities, and UnixNanos timestamps to build deterministic OHLCV values.

Integration with DataEngine

The DataEngine orchestrates the lifecycle of aggregators.

Aggregator Management

Rust aggregators are managed in the bar_aggregators collection and keyed by BarAggregatorKey, which includes the BarType and UUID4.

Data Flow Diagram

The following diagram illustrates how data flows from a client through the aggregation system to a final subscriber.

The aggregation sequence is DataClientDataEngineBarAggregatorBarBuilder → canonical BarMessageBus topic. Threshold or timer completion determines when the builder emits.

Custom Aggregation

Users can implement custom aggregation logic by extending the BarAggregator base class in legacy bindings or the BarAggregator trait in Rust.

Custom Aggregator Requirements

  1. Initialize a BarBuilder: To maintain OHLCV state.
  2. Implement update / _apply_update: Define the logic for when a bar should be "closed" (e.g., based on a custom mathematical formula).
  3. Call _build_and_send: To emit the bar and reset the builder once criteria are met.