Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Bug]: DSF (dsd) files are converted to pcm by MPD when streaming via subsonic api #3021

Closed
3 tasks done
GioF71 opened this issue May 12, 2024 · 6 comments
Closed
3 tasks done
Labels
bug triage New bug reports that need to be evaluated

Comments

@GioF71
Copy link

GioF71 commented May 12, 2024

I confirm that:

  • I have searched the existing open AND closed issues to see if an issue already exists for the bug I've encountered
  • I'm using the latest version (your issue may have been fixed already)

Version

0.52.0 (92a98cd)

Current Behavior

MPD will need to convert the dsf file coming from a subsonic stream url, supposedly because of the Content-Type header, set to audio/dsd. Setting it to audio/x-dsd might help solving the issue. At least that is what happened with Lightweight Music Server, see here

Expected Behavior

The stream should be reproduced in dsd mode using mpd with a dsd-capable dac

Steps To Reproduce

  1. Use ffmpeg as the file scanner extractor
  2. Add at least a .dsf file to the library
  3. Rescan the library
  4. identify the id of a dsf track using the subsonic api
  5. Create the subsonic stream url for that track
  6. Try to add and play the track on Music Player Daemon
  7. Verify (cat /proc/asound/YOUR-DEVICE/pcm0p/sub0/hw_params that the dac is playing a dsd format

Environment

- OS:docker 26.0.0 on Debian Bullseye, arm64
- Browser: not particularly relevant
- Client: Postman, Music Player Daemon

How Navidrome is installed?

Docker

Configuration

---
version: "3"

networks:
  navidrome-net:
  traefik:
    external: true
  openssh-server:
    external: true
  subsonic-servers:
    external: true

services:
  navidrome-app:
    image: c.homelab.bustocastle.xyz/deluan/navidrome
    container_name: navidrome-app
    user: "1000:1000"
    hostname: navidrome-app
    networks:
      - navidrome-net
      - traefik
      - openssh-server
      - subsonic-servers
    environment:
      #- ND_ENABLETRANSCODINGCONFIG="true"
      #- ND_SCANSCHEDULE=12h
      #- ND_LOGLEVEL=info  
      #- ND_BASEURL=""
      - ND_SCANNER_EXTRACTOR=ffmpeg
      - ND_SCANSCHEDULE=0
      #- ND_ENABLETRANSCODINGCONFIG=true
      - ND_SPOTIFY_ID=${ND_SPOTIFY_ID}
      - ND_SPOTIFY_SECRET=${ND_SPOTIFY_SECRET}
      - ND_LASTFM_APIKEY=${ND_LASTFM_APIKEY}
      - ND_LASTFM_SECRET=${ND_LASTFM_SECRET}
      #- ND_LOGLEVEL=debug
    volumes:
      - /mnt/local/synapse/docker-data/navidrome:/data
      - /mnt/local/s8tb02/music/exported:/music:ro
    ports:
      - 4533:4533
    labels:
      - com.centurylinklabs.watchtower.enable=false
    restart: unless-stopped

.env file

ND_SPOTIFY_ID=redacted
ND_SPOTIFY_SECRET=redacted
ND_LASTFM_APIKEY=redacted
ND_LASTFM_SECRET=redacted

Relevant log output

navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="API: New request /rest/getSong.view" client=upmpdcli requestId=navidrome-app/mQsSbhtZb4-000002 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Found matching player" client=upmpdcli id=a6aa176f-f04b-4c69-822f-1026d93fd17f requestId=navidrome-app/mQsSbhtZb4-000002 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000002 status=OK
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="HTTP: POST http://navidrome.homelab.local:4533/rest/getSong.view" elapsedTime=13ms httpStatus=200 remoteAddr="192.168.1.173:53598" requestId=navidrome-app/mQsSbhtZb4-000002 responseSize=960 userAgent=Python-urllib/3.10
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="API: New request /rest/stream" client=upmpdcli requestId=navidrome-app/mQsSbhtZb4-000003 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Found matching player" client=upmpdcli id=4450688c-c06b-4d06-9526-be69f2fb4415 requestId=navidrome-app/mQsSbhtZb4-000003 type="Music Player Daemon 0.23.15" username=giovanni
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Streaming RAW file" id=9e26a4f42de63690b40ac3d402a31ba4 originalBitrate=5644 originalFormat=dsf path="/music/Music05/Rock/My Artist/My Artist - So/02 - My Artist - My Song.dsf" requestBitrate=0 requestFormat= requestId=navidrome-app/mQsSbhtZb4-000003 requestOffset=0 selectedBitrate=0 selectedFormat=raw
navidrome-app    | time="2024-05-12T14:53:54Z" level=info msg="Streaming file" artist="My Artist" bitRate=0 cached=false format=raw originalBitRate=5644 originalFormat=dsf requestId=navidrome-app/mQsSbhtZb4-000003 title=My Song transcoding=false user=giovanni
navidrome-app    | time="2024-05-12T14:53:54Z" level=warning msg="Request was interrupted" endpoint=/rest/stream error="context canceled" requestId=navidrome-app/mQsSbhtZb4-000003
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="HTTP: GET http://navidrome.homelab.local:4533/rest/stream?id=9e26a4f42de63690b40ac3d402a31ba4&u=giovanni&s=[REDACTED]&t=[REDACTED]&c=upmpdcli&v=1.16.1" elapsedTime=16.6ms httpStatus=200 remoteAddr="192.168.1.44:40024" requestId=navidrome-app/mQsSbhtZb4-000003 responseSize=327680 userAgent="Music Player Daemon 0.23.15"
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="API: New request /rest/stream" client=upmpdcli requestId=navidrome-app/mQsSbhtZb4-000004 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Found matching player" client=upmpdcli id=4450688c-c06b-4d06-9526-be69f2fb4415 requestId=navidrome-app/mQsSbhtZb4-000004 type="Music Player Daemon 0.23.15" username=giovanni
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Streaming RAW file" id=9e26a4f42de63690b40ac3d402a31ba4 originalBitrate=5644 originalFormat=dsf path="/music/Music05/Rock/My Artist/My Artist - So/02 - My Artist - My Song.dsf" requestBitrate=0 requestFormat= requestId=navidrome-app/mQsSbhtZb4-000004 requestOffset=0 selectedBitrate=0 selectedFormat=raw
navidrome-app    | time="2024-05-12T14:53:54Z" level=info msg="Streaming file" artist="My Artist" bitRate=0 cached=false format=raw originalBitRate=5644 originalFormat=dsf requestId=navidrome-app/mQsSbhtZb4-000004 title=My Song transcoding=false user=giovanni
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="HTTP: GET http://navidrome.homelab.local:4533/rest/stream?id=9e26a4f42de63690b40ac3d402a31ba4&u=giovanni&s=[REDACTED]&t=[REDACTED]&c=upmpdcli&v=1.16.1" elapsedTime=6.4ms httpStatus=206 remoteAddr="192.168.1.44:40034" requestId=navidrome-app/mQsSbhtZb4-000004 responseSize=2830 userAgent="Music Player Daemon 0.23.15"
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="API: New request /rest/stream" client=upmpdcli requestId=navidrome-app/mQsSbhtZb4-000005 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Found matching player" client=upmpdcli id=4450688c-c06b-4d06-9526-be69f2fb4415 requestId=navidrome-app/mQsSbhtZb4-000005 type="Music Player Daemon 0.23.15" username=giovanni
navidrome-app    | time="2024-05-12T14:53:54Z" level=debug msg="Streaming RAW file" id=9e26a4f42de63690b40ac3d402a31ba4 originalBitrate=5644 originalFormat=dsf path="/music/Music05/Rock/My Artist/My Artist - So/02 - My Artist - My Song.dsf" requestBitrate=0 requestFormat= requestId=navidrome-app/mQsSbhtZb4-000005 requestOffset=0 selectedBitrate=0 selectedFormat=raw
navidrome-app    | time="2024-05-12T14:53:54Z" level=info msg="Streaming file" artist="My Artist" bitRate=0 cached=false format=raw originalBitRate=5644 originalFormat=dsf requestId=navidrome-app/mQsSbhtZb4-000005 title=My Song transcoding=false user=giovanni
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000006 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000006 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000006 status=OK
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=6.6ms httpStatus=200 remoteAddr="172.22.0.1:46668" requestId=navidrome-app/mQsSbhtZb4-000006 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000007 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000007 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000007 status=OK
navidrome-app    | time="2024-05-12T14:53:55Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=6.6ms httpStatus=200 remoteAddr="172.22.0.1:46682" requestId=navidrome-app/mQsSbhtZb4-000007 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:53:56Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000008 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:56Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000008 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:56Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000008 status=OK
navidrome-app    | time="2024-05-12T14:53:56Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=4.4ms httpStatus=200 remoteAddr="172.22.0.1:46694" requestId=navidrome-app/mQsSbhtZb4-000008 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:53:57Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000009 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:57Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000009 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:57Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000009 status=OK
navidrome-app    | time="2024-05-12T14:53:57Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=6.6ms httpStatus=200 remoteAddr="172.22.0.1:46696" requestId=navidrome-app/mQsSbhtZb4-000009 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:53:58Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000010 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:58Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000010 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:58Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000010 status=OK
navidrome-app    | time="2024-05-12T14:53:58Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=7.9ms httpStatus=200 remoteAddr="172.22.0.1:46706" requestId=navidrome-app/mQsSbhtZb4-000010 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:53:59Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000011 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:53:59Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000011 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:53:59Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000011 status=OK
navidrome-app    | time="2024-05-12T14:53:59Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=6.5ms httpStatus=200 remoteAddr="172.22.0.1:46722" requestId=navidrome-app/mQsSbhtZb4-000011 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:54:00Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000012 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:54:00Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000012 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:54:00Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000012 status=OK
navidrome-app    | time="2024-05-12T14:54:00Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=4.2ms httpStatus=200 remoteAddr="172.22.0.1:46730" requestId=navidrome-app/mQsSbhtZb4-000012 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:54:01Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000013 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:54:01Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000013 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:54:01Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000013 status=OK
navidrome-app    | time="2024-05-12T14:54:01Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=6.7ms httpStatus=200 remoteAddr="172.22.0.1:51610" requestId=navidrome-app/mQsSbhtZb4-000013 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:54:02Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000014 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:54:02Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000014 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:54:02Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000014 status=OK
navidrome-app    | time="2024-05-12T14:54:02Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=4.1ms httpStatus=200 remoteAddr="172.22.0.1:51616" requestId=navidrome-app/mQsSbhtZb4-000014 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:54:03Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000015 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:54:03Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000015 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:54:03Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000015 status=OK
navidrome-app    | time="2024-05-12T14:54:03Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=4.3ms httpStatus=200 remoteAddr="172.22.0.1:51620" requestId=navidrome-app/mQsSbhtZb4-000015 responseSize=960 userAgent=Python-urllib/3.12
navidrome-app    | time="2024-05-12T14:54:04Z" level=debug msg="API: New request /rest/getSong.view" client=mpd-subsonic-scrobbler requestId=navidrome-app/mQsSbhtZb4-000016 username=giovanni version=1.16.1
navidrome-app    | time="2024-05-12T14:54:04Z" level=debug msg="Found matching player" client=mpd-subsonic-scrobbler id=419546e3-988d-4e48-b1ef-81585ed4e824 requestId=navidrome-app/mQsSbhtZb4-000016 type=Python-urllib username=giovanni
navidrome-app    | time="2024-05-12T14:54:04Z" level=debug msg="API: Successful response" endpoint=/rest/getSong.view requestId=navidrome-app/mQsSbhtZb4-000016 status=OK
navidrome-app    | time="2024-05-12T14:54:04Z" level=debug msg="HTTP: POST http://192.168.1.174:4533/rest/getSong.view" elapsedTime=5.7ms httpStatus=200 remoteAddr="172.22.0.1:51628" requestId=navidrome-app/mQsSbhtZb4-000016 responseSize=960 userAgent=Python-urllib/3.12

Anything else?

In the log before, you will also find evidences of an additional client. That is mpd-subsonic-scrobbler running.

Code of Conduct

  • I agree to follow Navidrome's Code of Conduct
@GioF71 GioF71 added bug triage New bug reports that need to be evaluated labels May 12, 2024
@GioF71 GioF71 changed the title [Bug]: DSF (dsd) files are converted to pcm by pcm when streaming [Bug]: DSF (dsd) files are converted to pcm by MPD when streaming via subsonic api May 12, 2024
@deluan deluan closed this as completed in c556088 May 12, 2024
@deluan
Copy link
Member

deluan commented May 12, 2024

Thanks for reporting. Fixed:

Screenshot 2024-05-12 at 11 36 32 AM

@deluan
Copy link
Member

deluan commented May 12, 2024

By the way, taglib extractor now supports .dsf files, as it is using TagLib 2.0.1

@GioF71
Copy link
Author

GioF71 commented May 12, 2024

Thanks for reporting. Fixed:

Screenshot 2024-05-12 at 11 36 32 AM

awesome! Thank you very much!

@GioF71
Copy link
Author

GioF71 commented May 12, 2024

By the way, taglib extractor now supports .dsf files, as it is using TagLib 2.0.1

So I understand we can avoid to set ffmpeg as the scanner in order to support dsf file in the library.
But other than support dsf without having to change a default config parameter, is there some other advantage? Thank you again

@deluan
Copy link
Member

deluan commented May 12, 2024

So I understand we can avoid to set ffmpeg as the scanner in order to support dsf file in the library.

Yes.

But other than support dsf without having to change a default config parameter, is there some other advantage? Thank you again

ffmpeg was the original (and only) extractor, but I ended-up implementing taglib as it was faster. I kept ffmpeg around mainly because of DSF support.

Now with taglib 2.0.1 increasing its support for more tag/file formats, the only reason to keep ffmpeg around is that it is better at understanding malformed tags, and also supports some unconventional file formats.

But with multi-valued tags coming soon to Navidrome, taglib will be even more useful than ffmpeg.

@GioF71
Copy link
Author

GioF71 commented May 13, 2024

Very informative. Thank you!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug triage New bug reports that need to be evaluated
Projects
None yet
Development

No branches or pull requests

2 participants