Skip to content

Commit

Permalink
chore: Add metrics on types of filters in API (matter-labs#526)
Browse files Browse the repository at this point in the history
## What ❔

Add metrics on types of filters, especially:
* Count of the current amount of filters of specific type
* Frequency of requests to specific filter type
* Lifetime of filters of specific type
* Request count for a specific filter

## Why ❔

We receive a lot of requests in our WebSocket API to getFilterChanges
method.

We want to understand types of filters and distribution of load among
them.

## Checklist

- [x] PR title corresponds to the body of PR (we generate changelog
entries from PRs).
- [ ] Tests for the changes have been added / updated.
- [x] Documentation comments have been added / updated.
- [x] Code has been formatted via `zk fmt` and `zk lint`.

---------

Co-authored-by: Alex Ostrovski <[email protected]>
  • Loading branch information
Artemka374 and slowli authored Nov 22, 2023
1 parent 67ef133 commit 6e4d228
Show file tree
Hide file tree
Showing 5 changed files with 197 additions and 109 deletions.
9 changes: 0 additions & 9 deletions core/lib/web3_decl/src/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ use core::convert::{TryFrom, TryInto};
use core::fmt;
use core::marker::PhantomData;

use chrono::NaiveDateTime;
use itertools::unfold;
use rlp::Rlp;
use serde::{de, Deserialize, Serialize, Serializer};
Expand Down Expand Up @@ -105,14 +104,6 @@ pub enum FilterChanges {
Empty([u8; 0]),
}

/// Represents all kinds of `Filter`.
#[derive(Debug, Clone)]
pub enum TypedFilter {
Events(Filter, zksync_types::MiniblockNumber),
Blocks(zksync_types::MiniblockNumber),
PendingTransactions(NaiveDateTime),
}

/// Either value or array of values.
#[derive(Default, Debug, PartialEq, Clone)]
pub struct ValueOrArray<T>(pub Vec<T>);
Expand Down
42 changes: 39 additions & 3 deletions core/lib/zksync_core/src/api_server/web3/metrics.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,18 +2,17 @@
use vise::{
Buckets, Counter, EncodeLabelSet, EncodeLabelValue, Family, Gauge, Histogram, LabeledFamily,
LatencyObserver, Metrics,
LatencyObserver, Metrics, Unit,
};

use std::{
fmt,
time::{Duration, Instant},
};

use super::{ApiTransport, TypedFilter};
use zksync_types::api;

use super::ApiTransport;

#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, EncodeLabelValue, EncodeLabelSet)]
#[metrics(label = "scheme", rename_all = "UPPERCASE")]
pub(super) enum ApiTransportLabel {
Expand Down Expand Up @@ -195,3 +194,40 @@ pub(super) struct PubSubMetrics {

#[vise::register]
pub(super) static PUB_SUB_METRICS: vise::Global<PubSubMetrics> = vise::Global::new();

#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, EncodeLabelValue, EncodeLabelSet)]
#[metrics(label = "type", rename_all = "snake_case")]
pub(super) enum FilterType {
Events,
Blocks,
PendingTransactions,
}

impl From<&TypedFilter> for FilterType {
fn from(value: &TypedFilter) -> Self {
match value {
TypedFilter::Events(_, _) => FilterType::Events,
TypedFilter::Blocks(_) => FilterType::Blocks,
TypedFilter::PendingTransactions(_) => FilterType::PendingTransactions,
}
}
}

#[derive(Debug, Metrics)]
#[metrics(prefix = "api_web3_filter")]
pub(super) struct FilterMetrics {
/// Number of currently active filters grouped by the filter type
pub metrics_count: Family<FilterType, Gauge>,
/// Time in seconds between consecutive requests to the filter grouped by the filter type
#[metrics(buckets = Buckets::LATENCIES, unit = Unit::Seconds)]
pub request_frequency: Family<FilterType, Histogram<Duration>>,
/// Lifetime of a filter in seconds grouped by the filter type
#[metrics(buckets = Buckets::LATENCIES, unit = Unit::Seconds)]
pub filter_lifetime: Family<FilterType, Histogram<Duration>>,
/// Number of requests to the filter grouped by the filter type
#[metrics(buckets = Buckets::exponential(1.0..=1048576.0, 2.0))]
pub filter_count: Family<FilterType, Histogram<usize>>,
}

#[vise::register]
pub(super) static FILTER_METRICS: vise::Global<FilterMetrics> = vise::Global::new();
17 changes: 15 additions & 2 deletions core/lib/zksync_core/src/api_server/web3/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,10 @@ use jsonrpc_core::MetaIoHandler;
use jsonrpc_http_server::hyper;
use jsonrpc_pubsub::PubSubHandler;
use serde::Deserialize;
use tokio::sync::{oneshot, watch, RwLock};
use tokio::sync::{oneshot, watch, Mutex};
use tower_http::{cors::CorsLayer, metrics::InFlightRequestsLayer};

use chrono::NaiveDateTime;
use std::{net::SocketAddr, sync::Arc, time::Duration};
use tokio::task::JoinHandle;

Expand All @@ -23,6 +24,7 @@ use zksync_web3_decl::{
DebugNamespaceServer, EnNamespaceServer, EthNamespaceServer, NetNamespaceServer,
Web3NamespaceServer, ZksNamespaceServer,
},
types::Filter,
};

use crate::{
Expand Down Expand Up @@ -63,6 +65,17 @@ use self::state::{Filters, InternalApiConfig, RpcState, SealedMiniblockNumber};
/// Timeout for graceful shutdown logic within API servers.
const GRACEFUL_SHUTDOWN_TIMEOUT: Duration = Duration::from_secs(5);

/// Represents all kinds of `Filter`.
#[derive(Debug, Clone)]
pub(crate) enum TypedFilter {
// Events from some block with additional filters
Events(Filter, MiniblockNumber),
// Blocks from some block
Blocks(MiniblockNumber),
// Pending transactions from some timestamp
PendingTransactions(NaiveDateTime),
}

#[derive(Debug, Clone, Copy)]
enum ApiBackend {
Jsonrpsee,
Expand Down Expand Up @@ -278,7 +291,7 @@ impl<G: 'static + Send + Sync + L1GasPriceProvider> ApiBuilder<G> {
tokio::spawn(update_task);

RpcState {
installed_filters: Arc::new(RwLock::new(Filters::new(
installed_filters: Arc::new(Mutex::new(Filters::new(
self.filters_limit.unwrap_or(usize::MAX),
))),
connection_pool: self.pool,
Expand Down
Loading

0 comments on commit 6e4d228

Please sign in to comment.