Since Subsonic is dead, the official API won’t move forward and prevent clients from being able to implement advanced things that are possible with other type of Media Providers like Plex or Emby / Jellyfin.
I’d like to propose that we try to improve the situation with some of the main actors on the Subsonic compatible servers, to globally improve the Subsonic ecosystem and bring more joy to your users. And doing that without each server building their own API to keep the Subsonic ecosystem alive, the more common the API the more compatible clients. While Symfonium is already multi server and could easily use new API for each servers, it’s better for everyone to keep what was built alive.
Identify your server
Since each servers are different and implement things with subtle variation due the nature of Subsonic API, I’d like to first request the extension of the subsonic response to contain the server name and version so that client can adapt to your specificities.
Improve current API in non breaking way
Addition / clarification of the API
(X) Support empty query in search3
Necessary for the clients to do full database sync for offline cache.
Most already do
(X) Server name / version
Necessary for the clients to identify the server and adapt to it’s specificity.
See proposal
(X) /stream control of scrobling.
Necessary for the clients to be able to use the /stream endpoint without counting as a play (like to download transcoded media, since the download end point does not support that officially)
Add a new scrobble=true/false to control.
multiple genre
Enhance user experience for the server who support them
Add new result fields genres that contains the list. Since this may trigger slower queries on server, maybe only return them when requested by a new param extendedInfo=true
multiple artists
Enhance user experience for the server who support them
Add new result fields artists that contains the list. Since this may trigger slower queries on server, maybe only return them when requested by a new param extendedInfo=true
compilation
Enhance user experience for the server who support them
Add new result fields compilation true/false. Since this may trigger slower queries on server, maybe only return them when requested by a new param extendedInfo=true
album artist / artists / compilation only artists
Enhance user experience for the server who support them
To be defined, can be handled with new fields or new endpoints
(X) lastplayed
Reporting the field allows clients to have proper data on their side for playback that occurs outside of the clientapp.
Navidrome already support that)
(X) support timeOffset for audio too
Necessary to transcode to opus and seek. Opus codec is better than mp3 for transcoding in lower bitrates, but due to limitations in ffmpeg even with the size approximation seeking can fail.This allows clients to seek by restart the transcode at the proper timing.
Already defined in the api just need to agree to use it for audio too.
Expose if supporting post queries.
…
Expand the API
This will require a common decision on how to handle this.
New end points
More secure authentication
Proposal
Extend the subsonic API endpoint to expose:
serverName: String (Ex: Navidrome/0.48.0/docker)
apiExtension: bool (The server support the API extensions)
Add a new endpoint /apiExtensions
This endpoint would return the supported api extensions, this allows servers to support new things without supporting everything, and allow to support new end point even if not support the official 1.16.1 api for example.
Would be probably good to simplify clients devs life, that servers that support API extensions, do not fail request when passed parameters they do now know and just ignore. (Probably already the case, but worth validating that)
If most of the devs agree on this base then we can discuss the extensions
One thing Subsonic is missing is that a lot of the methods are album focused making it harder to search/list by artist. it’s all very album focused.
It also doesn’t have the ability to identify an album_artist vs a song_artist?
So i’d like something where you can say:
get albums for an artist (where they are a song artist && || album artist)
get all songs for a song_artist (don’t include songs from albums that aren’t them)
I would suggest 2 new Subsonic methods:
getSongsByArtist
getSongsByAlbumArtist
Ampache API6 will extend these methods a lot more to add filters song/album_artist. (the develop branch has a lot of reworking on this type of filtering)
Subsonic also needs to update it’s auth in a way Ampache can get rid of the plaintext password in the token generation. Does Subsonic store the password in plaintext on the db?
The way token and salt works i can’t think of an easy way to support the SHA256 encrypted passwords so we’re stuck using the API key.
The Ampache handshake is done using time
or the encrypted API key
Not sure how this would be made easier though. it’s a very fundamental difference.
Those are just some things off the top of my head that i’ve noticed from people. I do intend to raise the API support to 1.16.1 at some point before v6 of Ampache releases.
Since Subsonic official is dead, the API won’t move forward, that’s why it’s important to try to see what can be done to avoid each servers to invent their own API that will split the clients.
For me the major missing stuff will be updated in the first post, but if there’s moving from Subsonic official API, it’s important to define how this will be handled by the clients and how it can be handled by servers without too much pain and obligations.
All servers should use a common field in the subsonic response to give their name and version so that client can adapt to what they support or not, since not all servers support all or even support functions in the same way.
Improving the current API without breaking changes (adding new params, new returned fields,…)
Expanding the API with new endpoints
The first 2 points can be handled via simple ways of extensions to the API that are optional and not tied to the subsonic API version.
The 3rd point with the new endpoint / new auth you’d like it a lot more problematic and would require more discussions.
Yes, it stores it in plain text. There’s a simple way to increase the security, dropping the token/salt authentication and allowing the server to not store the password in plain text, but requires cooperation from the clients:
Client send token auth info to the server
Server responds with Error 41: "Token authentication not supported for LDAP users"
Client then fallback to password mode (“old” auth method)
I think if all maintained servers adopt this strategy, (maintained) clients will follow suit. But this could kill some old clients, like Madsonic, OG Subsonic…
Idea for a better authentication: We would implement a new endpoint (/auth) that would return an expirable token that clients should send on all subsequent requests. Clients would periodically refresh the tokens (/refresh) to avoid it getting expired. This is similar to OAuth2 client credentials flow.
@Tolriq for this discussion to move forward, we need other client developers here: Sonixd, Ultrasonic, play:Sub, substreamer, AskSonic, bonob, Subfire. These are the ones I know are active, but there are others.
@deluan before clients we needs to have the servers to agree to move to somewhere first
If most refuse to deviate or want to push their own API then there’s no need to expand this further.
And that’s also why I propose to have something iterative and non breaking.
If we can generate something, then clients will move with it, if you directly bring 100 person in a room this usually does not bring anything good.
For the auth, I think a new end point is necessary, many users do not understand https and security and sending plaintext password without user knowledge may not be good, so might not fit the goal to improve security.
Just keep in mind that even with a new endpoint, the plaintext password will need to be sent at least once to the server. This is true even if you are implementing OAuth2, and AFAIK there’s no way around it. So HTTPS is the only solution to avoid this.
Not necessarily, could be an apiKey generated by the server for each account and that users can renew / regenerate. then use that apiKey to generate a token with a defined lifetime.
Or could be the user manually generating appKeys that can be directly used by apps and revoked by the user.
Ah yes. In that case we don’t even need to change the authentication schema. We can generate these apiKeys and use that as “password” in the client application, and couple that with Error 41 as I described above. Actually that’s how Airsonic-Advance works, IIRC.
Regarding new endpoints, it would be awesome to be able to create an OpenAPI document for the subsonic API, so new developers could use code generators to bootstrap new clients and servers codebases. I tried to do it, but the current Subsonic API is not well suited for OpenAPI specs, and the generators get confused by the amount of workarounds I had to put in the spec
Lol yes generating a graph would be hard, specially with the small differences between servers. I think that it would bring too much constraints on the server side if we started to be too rigid in the API.
Else it would be like writing a new standard API but I doubt servers and client would follow.
That’s why I try to push this idea of extending the current Subsonic API.
I could directly use Ampache API and any API you currently use and will make public one day But let’s try to improve the whole ecosystem and all the apps around it. More good things and idea could come from this.
For the auth via keys needs to see how they would be handled, 1 per app / 1 per user then generating tokens, …
@deluan do you remember sumner from sublime music was talking about a “subsonic api expansion” document? it was hosted on readthedocs or something. one of the pages was about authentication for example. can’t find it now though, do yo remember it?
@Tolriq yep I’d be happy to work on some stuff on the gonic side. personally I’m interested in support for authentication
improvements and multi artist / genre support, but can also help with other stuff.
I think we should involve Sumner in the discussion since he wrote that page linked above
I propose we let this on a side of ours heads until next year and start real discussions.
Main points being:
New auth system allowing password encryption at server side. (probably something like API keys or app keys, if we want to avoid clear text password without https that is not mandatory)
small non breakijg API improvements to fix a few details.
bigger API improvements: Have them mostly optional at the exception of the way to announce the supported extensions. I guess this mostly prevent changing current API version and built something else that is simple enough to not bring burden on both sides.