@@ 107,69 107,64 @@ pub mod model {
}
pub use model::Root as Ctx;
-#[derive(Debug)]
-pub struct ResponseCtx(pub model::Root, pub StatusCode);
-
-impl ResponseCtx {
- pub async fn create(api_result: Result<Arc<(de::User, de::Track, de::TrackStub)>, (StatusCode, &'static str)>, font_query: Option<FontQuery>, query: BTreeMap<String, String>) -> ResponseCtx {
- match api_result {
- Ok(a) => {
- let (user, track, trackstub) = a.as_ref();
- ResponseCtx((model::Data {
- user: model::User {
- name: user.name.clone(),
- realname: user.realname.clone(),
-
- scrobble_count: user.playcount,
- artist_count: user.artist_count,
- track_count: user.track_count,
- album_count: user.track_count,
-
- image_url: user.images.iter().max_by(|a, b| a.size.cmp(&b.size)).map(|a| a.url.clone()).unwrap_or_else(|| "".into()),
-
- url: user.url.clone()
+pub async fn get_ctx(api_result: Result<Arc<(de::User, de::Track, de::TrackStub)>, (StatusCode, &'static str)>, font_query: Option<FontQuery>, query: BTreeMap<String, String>) -> (Ctx, StatusCode) {
+ match api_result {
+ Ok(a) => {
+ let (user, track, trackstub) = a.as_ref();
+ ((model::Data {
+ user: model::User {
+ name: user.name.clone(),
+ realname: user.realname.clone(),
+
+ scrobble_count: user.playcount,
+ artist_count: user.artist_count,
+ track_count: user.track_count,
+ album_count: user.track_count,
+
+ image_url: user.images.iter().max_by(|a, b| a.size.cmp(&b.size)).map(|a| a.url.clone()).unwrap_or_else(|| "".into()),
+
+ url: user.url.clone()
+ },
+ scrobble: model::Scrobble {
+ name: track.name.clone(),
+ album: track.album.title.clone(),
+ artist: model::Artist {
+ name: track.artist.name.clone(),
+// image_url: track.artist.images.iter().max_by(|a, b| a.size.cmp(&b.size)).map(|a| a.url.clone()).unwrap_or_else(|| "".into()),
+ url: track.artist.url.clone().unwrap_or_else(|| "".into())
},
- scrobble: model::Scrobble {
- name: track.name.clone(),
- album: track.album.title.clone(),
- artist: model::Artist {
- name: track.artist.name.clone(),
-// image_url: track.artist.images.iter().max_by(|a, b| a.size.cmp(&b.size)).map(|a| a.url.clone()).unwrap_or_else(|| "".into()),
- url: track.artist.url.clone().unwrap_or_else(|| "".into())
- },
- image_url: track.images.iter().max_by(|a, b| a.size.cmp(&b.size)).map(|a| a.url.clone()).filter(|s| !s.is_empty()).unwrap_or_else(|| "https://lastfm.freetls.fastly.net/i/u/128s/4128a6eb29f94943c9d206c08e625904.jpg".into()),
- now_playing: trackstub.attr.nowplaying,
- url: track.url.clone(),
- loved: track.loved.unwrap_or(false)
+ image_url: track.images.iter().max_by(|a, b| a.size.cmp(&b.size)).map(|a| a.url.clone()).filter(|s| !s.is_empty()).unwrap_or_else(|| "https://lastfm.freetls.fastly.net/i/u/128s/4128a6eb29f94943c9d206c08e625904.jpg".into()),
+ now_playing: trackstub.attr.nowplaying,
+ url: track.url.clone(),
+ loved: track.loved.unwrap_or(false)
+ },
+ font: match font_query {
+ Some(FontQuery { google_font: Some(f), .. }) if CONFIG.has_google_api_key() => {
+ let css = match crate::cache::font::get_fontinfo(&f.to_string()).await {
+ Ok(css) => css,
+ Err((status, error)) => { return (model::Root::Error {error}, status); }
+ };
+ Some(model::Font::External {
+ css,
+ name: f
+ })
},
- font: match font_query {
- Some(FontQuery { google_font: Some(f), .. }) if CONFIG.has_google_api_key() => {
- let css = match crate::cache::font::get_fontinfo(&f.to_string()).await {
- Ok(css) => css,
- Err((status, error)) => { return ResponseCtx(model::Root::Error {error}, status); }
- };
- Some(model::Font::External {
- css,
- name: f
- })
- },
- Some(FontQuery { include_font: Some(f), .. }) => Some(
- model::Font::External {
- css: format!(
- "@font-face {{ font-family: 'included_font'; src: url('{}'); }}",
- f.replace('\\', "\\\\")
- .replace('\'', "\\'")).into(),
- name: "included_font".into()
- }),
- Some(FontQuery { font: Some(s), .. }) => Some(model::Font::Name { name: s }),
- _ => None,
- },
- query
- }).into(), StatusCode::OK)
- },
- Err((status, error)) => {
- ResponseCtx(model::Root::Error {error}, status)
- }
+ Some(FontQuery { include_font: Some(f), .. }) => Some(
+ model::Font::External {
+ css: format!(
+ "@font-face {{ font-family: 'included_font'; src: url('{}'); }}",
+ f.replace('\\', "\\\\")
+ .replace('\'', "\\'")).into(),
+ name: "included_font".into()
+ }),
+ Some(FontQuery { font: Some(s), .. }) => Some(model::Font::Name { name: s }),
+ _ => None,
+ },
+ query
+ }).into(), StatusCode::OK)
+ },
+ Err((status, error)) => {
+ (model::Root::Error {error}, status)
}
}
}
@@ 5,8 5,11 @@ use std::collections::BTreeMap;
use std::fs::File;
use std::sync::Arc;
-use lfm_embed::{CONFIG, ResponseCtx};
+use lfm_embed::CONFIG;
+use lfm_embed::ctx::get_ctx;
+use lfm_embed::cache::user::get_userinfo;
use lfm_embed::cache::font::FontQuery;
+use lfm_embed::theming::render_theme;
use log::LevelFilter;
use dotenv::var;
@@ 45,12 48,12 @@ async fn main() {
let user = warp::path!("user" / String)
.and(warp::query::<UserQuery>())
.then(|s, q: UserQuery| async move {
- log::debug!(target: "lfm_embed::server::user", "Handling request for user `{s}` with {q:?}");
- let (ctx, dur) = lfm_embed::cache::user::get_userinfo(&s).await;
- let ResponseCtx(data, status) = ResponseCtx::create(ctx, q.font, q.rest).await;
+ log::debug!(target: "lfm_embed::main::user", "Handling request for user `{s}` with {q:?}");
+ let (userinfo, refresh) = get_userinfo(&s).await;
+ let (ctx, status) = get_ctx(userinfo, q.font, q.rest).await;
- let (theme, res) = lfm_embed::theming::render_theme(q.theme.as_deref(), &data);
- log::debug!(target: "lfm_embed::server::user", "Using theme {theme}");
+ let (theme, res) = render_theme(q.theme.as_deref(), &ctx);
+ log::debug!(target: "lfm_embed::main::user", "Using theme {theme}");
match res {
Err(status) =>
@@ 63,7 66,7 @@ async fn main() {
Ok(contents) =>
http::Response::builder()
.status(status)
- .header("Refresh", dur.as_secs())
+ .header("Refresh", refresh.as_secs())
.header("X-Selected-Theme", theme)
.header("Content-Type", "text/html")
.body(contents)