refactor: app -> rave; and some other poking
This commit is contained in:
parent
7198eda4ee
commit
b18d0dd747
29 changed files with 453 additions and 51 deletions
|
|
@ -1,5 +1,5 @@
|
|||
[workspace]
|
||||
members = ["app", "entities", "migration"]
|
||||
members = ["rave", "entities", "migration"]
|
||||
resolver = "2"
|
||||
|
||||
[workspace.dependencies]
|
||||
|
|
|
|||
|
|
@ -1,30 +0,0 @@
|
|||
use crate::{
|
||||
authentication::Authentication,
|
||||
subsonic::SubsonicResponse,
|
||||
utils::{self},
|
||||
};
|
||||
|
||||
use poem::web::{Data, Query};
|
||||
use poem_ext::db::DbTxn;
|
||||
use serde::Deserialize;
|
||||
|
||||
#[poem::handler]
|
||||
pub async fn get_album(
|
||||
Data(txn): Data<&DbTxn>,
|
||||
auth: Authentication,
|
||||
Query(params): Query<GetAlbumParams>,
|
||||
) -> SubsonicResponse {
|
||||
let u = utils::verify_user(txn.clone(), auth).await;
|
||||
|
||||
match u {
|
||||
Ok(_) => {}
|
||||
Err(e) => return e,
|
||||
}
|
||||
|
||||
todo!("get_album not implemented");
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Deserialize)]
|
||||
pub struct GetAlbumParams {
|
||||
pub id: i32,
|
||||
}
|
||||
|
|
@ -9,9 +9,8 @@ pub struct Model {
|
|||
#[sea_orm(primary_key)]
|
||||
pub id: i64,
|
||||
pub name: String,
|
||||
pub artist: Option<String>,
|
||||
pub artist_id: Option<i64>,
|
||||
pub cover_art: Option<String>,
|
||||
pub cover_art_id: Option<i64>,
|
||||
pub song_count: i32,
|
||||
pub duration: i64,
|
||||
pub play_count: i64,
|
||||
|
|
@ -32,6 +31,14 @@ pub enum Relation {
|
|||
on_delete = "SetNull"
|
||||
)]
|
||||
Artist,
|
||||
#[sea_orm(
|
||||
belongs_to = "super::cover_art::Entity",
|
||||
from = "Column::CoverArtId",
|
||||
to = "super::cover_art::Column::Id",
|
||||
on_update = "NoAction",
|
||||
on_delete = "SetNull"
|
||||
)]
|
||||
CoverArt,
|
||||
#[sea_orm(
|
||||
belongs_to = "super::music_folder::Entity",
|
||||
from = "Column::MusicFolderId",
|
||||
|
|
@ -40,6 +47,8 @@ pub enum Relation {
|
|||
on_delete = "Cascade"
|
||||
)]
|
||||
MusicFolder,
|
||||
#[sea_orm(has_many = "super::track::Entity")]
|
||||
Track,
|
||||
}
|
||||
|
||||
impl Related<super::artist::Entity> for Entity {
|
||||
|
|
@ -48,10 +57,22 @@ impl Related<super::artist::Entity> for Entity {
|
|||
}
|
||||
}
|
||||
|
||||
impl Related<super::cover_art::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::CoverArt.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::music_folder::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::MusicFolder.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::track::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Track.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl ActiveModelBehavior for ActiveModel {}
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ pub struct Model {
|
|||
pub id: i64,
|
||||
#[sea_orm(unique)]
|
||||
pub name: String,
|
||||
pub cover_art: Option<String>,
|
||||
pub cover_art_id: Option<i64>,
|
||||
pub artist_image_url: Option<String>,
|
||||
pub album_count: i32,
|
||||
pub starred: bool,
|
||||
|
|
@ -20,6 +20,16 @@ pub struct Model {
|
|||
pub enum Relation {
|
||||
#[sea_orm(has_many = "super::album::Entity")]
|
||||
Album,
|
||||
#[sea_orm(
|
||||
belongs_to = "super::cover_art::Entity",
|
||||
from = "Column::CoverArtId",
|
||||
to = "super::cover_art::Column::Id",
|
||||
on_update = "NoAction",
|
||||
on_delete = "SetNull"
|
||||
)]
|
||||
CoverArt,
|
||||
#[sea_orm(has_many = "super::track::Entity")]
|
||||
Track,
|
||||
}
|
||||
|
||||
impl Related<super::album::Entity> for Entity {
|
||||
|
|
@ -28,4 +38,16 @@ impl Related<super::album::Entity> for Entity {
|
|||
}
|
||||
}
|
||||
|
||||
impl Related<super::cover_art::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::CoverArt.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::track::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Track.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl ActiveModelBehavior for ActiveModel {}
|
||||
|
|
|
|||
42
entities/src/cover_art.rs
Normal file
42
entities/src/cover_art.rs
Normal file
|
|
@ -0,0 +1,42 @@
|
|||
//! `SeaORM` Entity. Generated by sea-orm-codegen 0.12.3
|
||||
|
||||
use sea_orm::entity::prelude::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq, Serialize, Deserialize)]
|
||||
#[sea_orm(table_name = "cover_art")]
|
||||
pub struct Model {
|
||||
#[sea_orm(primary_key)]
|
||||
pub id: i32,
|
||||
pub path: String,
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
|
||||
pub enum Relation {
|
||||
#[sea_orm(has_many = "super::album::Entity")]
|
||||
Album,
|
||||
#[sea_orm(has_many = "super::artist::Entity")]
|
||||
Artist,
|
||||
#[sea_orm(has_many = "super::track::Entity")]
|
||||
Track,
|
||||
}
|
||||
|
||||
impl Related<super::album::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Album.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::artist::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Artist.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::track::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Track.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl ActiveModelBehavior for ActiveModel {}
|
||||
|
|
@ -4,5 +4,7 @@ pub mod prelude;
|
|||
|
||||
pub mod album;
|
||||
pub mod artist;
|
||||
pub mod cover_art;
|
||||
pub mod music_folder;
|
||||
pub mod track;
|
||||
pub mod user;
|
||||
|
|
|
|||
|
|
@ -2,5 +2,7 @@
|
|||
|
||||
pub use super::album::Entity as Album;
|
||||
pub use super::artist::Entity as Artist;
|
||||
pub use super::cover_art::Entity as CoverArt;
|
||||
pub use super::music_folder::Entity as MusicFolder;
|
||||
pub use super::track::Entity as Track;
|
||||
pub use super::user::Entity as User;
|
||||
|
|
|
|||
72
entities/src/track.rs
Normal file
72
entities/src/track.rs
Normal file
|
|
@ -0,0 +1,72 @@
|
|||
//! `SeaORM` Entity. Generated by sea-orm-codegen 0.12.3
|
||||
|
||||
use sea_orm::entity::prelude::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq, Serialize, Deserialize)]
|
||||
#[sea_orm(table_name = "track")]
|
||||
pub struct Model {
|
||||
#[sea_orm(primary_key)]
|
||||
pub id: i64,
|
||||
pub title: String,
|
||||
pub album_id: Option<i64>,
|
||||
pub artist_id: Option<i64>,
|
||||
pub is_dir: bool,
|
||||
pub cover_art_id: Option<i64>,
|
||||
pub created: DateTimeWithTimeZone,
|
||||
pub duration: i64,
|
||||
pub bit_rate: i64,
|
||||
pub size: i64,
|
||||
pub suffix: String,
|
||||
pub content_type: String,
|
||||
pub is_video: bool,
|
||||
pub path: String,
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
|
||||
pub enum Relation {
|
||||
#[sea_orm(
|
||||
belongs_to = "super::album::Entity",
|
||||
from = "Column::AlbumId",
|
||||
to = "super::album::Column::Id",
|
||||
on_update = "Cascade",
|
||||
on_delete = "Cascade"
|
||||
)]
|
||||
Album,
|
||||
#[sea_orm(
|
||||
belongs_to = "super::artist::Entity",
|
||||
from = "Column::ArtistId",
|
||||
to = "super::artist::Column::Id",
|
||||
on_update = "Cascade",
|
||||
on_delete = "Cascade"
|
||||
)]
|
||||
Artist,
|
||||
#[sea_orm(
|
||||
belongs_to = "super::cover_art::Entity",
|
||||
from = "Column::CoverArtId",
|
||||
to = "super::cover_art::Column::Id",
|
||||
on_update = "Cascade",
|
||||
on_delete = "Cascade"
|
||||
)]
|
||||
CoverArt,
|
||||
}
|
||||
|
||||
impl Related<super::album::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Album.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::artist::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Artist.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::cover_art::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::CoverArt.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl ActiveModelBehavior for ActiveModel {}
|
||||
|
|
@ -2,8 +2,10 @@ pub use sea_orm_migration::prelude::*;
|
|||
|
||||
mod m20220101_000001_create_user;
|
||||
mod m20231009_181004_create_music_folder;
|
||||
mod m20231009_181104_create_artist;
|
||||
mod m20231009_181104_create_cover_art;
|
||||
mod m20231009_181204_create_artist;
|
||||
mod m20231009_181346_create_album;
|
||||
mod m20231009_185712_create_track;
|
||||
|
||||
pub struct Migrator;
|
||||
|
||||
|
|
@ -13,8 +15,10 @@ impl MigratorTrait for Migrator {
|
|||
vec![
|
||||
Box::new(m20220101_000001_create_user::Migration),
|
||||
Box::new(m20231009_181004_create_music_folder::Migration),
|
||||
Box::new(m20231009_181104_create_artist::Migration),
|
||||
Box::new(m20231009_181104_create_cover_art::Migration),
|
||||
Box::new(m20231009_181204_create_artist::Migration),
|
||||
Box::new(m20231009_181346_create_album::Migration),
|
||||
Box::new(m20231009_185712_create_track::Migration),
|
||||
]
|
||||
}
|
||||
}
|
||||
|
|
|
|||
40
migration/src/m20231009_181104_create_cover_art.rs
Normal file
40
migration/src/m20231009_181104_create_cover_art.rs
Normal file
|
|
@ -0,0 +1,40 @@
|
|||
use sea_orm_migration::prelude::*;
|
||||
|
||||
#[derive(DeriveMigrationName)]
|
||||
pub struct Migration;
|
||||
|
||||
#[async_trait::async_trait]
|
||||
impl MigrationTrait for Migration {
|
||||
async fn up(&self, manager: &SchemaManager) -> Result<(), DbErr> {
|
||||
manager
|
||||
.create_table(
|
||||
Table::create()
|
||||
.table(CoverArt::Table)
|
||||
.if_not_exists()
|
||||
.col(
|
||||
ColumnDef::new(CoverArt::Id)
|
||||
.integer()
|
||||
.not_null()
|
||||
.auto_increment()
|
||||
.primary_key()
|
||||
.unique_key(),
|
||||
)
|
||||
.col(ColumnDef::new(CoverArt::Path).string().not_null())
|
||||
.to_owned(),
|
||||
)
|
||||
.await
|
||||
}
|
||||
|
||||
async fn down(&self, manager: &SchemaManager) -> Result<(), DbErr> {
|
||||
manager
|
||||
.drop_table(Table::drop().table(CoverArt::Table).to_owned())
|
||||
.await
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(DeriveIden)]
|
||||
pub enum CoverArt {
|
||||
Table,
|
||||
Id,
|
||||
Path,
|
||||
}
|
||||
|
|
@ -1,5 +1,7 @@
|
|||
use sea_orm_migration::prelude::*;
|
||||
|
||||
use crate::m20231009_181104_create_cover_art::CoverArt;
|
||||
|
||||
#[derive(DeriveMigrationName)]
|
||||
pub struct Migration;
|
||||
|
||||
|
|
@ -25,7 +27,7 @@ impl MigrationTrait for Migration {
|
|||
.not_null()
|
||||
.unique_key(),
|
||||
)
|
||||
.col(ColumnDef::new(Artist::CoverArt).string().null())
|
||||
.col(ColumnDef::new(Artist::CoverArtId).big_integer().null())
|
||||
.col(ColumnDef::new(Artist::ArtistImageUrl).string().null())
|
||||
.col(
|
||||
ColumnDef::new(Artist::AlbumCount)
|
||||
|
|
@ -41,7 +43,21 @@ impl MigrationTrait for Migration {
|
|||
)
|
||||
.to_owned(),
|
||||
)
|
||||
.await
|
||||
.await?;
|
||||
|
||||
manager
|
||||
.create_foreign_key(
|
||||
ForeignKey::create()
|
||||
.from_tbl(Artist::Table)
|
||||
.from_col(Artist::CoverArtId)
|
||||
.to_tbl(CoverArt::Table)
|
||||
.to_col(CoverArt::Id)
|
||||
.on_delete(ForeignKeyAction::SetNull)
|
||||
.to_owned(),
|
||||
)
|
||||
.await?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
async fn down(&self, manager: &SchemaManager) -> Result<(), DbErr> {
|
||||
|
|
@ -56,7 +72,7 @@ pub enum Artist {
|
|||
Table,
|
||||
Id,
|
||||
Name,
|
||||
CoverArt,
|
||||
CoverArtId,
|
||||
ArtistImageUrl,
|
||||
AlbumCount,
|
||||
Starred,
|
||||
|
|
@ -1,7 +1,8 @@
|
|||
use sea_orm_migration::prelude::*;
|
||||
|
||||
use crate::{
|
||||
m20231009_181004_create_music_folder::MusicFolder, m20231009_181104_create_artist::Artist,
|
||||
m20231009_181004_create_music_folder::MusicFolder, m20231009_181104_create_cover_art::CoverArt,
|
||||
m20231009_181204_create_artist::Artist,
|
||||
};
|
||||
|
||||
#[derive(DeriveMigrationName)]
|
||||
|
|
@ -23,9 +24,8 @@ impl MigrationTrait for Migration {
|
|||
.primary_key(),
|
||||
)
|
||||
.col(ColumnDef::new(Album::Name).string().not_null())
|
||||
.col(ColumnDef::new(Album::Artist).string().null())
|
||||
.col(ColumnDef::new(Album::ArtistId).big_integer().null())
|
||||
.col(ColumnDef::new(Album::CoverArt).string().null())
|
||||
.col(ColumnDef::new(Album::CoverArtId).big_integer().null())
|
||||
.col(ColumnDef::new(Album::SongCount).integer().not_null())
|
||||
.col(ColumnDef::new(Album::Duration).big_integer().not_null())
|
||||
.col(
|
||||
|
|
@ -75,6 +75,18 @@ impl MigrationTrait for Migration {
|
|||
)
|
||||
.await?;
|
||||
|
||||
manager
|
||||
.create_foreign_key(
|
||||
ForeignKey::create()
|
||||
.from_tbl(Album::Table)
|
||||
.from_col(Album::CoverArtId)
|
||||
.to_tbl(CoverArt::Table)
|
||||
.to_col(CoverArt::Id)
|
||||
.on_delete(ForeignKeyAction::SetNull)
|
||||
.to_owned(),
|
||||
)
|
||||
.await?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
|
@ -90,9 +102,8 @@ pub enum Album {
|
|||
Table,
|
||||
Id,
|
||||
Name,
|
||||
Artist,
|
||||
ArtistId,
|
||||
CoverArt,
|
||||
CoverArtId,
|
||||
SongCount,
|
||||
Duration,
|
||||
PlayCount,
|
||||
|
|
|
|||
124
migration/src/m20231009_185712_create_track.rs
Normal file
124
migration/src/m20231009_185712_create_track.rs
Normal file
|
|
@ -0,0 +1,124 @@
|
|||
use sea_orm_migration::prelude::*;
|
||||
|
||||
use crate::{
|
||||
m20231009_181104_create_cover_art::CoverArt, m20231009_181204_create_artist::Artist,
|
||||
m20231009_181346_create_album::Album,
|
||||
};
|
||||
|
||||
#[derive(DeriveMigrationName)]
|
||||
pub struct Migration;
|
||||
|
||||
#[async_trait::async_trait]
|
||||
impl MigrationTrait for Migration {
|
||||
async fn up(&self, manager: &SchemaManager) -> Result<(), DbErr> {
|
||||
manager
|
||||
.create_table(
|
||||
Table::create()
|
||||
.table(Track::Table)
|
||||
.if_not_exists()
|
||||
.col(
|
||||
ColumnDef::new(Track::Id)
|
||||
.big_integer()
|
||||
.not_null()
|
||||
.auto_increment()
|
||||
.primary_key()
|
||||
.unique_key(),
|
||||
)
|
||||
.col(ColumnDef::new(Track::Title).string().not_null())
|
||||
.col(ColumnDef::new(Track::AlbumId).big_integer().null())
|
||||
.col(ColumnDef::new(Track::ArtistId).big_integer().null())
|
||||
.col(
|
||||
ColumnDef::new(Track::IsDir)
|
||||
.boolean()
|
||||
.not_null()
|
||||
.default(false),
|
||||
)
|
||||
.col(ColumnDef::new(Track::CoverArtId).big_integer().null())
|
||||
.col(
|
||||
ColumnDef::new(Track::Created)
|
||||
.timestamp_with_time_zone()
|
||||
.not_null(),
|
||||
)
|
||||
.col(ColumnDef::new(Track::Duration).big_integer().not_null())
|
||||
.col(ColumnDef::new(Track::BitRate).big_integer().not_null())
|
||||
.col(ColumnDef::new(Track::Size).big_integer().not_null())
|
||||
.col(ColumnDef::new(Track::Suffix).string().not_null())
|
||||
.col(ColumnDef::new(Track::ContentType).string().not_null())
|
||||
.col(
|
||||
ColumnDef::new(Track::IsVideo)
|
||||
.boolean()
|
||||
.not_null()
|
||||
.default(false),
|
||||
)
|
||||
.col(ColumnDef::new(Track::Path).string().not_null())
|
||||
.to_owned(),
|
||||
)
|
||||
.await?;
|
||||
|
||||
manager
|
||||
.create_foreign_key(
|
||||
ForeignKey::create()
|
||||
.from_tbl(Track::Table)
|
||||
.from_col(Track::AlbumId)
|
||||
.to_tbl(Album::Table)
|
||||
.to_col(Album::Id)
|
||||
.on_delete(ForeignKeyAction::Cascade)
|
||||
.on_update(ForeignKeyAction::Cascade)
|
||||
.to_owned(),
|
||||
)
|
||||
.await?;
|
||||
|
||||
manager
|
||||
.create_foreign_key(
|
||||
ForeignKey::create()
|
||||
.from_tbl(Track::Table)
|
||||
.from_col(Track::ArtistId)
|
||||
.to_tbl(Artist::Table)
|
||||
.to_col(Artist::Id)
|
||||
.on_delete(ForeignKeyAction::Cascade)
|
||||
.on_update(ForeignKeyAction::Cascade)
|
||||
.to_owned(),
|
||||
)
|
||||
.await?;
|
||||
|
||||
manager
|
||||
.create_foreign_key(
|
||||
ForeignKey::create()
|
||||
.from_tbl(Track::Table)
|
||||
.from_col(Track::CoverArtId)
|
||||
.to_tbl(CoverArt::Table)
|
||||
.to_col(CoverArt::Id)
|
||||
.on_delete(ForeignKeyAction::Cascade)
|
||||
.on_update(ForeignKeyAction::Cascade)
|
||||
.to_owned(),
|
||||
)
|
||||
.await?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
async fn down(&self, manager: &SchemaManager) -> Result<(), DbErr> {
|
||||
manager
|
||||
.drop_table(Table::drop().table(Track::Table).to_owned())
|
||||
.await
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(DeriveIden)]
|
||||
pub enum Track {
|
||||
Table,
|
||||
Id,
|
||||
Title,
|
||||
AlbumId,
|
||||
ArtistId,
|
||||
IsDir,
|
||||
CoverArtId,
|
||||
Created,
|
||||
Duration,
|
||||
BitRate,
|
||||
Size,
|
||||
Suffix,
|
||||
ContentType,
|
||||
IsVideo,
|
||||
Path,
|
||||
}
|
||||
|
|
@ -3,6 +3,7 @@ name = "rave"
|
|||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
publish = ["forge-lys-ee"]
|
||||
default-run = "rave"
|
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
|
||||
56
rave/src/rest/get_album.rs
Normal file
56
rave/src/rest/get_album.rs
Normal file
|
|
@ -0,0 +1,56 @@
|
|||
use crate::{
|
||||
authentication::Authentication,
|
||||
subsonic::{Error, SubsonicResponse},
|
||||
utils,
|
||||
};
|
||||
|
||||
use entities::prelude::{Album, Track};
|
||||
use poem::web::{Data, Query};
|
||||
use poem_ext::db::DbTxn;
|
||||
use sea_orm::{EntityTrait, ModelTrait};
|
||||
use serde::Deserialize;
|
||||
use tracing::warn;
|
||||
|
||||
#[poem::handler]
|
||||
pub async fn get_album(
|
||||
Data(txn): Data<&DbTxn>,
|
||||
auth: Authentication,
|
||||
Query(params): Query<GetAlbumParams>,
|
||||
) -> SubsonicResponse {
|
||||
let txn = txn.clone();
|
||||
let u = utils::verify_user(txn.clone(), auth).await;
|
||||
|
||||
match u {
|
||||
Ok(_) => {}
|
||||
Err(e) => return e,
|
||||
}
|
||||
|
||||
let album = Album::find_by_id(params.id).one(&*txn).await;
|
||||
let Ok(Some(album)) = album else {
|
||||
match album {
|
||||
Ok(Some(_)) => unreachable!("Some(album) covered by `let .. else`"),
|
||||
Ok(None) => return SubsonicResponse::new_error(Error::RequestedDataWasNotFound(None)),
|
||||
Err(e) => {
|
||||
warn!("Error getting album: {}", e);
|
||||
return SubsonicResponse::new_error(Error::Generic(None));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
let tracks = album.find_related(Track).all(&*txn).await;
|
||||
|
||||
let tracks = match tracks {
|
||||
Ok(t) => t,
|
||||
Err(e) => {
|
||||
warn!("Error getting tracks: {}", e);
|
||||
return SubsonicResponse::new_error(Error::Generic(None));
|
||||
}
|
||||
};
|
||||
|
||||
SubsonicResponse::new_album(album, tracks)
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Deserialize)]
|
||||
pub struct GetAlbumParams {
|
||||
pub id: i32,
|
||||
}
|
||||
|
|
@ -1,10 +1,17 @@
|
|||
#![allow(clippy::unused_async)] // todo: remove
|
||||
|
||||
use entities::{album, prelude::Album};
|
||||
use poem::web::{Data, Query};
|
||||
use entities::{
|
||||
album, artist,
|
||||
prelude::{Album, Artist},
|
||||
};
|
||||
use poem::{
|
||||
web::{Data, Query},
|
||||
Request,
|
||||
};
|
||||
use poem_ext::db::DbTxn;
|
||||
use sea_orm::{ColumnTrait, EntityTrait, QueryFilter, QueryOrder, QuerySelect};
|
||||
use serde::Deserialize;
|
||||
use tracing::debug;
|
||||
|
||||
use crate::{
|
||||
authentication::Authentication,
|
||||
|
|
@ -24,6 +31,7 @@ macro_rules! error_or {
|
|||
|
||||
#[poem::handler]
|
||||
pub async fn get_album_list(
|
||||
req: &Request,
|
||||
Data(txn): Data<&DbTxn>,
|
||||
auth: Authentication,
|
||||
Query(params): Query<GetAlbumListParams>,
|
||||
|
|
@ -55,7 +63,14 @@ pub async fn get_album_list(
|
|||
};
|
||||
|
||||
match album_list {
|
||||
Ok(a) => SubsonicResponse::new_album_list(a),
|
||||
Ok(a) => {
|
||||
debug!("uri path: {}", req.uri().path());
|
||||
if req.uri().path().contains("getAlbumList2") {
|
||||
SubsonicResponse::new_album_list2(a)
|
||||
} else {
|
||||
SubsonicResponse::new_album_list(a)
|
||||
}
|
||||
}
|
||||
Err(e) => SubsonicResponse::new_error(e),
|
||||
}
|
||||
}
|
||||
|
|
@ -141,12 +156,16 @@ async fn get_album_list_alphabetical_by_artist(
|
|||
params: GetAlbumListParams,
|
||||
) -> Result<Vec<album::Model>, Error> {
|
||||
let albums = Album::find()
|
||||
.order_by_desc(album::Column::Artist)
|
||||
.filter(album::Column::ArtistId.is_not_null())
|
||||
.find_also_related(Artist)
|
||||
.order_by_desc(artist::Column::Name)
|
||||
.limit(params.size)
|
||||
.offset(params.offset)
|
||||
.all(&*conn)
|
||||
.await;
|
||||
|
||||
let albums = albums.map(|c| c.into_iter().map(|c| c.0).collect());
|
||||
|
||||
error_or!(albums)
|
||||
}
|
||||
|
||||
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
use std::fmt::Display;
|
||||
|
||||
use entities::album;
|
||||
use entities::{album, track};
|
||||
use poem::{http::StatusCode, IntoResponse, Response};
|
||||
use serde::{ser::SerializeStruct, Serialize};
|
||||
use time::OffsetDateTime;
|
||||
|
|
@ -51,7 +51,7 @@ impl SubsonicResponse {
|
|||
Self::new(SubResponseType::AlbumList2 { albums })
|
||||
}
|
||||
|
||||
pub fn new_album(album: album::Model, songs: Vec<Child>) -> Self {
|
||||
pub fn new_album(album: album::Model, songs: Vec<track::Model>) -> Self {
|
||||
Self::new(SubResponseType::Album { album, songs })
|
||||
}
|
||||
|
||||
|
|
@ -98,7 +98,7 @@ pub enum SubResponseType {
|
|||
#[serde(flatten)]
|
||||
album: album::Model,
|
||||
#[serde(flatten)]
|
||||
songs: Vec<Child>,
|
||||
songs: Vec<track::Model>,
|
||||
},
|
||||
Empty,
|
||||
}
|
||||
Loading…
Reference in a new issue