在 Linux 上通过 MPRIS DBus 控制 Spotify 桌面客户端 —— 无需浏览器自动化或模拟点击。
前提条件:
Spotify 桌面客户端已安装(/opt/spotify/spotify,通过 /usr/bin/spotify 包装)
具有 $XAUTHORITY 的活动 X11/Wayland 会话
dbus-send(随 DBus 捆绑,始终存在)
快速开始:
# 暂停/播放切换
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 org.mpris.MediaPlayer2.Player.PlayPause
# 下一首/上一首
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 org.mpris.MediaPlayer2.Player.Next
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 org.mpris.MediaPlayer2.Player.Previous
Spotify 必须以正确的 X11 身份和完全分离的代理进程树启动,因此 OpenClaw 重启不会杀死它。
步骤:
# 1. 发现 Xauthority 路径
XAUTHORITY=$(ps aux | grep -E 'Xwayland|Xorg' | grep -oP '\-auth \S+' | head -1 | cut -d' ' -f2)
# 2. 使用 setsid 启动(完全分离,重启后存活)
DISPLAY=:0 XAUTHORITY="$XAUTHORITY" setsid -f spotify >/dev/null 2>&1
# 3. 等待 DBus 注册(Spotify 需要 ~5-8 秒)
for i in $(seq 1 10); do sleep 1
if dbus-send --session --dest=org.freedesktop.DBus --type=method_call --print-reply \
/org/freedesktop/DBus org.freedesktop.DBus.ListNames 2>/dev/null | grep -q spotify; then
break
fi
done
关键:setsid -f 将 Spotify 放在其自己的会话中,独立于启动进程树。没有它,nohup & 仍然将进程绑定到同一会话,并且在父会话终止时死亡。
MPRIS 没有搜索方法。工作流程:web 搜索 → 提取 Spotify 曲目 ID → OpenUri。
# 步骤 1:在网上搜索曲目以获取其 Spotify URL
# 示例搜索: "李白 李荣浩 spotify"
# 从 URL 中提取曲目 ID,如:https://open.spotify.com/track/0aLtafjN146xAdZeqYN8Ho
# 步骤 2:使用 spotify:track: URI 调用 OpenUri
TRACK_ID="0aLtafjN146xAdZeqYN8Ho"
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 \
org.mpris.MediaPlayer2.Player.OpenUri \
string:"spotify:track:$TRACK_ID"
紧急:Spotify 客户端加载曲目并立即开始播放 —— 不需要在 OpenUri 后调用 Play。
支持的 URL 类型:
spotify:track: —— 单曲
spotify:album: —— 全部专辑
spotify:playlist: —— 播放列表
spotify:artist: —— 艺术家页面
# 当前播放/暂停状态
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 \
org.freedesktop.DBus.Properties.Get \
string:org.mpris.MediaPlayer2.Player string:PlaybackStatus
# 当前曲目元数据(标题、艺术家、专辑、URL、艺术等)
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 \
org.freedesktop.DBus.Properties.Get \
string:org.mpris.MediaPlayer2.Player string:Metadata
返回字典中的关键元数据字段:
xesam:title —— 曲目标题
xesam:artist —— 艺术家(数组)
xesam:album —— 专辑名称
xesam:url —— Spotify 网页 URL
mpris:trackid —— 内部曲目 ID 路径
mpris:artUrl —— 专辑艺术 URL
# 设置音量(0.0 到 1.0)
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 \
org.freedesktop.DBus.Properties.Set \
string:org.mpris.MediaPlayer2.Player string:Volume \
variant:double:0.5
# 读取当前音量
dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify \
/org/mpris/MediaPlayer2 \
org.freedesktop.DBus.Properties.Get \
string:org.mpris.MediaPlayer2.Player string:Volume
# 快速:进程检查
pgrep -a spotify
# 可靠:DBus 检查(确认完全初始化)
dbus-send --session --dest=org.freedesktop.DBus --type=method_call --print-reply \
/org/freedesktop/DBus org.freedesktop.DBus.ListNames 2>/dev/null | grep spotify
DBus 检查是首选的,因为它确认客户端已完全初始化并准备好接收命令;仅进程检查可能在 Spotify 启动时返回假阳性。
常见 DBus 目的地
操作 方法
播放 org.mpris.MediaPlayer2.Player.Play
暂停 org.mpris.MediaPlayer2.Player.Pause
播放/暂停切换 org.mpris.MediaPlayer2.Player.PlayPause
下一首 org.mpris.MediaPlayer2.Player.Next
上一首 org.mpris.MediaPlayer2.Player.Previous
停止 org.mpris.MediaPlayer2.Player.Stop
寻找 org.mpris.MediaPlayer2.Player.Seek(int64:offset-us)
OpenUri org.mpris.MediaPlayer2.Player.OpenUri(string:uri)
设置位置 org.mpris.MediaPlayer2.Player.SetPosition(trackId,position)