Skip to content

Commit

Permalink
Bad token detector metrics
Browse files Browse the repository at this point in the history
  • Loading branch information
squadgazzz committed Jan 9, 2025
1 parent 672b30f commit a9282c8
Show file tree
Hide file tree
Showing 6 changed files with 52 additions and 13 deletions.
20 changes: 18 additions & 2 deletions crates/driver/src/domain/competition/bad_tokens/metrics.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
use {
super::Quality,
crate::domain::eth,
crate::{
domain::eth,
infra::{observe::metrics, solver},
},
dashmap::DashMap,
std::{
sync::Arc,
Expand All @@ -27,6 +30,7 @@ pub struct Detector {
counter: Arc<DashMap<eth::TokenAddress, TokenStatistics>>,
log_only: bool,
token_freeze_time: Duration,
solver: solver::Name,
}

impl Detector {
Expand All @@ -35,13 +39,15 @@ impl Detector {
required_measurements: u32,
log_only: bool,
token_freeze_time: Duration,
solver: solver::Name,
) -> Self {
Self {
failure_ratio,
required_measurements,
counter: Default::default(),
log_only,
token_freeze_time,
solver,
}
}

Expand Down Expand Up @@ -120,6 +126,10 @@ impl Detector {
tokens = ?new_unsupported_tokens,
"mark tokens as unsupported"
);
metrics::get()
.bad_token_detection
.with_label_values(&[&self.solver.0, "metrics"])
.inc_by(new_unsupported_tokens.len() as u64);
}
}
}
Expand All @@ -133,7 +143,13 @@ mod tests {
#[tokio::test]
async fn unfreeze_bad_tokens() {
const FREEZE_DURATION: Duration = Duration::from_millis(50);
let detector = Detector::new(0.5, 2, false, FREEZE_DURATION);
let detector = Detector::new(
0.5,
2,
false,
FREEZE_DURATION,
solver::Name("mysolver".to_string()),
);

let token_a = eth::TokenAddress(eth::ContractAddress(H160([1; 20])));
let token_b = eth::TokenAddress(eth::ContractAddress(H160([2; 20])));
Expand Down
31 changes: 24 additions & 7 deletions crates/driver/src/domain/competition/bad_tokens/simulation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ use {
},
eth,
},
infra,
infra::{self, observe::metrics, solver},
},
futures::FutureExt,
model::interaction::InteractionData,
Expand All @@ -27,15 +27,21 @@ use {
/// solvers. Checks the behavior on transfer using a `trace_callMany`
/// based simulation.
#[derive(Clone)]
pub struct Detector(Arc<Inner>);
pub struct Detector {
inner: Arc<Inner>,
solver: solver::Name,
}

#[derive(Clone)]
pub struct DetectorBuilder(Arc<Inner>);

struct Inner {
cache: Cache,
detector: TraceCallDetectorRaw,
sharing: BoxRequestSharing<order::Uid, Quality>,
}

impl Detector {
impl DetectorBuilder {
pub fn new(max_age: Duration, eth: &infra::Ethereum) -> Self {
let detector =
TraceCallDetectorRaw::new(eth.web3().clone(), eth.contracts().settlement().address());
Expand All @@ -46,11 +52,20 @@ impl Detector {
}))
}

pub fn build(self, solver: solver::Name) -> Detector {
Detector {
inner: self.0.clone(),
solver,
}
}
}

impl Detector {
/// Simulates how the sell token behaves during transfers. Assumes that
/// the order owner has the required sell token balance and approvals
/// set.
pub async fn determine_sell_token_quality(&self, order: &Order, now: Instant) -> Quality {
let cache = &self.0.cache;
let cache = &self.inner.cache;
let quality = cache.get_quality(&order.sell.token, now);
if quality != Quality::Unknown {
return quality;
Expand All @@ -62,10 +77,10 @@ impl Detector {
// if an equivalent request is already in-flight and awaits that instead of
// creating a new one.
let uid = order.uid;
self.0
self.inner
.sharing
.shared_or_else(uid, move |_uid| {
let inner = self.0.clone();
let inner = self.inner.clone();
let sell_token = order.sell.token;
let pre_interactions: Vec<_> = order
.pre_interactions
Expand All @@ -82,6 +97,7 @@ impl Detector {
order::Partial::No => order.sell.amount.0,
};

let solver_name = self.solver.0.clone();
async move {
let result = inner
.detector
Expand All @@ -100,6 +116,7 @@ impl Detector {
}
Ok(TokenQuality::Bad { reason }) => {
tracing::debug!(reason, token=?sell_token.0, "cache token as unsupported");
metrics::get().bad_token_detection.with_label_values(&[&solver_name,"simulation"]).inc();
inner
.cache
.update_quality(sell_token, false, now);
Expand All @@ -117,6 +134,6 @@ impl std::ops::Deref for Detector {
type Target = Cache;

fn deref(&self) -> &Self::Target {
&self.0.cache
&self.inner.cache
}
}
7 changes: 5 additions & 2 deletions crates/driver/src/infra/api/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ pub struct Api {
pub eth: Ethereum,
pub mempools: Mempools,
pub addr: SocketAddr,
pub bad_token_detector: bad_tokens::simulation::Detector,
pub bad_token_detector_builder: bad_tokens::simulation::DetectorBuilder,
/// If this channel is specified, the bound address will be sent to it. This
/// allows the driver to bind to 0.0.0.0:0 during testing.
pub addr_sender: Option<oneshot::Sender<SocketAddr>>,
Expand Down Expand Up @@ -75,7 +75,9 @@ impl Api {
let mut bad_tokens =
bad_tokens::Detector::new(bad_token_config.tokens_supported.clone());
if bad_token_config.enable_simulation_strategy {
bad_tokens.with_simulation_detector(self.bad_token_detector.clone());
bad_tokens.with_simulation_detector(
self.bad_token_detector_builder.clone().build(name.clone()),
);
}

if bad_token_config.enable_metrics_strategy {
Expand All @@ -84,6 +86,7 @@ impl Api {
bad_token_config.metrics_strategy_required_measurements,
bad_token_config.metrics_strategy_log_only,
bad_token_config.metrics_strategy_token_freeze_time,
name.clone(),
));
}

Expand Down
3 changes: 3 additions & 0 deletions crates/driver/src/infra/observe/metrics.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,9 @@ pub struct Metrics {
/// The results of the mempool submission.
#[metric(labels("mempool", "result"))]
pub mempool_submission: prometheus::IntCounterVec,
/// Bad token detection metrics by solver and detection strategy.
#[metric(labels("solver", "strategy"))]
pub bad_token_detection: prometheus::IntCounterVec,
}

/// Setup the metrics registry.
Expand Down
2 changes: 1 addition & 1 deletion crates/driver/src/infra/observe/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ use {
url::Url,
};

mod metrics;
pub mod metrics;

/// Setup the observability. The log argument configures the tokio tracing
/// framework.
Expand Down
2 changes: 1 addition & 1 deletion crates/driver/src/run.rs
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ async fn run_with(args: cli::Args, addr_sender: Option<oneshot::Sender<SocketAdd
eth.clone(),
)
.unwrap(),
bad_token_detector: bad_tokens::simulation::Detector::new(
bad_token_detector_builder: bad_tokens::simulation::DetectorBuilder::new(
config.simulation_bad_token_max_age,
&eth,
),
Expand Down

0 comments on commit a9282c8

Please sign in to comment.