Intégration externe - Subsonic

[Intégration] Subsonic — reliez Gladys à votre serveur musical (Navidrome, Airsonic…)

Bonjour à tous :wave:

Je viens de publier Subsonic, une intégration externe qui relie Gladys à n’importe quel serveur musical implémentant l’API Subsonic : Navidrome, Airsonic-Advanced, Gonic, LMS, Subsonic…

Mon besoin de départ était simple : que Gladys sache ce qui se passe sur mon instance Navidrome, et puisse déclencher de la musique depuis mes scènes. Elle est développée et testée d’abord contre Navidrome, mais rien n’y est spécifique à ce serveur.

:link: Dépôt : GitHub - guim31/gladys-subsonic · GitHub


Ce que ça apporte

Appareil « Subsonic server » — 6 capteurs

Capteur Ce qu’il donne
Now playing Le morceau en cours, au format Artiste — Titre (auditeur)
Album cover La pochette de l’album écouté, rafraîchie à chaque changement de morceau
Active streams Combien de morceaux sont écoutés en ce moment
Songs / Artists / Albums in library La taille de votre bibliothèque

Afficher la pochette sur le tableau de bord

La pochette emprunte le canal image de Gladys : ajoutez un widget Caméra et choisissez l’appareil « Subsonic server ». Le nom du widget surprend au premier abord, mais c’est le seul de Gladys qui affiche l’image d’un appareil et se met à jour en direct. Le widget Photo, lui, n’accepte qu’une liste d’URL figées saisies à la main : il ne peut pas suivre ce qui joue.

Appareil « Subsonic jukebox » (optionnel)

Pilotage de la lecture côté serveur (fonction jukebox de l’API) : lecture/pause, précédent/suivant, volume et état de lecture. À activer explicitement, côté Gladys et côté serveur. Le widget Musique du tableau de bord pilote directement ces commandes.

Boutons dans l’écran de configuration

  • Tester la connexion — affiche l’identité du serveur (ex. navidrome 0.63.2, API 1.16.1)
  • Scanner la bibliothèque musicale
  • Jukebox : lecture aléatoire (N morceaux au hasard)
  • Jukebox : jouer une playlist (par son nom)

Quelques idées de scènes

  • Ne pas déranger : si Active streams > 0, ne pas lancer l’aspirateur ou couper les enceintes.
  • Réveil en musique : à 7 h, l’action « jouer une playlist » lance votre playlist du matin sur le jukebox.
  • Réagir au morceau : le capteur « Now playing » est une feature texte, et Gladys déclenche ses scènes sur le changement de sa valeur — vous pouvez donc faire réagir votre installation à chaque nouveau morceau (afficher le titre, ajuster les lumières…).
  • Tableau de bord : la pochette en grand (widget Caméra), le titre en cours et les commandes du jukebox côte à côte.

Installation

Prérequis : Gladys 4.86.0 ou plus.

Depuis Intégrations → Installer une intégration, cherchez « Subsonic » dans le catalogue.

Ensuite, dans l’onglet Configuration :

  1. URL du serveur : la racine, sans /rest — ex. http://192.168.1.10:4533 (port par défaut de Navidrome).
  2. Utilisateur / Mot de passe : un compte de votre serveur (créez-en un dédié si possible).
  3. Méthode d’authentification : laissez Jeton. Le mot de passe ne transite jamais, seul un hachage md5 salé est envoyé. Basculez sur Legacy uniquement pour un serveur très ancien (API < 1.13) ou un compte LDAP qui refuse le jeton.
  4. Cliquez sur Tester la connexion, puis récupérez l’appareil dans l’onglet Découverte.

Pour le jukebox

Il joue la musique sur la machine qui héberge le serveur (celle reliée à vos enceintes). Il faut l’activer des deux côtés — dans Navidrome :

[Jukebox]
Enabled = true

(ou ND_JUKEBOX_ENABLED=true), puis cocher Activer l’appareil jukebox dans la configuration de l’intégration.


Ce que ça ne fait pas (pour éviter les malentendus)

Autant être clair sur les limites, qui viennent de l’API Subsonic elle-même :

  • Le jukebox joue sur l’hôte du serveur, pas sur la machine de Gladys : ce n’est pas une solution multiroom.
  • Impossible de piloter un autre client (votre téléphone, le lecteur web) : l’API ne permet pas de commander la lecture d’un client tiers.
  • Pas d’annonce vocale via cette intégration : l’action « Jouer une notification » de Gladys envoie une URL audio TTS, or le jukebox Subsonic ne sait jouer que des morceaux de la bibliothèque. Ça reste le terrain de Sonos / Chromecast.

Côté technique

Construite à partir du template officiel JavaScript et du SDK @gladysassistant/integration-sdk. Node 24 Alpine, image multi-arch (amd64 + arm64), rootfs en lecture seule, tests unitaires et CI (Prettier / ESLint / tests) sur chaque commit. Licence Apache-2.0.

Petit soin particulier sur les requêtes envoyées au serveur : la liste complète des artistes n’est relue que lorsque la bibliothèque a changé (signature de scan) ou une fois par heure, au lieu d’être retéléchargée à chaque relevé — les valeurs restent pourtant publiées à chaque cycle. La pochette suit la même logique : elle n’est téléchargée que lorsque le morceau change, et dans la plus grande taille qui tienne sous la limite du canal image.


Les retours, remontées de bugs et idées de fonctionnalités sont les bienvenus, ici ou dans les issues du dépôt. Si vous l’essayez avec autre chose que Navidrome, ça m’intéresse beaucoup de savoir si tout se comporte bien :slight_smile:

Bonjour @guim31 , je voulais savoir comment lier LMS dont je dispose avec ton intégration. Ma configuration LMS ne nécessite pas d’authentification et c’est obligatoire dans l’intégration. Y-a-t-il une solution ?

Salut @Tolkyen :wave:

Bonne nouvelle : ça devrait fonctionner sans rien changer, mais il faut passer par une clé d’API.

Ce n’est pas l’intégration qui est trop exigeante : le protocole Subsonic transporte des identifiants dans chaque requête, il n’a tout simplement pas de mode « sans authentification ». Et côté LMS (si c’est bien Lightweight Music Server que tu utilises), c’est encore plus net — sa documentation précise que son API Subsonic accepte uniquement l’authentification par clé d’API, indépendamment du fait que ton interface web ne te demande rien.

Concrètement :

  1. Dans LMS, ouvre la page Settings de ton utilisateur et génère une clé d’API.
  2. Dans la configuration de l’intégration Gladys :
    • Utilisateur : ton identifiant LMS
    • Mot de passe : la clé d’API (et non un mot de passe de compte)
    • Méthode d’authentification : laisse Jeton
  3. Clique sur Tester la connexion.

J’ai vérifié dans le code de LMS : avec la méthode Jeton, il calcule le hachage salé de chacune des clés d’API de ton utilisateur et les compare à celui qu’on envoie — donc le schéma par défaut de l’intégration convient. Si jamais ça coince, bascule sur Legacy, LMS gère aussi ce format.

Un point d’attention quand même : je n’ai testé que Navidrome. Le jukebox notamment risque de se comporter différemment — LMS a sa propre implémentation. Ton retour m’intéresse beaucoup, tu serais le premier sur LMS :slight_smile:

Je comprends d’où vient mon problème, quand j’ai lu LMS, j’ai compris Logitech Media Server et non Lightweight Music Server :sweat_smile:

Ah mince… en effet ça ne pouvait pas fonctionner, Logitech Media Server n’est pas basé sur l’API Subsonic ! Va falloir que tu demandes une intégration pour toi :wink:

Hello,

Merci pour cette intégration
Je suis en train de l’installer avec un serveur navidrome
J’ai donc créé un utilisateur dédié
La connexion est ok mais j’ai un message d’erreur sur le scan :

J’ai créé un utilisateur classique sans droit administrateur
J’ai peut-être raté un truc mais je vois pas quoi :sweat_smile:

J’ai testé via la méthode Jeton et Legacy et j’ai le même résultat

Merci

Salut @prohand, merci pour le retour :slight_smile:

startScan est le seul endpoint utilisé par l’intégration que Navidrome réserve aux administrateurs (c’est codé en dur dans son routeur Subsonic). Ton utilisateur dédié étant un compte standard, Navidrome refuse l’opération — d’où l’erreur 50. C’est d’ailleurs pour ça que Jeton et Legacy donnent le même résultat : l’authentification passe très bien (ton « Tester la connexion » est vert), c’est l’autorisation qui bloque, et la méthode d’authentification n’y change rien.

Deux options :

  • Ne rien faire — c’est ce que je recommande. Ce bouton n’est qu’un raccourci de confort : Navidrome scanne déjà tout seul (selon sa planification et sa surveillance des dossiers), et les capteurs de l’intégration suivront au relevé suivant. Aucune autre fonctionnalité n’a besoin des droits admin.
  • Passer ce compte en administrateur dans Navidrome, si tu tiens à déclencher le scan depuis Gladys.

Tout le reste fonctionne parfaitement avec un compte standard : les capteurs, le morceau en cours, la pochette d’album, et même le jukebox (là, c’est Jukebox.Enabled côté serveur qui compte, pas les droits admin).

Le vrai défaut ici est de mon côté : le message s’affiche en vert, comme un succès, alors que c’est un refus — et il n’explique pas la cause. Je vais corriger ça pour qu’il apparaisse clairement comme une erreur, avec la raison. Merci de l’avoir signalé !

Merci pour le retour
Je viens de vérifier et effectivement je vois bien mon serveur :slight_smile:

Merci :wink:

Je ne sais pas si c’est un bug ou normal mais je viens d’arrêter la musique côté Navidrome et il m’indique qu’il y a toujours une musique en cours d’écoute

Pour la musique qui reste affichée : ce n’est pas un bug, c’est le fonctionnement de la liste « en cours de lecture » de Navidrome. Une session y est conservée après l’arrêt — 30 minutes si le lecteur a signalé la pause ou l’arrêt, sinon jusqu’à la fin théorique du morceau, car le protocole Subsonic classique n’a pas de notion d’« arrêt » : un client se contente de ne plus rien demander.

Mais je ne tirais pas parti d’une information que Navidrome fournit : l’état réel de chaque session. C’est corrigé dans la prochaine version — seules les sessions réellement en lecture sont désormais comptées, donc ton arrêt sera pris en compte au relevé suivant (60 s max).

Il restera un cas irréductible : un lecteur qu’on ferme sans qu’il prévienne le serveur reste listé jusqu’à la fin du morceau. Là, personne ne peut faire mieux.

Et j’ai aussi corrigé le message du scan : il s’affiche maintenant en rouge, avec l’explication (droits administrateur) plutôt qu’un code d’erreur brut. Merci pour ces deux retours!! :slight_smile:

Merci pour les corrections :smiling_face: