From dbe196f388c8ba701e41e0c1d56150a965bfc200 Mon Sep 17 00:00:00 2001 From: Marco De Araujo Date: Mon, 22 Dec 2025 11:40:28 -0400 Subject: [PATCH] Get info from status page json --- src/heartbeat/mod.rs | 4 +-- src/heartbeat/parser.rs | 25 +++------------- src/locales/en-US/main.ftl | 2 ++ src/locales/pt-BR/main.ftl | 2 ++ src/main.rs | 37 ++++++++++++++++++----- src/status_page/mod.rs | 4 +++ src/status_page/model.rs | 61 ++++++++++++++++++++++++++++++++++++++ src/status_page/parser.rs | 8 +++++ 8 files changed, 113 insertions(+), 30 deletions(-) create mode 100644 src/status_page/mod.rs create mode 100644 src/status_page/model.rs create mode 100644 src/status_page/parser.rs diff --git a/src/heartbeat/mod.rs b/src/heartbeat/mod.rs index 80f15d7..33118d8 100644 --- a/src/heartbeat/mod.rs +++ b/src/heartbeat/mod.rs @@ -1,4 +1,4 @@ -pub mod parser; pub mod model; -pub use parser::{format_duration, parse_response,status_to_string}; +pub mod parser; pub use model::HeartbeatResponse; +pub use parser::parse_response; diff --git a/src/heartbeat/parser.rs b/src/heartbeat/parser.rs index 6153c50..3733065 100644 --- a/src/heartbeat/parser.rs +++ b/src/heartbeat/parser.rs @@ -1,28 +1,11 @@ -use anyhow::{Context, Ok, Result}; -use std::collections::HashMap; -use crate::i18n::t; use super::HeartbeatResponse; +use crate::i18n::t; +use anyhow::{Context, Ok, Result}; pub fn parse_response(json_text: &str) -> Result { - let mut response: HeartbeatResponse = serde_json::from_str(json_text) - .with_context(|| t("invalid-json-heartbeat"))?; + let mut response: HeartbeatResponse = + serde_json::from_str(json_text).with_context(|| t("invalid-json-heartbeat"))?; response.process()?; Ok(response) } - -pub fn status_to_string(status: u8) -> String { - match status { - 1 => t("up"), - 2 => t("down"), - _ => t("unknown"), - } -} - -pub fn format_duration(duration_ms:Option) -> String { - match duration_ms { - Some(ms) if ms < 1000 => format!("{}ms", ms), - Some(ms) => format!("{:.1}s", ms), - None => "N/A".to_string(), - } -} diff --git a/src/locales/en-US/main.ftl b/src/locales/en-US/main.ftl index f43f11b..d799d93 100644 --- a/src/locales/en-US/main.ftl +++ b/src/locales/en-US/main.ftl @@ -3,3 +3,5 @@ missing_api_key = ❌ API key not provided. Use --api-key or environment variabl success = ✅ Metrics received successfully! metrics_preview = 📋 First 200 characters of metrics: Response = Response +invalid-json-status-page = ❌ Error parssing status page JSON +invalid-json-heartbeat = ❌ Error parssing heartbeat JSON diff --git a/src/locales/pt-BR/main.ftl b/src/locales/pt-BR/main.ftl index ccb34a1..dff7127 100644 --- a/src/locales/pt-BR/main.ftl +++ b/src/locales/pt-BR/main.ftl @@ -3,3 +3,5 @@ metrics_preview = 📋 Primeiras 200 caracteres das métricas: missing_api_key = ❌ API key não fornecida. Use --api-key ou a variável de ambiente UPTIME_API_KEY missing_url = ❌ URL não fornecida. Use --url ou a variável de ambiente UPTIME_URL Response = Resposta +invalid-json-status-page = ❌ Falha ao parsear JSON do status page +invalid-json-heartbeat = ❌ Falha ao parsear JSON do heartbeat diff --git a/src/main.rs b/src/main.rs index 7135534..f4a767b 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,6 +5,7 @@ use std::result::Result::Ok; mod i18n; use i18n::{init_locales, t}; mod heartbeat; +mod status_page; #[derive(Debug, Parser)] #[command(author, version, about)] @@ -19,27 +20,49 @@ struct Args { fn main() -> Result<()> { init_locales()?; let args = Args::parse(); + let base_url = args.base_url.trim_end_matches("/"); let heartbeat_url = format!( "{}/api/status-page/heartbeat/{}", - args.base_url.trim_end_matches("/"), + base_url, args.slug ); + let status_page_url = format!( + "{}/api/status-page/{}", + base_url, + args.slug + ); + let client = Client::new(); - println!("{}", heartbeat_url); + println!("Heartbeat URL: {}", heartbeat_url); - let response = client.get(heartbeat_url).send()?; + let heartbeat_response = client.get(heartbeat_url).send()?; - if response.status().is_success() { - let json_text = response.text()?; + if heartbeat_response.status().is_success() { + let json_text = heartbeat_response.text()?; match heartbeat::parse_response(&json_text) { Ok(data) => println!("moises: {}", data.uptime_data[0].get_perc_formated()), Err(e) => println!("{}", e), } } else { - println!("{}", response.status()); - println!("{}: {}", t("Response"), response.text()?); + println!("{}", heartbeat_response.status()); + println!("{}: {}", t("Response"), heartbeat_response.text()?); + } + + println!("Status Page URL: {}", status_page_url); + + let status_page_response = client.get(status_page_url).send()?; + + if status_page_response.status().is_success() { + let json_text = status_page_response.text()?; + match status_page::parse_response(&json_text) { + Ok(data) => println!("moises: {}", data.config.title), + Err(e) => println!("{}", e), + } + } else { + println!("{}", status_page_response.status()); + println!("{}: {}", t("Response"), status_page_response.text()?); } Ok(()) } diff --git a/src/status_page/mod.rs b/src/status_page/mod.rs new file mode 100644 index 0000000..a01983d --- /dev/null +++ b/src/status_page/mod.rs @@ -0,0 +1,4 @@ +pub mod model; +pub mod parser; +pub use model::StatusPageResponse; +pub use parser::parse_response; diff --git a/src/status_page/model.rs b/src/status_page/model.rs new file mode 100644 index 0000000..b659599 --- /dev/null +++ b/src/status_page/model.rs @@ -0,0 +1,61 @@ +use std::collections::HashMap; + +use anyhow::{Context, Result}; +use serde::{Deserialize, Serialize}; + +use crate::i18n::t; + +#[derive(Debug, Clone, Deserialize, Serialize)] +pub struct StatusPageConfig { + pub slug: String, + pub title: String, + #[serde(default)] + pub description: Option, + pub icon: String, + #[serde(rename = "autoRefreshInterval")] + pub auto_refresh_interval: u32, + pub theme: String, + pub published: bool, + #[serde(rename = "showTags")] + pub show_tags: bool, + #[serde(rename = "customCSS")] + pub custon_css: String, + #[serde(rename = "footerText", default)] + pub footer_text: Option, + #[serde(rename = "showPoweredBy")] + pub show_powered_by: bool, + #[serde(rename = "googleAnalyticsId", default)] + pub google_analytics_id: Option, + #[serde(rename = "showCertificateExpiry")] + pub show_certificate_expiry: bool, +} + +#[derive(Debug, Clone, Deserialize, Serialize)] +pub struct MonitorInfo { + pub id: u64, + pub name: String, + #[serde(rename = "sendUrl")] + pub send_url: u8, + #[serde(rename = "type")] + pub monitor_type: String, +} + +#[derive(Debug, Clone, Deserialize, Serialize)] +pub struct StatusPageGroup { + pub id: u64, + pub name: String, + pub weight: u32, + #[serde(rename = "monitorList")] + pub monitor_list: Vec, +} + +#[derive(Debug, Clone, Deserialize, Serialize)] +pub struct StatusPageResponse { + pub config: StatusPageConfig, + #[serde(skip, default)] + pub incident: Option, + #[serde(rename = "publicGroupList")] + pub public_group_list: Vec, + #[serde(rename = "maintenanceList", skip)] + pub maintenance_list: Vec, +} diff --git a/src/status_page/parser.rs b/src/status_page/parser.rs new file mode 100644 index 0000000..981b4df --- /dev/null +++ b/src/status_page/parser.rs @@ -0,0 +1,8 @@ +use super::model::StatusPageResponse; +use crate::i18n::t; +use anyhow::{Context, Ok, Result}; + +pub fn parse_response(json_text: &str) -> Result { + let mut response: StatusPageResponse = serde_json::from_str(json_text)?; //.with_context(|| t("invalid-json-status-page"))?; + Ok(response) +}