-
Notifications
You must be signed in to change notification settings - Fork 258
Description
(Note: I am running this on top of PR #720 (#720) since the master branch currently cannot get past the login screen. Once logged in via that PR's WebAPI fix, I ran into these search crashes.)
Describe the bug
When searching any song/artist/album:
Error: json: invalid type: null, expected struct Playlist at line 1 column 16998
...and after fixing it:
Error: json: missing field 'tracks' at line 1 column 18887
To Reproduce
Search for any song.
Expected behavior
Return a list of results.
Environment
- OS: Win 11
Additional context
I guess Spotify changed their API payloads, causing psst to crash immediately when using the Search function.
I traced the panics to three specific API payload changes and successfully fixed them locally:
1. Search arrays occasionally return null items
The items array sometimes contains null instead of a valid struct (e.g., if a track is region-blocked).
Fix: In psst-gui/src/data/utils.rs, I updated the Page<T> struct to safely drop nulls using a custom deserializer:
#[derive(Deserialize, Default)]
pub struct Page<T: Clone> {
#[serde(
deserialize_with = "deserialize_ignore_nulls",
bound = "T: serde::Deserialize<'de>"
)]
pub items: Vector<T>,
pub limit: usize,
pub offset: usize,
pub total: usize,
}
And added this helper:
pub fn deserialize_ignore_nulls<'de, D, T>(deserializer: D) -> Result<Vector<T>, D::Error>
where
D: serde::Deserializer<'de>,
T: serde::Deserialize<'de> + Clone,
{
let opt_vec: Option<Vec<Option<T>>> = Option::deserialize(deserializer)?;
Ok(opt_vec.unwrap_or_default().into_iter().flatten().collect())
}
- Playlists occasionally omit the tracks field entirely
Fix: In psst-gui/src/data/playlist.rs, added #[serde(default)] to pub track_count: Option and made the deserialize_track_count helper gracefully handle nulls via Option::deserialize.
#[derive(Clone, Debug, Data, Lens, Deserialize)]
pub struct Playlist {
pub id: Arc<str>,
pub name: Arc<str>,
#[serde(skip_serializing_if = "Option::is_none")]
pub images: Option<Vector<Image>>,
#[serde(deserialize_with = "deserialize_description")]
pub description: Arc<str>,
#[serde(default)]
#[serde(rename = "tracks")]
#[serde(deserialize_with = "deserialize_track_count")]
pub track_count: Option<usize>,
pub owner: PublicUser,
pub collaborative: bool,
#[serde(rename = "public")]
pub public: Option<bool>,
}
- Shows/Podcasts occasionally omit the publisher field
Fix: In psst-gui/src/data/show.rs, added #[serde(default)] above pub publisher: Arc.
#[derive(Clone, Data, Lens, Deserialize)]
pub struct Show {
pub id: Arc<str>,
pub name: Arc<str>,
pub images: Vector<Image>,
#[serde(default)]
pub publisher: Arc<str>,
pub description: Arc<str>,
pub total_episodes: Option<usize>,
}
These three simple serde additions completely restored Search functionality for me! Can't load an Artist page but can use the app for the most part.