aboutsummaryrefslogtreecommitdiffstats
path: root/src/font.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/font.rs')
-rw-r--r--src/font.rs40
1 files changed, 40 insertions, 0 deletions
diff --git a/src/font.rs b/src/font.rs
index ba3bbd9..6454770 100644
--- a/src/font.rs
+++ b/src/font.rs
@@ -1,4 +1,11 @@
use std::sync::Arc;
+use std::time::Duration;
+
+use tokio::sync::RwLock;
+use reqwest::StatusCode;
+
+use super::cache::{CacheFuture, CacheGetter, Cache, AsyncCache};
+use crate::STATE;
#[derive(serde::Deserialize, Debug, Default)]
#[serde(default)]
@@ -9,3 +16,36 @@ pub struct FontQuery {
pub google_font: Option<Arc<str>>,
// pub small_font: Option<()>
}
+
+pub type FontFuture = CacheFuture<Arc<str>>;
+pub type FontGetter = CacheGetter<Arc<str>>;
+pub type FontCache = Cache<Arc<str>>;
+
+fn font_getter(fontname: &String) -> FontFuture {
+ let fontname = urlencoding::encode(fontname.as_ref()).to_string();
+ Box::pin(async move {
+ let Some(google_api_key) = STATE.google_api_key.clone()
+ else {
+ unreachable!();
+ };
+
+ let fontreq = STATE.http.get(format!("https://www.googleapis.com/webfonts/v1/webfonts?key={}&family={fontname}", google_api_key))
+ .send().await
+ .map_err(|e| {log::error!("Failed to get info for font `{fontname}`: {e}"); (StatusCode::SERVICE_UNAVAILABLE, "Couldn't connect to Google Fonts!")})?;
+ if fontreq.status() == StatusCode::NOT_FOUND { return Err((StatusCode::NOT_FOUND, "Font does not exist!")); }
+ if fontreq.status() == StatusCode::FORBIDDEN {
+ log::error!("Invalid Google API key in config!");
+ return Err((StatusCode::SERVICE_UNAVAILABLE, "This instance is not configured to support Google Fonts properly, please use a different font."));
+ }
+
+ let cssreq = STATE.http.get(format!("https://fonts.googleapis.com/css2?family={fontname}"))
+ .send().await
+ .map_err(|e| {log::error!("Failed to get CSS for font `{fontname}`: {e}"); (StatusCode::SERVICE_UNAVAILABLE, "Couldn't download font CSS!")})?;
+
+ Ok(cssreq.text().await.unwrap().into())
+ })
+}
+
+pub fn font_cache() -> FontCache {
+ Arc::new(RwLock::new(AsyncCache::new(Duration::from_secs(86400), font_getter as FontGetter)))
+}