fix: parsing error when no music_related content available
This commit is contained in:
parent
77ee923778
commit
8fbd6b95b6
2 changed files with 52 additions and 45 deletions
|
|
@ -306,19 +306,14 @@ impl MapResponse<Lyrics> for response::MusicLyrics {
|
|||
) -> Result<MapResult<Lyrics>, ExtractionError> {
|
||||
let lyrics = self
|
||||
.contents
|
||||
.section_list_renderer
|
||||
.and_then(|sl| {
|
||||
sl.contents
|
||||
.into_iter()
|
||||
.find_map(|item| item.music_description_shelf_renderer)
|
||||
})
|
||||
.ok_or(match self.contents.message_renderer {
|
||||
Some(msg) => ExtractionError::NotFound {
|
||||
id: id.to_owned(),
|
||||
msg: msg.text.into(),
|
||||
},
|
||||
None => ExtractionError::InvalidData(Cow::Borrowed("no content")),
|
||||
})?;
|
||||
.into_res()
|
||||
.map_err(|msg| ExtractionError::NotFound {
|
||||
id: id.to_owned(),
|
||||
msg: msg.into(),
|
||||
})?
|
||||
.into_iter()
|
||||
.find_map(|item| item.music_description_shelf_renderer)
|
||||
.ok_or(ExtractionError::InvalidData(Cow::Borrowed("no content")))?;
|
||||
|
||||
Ok(MapResult {
|
||||
c: Lyrics {
|
||||
|
|
@ -333,36 +328,39 @@ impl MapResponse<Lyrics> for response::MusicLyrics {
|
|||
impl MapResponse<MusicRelated> for response::MusicRelated {
|
||||
fn map_response(
|
||||
self,
|
||||
_id: &str,
|
||||
id: &str,
|
||||
lang: Language,
|
||||
_deobf: Option<&crate::deobfuscate::DeobfData>,
|
||||
_vdata: Option<&str>,
|
||||
) -> Result<MapResult<MusicRelated>, ExtractionError> {
|
||||
let contents = self
|
||||
.contents
|
||||
.into_res()
|
||||
.map_err(|msg| ExtractionError::NotFound {
|
||||
id: id.to_owned(),
|
||||
msg: msg.into(),
|
||||
})?;
|
||||
|
||||
// Find artist
|
||||
let artist_id = self
|
||||
.contents
|
||||
.section_list_renderer
|
||||
.contents
|
||||
.iter()
|
||||
.find_map(|section| match section {
|
||||
response::music_item::ItemSection::MusicCarouselShelfRenderer(shelf) => {
|
||||
shelf.header.as_ref().and_then(|h| {
|
||||
h.music_carousel_shelf_basic_header_renderer
|
||||
.title
|
||||
.0
|
||||
.iter()
|
||||
.find_map(|c| {
|
||||
let artist = ArtistId::from(c.clone());
|
||||
if artist.id.is_some() {
|
||||
Some(artist)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
_ => None,
|
||||
});
|
||||
let artist_id = contents.iter().find_map(|section| match section {
|
||||
response::music_item::ItemSection::MusicCarouselShelfRenderer(shelf) => {
|
||||
shelf.header.as_ref().and_then(|h| {
|
||||
h.music_carousel_shelf_basic_header_renderer
|
||||
.title
|
||||
.0
|
||||
.iter()
|
||||
.find_map(|c| {
|
||||
let artist = ArtistId::from(c.clone());
|
||||
if artist.id.is_some() {
|
||||
Some(artist)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
_ => None,
|
||||
});
|
||||
|
||||
let mut mapper_tracks = MusicListMapper::new(lang);
|
||||
let mut mapper = match artist_id {
|
||||
|
|
@ -370,7 +368,7 @@ impl MapResponse<MusicRelated> for response::MusicRelated {
|
|||
None => MusicListMapper::new(lang),
|
||||
};
|
||||
|
||||
let mut sections = self.contents.section_list_renderer.contents.into_iter();
|
||||
let mut sections = contents.into_iter();
|
||||
if let Some(response::music_item::ItemSection::MusicCarouselShelfRenderer(shelf)) =
|
||||
sections.next()
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@ use super::AlertRenderer;
|
|||
use super::ContentsRenderer;
|
||||
use super::{
|
||||
music_item::{ItemSection, PlaylistPanelRenderer},
|
||||
ContentRenderer, SectionList,
|
||||
ContentRenderer,
|
||||
};
|
||||
|
||||
/// Response model for YouTube Music track details
|
||||
|
|
@ -108,14 +108,14 @@ pub(crate) struct PlaylistPanel {
|
|||
#[derive(Debug, Deserialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub(crate) struct MusicLyrics {
|
||||
pub contents: LyricsContents,
|
||||
pub contents: ListOrMessage<LyricsSection>,
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub(crate) struct LyricsContents {
|
||||
pub message_renderer: Option<AlertRenderer>,
|
||||
pub section_list_renderer: Option<ContentsRenderer<LyricsSection>>,
|
||||
pub(crate) enum ListOrMessage<T> {
|
||||
SectionListRenderer(ContentsRenderer<T>),
|
||||
MessageRenderer(AlertRenderer),
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
|
|
@ -137,5 +137,14 @@ pub(crate) struct LyricsRenderer {
|
|||
#[derive(Debug, Deserialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub(crate) struct MusicRelated {
|
||||
pub contents: SectionList<ItemSection>,
|
||||
pub contents: ListOrMessage<ItemSection>,
|
||||
}
|
||||
|
||||
impl<T> ListOrMessage<T> {
|
||||
pub fn into_res(self) -> Result<Vec<T>, String> {
|
||||
match self {
|
||||
ListOrMessage::SectionListRenderer(c) => Ok(c.contents),
|
||||
ListOrMessage::MessageRenderer(msg) => Err(msg.text),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Reference in a new issue