This commit is contained in:
2026-05-05 20:49:45 +02:00
parent f2c227e08f
commit 348e76660c
28 changed files with 3279 additions and 210 deletions

View File

@@ -0,0 +1,444 @@
// file: kb_lib/src/db/dtos/local_pipeline_diagnostics.rs
//! DTOs for local pipeline diagnostics.
/// Local pipeline diagnostics summary.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalPipelineDiagnosticSummaryDto {
/// Total persisted chain transactions.
pub transaction_count: i64,
/// Total successful chain transactions.
pub ok_transaction_count: i64,
/// Total failed chain transactions.
pub failed_transaction_count: i64,
/// Total decoded DEX events.
pub decoded_event_count: i64,
/// Total decoded DEX trade candidates.
pub decoded_trade_candidate_count: i64,
/// Total decoded DEX candle candidates.
pub decoded_candle_candidate_count: i64,
/// Whether the local persisted pipeline has no blocking diagnostic issue.
pub diagnostics_clean: bool,
/// Number of blocking diagnostic issues.
///
/// This currently includes actionable missing trade events, invalid trade
/// events, duplicate decoded-event trade rows, and duplicate candle buckets.
pub blocking_issue_count: i64,
/// Total decoded DEX events that are trade candidates but have no trade event,
/// including intentionally ignored failed transactions.
pub missing_trade_event_count: i64,
/// Total persisted trade events.
pub trade_event_count: i64,
/// Explicit alias for decoded trade candidates without linked trade event.
pub decoded_trade_candidate_without_trade_event_count: i64,
/// Trade candidates without linked trade event on successful transactions.
pub decoded_trade_candidate_without_trade_event_on_ok_transaction_count: i64,
/// Trade candidates without linked trade event on failed transactions.
pub decoded_trade_candidate_without_trade_event_on_failed_transaction_count: i64,
/// Actionable missing trade events on successful transactions.
pub actionable_missing_trade_event_count: i64,
/// Ignored missing trade events caused by failed transactions.
pub ignored_failed_transaction_trade_candidate_count: i64,
/// Trade candidates without linked trade event and without explicit base/quote payload amounts.
pub decoded_trade_candidate_without_amount_payload_count: i64,
/// Total trade events with missing or invalid pricing fields.
pub invalid_trade_event_count: i64,
/// Total persisted pair candles.
pub pair_candle_count: i64,
/// Real duplicate trade rows grouped by decoded event id.
pub duplicate_decoded_event_trade_count: i64,
/// Multi-trade groups sharing the same signature and pair id.
pub multi_trade_signature_pair_count: i64,
/// Total duplicate candle buckets.
pub duplicate_candle_bucket_count: i64,
/// Total known tokens.
pub token_count: i64,
/// Total tokens missing symbol or name.
pub token_metadata_missing_count: i64,
/// Total known pools.
pub pool_count: i64,
/// Total known pairs.
pub pair_count: i64,
/// Total pairs without trade event.
pub pair_without_trade_count: i64,
/// Total pairs without candle.
pub pair_without_candle_count: i64,
/// Diagnostics grouped by DEX.
pub dex_summaries: std::vec::Vec<crate::KbLocalDexDiagnosticSummaryDto>,
/// Diagnostics grouped by pair.
pub pair_summaries: std::vec::Vec<crate::KbLocalPairDiagnosticSummaryDto>,
/// Diagnostics grouped by decoded event kind.
pub decoded_event_summaries: std::vec::Vec<crate::KbLocalDecodedEventDiagnosticSummaryDto>,
/// Samples of decoded trade candidates without linked trade event.
pub missing_trade_event_samples:
std::vec::Vec<crate::KbLocalMissingTradeEventDiagnosticSampleDto>,
/// Samples of duplicated trade rows by decoded event id.
pub duplicate_decoded_event_trade_samples:
std::vec::Vec<crate::KbLocalDuplicateDecodedEventTradeDiagnosticSampleDto>,
/// Samples of multi-trade signature/pair groups.
pub multi_trade_signature_pair_samples:
std::vec::Vec<crate::KbLocalMultiTradeSignaturePairDiagnosticSampleDto>,
/// Samples of pairs without trade.
pub pair_without_trade_samples: std::vec::Vec<crate::KbLocalPairGapDiagnosticSampleDto>,
/// Samples of pairs without candle.
pub pair_without_candle_samples: std::vec::Vec<crate::KbLocalPairGapDiagnosticSampleDto>,
}
/// Local DEX diagnostics summary.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalDexDiagnosticSummaryDto {
/// DEX code or protocol name.
pub dex_code: std::string::String,
/// Total known pools for this DEX.
pub pool_count: i64,
/// Total known pairs for this DEX.
pub pair_count: i64,
/// Total decoded events for this DEX.
pub decoded_event_count: i64,
/// Total decoded trade candidates for this DEX.
pub decoded_trade_candidate_count: i64,
/// Total decoded candle candidates for this DEX.
pub decoded_candle_candidate_count: i64,
/// Total persisted trade events for this DEX.
pub trade_event_count: i64,
/// Total persisted candles for this DEX.
pub pair_candle_count: i64,
}
/// Local pair diagnostics summary.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalPairDiagnosticSummaryDto {
/// Pair id.
pub pair_id: i64,
/// Pool address.
pub pool_address: std::string::String,
/// DEX code.
pub dex_code: std::string::String,
/// Base token mint.
pub base_mint: std::string::String,
/// Base token symbol.
pub base_symbol: std::option::Option<std::string::String>,
/// Quote token mint.
pub quote_mint: std::string::String,
/// Quote token symbol.
pub quote_symbol: std::option::Option<std::string::String>,
/// Pair symbol.
pub pair_symbol: std::option::Option<std::string::String>,
/// Total decoded events attached to the pool.
pub decoded_event_count: i64,
/// Total decoded trade candidates attached to the pool.
pub decoded_trade_candidate_count: i64,
/// Total decoded candle candidates attached to the pool.
pub decoded_candle_candidate_count: i64,
/// Total trade events attached to the pair.
pub trade_event_count: i64,
/// Total invalid trade events attached to the pair.
pub invalid_trade_event_count: i64,
/// Total candle buckets attached to the pair.
pub pair_candle_count: i64,
/// Last known price.
pub last_price_quote_per_base: std::option::Option<f64>,
}
/// Local decoded-event diagnostics summary.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalDecodedEventDiagnosticSummaryDto {
/// Protocol name.
pub protocol_name: std::string::String,
/// Event kind.
pub event_kind: std::string::String,
/// Event category.
pub event_category: std::option::Option<std::string::String>,
/// Whether payload says this event is a trade candidate.
pub trade_candidate: std::option::Option<bool>,
/// Whether payload says this event is a candle candidate.
pub candle_candidate: std::option::Option<bool>,
/// Event count.
pub event_count: i64,
/// Trade-event count linked to these decoded events.
pub trade_event_count: i64,
}
/// Internal flat counter row for local diagnostics.
#[derive(Debug, Clone)]
pub struct KbLocalPipelineDiagnosticCountersDto {
/// Total persisted chain transactions.
pub transaction_count: i64,
/// Total successful chain transactions.
pub ok_transaction_count: i64,
/// Total failed chain transactions.
pub failed_transaction_count: i64,
/// Total decoded DEX events.
pub decoded_event_count: i64,
/// Total decoded DEX trade candidates.
pub decoded_trade_candidate_count: i64,
/// Total decoded DEX candle candidates.
pub decoded_candle_candidate_count: i64,
/// Total decoded trade candidates without trade event, including ignored failed transactions.
pub missing_trade_event_count: i64,
/// Explicit alias for decoded trade candidates without linked trade event.
pub decoded_trade_candidate_without_trade_event_count: i64,
/// Trade candidates without linked trade event on successful transactions.
pub decoded_trade_candidate_without_trade_event_on_ok_transaction_count: i64,
/// Trade candidates without linked trade event on failed transactions.
pub decoded_trade_candidate_without_trade_event_on_failed_transaction_count: i64,
/// Actionable missing trade events on successful transactions.
pub actionable_missing_trade_event_count: i64,
/// Ignored missing trade events caused by failed transactions.
pub ignored_failed_transaction_trade_candidate_count: i64,
/// Trade candidates without linked trade event and without explicit base/quote payload amounts.
pub decoded_trade_candidate_without_amount_payload_count: i64,
/// Total persisted trade events.
pub trade_event_count: i64,
/// Total invalid trade events.
pub invalid_trade_event_count: i64,
/// Total persisted candles.
pub pair_candle_count: i64,
/// Real duplicate trade rows grouped by decoded event id.
pub duplicate_decoded_event_trade_count: i64,
/// Multi-trade groups sharing the same signature and pair id.
pub multi_trade_signature_pair_count: i64,
/// Total duplicate candle groups.
pub duplicate_candle_bucket_count: i64,
/// Total known tokens.
pub token_count: i64,
/// Total tokens missing metadata.
pub token_metadata_missing_count: i64,
/// Total known pools.
pub pool_count: i64,
/// Total known pairs.
pub pair_count: i64,
/// Total pairs without trade.
pub pair_without_trade_count: i64,
/// Total pairs without candle.
pub pair_without_candle_count: i64,
}
/// SQL row for global local pipeline diagnostic counters.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalPipelineDiagnosticCountersRow {
pub(crate) transaction_count: i64,
pub(crate) ok_transaction_count: i64,
pub(crate) failed_transaction_count: i64,
pub(crate) decoded_event_count: i64,
pub(crate) decoded_trade_candidate_count: i64,
pub(crate) decoded_candle_candidate_count: i64,
pub(crate) missing_trade_event_count: i64,
pub(crate) decoded_trade_candidate_without_trade_event_count: i64,
pub(crate) decoded_trade_candidate_without_trade_event_on_ok_transaction_count: i64,
pub(crate) decoded_trade_candidate_without_trade_event_on_failed_transaction_count: i64,
pub(crate) actionable_missing_trade_event_count: i64,
pub(crate) ignored_failed_transaction_trade_candidate_count: i64,
pub(crate) decoded_trade_candidate_without_amount_payload_count: i64,
pub(crate) trade_event_count: i64,
pub(crate) invalid_trade_event_count: i64,
pub(crate) pair_candle_count: i64,
pub(crate) duplicate_decoded_event_trade_count: i64,
pub(crate) multi_trade_signature_pair_count: i64,
pub(crate) duplicate_candle_bucket_count: i64,
pub(crate) token_count: i64,
pub(crate) token_metadata_missing_count: i64,
pub(crate) pool_count: i64,
pub(crate) pair_count: i64,
pub(crate) pair_without_trade_count: i64,
pub(crate) pair_without_candle_count: i64,
}
/// SQL row for local DEX diagnostics.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalDexDiagnosticSummaryRow {
pub(crate) dex_code: std::string::String,
pub(crate) pool_count: i64,
pub(crate) pair_count: i64,
pub(crate) decoded_event_count: i64,
pub(crate) decoded_trade_candidate_count: i64,
pub(crate) decoded_candle_candidate_count: i64,
pub(crate) trade_event_count: i64,
pub(crate) pair_candle_count: i64,
}
/// SQL row for local pair diagnostics.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalPairDiagnosticSummaryRow {
pub(crate) pair_id: i64,
pub(crate) pool_address: std::string::String,
pub(crate) dex_code: std::string::String,
pub(crate) base_mint: std::string::String,
pub(crate) base_symbol: std::option::Option<std::string::String>,
pub(crate) quote_mint: std::string::String,
pub(crate) quote_symbol: std::option::Option<std::string::String>,
pub(crate) pair_symbol: std::option::Option<std::string::String>,
pub(crate) decoded_event_count: i64,
pub(crate) decoded_trade_candidate_count: i64,
pub(crate) decoded_candle_candidate_count: i64,
pub(crate) trade_event_count: i64,
pub(crate) invalid_trade_event_count: i64,
pub(crate) pair_candle_count: i64,
pub(crate) last_price_quote_per_base: std::option::Option<f64>,
}
/// SQL row for local decoded-event diagnostics.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalDecodedEventDiagnosticSummaryRow {
pub(crate) protocol_name: std::string::String,
pub(crate) event_kind: std::string::String,
pub(crate) event_category: std::option::Option<std::string::String>,
pub(crate) trade_candidate: std::option::Option<i64>,
pub(crate) candle_candidate: std::option::Option<i64>,
pub(crate) event_count: i64,
pub(crate) trade_event_count: i64,
}
/// Sample of a decoded trade candidate without linked trade event.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalMissingTradeEventDiagnosticSampleDto {
/// Decoded event id.
pub decoded_event_id: i64,
/// Chain transaction id.
pub transaction_id: std::option::Option<i64>,
/// Transaction signature.
pub signature: std::option::Option<std::string::String>,
/// Protocol name.
pub protocol_name: std::string::String,
/// Event kind.
pub event_kind: std::string::String,
/// Pool account.
pub pool_account: std::option::Option<std::string::String>,
/// Whether the source transaction failed.
pub transaction_failed: bool,
/// Diagnostic reason explaining why no trade event was linked.
pub reason: std::string::String,
/// Whether payload has an explicit base amount.
pub has_base_amount_payload: bool,
/// Whether payload has an explicit quote amount.
pub has_quote_amount_payload: bool,
/// Whether payload has an explicit price.
pub has_price_payload: bool,
}
/// Sample of duplicated trade rows grouped by decoded event id.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalDuplicateDecodedEventTradeDiagnosticSampleDto {
/// Decoded event id.
pub decoded_event_id: i64,
/// Protocol name.
pub protocol_name: std::option::Option<std::string::String>,
/// Event kind.
pub event_kind: std::option::Option<std::string::String>,
/// Pool account.
pub pool_account: std::option::Option<std::string::String>,
/// Duplicate trade row count.
pub trade_event_count: i64,
/// Trade event ids.
pub trade_event_ids: std::option::Option<std::string::String>,
/// Signatures.
pub signatures: std::option::Option<std::string::String>,
}
/// Sample of multi-trade groups sharing the same signature and pair id.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalMultiTradeSignaturePairDiagnosticSampleDto {
/// Transaction signature.
pub signature: std::string::String,
/// Pair id.
pub pair_id: i64,
/// Pool address.
pub pool_address: std::option::Option<std::string::String>,
/// DEX code.
pub dex_code: std::option::Option<std::string::String>,
/// Trade event count.
pub trade_event_count: i64,
/// Distinct decoded event count.
pub decoded_event_count: i64,
/// Trade event ids.
pub trade_event_ids: std::option::Option<std::string::String>,
/// Decoded event ids.
pub decoded_event_ids: std::option::Option<std::string::String>,
}
/// Sample of a pair gap.
#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct KbLocalPairGapDiagnosticSampleDto {
/// Pair id.
pub pair_id: i64,
/// Pool address.
pub pool_address: std::string::String,
/// DEX code.
pub dex_code: std::string::String,
/// Base mint.
pub base_mint: std::string::String,
/// Base symbol.
pub base_symbol: std::option::Option<std::string::String>,
/// Quote mint.
pub quote_mint: std::string::String,
/// Quote symbol.
pub quote_symbol: std::option::Option<std::string::String>,
/// Pair symbol.
pub pair_symbol: std::option::Option<std::string::String>,
/// Decoded event count.
pub decoded_event_count: i64,
/// Decoded trade candidate count.
pub decoded_trade_candidate_count: i64,
/// Trade event count.
pub trade_event_count: i64,
/// Pair candle count.
pub pair_candle_count: i64,
}
/// SQL row for missing trade event samples.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalMissingTradeEventDiagnosticSampleRow {
pub(crate) decoded_event_id: i64,
pub(crate) transaction_id: std::option::Option<i64>,
pub(crate) signature: std::option::Option<std::string::String>,
pub(crate) protocol_name: std::string::String,
pub(crate) event_kind: std::string::String,
pub(crate) pool_account: std::option::Option<std::string::String>,
pub(crate) transaction_failed: i64,
pub(crate) reason: std::string::String,
pub(crate) has_base_amount_payload: i64,
pub(crate) has_quote_amount_payload: i64,
pub(crate) has_price_payload: i64,
}
/// SQL row for duplicated decoded event trade samples.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalDuplicateDecodedEventTradeDiagnosticSampleRow {
pub(crate) decoded_event_id: i64,
pub(crate) protocol_name: std::option::Option<std::string::String>,
pub(crate) event_kind: std::option::Option<std::string::String>,
pub(crate) pool_account: std::option::Option<std::string::String>,
pub(crate) trade_event_count: i64,
pub(crate) trade_event_ids: std::option::Option<std::string::String>,
pub(crate) signatures: std::option::Option<std::string::String>,
}
/// SQL row for multi-trade signature/pair samples.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalMultiTradeSignaturePairDiagnosticSampleRow {
pub(crate) signature: std::string::String,
pub(crate) pair_id: i64,
pub(crate) pool_address: std::option::Option<std::string::String>,
pub(crate) dex_code: std::option::Option<std::string::String>,
pub(crate) trade_event_count: i64,
pub(crate) decoded_event_count: i64,
pub(crate) trade_event_ids: std::option::Option<std::string::String>,
pub(crate) decoded_event_ids: std::option::Option<std::string::String>,
}
/// SQL row for pair gap samples.
#[derive(Debug, Clone, sqlx::FromRow)]
pub(crate) struct KbLocalPairGapDiagnosticSampleRow {
pub(crate) pair_id: i64,
pub(crate) pool_address: std::string::String,
pub(crate) dex_code: std::string::String,
pub(crate) base_mint: std::string::String,
pub(crate) base_symbol: std::option::Option<std::string::String>,
pub(crate) quote_mint: std::string::String,
pub(crate) quote_symbol: std::option::Option<std::string::String>,
pub(crate) pair_symbol: std::option::Option<std::string::String>,
pub(crate) decoded_event_count: i64,
pub(crate) decoded_trade_candidate_count: i64,
pub(crate) trade_event_count: i64,
pub(crate) pair_candle_count: i64,
}