Skip to content

Commit

Permalink
Artists live in central artists.json file now
Browse files Browse the repository at this point in the history
  • Loading branch information
Stridsvagn69420 committed Dec 4, 2022
1 parent 1ceca0a commit b79cfa3
Show file tree
Hide file tree
Showing 5 changed files with 40 additions and 32 deletions.
47 changes: 22 additions & 25 deletions src/artist.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
use serde::{Serialize, Deserialize};
use uuid::Uuid;
use dirs::home_dir;
use std::fmt::{Display, Result};
use std::cmp::PartialEq;
use std::convert::From;
use std::path::{Path, PathBuf};
use std::fs;
use std::io;
use super::Owner;
use std::path::Path;
use std::{fs, io, env};
use super::{Owner, meta};

/// Artist
///
Expand Down Expand Up @@ -39,35 +39,32 @@ impl Artist {
}
}

/// Load single .artists.json
/// Load artists.json
///
/// Loads a single `.artists.json` as a [Vec] of [Artist]s
pub fn load_artists(path: impl AsRef<Path>) -> io::Result<Vec<Artist>> {
/// Loads a `artists.json` as a [Vec] of [Artist]s
pub fn load(path: impl AsRef<Path>) -> io::Result<Vec<Artist>> {
let rawdata = fs::read_to_string(path)?;
Ok(serde_json::from_str(rawdata.as_str())?)
}

/// Load multiple .artists.json
/// Cascade Loading
///
/// Loads multiple `.artists.json` as a combined [Vec] of [Artist]s
pub fn load_multiple_artists(paths: Vec<impl AsRef<Path>>) -> io::Result<Vec<Artist>> {
let mut res: Vec<Artist> = Vec::new();
for pth in paths {
let artst = Artist::load_artists(pth)?;
res.extend(artst);
/// Attempts to load a config file by:
/// 1. Provided [String]
/// 2. `CYRKENSIA_ARTISTS` environment variable
/// 3. `~/.config/cyrkensia/artists.json` file
pub fn load_cascade(cmdarg: &Option<String>) -> io::Result<Vec<Artist>> {
// Select extra path
let envvar = env::var(meta::ARTISTS_ENVVAR);

// Read config from extra location
if let Some(path) = cmdarg.as_ref().or_else(|| envvar.as_ref().ok()) {
return Artist::load(path);
}
Ok(res)
}

/// Read multiple folders' .artists.json
///
/// Reads the .artists.json of multiple folders. Essentially like `load_multiple_artists`, but with `.artists.json` appended.
pub fn read_multiple(paths: &[String]) -> io::Result<Vec<Artist>> {
let conv_paths: Vec<PathBuf> = paths.iter()
.map(|x| Path::new(x).join(".artists.json")).collect();

// Read all artists
Artist::load_multiple_artists(conv_paths)
// Read with default path
let localpath = home_dir().unwrap_or_default().join(meta::ARTISTS_PATH);
Artist::load(localpath)
}
}

Expand Down
9 changes: 8 additions & 1 deletion src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,9 +41,15 @@ pub struct Config {
/// Note that the file must be a JSON of [Vec]<[Account](super::account::Account)>.
pub htpasswd: Option<String>,

/// Artists file
///
/// The path to the central artists file, used for displaying an album's artists.
/// It will cascade load the file as described in [Artist](crate::Artist)'s `load_cascade()` function.
pub artists: Option<String>,

/// Bind address
///
/// The IP address to bind to, e.g. `127.0.0.1`, `0.0.0.0:80` or a Unix socket (Unix only).
/// The IP address to bind to, e.g. `127.0.0.1`, `0.0.0.0:80` or a Unix Domain Socket (Unix only).
pub bindaddr: String,

/// Owners
Expand Down Expand Up @@ -104,6 +110,7 @@ impl From<Hostinfo> for Config {
icon: x.icon,
htpasswd: None,
bindaddr: "".to_string(),
artists: None,
owners: x.owners,
max_age: None
}
Expand Down
4 changes: 3 additions & 1 deletion src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@
//! // Load the config file
//! let config = Config::load_file("config.json").unwrap();
//! // Load the artists
//! let artists = Artist::read_multiple(&config.root).unwrap();
//! let artists = Artist::load_cascade(&None).unwrap();
//! // Generate the corresponding Hostinfo
//! let mut hostinfo = Hostinfo::generate(&config, &artists).unwrap();
//! ```
Expand Down Expand Up @@ -79,6 +79,8 @@ pub mod meta {
pub const CONFIG_PATH: &str = concat!(".config/", env!("CARGO_PKG_NAME"), "/config.json");
pub const USERS_ENVVAR: &str = "CYRKENSIA_USERS";
pub const USERS_PATH: &str = concat!(".config/", env!("CARGO_PKG_NAME"), "/users.json");
pub const ARTISTS_ENVVAR: &str = "CYRKENSIA_ARTISTS";
pub const ARTISTS_PATH: &str = concat!(".config/", env!("CARGO_PKG_NAME"), "/artists.json");
}

#[cfg(feature = "server")]
Expand Down
2 changes: 1 addition & 1 deletion src/server/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ impl CyrkensiaState {

// State with caching
if cfg.max_age.is_some() {
let arts = Artist::read_multiple(&cfg.root)?;
let arts = Artist::load_cascade(&cfg.artists)?;
let hostinfo = Hostinfo::generate(&cfg, &arts)?;
return Ok(CyrkensiaState {
last_updated: Mutex::new(Instant::now()),
Expand Down
10 changes: 6 additions & 4 deletions src/server/routes.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ pub async fn hostinfo(data: web::Data<CyrkensiaState>) -> impl Responder {
// Get config
let Some(delay) = data.config.max_age else {
// Ad hoch Hostinfo
let Ok(artists) = Artist::read_multiple(&data.config.root) else {
let Ok(artists) = Artist::load_cascade(&data.config.artists) else {
return responses::server_500(Some("Failed to generate hostinfo"));
};
let Ok(resp) = responses::hostinfo_json(&data.config, &artists) else {
Expand All @@ -35,7 +35,7 @@ pub async fn hostinfo(data: web::Data<CyrkensiaState>) -> impl Responder {
// Update Cache if expired
if last_updated.elapsed().as_secs() >= delay {
// Read updated artists
let Ok(new_artists) = Artist::read_multiple(&data.config.root) else {
let Ok(new_artists) = Artist::load_cascade(&data.config.artists) else {
return responses::server_500(Some("Failed to update hostinfo"));
};

Expand Down Expand Up @@ -105,11 +105,13 @@ pub async fn index(p: web::Path<IndexParams>, data: web::Data<CyrkensiaState>) -
};

// Codegen
let headmeta = r"<style>
let headmeta = r###"<meta name="viewport" content="width=device-width, initial-scale=1.0">
<style>
h2 { color: white; text-decoration: underline; }
a { color: cyan; margin: 8px; }
body { font-family: sans-serif, system-ui; background-color: #252545; }
</style>";
</style>
"###;
let headstr = format!("<h2>{} ({})</h2>", meta.0, meta.1);
let bodystr = meta.2.into_iter().fold(String::new(), |total, item| total + &format!("<a href=\"{}\">{}</a><br>\n", item, item));

Expand Down

0 comments on commit b79cfa3

Please sign in to comment.