feat: fuck NULLs.
This commit is contained in:
parent
ace6ec1683
commit
fac22a2806
6 changed files with 48 additions and 40 deletions
2
Justfile
2
Justfile
|
|
@ -10,7 +10,7 @@ unmount:
|
||||||
bash ./mount-tool.sh unmount
|
bash ./mount-tool.sh unmount
|
||||||
|
|
||||||
run: mount
|
run: mount
|
||||||
RAVE_STORAGE_DIR=/tmp/media-for-rave RAVE_CACHE_DIR=/tmp/cache-for-rave cargo r
|
RAVE_STORAGE_DIR=/home/lys/Programming/fuck RAVE_CACHE_DIR=/tmp/cache-for-rave cargo r
|
||||||
|
|
||||||
refresh:
|
refresh:
|
||||||
sea migrate fresh
|
sea migrate fresh
|
||||||
|
|
|
||||||
|
|
@ -194,17 +194,14 @@ mod mp3;
|
||||||
async fn find_or_create_genre(tx: &DatabaseTransaction, name: &str) -> Result<i64, Report> {
|
async fn find_or_create_genre(tx: &DatabaseTransaction, name: &str) -> Result<i64, Report> {
|
||||||
let name = name.replace('\0', ""); // remove null bytes. they're not allowed :3
|
let name = name.replace('\0', ""); // remove null bytes. they're not allowed :3
|
||||||
let name = name.trim();
|
let name = name.trim();
|
||||||
debug!("Finding genre with name {name}");
|
|
||||||
let res = Genre::find()
|
let res = Genre::find()
|
||||||
.filter(genre::Column::Name.eq(name))
|
.filter(genre::Column::Name.eq(name))
|
||||||
.one(tx)
|
.one(tx)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
if let Some(genre) = res {
|
if let Some(genre) = res {
|
||||||
debug!("Found genre with id {}", genre.id);
|
|
||||||
Ok(genre.id)
|
Ok(genre.id)
|
||||||
} else {
|
} else {
|
||||||
debug!("Trying to create genre");
|
|
||||||
let am = genre::ActiveModel {
|
let am = genre::ActiveModel {
|
||||||
name: Set(name.to_string()),
|
name: Set(name.to_string()),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
|
|
@ -222,8 +219,6 @@ async fn find_or_create_genre(tx: &DatabaseTransaction, name: &str) -> Result<i6
|
||||||
return Err(Report::new(err));
|
return Err(Report::new(err));
|
||||||
};
|
};
|
||||||
|
|
||||||
debug!("Inserted genre with id {}", model.id);
|
|
||||||
|
|
||||||
Ok(model.id)
|
Ok(model.id)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -263,7 +258,6 @@ async fn create_root_music_folder(
|
||||||
}
|
}
|
||||||
return ControlFlow::Break(());
|
return ControlFlow::Break(());
|
||||||
};
|
};
|
||||||
debug!("created transaction");
|
|
||||||
|
|
||||||
let name = root_dir.to_string_lossy().to_string();
|
let name = root_dir.to_string_lossy().to_string();
|
||||||
|
|
||||||
|
|
@ -283,12 +277,9 @@ async fn create_root_music_folder(
|
||||||
name: Set(name),
|
name: Set(name),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
};
|
};
|
||||||
debug!("created new music folder model");
|
|
||||||
|
|
||||||
let mf = MusicFolder::insert(new_music_folder).exec(&txn).await;
|
let mf = MusicFolder::insert(new_music_folder).exec(&txn).await;
|
||||||
|
|
||||||
debug!("inserted new music folder model");
|
|
||||||
|
|
||||||
let Ok(mf) = mf else {
|
let Ok(mf) = mf else {
|
||||||
let err = mf.expect_err("somehow not err");
|
let err = mf.expect_err("somehow not err");
|
||||||
error!(
|
error!(
|
||||||
|
|
@ -403,8 +394,6 @@ async fn find_or_create_cover_art(
|
||||||
) -> Result<cover_art::Model, Report> {
|
) -> Result<cover_art::Model, Report> {
|
||||||
let hash = blake3::hash(data).to_string();
|
let hash = blake3::hash(data).to_string();
|
||||||
|
|
||||||
debug!("Finding cover art with hash {hash}");
|
|
||||||
|
|
||||||
let res = CoverArt::find()
|
let res = CoverArt::find()
|
||||||
.filter(cover_art::Column::Hash.eq(&hash))
|
.filter(cover_art::Column::Hash.eq(&hash))
|
||||||
.one(tx)
|
.one(tx)
|
||||||
|
|
@ -414,8 +403,6 @@ async fn find_or_create_cover_art(
|
||||||
return Ok(cover_art);
|
return Ok(cover_art);
|
||||||
}
|
}
|
||||||
|
|
||||||
debug!("Trying to create cover art");
|
|
||||||
|
|
||||||
let path = get_cache_dir();
|
let path = get_cache_dir();
|
||||||
let path = path
|
let path = path
|
||||||
.join(hash.clone())
|
.join(hash.clone())
|
||||||
|
|
|
||||||
|
|
@ -14,7 +14,7 @@ use sea_orm::{
|
||||||
};
|
};
|
||||||
use time::OffsetDateTime;
|
use time::OffsetDateTime;
|
||||||
use tokio::{fs::File, sync::RwLock};
|
use tokio::{fs::File, sync::RwLock};
|
||||||
use tracing::{debug, error, instrument, warn};
|
use tracing::{error, instrument, warn};
|
||||||
|
|
||||||
use super::ScanState;
|
use super::ScanState;
|
||||||
|
|
||||||
|
|
@ -50,11 +50,14 @@ pub async fn handle(
|
||||||
|
|
||||||
let mut am = track::ActiveModel::new();
|
let mut am = track::ActiveModel::new();
|
||||||
|
|
||||||
am.title = Set(tag.title().unwrap_or(&stem).to_string());
|
let title = tag.title().unwrap_or(&stem).to_string();
|
||||||
|
let title = title.replace("\0 ", "").replace('\0', ""); // fuck NULLs.
|
||||||
|
|
||||||
|
am.title = Set(title);
|
||||||
am.album_id = Set(Some(album.id));
|
am.album_id = Set(Some(album.id));
|
||||||
am.artist_id = Set(artist.as_ref().map(|c| c.id));
|
am.artist_id = Set(artist.as_ref().map(|c| c.id));
|
||||||
am.content_type = Set("audio/mpeg".to_string());
|
am.content_type = Set("audio/flac".to_string());
|
||||||
am.suffix = Set("mp3".to_string());
|
am.suffix = Set("flac".to_string());
|
||||||
am.path = Set(path.to_string_lossy().to_string());
|
am.path = Set(path.to_string_lossy().to_string());
|
||||||
am.is_dir = Set(false);
|
am.is_dir = Set(false);
|
||||||
am.track_number = Set(tag
|
am.track_number = Set(tag
|
||||||
|
|
@ -69,12 +72,8 @@ pub async fn handle(
|
||||||
am.is_video = Set(false);
|
am.is_video = Set(false);
|
||||||
am.duration = {
|
am.duration = {
|
||||||
let duration = tag.duration();
|
let duration = tag.duration();
|
||||||
|
|
||||||
let duration = duration.unwrap_or_default();
|
let duration = duration.unwrap_or_default();
|
||||||
|
|
||||||
debug!("Duration: {duration}");
|
|
||||||
let duration = duration.round().rem_euclid(2f64.powi(32)) as i64;
|
let duration = duration.round().rem_euclid(2f64.powi(32)) as i64;
|
||||||
debug!("math'd duration: {duration}");
|
|
||||||
|
|
||||||
Set(duration)
|
Set(duration)
|
||||||
};
|
};
|
||||||
|
|
@ -139,7 +138,7 @@ async fn find_album(
|
||||||
// otherwise, create it
|
// otherwise, create it
|
||||||
let mut am = album::ActiveModel::new();
|
let mut am = album::ActiveModel::new();
|
||||||
|
|
||||||
am.name = Set(album.title.to_string());
|
am.name = Set(album.title.to_string().replace("\0 ", "").replace('\0', ""));
|
||||||
am.music_folder_id = Set(state.read().await.music_folder_id);
|
am.music_folder_id = Set(state.read().await.music_folder_id);
|
||||||
am.artist_id = Set(artist_id);
|
am.artist_id = Set(artist_id);
|
||||||
am.year = Set(tag.year());
|
am.year = Set(tag.year());
|
||||||
|
|
@ -215,10 +214,24 @@ async fn find_artist(
|
||||||
) -> Result<Option<artist::Model>, Report> {
|
) -> Result<Option<artist::Model>, Report> {
|
||||||
let artist_to_search = match (tag.album_artist(), tag.artists()) {
|
let artist_to_search = match (tag.album_artist(), tag.artists()) {
|
||||||
(Some(tag_artist), None) => Some(tag_artist.to_string()),
|
(Some(tag_artist), None) => Some(tag_artist.to_string()),
|
||||||
(None, Some(tag_artists)) => Some(tag_artists.join(", ")),
|
(None, Some(tag_artists)) => {
|
||||||
|
let tag_artists = tag_artists
|
||||||
|
.iter()
|
||||||
|
.flat_map(|artist| artist.split('\0'))
|
||||||
|
.map(str::trim)
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
Some(tag_artists.join(", "))
|
||||||
|
}
|
||||||
(Some(tag_artist), Some(tag_artists)) => {
|
(Some(tag_artist), Some(tag_artists)) => {
|
||||||
let mut artists = tag_artists.clone();
|
let mut artists = tag_artists.clone();
|
||||||
artists.push(tag_artist);
|
artists.push(tag_artist);
|
||||||
|
|
||||||
|
let artists = artists
|
||||||
|
.iter()
|
||||||
|
.flat_map(|artist| artist.split('\0'))
|
||||||
|
.map(str::trim)
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
Some(artists.join(", "))
|
Some(artists.join(", "))
|
||||||
}
|
}
|
||||||
_ => None,
|
_ => None,
|
||||||
|
|
@ -228,7 +241,7 @@ async fn find_artist(
|
||||||
Some(artist_to_search) => {
|
Some(artist_to_search) => {
|
||||||
let artist_to_search = artist_to_search.trim();
|
let artist_to_search = artist_to_search.trim();
|
||||||
let attempt = Artist::find()
|
let attempt = Artist::find()
|
||||||
.filter(artist::Column::Name.like(artist_to_search))
|
.filter(artist::Column::Name.eq(artist_to_search))
|
||||||
.one(tx)
|
.one(tx)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -14,7 +14,7 @@ use sea_orm::{
|
||||||
};
|
};
|
||||||
use time::OffsetDateTime;
|
use time::OffsetDateTime;
|
||||||
use tokio::{fs::File, sync::RwLock};
|
use tokio::{fs::File, sync::RwLock};
|
||||||
use tracing::{debug, error, instrument, warn};
|
use tracing::{error, instrument, warn};
|
||||||
|
|
||||||
use super::ScanState;
|
use super::ScanState;
|
||||||
|
|
||||||
|
|
@ -50,7 +50,10 @@ pub async fn handle(
|
||||||
|
|
||||||
let mut am = track::ActiveModel::new();
|
let mut am = track::ActiveModel::new();
|
||||||
|
|
||||||
am.title = Set(tag.title().unwrap_or(&stem).to_string());
|
let title = tag.title().unwrap_or(&stem).to_string();
|
||||||
|
let title = title.replace("\0 ", "").replace('\0', ""); // fuck NULLs.
|
||||||
|
|
||||||
|
am.title = Set(title);
|
||||||
am.album_id = Set(Some(album.id));
|
am.album_id = Set(Some(album.id));
|
||||||
am.artist_id = Set(artist.as_ref().map(|c| c.id));
|
am.artist_id = Set(artist.as_ref().map(|c| c.id));
|
||||||
am.content_type = Set("audio/mpeg".to_string());
|
am.content_type = Set("audio/mpeg".to_string());
|
||||||
|
|
@ -69,12 +72,8 @@ pub async fn handle(
|
||||||
am.is_video = Set(false);
|
am.is_video = Set(false);
|
||||||
am.duration = {
|
am.duration = {
|
||||||
let duration = tag.duration();
|
let duration = tag.duration();
|
||||||
|
|
||||||
let duration = duration.unwrap_or_default();
|
let duration = duration.unwrap_or_default();
|
||||||
|
|
||||||
debug!("Duration: {duration}");
|
|
||||||
let duration = duration.round().rem_euclid(2f64.powi(32)) as i64;
|
let duration = duration.round().rem_euclid(2f64.powi(32)) as i64;
|
||||||
debug!("math'd duration: {duration}");
|
|
||||||
|
|
||||||
Set(duration)
|
Set(duration)
|
||||||
};
|
};
|
||||||
|
|
@ -139,7 +138,7 @@ async fn find_album(
|
||||||
// otherwise, create it
|
// otherwise, create it
|
||||||
let mut am = album::ActiveModel::new();
|
let mut am = album::ActiveModel::new();
|
||||||
|
|
||||||
am.name = Set(album.title.to_string());
|
am.name = Set(album.title.to_string().replace("\0 ", "").replace('\0', ""));
|
||||||
am.music_folder_id = Set(state.read().await.music_folder_id);
|
am.music_folder_id = Set(state.read().await.music_folder_id);
|
||||||
am.artist_id = Set(artist_id);
|
am.artist_id = Set(artist_id);
|
||||||
am.year = Set(tag.year());
|
am.year = Set(tag.year());
|
||||||
|
|
@ -215,10 +214,24 @@ async fn find_artist(
|
||||||
) -> Result<Option<artist::Model>, Report> {
|
) -> Result<Option<artist::Model>, Report> {
|
||||||
let artist_to_search = match (tag.album_artist(), tag.artists()) {
|
let artist_to_search = match (tag.album_artist(), tag.artists()) {
|
||||||
(Some(tag_artist), None) => Some(tag_artist.to_string()),
|
(Some(tag_artist), None) => Some(tag_artist.to_string()),
|
||||||
(None, Some(tag_artists)) => Some(tag_artists.join(", ")),
|
(None, Some(tag_artists)) => {
|
||||||
|
let tag_artists = tag_artists
|
||||||
|
.iter()
|
||||||
|
.flat_map(|artist| artist.split('\0'))
|
||||||
|
.map(str::trim)
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
Some(tag_artists.join(", "))
|
||||||
|
}
|
||||||
(Some(tag_artist), Some(tag_artists)) => {
|
(Some(tag_artist), Some(tag_artists)) => {
|
||||||
let mut artists = tag_artists.clone();
|
let mut artists = tag_artists.clone();
|
||||||
artists.push(tag_artist);
|
artists.push(tag_artist);
|
||||||
|
|
||||||
|
let artists = artists
|
||||||
|
.iter()
|
||||||
|
.flat_map(|artist| artist.split('\0'))
|
||||||
|
.map(str::trim)
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
Some(artists.join(", "))
|
Some(artists.join(", "))
|
||||||
}
|
}
|
||||||
_ => None,
|
_ => None,
|
||||||
|
|
@ -228,7 +241,7 @@ async fn find_artist(
|
||||||
Some(artist_to_search) => {
|
Some(artist_to_search) => {
|
||||||
let artist_to_search = artist_to_search.trim();
|
let artist_to_search = artist_to_search.trim();
|
||||||
let attempt = Artist::find()
|
let attempt = Artist::find()
|
||||||
.filter(artist::Column::Name.like(artist_to_search))
|
.filter(artist::Column::Name.eq(artist_to_search))
|
||||||
.one(tx)
|
.one(tx)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -13,7 +13,7 @@ use poem::{
|
||||||
use sea_orm::{ColumnTrait, EntityTrait, QueryFilter, Set};
|
use sea_orm::{ColumnTrait, EntityTrait, QueryFilter, Set};
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use time::format_description::well_known::Iso8601;
|
use time::format_description::well_known::Iso8601;
|
||||||
use tracing::{debug, error};
|
use tracing::error;
|
||||||
|
|
||||||
#[poem::handler]
|
#[poem::handler]
|
||||||
pub async fn login_ui(Data(txn): Data<&DbTxn>, cookie: &Session) -> Response {
|
pub async fn login_ui(Data(txn): Data<&DbTxn>, cookie: &Session) -> Response {
|
||||||
|
|
@ -84,8 +84,6 @@ pub async fn login(
|
||||||
.exec_with_returning(&**txn)
|
.exec_with_returning(&**txn)
|
||||||
.await;
|
.await;
|
||||||
|
|
||||||
debug!("Created session: {session_token:?}");
|
|
||||||
|
|
||||||
if let Ok(token) = session_token {
|
if let Ok(token) = session_token {
|
||||||
session.clear();
|
session.clear();
|
||||||
session.set("session_token", token.token);
|
session.set("session_token", token.token);
|
||||||
|
|
|
||||||
|
|
@ -4,8 +4,6 @@ use poem::{
|
||||||
session::{CookieConfig, CookieSession},
|
session::{CookieConfig, CookieSession},
|
||||||
Endpoint, EndpointExt, Route,
|
Endpoint, EndpointExt, Route,
|
||||||
};
|
};
|
||||||
use tracing::debug;
|
|
||||||
|
|
||||||
mod dashboard;
|
mod dashboard;
|
||||||
mod errors;
|
mod errors;
|
||||||
mod index;
|
mod index;
|
||||||
|
|
@ -15,7 +13,6 @@ mod logout;
|
||||||
pub fn build() -> Box<dyn Endpoint<Output = poem::Response>> {
|
pub fn build() -> Box<dyn Endpoint<Output = poem::Response>> {
|
||||||
let working_directory = std::env::current_dir().expect("Failed to get current directory");
|
let working_directory = std::env::current_dir().expect("Failed to get current directory");
|
||||||
|
|
||||||
debug!("Working directory: {:?}", working_directory);
|
|
||||||
let path = working_directory.join("static/css");
|
let path = working_directory.join("static/css");
|
||||||
|
|
||||||
Route::new()
|
Route::new()
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue