alert2muc/src/main.rs

105 lines
2.5 KiB
Rust
Raw Normal View History

use std::net::SocketAddr;
use askama::Template;
2022-12-17 00:17:53 +01:00
use axum::{
extract::State,
routing::post,
http::StatusCode,
response::{IntoResponse, Response},
Json, Router,
};
use serde::Deserialize;
mod jabber;
#[derive(Debug, Clone, Deserialize)]
struct Payload {
alerts: Vec<Alert>,
}
#[derive(Debug, Clone, Deserialize, Template)]
#[template(path="alert.txt", escape="none")]
2022-12-17 00:17:53 +01:00
struct Alert {
status: String,
labels: AlertLabels,
2022-12-17 00:17:53 +01:00
annotations: AlertAnnotations,
#[serde(rename = "generatorURL")]
generator_url: String,
2022-12-17 00:17:53 +01:00
}
#[derive(Debug, Clone, Deserialize)]
struct AlertLabels {
alertname: Option<String>,
host: Option<String>,
instance: Option<String>,
2022-12-18 03:44:01 +01:00
exported_instance: Option<String>,
2022-12-17 00:17:53 +01:00
}
#[derive(Debug, Clone, Deserialize)]
struct AlertAnnotations {
message: Option<String>,
description: Option<String>,
2022-12-17 00:17:53 +01:00
}
async fn alerts(
State(jabber): State<jabber::Handle>,
Json(payload): Json<Payload>,
2022-12-17 00:17:53 +01:00
) -> Response {
let mut error_message = None;
2022-12-17 00:17:53 +01:00
for alert in payload.alerts {
match alert.render() {
Ok(message) => {
jabber.send_message(message).await;
}
Err(e) => {
error_message = Some(format!("{}", e));
2022-12-17 00:17:53 +01:00
}
}
}
match error_message {
None =>
StatusCode::OK.into_response(),
Some(error_message) =>
(StatusCode::INTERNAL_SERVER_ERROR,
error_message
).into_response()
2022-12-17 00:17:53 +01:00
}
}
2022-12-17 00:46:47 +01:00
#[derive(Deserialize)]
struct Config {
listen_port: u16,
jid: String,
password: String,
muc: String,
}
2022-12-17 00:17:53 +01:00
#[tokio::main]
async fn main() {
// initialize tracing
tracing_subscriber::fmt::init();
2022-12-17 00:58:05 +01:00
let config: Config = serde_json::from_str(
2022-12-17 00:46:47 +01:00
&std::fs::read_to_string(
2022-12-17 00:52:36 +01:00
std::env::args().nth(1)
2022-12-17 00:46:47 +01:00
.expect("Call with config.json")
).expect("read config")
).expect("parse config");
2022-12-17 00:58:05 +01:00
let jabber = jabber::run(config.jid, config.password, config.muc).await;
2022-12-17 00:17:53 +01:00
// build our application with a route
let app = Router::new()
.route("/alert", post(alerts))
.with_state(jabber);
2022-12-17 00:17:53 +01:00
2022-12-17 00:58:05 +01:00
let addr = SocketAddr::from(([127, 0, 0, 1], config.listen_port));
2022-12-17 00:17:53 +01:00
tracing::debug!("listening on {}", addr);
2022-12-17 00:20:30 +01:00
let server = axum::Server::bind(&addr)
.serve(app.into_make_service());
systemd::daemon::notify(false, [(systemd::daemon::STATE_READY, "1")].iter())
.unwrap();
server.await
2022-12-17 00:17:53 +01:00
.unwrap();
}