feat: qbz-1 streaming, gapless prefetch, accurate scrobbling, Range-seek
Port proven playback architecture from qbqt fork: - Bounded VecDeque buffer with condvar backpressure (4MB cap) - decrypt_and_extract_frames for clean FLAC frame extraction from ISOBMFF - Cancel+restart seeking with sub-segment sample skipping - start_prefetch / QueueNext for gapless transitions with pre-started downloads - track_transitioned signaling for scrobbler during gapless playback - Range-request HTTP seeking for non-segmented (MP3) tracks - OnceLock HTTP client singleton with cancel-aware chunked downloads - Accumulated listening time scrobbling (prevents false scrobbles from seeking) - Array-format Last.fm scrobble params (artist[0], track[0], etc.) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -74,12 +74,16 @@ pub struct AudioInfoDto {
|
||||
#[derive(Debug, Deserialize, Clone, Serialize)]
|
||||
pub struct TrackFileUrlDto {
|
||||
pub track_id: Option<i64>,
|
||||
pub duration: Option<i64>,
|
||||
pub duration: Option<f64>,
|
||||
pub url: Option<String>,
|
||||
pub url_template: Option<String>,
|
||||
pub n_segments: Option<u32>,
|
||||
pub format_id: Option<i32>,
|
||||
pub mime_type: Option<String>,
|
||||
pub sampling_rate: Option<f64>,
|
||||
pub bit_depth: Option<i32>,
|
||||
/// qbz-1 encryption key: "qbz-1.<base64url_aes_key>.<base64url_iv>"
|
||||
pub key: Option<String>,
|
||||
}
|
||||
|
||||
// --- Album ---
|
||||
@@ -219,6 +223,15 @@ pub struct FavArtistDto {
|
||||
pub image: Option<ImageDto>,
|
||||
}
|
||||
|
||||
// --- Favorite IDs ---
|
||||
|
||||
#[derive(Debug, Deserialize, Serialize)]
|
||||
pub struct FavIdsDto {
|
||||
pub tracks: Option<Vec<i64>>,
|
||||
pub albums: Option<Vec<String>>,
|
||||
pub artists: Option<Vec<i64>>,
|
||||
}
|
||||
|
||||
// --- Format ---
|
||||
|
||||
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
|
||||
|
||||
Reference in New Issue
Block a user