Observers
Relevant source files
The following files were used as context for generating this wiki page:
Observers are specialized entities within the Backtrader framework designed to monitor the internal state of a strategy and its interaction with the broker. Unlike indicators, which primarily process market data to generate signals, Observers track the evolution of account-related metrics such as cash levels, portfolio value, and trade performance. They are integrated into the core execution loop and typically provide data lines that can be automatically plotted alongside price data.
Sources: backtrader/observers/broker.py:27, backtrader/strategy.py:165
Architecture and Execution Flow
Observers are categorized as a type of LineIterator. They are managed by the Strategy class and are stored in an ItemCollection accessible via self.stats or self.observers. The framework ensures that observers are updated synchronously with the strategy's data bars.
Lifecycle Management
The integration of observers follows a specific sequence:
- Registration: Observers are added to the system via
cerebro.addobserver()or internally within the strategy using_addobserver. - Initialization: During the strategy's
_start()phase, each observer's_start()method is invoked. - Iteration: Every time a new data bar is processed, the strategy calls
_next_observers(), which triggers the observer'snext(),prenext(), ornextstart()methods depending on the synchronization status of the data feeds.
Sources: backtrader/strategy.py:165, backtrader/strategy.py:461-496, backtrader/strategy.py:532-540
The diagram above illustrates how the Strategy coordinates with Observers to pull financial data from the Broker and update internal lines at every bar.
Standard Observer Implementations
The framework provides a set of built-in observers to track various aspects of the trading environment.
Broker Statistics
The broker.py module contains classes that interface directly with the broker to report account status.
| Class | Line Name | Purpose |
|---|---|---|
Cash | cash | Tracks the current amount of liquid cash available in the broker. |
Value | value | Tracks the total portfolio value (cash + market value of positions). |
Broker | cash, value | A combined observer tracking both cash and value simultaneously. |
FundValue | fundval | Tracks current fund-like values for fund accounting modes. |
FundShares | fundshares | Tracks the number of fund-like shares issued. |
Sources: backtrader/observers/broker.py:27-147
Trade Performance
Observers like Trades track the profit and loss (PnL) of closed trades. These are often used for visual validation of strategy performance on a chart, showing markers where trades were completed.
Sources: backtrader/observers/trades.py, arbitrage/JM_J_strategy_CUSUM.py:365
Implementation Details
Observers utilize the _owner attribute to access the strategy that created them, which in turn provides access to the broker and datas.
Compound Returns Logic
The CumValue observer calculates cumulative compounded returns by tracking the day-to-day return relative to the previous portfolio value.
def next(self):
current_value = self._owner.broker.getvalue()
# Calculate day-to-day return
daily_return = (
0 if self._prev_value == 0 else (current_value / self._prev_value) - 1
)
daily_return = 0 if daily_return == -1 else daily_return
# Multiply by (1 + daily_return) to get compound effect
self._cum_return *= 1 + daily_return
self.lines[0][0] = self._cum_return
self._prev_value = current_value
Sources: backtrader/observers/broker.py:47-75
Configuration Options
Observers can be configured with parameters. For example, the Broker and Value observers support a fund parameter to toggle between standard portfolio valuation and fund-mode valuation.
Sources: backtrader/observers/broker.py:82-90
Integration with Cerebro and CLI
Observers can be added to a backtest either programmatically or via command-line arguments when using the btrun utility.
- Programmatic:
cerebro.addobserver(bt.observers.Cash) - Command Line:
python -m backtrader.btrun --observer module:classname:kwargs
The btrun module dynamically loads observers using the getobjects helper, which matches the provided class names against available classes in backtrader.observers.
Sources: backtrader/btrun/btrun.py:175-177, backtrader/btrun/btrun.py:288-336
The flowchart describes the path from adding an observer to its repetitive updates within the strategy execution loop.
Performance Monitoring
Observers are often used for benchmarking strategies against specific indices or tracking time-weighted returns. The Benchmark observer allows a strategy to compare its own portfolio value against a second data feed (the benchmark).
Sources: samples/observer-benchmark/observer-benchmark.py:87-97
Observers provide the backbone for real-time and post-trade analysis in the project, enabling developers to visualize how account equity and cash fluctuate in response to strategy logic and execution. Their design as LineIterator types ensures they maintain high performance and perfect synchronization with market data events.
Sources: backtrader/strategy.py:461, backtrader/observers/broker.py:27