Files
pmomusic/Blackboard/Report/Bug_lecture_open_home.md
Eric Coissac 5701fbf465 Fix queue duplication and internal queue playback bugs
Fix bug where tracks were duplicated in queue position 0 during playlist refreshes by comparing items with URI or didl_id

Fix race condition in internal queue playback where transient STOPPED states caused unwanted auto-advance

- Updated sync_queue in interne.rs to use didl_id as fallback for URI comparison
- Added items_match function in openhome.rs for robust item comparison
- Modified lcs_flags in openhome.rs to use items_match for LCS algorithm
- Added has_played_since_track_start flag in musicrenderer.rs to prevent auto-advance on transient STOPPED states
- Updated play_* methods in musicrenderer.rs to reset the has_played flag before starting playback
- Added diagnostic logs in sync_queue for tracking item matching issues
2026-01-16 22:46:05 +01:00

3.1 KiB

Rapport : Bug de duplication de piste en position 0

Résumé

Correction d'un bug où la piste en cours de lecture était dupliquée en position 0 de la queue après un certain temps.

Problème identifié

Symptôme

Lors de la lecture d'une playlist liée à une queue (OpenHome ou interne), après le passage à une nouvelle piste, celle-ci finissait par être dupliquée en première position de la queue.

Cause racine

La fonction sync_queue (utilisée lors des refreshes périodiques de playlist toutes les 60 secondes) comparait les items uniquement par leur URI. Si le MediaServer retournait une URI légèrement différente pour le même morceau (tokens de session, encodage différent, etc.), l'item courant n'était pas reconnu dans la nouvelle playlist et était préservé en position 0, créant ainsi une duplication.

Mécanisme détaillé

  1. Une playlist est attachée à un renderer
  2. La lecture commence sur la piste N
  3. Après 60 secondes, un refresh périodique déclenche sync_queue
  4. sync_queue compare l'URI de la piste courante avec les URIs de la playlist rafraîchie
  5. Si les URIs ne correspondent pas exactement, la piste courante est considérée comme "absente" de la playlist
  6. La logique de préservation insère alors la piste courante en position 0
  7. Résultat : duplication de la piste

Solution appliquée

Modification de la logique de comparaison

La comparaison des items a été étendue pour utiliser l'URI OU le didl_id comme critère d'identification. Le didl_id est l'identifiant DIDL-Lite stable assigné par le MediaServer, indépendant de l'URI de streaming.

Fichiers modifiés

1. pmocontrol/src/queue/interne.rs

  • Ajout de la comparaison par didl_id en fallback dans sync_queue
  • Ajout de logs de diagnostic pour tracer les cas de non-correspondance
// Avant
let new_idx = items.iter().position(|item| item.uri == current_uri);

// Après
let new_idx = items.iter().position(|item| item.uri == current_uri)
    .or_else(|| items.iter().position(|item| item.didl_id == current_didl_id));

2. pmocontrol/src/queue/openhome.rs

  • Ajout de la fonction items_match pour encapsuler la logique de comparaison
  • Modification de sync_queue pour utiliser URI ou didl_id
  • Modification de lcs_flags (algorithme LCS) pour utiliser la même logique de comparaison
fn items_match(a: &PlaybackItem, b: &PlaybackItem) -> bool {
    a.uri == b.uri || a.didl_id == b.didl_id
}

Tests recommandés

  1. Attacher une playlist à un renderer OpenHome
  2. Lancer la lecture
  3. Attendre plusieurs cycles de refresh (> 60 secondes)
  4. Vérifier que la queue ne contient pas de duplications
  5. Cliquer sur différentes pistes et vérifier le même comportement

Diagnostic

Pour activer les logs de diagnostic :

RUST_LOG=pmocontrol::queue=debug

Les messages suivants permettent de tracer le comportement :

  • sync_queue: current item found in new playlist - Comportement normal
  • sync_queue: current item NOT found in new playlist, preserving as first item - Cas problématique (ne devrait plus apparaître avec le fix)