Skip to content

feat: 完善流媒体收藏、播放上报与同步可靠性 - #379

Merged
imsyy merged 5 commits into
devfrom
feat/streaming-refactor
Oct 15, 2026
Merged

imsyy merged 5 commits into
devfrom
feat/streaming-refactor

Conversation

@imsyy

@imsyy imsyy commented Oct 15, 2026 •

Copy link
Copy Markdown
Member

改动类型

  • 新功能(feat)
  • 缺陷修复(fix)
  • 重构 / 优化(不改变对外行为)
  • 文档(docs)
  • 其他(请在「改动说明」中注明)

是否包含破坏性变更

  • 是(见下方凭据存储说明)
  • 否

改动说明

补齐 Subsonic / OpenSubsonic / Navidrome / Jellyfin / Emby 的收藏与播放上报,新增「仅看收藏」,完善同步、鉴权、缓存、下载、封面和歌词流程

凭据仅使用系统安全存储,旧的非加密凭据需重新输入,Linux 需要可用的系统密钥环

包含 AI 辅助编写的代码

关联 Issue

Closes #330

自查清单

  • 仅包含流媒体相关改动
  • 已完成本地验证与代码复核,包括 AI 辅助编写的代码
  • 已格式化所有变更文件,类型检查与 ESLint 通过
  • 未修改原生模块,未手写 native 模块声明
  • 目标分支为 dev

@imsyy
imsyy force-pushed the feat/streaming-refactor branch from 667cd0d to f74ac9e Compare October 15, 2026 04:09
@imsyy
imsyy marked this pull request as ready for review October 15, 2026 04:12
Copilot AI balanced review requested due to automatic review settings October 15, 2026 04:12

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

收藏状态一致性、监听器生命周期、跨服务器页面刷新及重复歌曲歌单加载仍有需修复的问题。

6 open findings
What changed in this PR

为服务器型音乐来源补齐 Issue #330 所需的收藏与播放上报,并完善流媒体同步、凭据存储及资源身份隔离。

改动:

  • 新增服务端收藏同步、「仅看收藏」及独立播放会话上报
  • 将鉴权音源解析集中到主进程,完善下载、缓存、封面和歌词流程
  • 引入可取消的原子快照同步,补充跨服务器导航及相关测试
File Description
src/​utils/​navigate.ts 导航携带服务器身份
src/​stores/​streaming.ts 管理收藏、同步状态和服务器身份
src/​stores/​streaming.spec.ts 验证收藏与快照更新
src/​services/​streaming/​session.ts 删除渲染端会话生成器
src/​services/​nextTrackPreloader.ts 移除预载端会话参数
src/​services/​download/​source.ts 下载使用身份占位符
src/​services/​collection/​types.ts 合集加载支持服务器身份
src/​services/​collection/​streaming.ts 按所属服务器加载合集
src/​services/​audioSource.ts 使用占位符及分代缓存键
src/​services/​audioSource.spec.ts 验证流媒体身份占位符
src/​services/​artistLoader.ts 加载所属服务器的歌曲和专辑
src/​pages/​Streaming/​Songs.vue 新增收藏筛选
src/​pages/​Streaming/​Songs.spec.ts 验证筛选与播放全部
src/​pages/​Streaming/​Playlists.vue 歌单导航携带服务器身份
src/​pages/​Streaming/​Index.vue 显示同步错误
src/​pages/​Streaming/​Artists.vue 歌手导航携带服务器身份
src/​pages/​Streaming/​Albums.vue 专辑导航携带服务器身份
src/​pages/​Collection.vue 传递合集服务器参数
src/​pages/​Artist.vue 传递歌手及专辑服务器参数
src/​i18n/​locales/​zh-CN.json 补充中文提示
src/​i18n/​locales/​en-US.json 补充英文提示
src/​core/​player/​index.ts 流媒体重播重新加载
src/​core/​player/​failure.spec.ts 验证重播及取消竞态
src/​core/​player/​events.ts 使用统一重播入口
src/​composables/​useFavorite.ts 接入流媒体收藏
src/​components/​stats/​StatsTopList.vue 统计导航保留服务器身份
src/​components/​player/​TrackInfo.vue 歌手链接保留服务器身份
src/​components/​player/​PlayerBar.vue 禁用不支持的收藏操作
src/​components/​player/​FullPlayer/​PlayerData.vue 资源链接保留服务器身份
src/​components/​player/​FullPlayer/​index.vue 控制收藏按钮可用性
src/​components/​list/​SongList.vue 更新资源导航及收藏按钮
shared/​utils/​streamingSource.ts 编解码无凭据音源身份
shared/​types/​streaming.ts 扩展收藏、同步和配置类型
shared/​types/​player.ts 增加收藏及媒体身份字段
shared/​types/​errors.ts 新增权限错误码
shared/​types/​download.ts 下载身份包含媒体代次
electron/​preload/​index.ts 暴露收藏和同步接口
electron/​main/​services/​streaming/​sync.ts 可取消的完整媒体库同步
electron/​main/​services/​streaming/​snapshot.ts 暂存并原子发布快照
electron/​main/​services/​streaming/​snapshot.spec.ts 验证原子性、分页和取消
electron/​main/​services/​streaming/​playbackSession.ts 管理单次播放上报状态
electron/​main/​services/​streaming/​playbackSession.test.ts 验证收听计时与上报顺序
electron/​main/​services/​streaming/​playback.ts 协调主进程播放会话
electron/​main/​services/​streaming/​playback.spec.ts 验证会话隔离及停止顺序
electron/​main/​services/​streaming/​pagination.ts 完整分页及重复检测
electron/​main/​services/​streaming/​pagination.test.ts 验证分页边界与取消
electron/​main/​services/​streaming/​mediaSource.ts 解析播放源及原文件下载
electron/​main/​services/​streaming/​mediaSource.spec.ts 验证鉴权、权限和下载取消
electron/​main/​services/​streaming/​mediaIdentity.test.ts 验证音源身份及代次
electron/​main/​services/​streaming/​lyrics.ts 统一歌词时间转换
electron/​main/​services/​streaming/​errors.ts 区分协议错误类型
electron/​main/​services/​streaming/​coverProtocol.ts 传递封面版本并限制请求时间
electron/​main/​services/​streaming/​connection.ts 增加鉴权恢复和配置代次检查
electron/​main/​services/​streaming/​connection.spec.ts 验证鉴权恢复及过期请求
electron/​main/​services/​streaming/​config.ts 强制安全存储并维护身份代次
electron/​main/​services/​streaming/​config.spec.ts 验证凭据存储与身份变化
electron/​main/​services/​streaming/​adapters/​types.ts 扩展协议适配器契约
electron/​main/​services/​streaming/​adapters/​subsonic.ts 实现收藏、上报及目录遍历
electron/​main/​services/​streaming/​adapters/​resolve.ts 隔离共享登录与任务取消
electron/​main/​services/​streaming/​adapters/​jellyfin.ts 完善收藏、上报和资源读取
electron/​main/​services/​streaming/​adapters/​adapters.spec.ts 验证各协议请求与映射
electron/​main/​services/​songCache.ts 主进程解析缓存下载地址
electron/​main/​services/​songCache.spec.ts 验证缓存鉴权地址解析
electron/​main/​services/​downloadManager.ts 原文件下载及分代去重
electron/​main/​ipc/​streaming.ts 接入收藏和服务器生命周期
electron/​main/​ipc/​playerTransition.spec.ts 验证流媒体加载及停止竞态
electron/​main/​ipc/​player.ts 接入原生播放事件和会话收尾
electron/​main/​database/​streaming/​tracks.ts 更新单曲收藏状态
electron/​main/​database/​downloads.ts 按媒体代次查询下载记录
electron/​main/​database/​downloads.spec.ts 验证下载身份隔离
components.d.ts 补充红心图标组件声明
AGENTS.md 更新流媒体架构和注释说明

🧠 Review effort: Balanced


💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread electron/main/ipc/streaming.ts Outdated
Comment on lines +82 to +87
const favorite = await withStreamingAdapter(serverId, (config, adapter) =>
adapter.getFavorite(config, trackId),
);
if (isDbOpen()) updateStreamingFavorite(serverId, trackId, favorite);
if (isDbOpen()) recordStreamingStageFavorite(serverId, trackId, favorite);
sendToMain("streaming:favoriteChanged", { serverId, trackId, favorite });
Comment on lines +485 to 489
const items = await fetchAllItems(
config,
`Playlists/${playlistId}/Items?${params.toString()}`,
{ Fields: "MediaSources" },
`Playlists/${playlistId}/Items`,
);
Comment thread src/composables/useFavorite.ts Outdated
Comment on lines +32 to +36
watch(
() => media.track?.id,
() => {
if (media.track?.source === "streaming")
void streaming.refreshFavorite(media.track).catch(() => {});
Comment thread src/pages/Artist.vue

try {
await loadArtistService(source, id, {
serverId: typeof route.query.serverId === "string" ? route.query.serverId : undefined,
Comment thread src/pages/Collection.vue

try {
await loadCollectionService(source, type, id, {
serverId: typeof route.query.serverId === "string" ? route.query.serverId : undefined,
Comment thread src/stores/streaming.ts Outdated
Comment on lines +90 to +91
const isFavorite = (track: Track): boolean =>
favoriteOverrides.value.get(track.id)?.favorite ?? track.favorite ?? false;
@imsyy
imsyy merged commit b2ff2d7 into dev Oct 15, 2026
9 checks passed
@imsyy
imsyy deleted the feat/streaming-refactor branch October 15, 2026 13:31
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

为流媒体来源补齐收藏与播放上报(Subsonic/OpenSubsonic/Jellyfin/Emby)

2 participants