nautechsystems/nautilus_trader · error
Python on_pool failed: {e}
Error message
Python on_pool failed: {e} What it means
This error wraps any Python exception raised inside the actor's `on_pool` callback when a DeFi `Pool` update is dispatched to the Python subclass (only compiled with the `defi` feature). The Rust `PyDataActor` clones the pool, converts it via `into_py_any`, and calls the Python method via `call_method1`; a resulting `PyErr` is converted to an anyhow error with this message. The underlying exception is raised in the user's Python override or during conversion.
Source
Thrown at crates/common/src/python/actor.rs:1175
self.dispatch_on_option_greeks(*greeks)
.map_err(|e| anyhow::anyhow!("Python on_option_greeks failed: {e}"))
}
fn on_option_chain(&mut self, slice: &OptionChainSlice) -> anyhow::Result<()> {
self.dispatch_on_option_chain(slice.clone())
.map_err(|e| anyhow::anyhow!("Python on_option_chain failed: {e}"))
}
#[cfg(feature = "defi")]
fn on_block(&mut self, block: &Block) -> anyhow::Result<()> {
self.dispatch_on_block(block.clone())
.map_err(|e| anyhow::anyhow!("Python on_block failed: {e}"))
}
#[cfg(feature = "defi")]
fn on_pool(&mut self, pool: &Pool) -> anyhow::Result<()> {
self.dispatch_on_pool(pool.clone())
.map_err(|e| anyhow::anyhow!("Python on_pool failed: {e}"))
}
#[cfg(feature = "defi")]
fn on_pool_swap(&mut self, swap: &PoolSwap) -> anyhow::Result<()> {
self.dispatch_on_pool_swap(swap.clone())
.map_err(|e| anyhow::anyhow!("Python on_pool_swap failed: {e}"))
}
#[cfg(feature = "defi")]
fn on_pool_liquidity_update(&mut self, update: &PoolLiquidityUpdate) -> anyhow::Result<()> {
self.dispatch_on_pool_liquidity_update(update.clone())
.map_err(|e| anyhow::anyhow!("Python on_pool_liquidity_update failed: {e}"))
}
#[cfg(feature = "defi")]
fn on_pool_fee_collect(&mut self, collect: &PoolFeeCollect) -> anyhow::Result<()> {
self.dispatch_on_pool_fee_collect(collect.clone())
.map_err(|e| anyhow::anyhow!("Python on_pool_fee_collect failed: {e}"))View on GitHub (pinned to 18893faf8b)
Solutions
- Read the appended Python traceback after 'Python on_pool failed:' to locate the raising line.
- Guard against zero/None liquidity and price fields before division or comparison.
- Register the pool instrument before processing its updates so lookups succeed.
- Verify Pool field names/types against the installed nautilus_trader version.
Example fix
// before
def on_pool(self, pool):
price = pool.token0_reserve / pool.token1_reserve
// after
def on_pool(self, pool):
if not pool.token1_reserve:
return
price = pool.token0_reserve / pool.token1_reserve Defensive patterns
Strategy: validation
Validate before calling
r0, r1 = pool.token0_reserve, pool.token1_reserve
if not r0 or not r1:
return # zero liquidity or uninitialized pool Type guard
def is_tradeable_pool(pool):
r0 = getattr(pool, "token0_reserve", 0)
r1 = getattr(pool, "token1_reserve", 0)
return r0 and r1 and r0 > 0 and r1 > 0 Try / catch
def on_pool(self, pool):
try:
self._track_pool(pool)
except Exception as e:
self.log.error(f"on_pool failed: {e}", exc_info=True) Prevention
- Guard against zero/None reserves before computing pool price
- Register pool instruments before processing their updates
- Use .get() defaults for per-pool state to avoid KeyError
- Test handlers against freshly created and drained pools
When it happens
Trigger: Any exception raised by the user's `on_pool(self, pool)` override — e.g. Decimal division by pool liquidity of zero, dict lookups on an unseen pool address/instrument_id, or a raising Rust-to-Python conversion of Pool.
Common situations: AMM/LP strategies tracking pools that encounter a freshly created or drained pool with zero liquidity; handlers written for an older Pool binding before an upgrade; pool identifiers changing format between chain deployments.
Related errors
- Python on_block failed: {e}
- Python on_book failed: {e}
- Python on_mark_price failed: {e}
- Python on_index_price failed: {e}
- Python on_funding_rate failed: {e}
AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08).
Data as JSON: /api/errors/43c47d77aafdcdac.
Report an issue: GitHub.