Skip to content

Commit 3ffa9f1

Browse files
fix for daily stats for querier (#811)
returns querier stats + sum of all ingestors' stats
1 parent 6129992 commit 3ffa9f1

File tree

3 files changed

+124
-5
lines changed

3 files changed

+124
-5
lines changed

server/src/handlers/http/cluster/mod.rs

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ use crate::handlers::{STATIC_SCHEMA_FLAG, TIME_PARTITION_KEY};
2727
use crate::option::CONFIG;
2828

2929
use crate::metrics::prom_utils::Metrics;
30+
use crate::stats::Stats;
3031
use crate::storage::object_storage::ingestor_metadata_path;
3132
use crate::storage::PARSEABLE_ROOT_DIRECTORY;
3233
use crate::storage::{ObjectStorageError, STREAM_ROOT_DIRECTORY};
@@ -156,6 +157,67 @@ pub async fn sync_streams_with_ingestors(
156157
Ok(())
157158
}
158159

160+
pub async fn fetch_daily_stats_from_ingestors(
161+
stream_name: &str,
162+
date: &str,
163+
) -> Result<Stats, StreamError> {
164+
let mut total_events_ingested: u64 = 0;
165+
let mut total_ingestion_size: u64 = 0;
166+
let mut total_storage_size: u64 = 0;
167+
168+
let ingestor_infos = get_ingestor_info().await.map_err(|err| {
169+
log::error!("Fatal: failed to get ingestor info: {:?}", err);
170+
StreamError::Anyhow(err)
171+
})?;
172+
for ingestor in ingestor_infos.iter() {
173+
let uri = Url::parse(&format!(
174+
"{}{}/metrics",
175+
&ingestor.domain_name,
176+
base_path_without_preceding_slash()
177+
))
178+
.map_err(|err| {
179+
StreamError::Anyhow(anyhow::anyhow!("Invalid URL in Ingestor Metadata: {}", err))
180+
})?;
181+
182+
let res = reqwest::Client::new()
183+
.get(uri)
184+
.header(header::CONTENT_TYPE, "application/json")
185+
.send()
186+
.await;
187+
188+
if let Ok(res) = res {
189+
let text = res
190+
.text()
191+
.await
192+
.map_err(|err| StreamError::Anyhow(anyhow::anyhow!("Request failed: {}", err)))?;
193+
let lines: Vec<Result<String, std::io::Error>> =
194+
text.lines().map(|line| Ok(line.to_owned())).collect_vec();
195+
196+
let sample = prometheus_parse::Scrape::parse(lines.into_iter())
197+
.map_err(|err| {
198+
StreamError::Anyhow(anyhow::anyhow!(
199+
"Invalid URL in Ingestor Metadata: {}",
200+
err
201+
))
202+
})?
203+
.samples;
204+
205+
let (events_ingested, ingestion_size, storage_size) =
206+
Metrics::get_daily_stats_from_samples(sample, stream_name, date);
207+
total_events_ingested += events_ingested;
208+
total_ingestion_size += ingestion_size;
209+
total_storage_size += storage_size;
210+
}
211+
}
212+
213+
let stats = Stats {
214+
events: total_events_ingested,
215+
ingestion: total_ingestion_size,
216+
storage: total_storage_size,
217+
};
218+
Ok(stats)
219+
}
220+
159221
/// get the cumulative stats from all ingestors
160222
pub async fn fetch_stats_from_ingestors(
161223
stream_name: &str,

server/src/handlers/http/logstream.rs

Lines changed: 21 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,9 @@
1919
use self::error::{CreateStreamError, StreamError};
2020
use super::base_path_without_preceding_slash;
2121
use super::cluster::utils::{merge_quried_stats, IngestionStats, QueriedStats, StorageStats};
22-
use super::cluster::{fetch_stats_from_ingestors, INTERNAL_STREAM_NAME};
22+
use super::cluster::{
23+
fetch_daily_stats_from_ingestors, fetch_stats_from_ingestors, INTERNAL_STREAM_NAME,
24+
};
2325
use crate::alerts::Alerts;
2426
use crate::handlers::{
2527
CUSTOM_PARTITION_KEY, STATIC_SCHEMA_FLAG, TIME_PARTITION_KEY, TIME_PARTITION_LIMIT_KEY,
@@ -607,10 +609,24 @@ pub async fn get_stats(req: HttpRequest) -> Result<impl Responder, StreamError>
607609
}
608610

609611
if !date_value.is_empty() {
610-
let stats = get_stats_date(&stream_name, date_value).await?;
611-
let stats = serde_json::to_value(stats)?;
612-
613-
return Ok((web::Json(stats), StatusCode::OK));
612+
if CONFIG.parseable.mode == Mode::Query {
613+
let querier_stats = get_stats_date(&stream_name, date_value).await?;
614+
let ingestor_stats =
615+
fetch_daily_stats_from_ingestors(&stream_name, date_value).await?;
616+
let total_stats = Stats {
617+
events: querier_stats.events + ingestor_stats.events,
618+
ingestion: querier_stats.ingestion + ingestor_stats.ingestion,
619+
storage: querier_stats.storage + ingestor_stats.storage,
620+
};
621+
let stats = serde_json::to_value(total_stats)?;
622+
623+
return Ok((web::Json(stats), StatusCode::OK));
624+
} else {
625+
let stats = get_stats_date(&stream_name, date_value).await?;
626+
let stats = serde_json::to_value(stats)?;
627+
628+
return Ok((web::Json(stats), StatusCode::OK));
629+
}
614630
}
615631
}
616632

server/src/metrics/prom_utils.rs

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,47 @@ impl Metrics {
113113
}
114114

115115
impl Metrics {
116+
pub fn get_daily_stats_from_samples(
117+
samples: Vec<PromSample>,
118+
stream_name: &str,
119+
date: &str,
120+
) -> (u64, u64, u64) {
121+
let mut events_ingested: u64 = 0;
122+
let mut ingestion_size: u64 = 0;
123+
let mut storage_size: u64 = 0;
124+
for sample in samples {
125+
if let PromValue::Gauge(val) = sample.value {
126+
match sample.metric.as_str() {
127+
"parseable_events_ingested_date" => {
128+
if sample.labels.get("stream").expect("stream name is present")
129+
== stream_name
130+
&& sample.labels.get("date").expect("date is present") == date
131+
{
132+
events_ingested = val as u64;
133+
}
134+
}
135+
"parseable_events_ingested_size_date" => {
136+
if sample.labels.get("stream").expect("stream name is present")
137+
== stream_name
138+
&& sample.labels.get("date").expect("date is present") == date
139+
{
140+
ingestion_size = val as u64;
141+
}
142+
}
143+
"parseable_events_storage_size_date" => {
144+
if sample.labels.get("stream").expect("stream name is present")
145+
== stream_name
146+
&& sample.labels.get("date").expect("date is present") == date
147+
{
148+
storage_size = val as u64;
149+
}
150+
}
151+
_ => {}
152+
}
153+
}
154+
}
155+
(events_ingested, ingestion_size, storage_size)
156+
}
116157
pub async fn from_prometheus_samples(
117158
samples: Vec<PromSample>,
118159
ingestor_metadata: &IngestorMetadata,

0 commit comments

Comments
 (0)