A music player that connects to your cloud/distributed storage.
5
fork

Configure Feed

Select the types of activity you want to include in your feed.

chore: don't process disabled sources

+64 -32
+3 -1
src/common/facets/constants.js
··· 18 18 "facets/data/sources/index.html", 19 19 "facets/themes/blur/artwork-controller/facet/index.html", 20 20 21 - // PRELUDES 21 + // PRELUDES (BASE) 22 22 "facets/data/metadata-bundle/index.html", 23 23 "facets/data/artwork-bundle/index.html", 24 24 "facets/data/input-bundle/index.html", 25 25 "facets/data/output-bundle/index.html", 26 + 27 + // PRELUDES 26 28 "facets/data/process-tracks/prelude/index.html", 27 29 "facets/misc/scrobble/index.html", 28 30 "facets/playback/auto-queue/prelude/index.html",
+7 -1
src/components/orchestrator/process-tracks/element.js
··· 7 7 import { signal, untracked } from "~/common/signal.js"; 8 8 import { listen } from "~/common/worker.js"; 9 9 10 + import { parseDisabledUris } from "~/components/orchestrator/sources/common.js"; 11 + 10 12 /** 11 13 * @import {ProxiedActions} from "~/common/worker.d.ts" 12 14 * @import {InputElement} from "~/components/input/types.d.ts" ··· 199 201 console.log("🪵 Processing initiated"); 200 202 201 203 const cachedTracks = await data(this.output.tracks); 202 - const result = await this.#proxy.process(cachedTracks); 204 + 205 + const settings = await data(this.output.settings); 206 + const disabledUris = parseDisabledUris(settings); 207 + 208 + const result = await this.#proxy.process({ tracks: cachedTracks, disabledUris }); 203 209 204 210 if (result) { 205 211 await this.output.tracks.save(mergeTracks(cachedTracks, result));
+1 -1
src/components/orchestrator/process-tracks/types.d.ts
··· 6 6 }; 7 7 8 8 export type Actions = { 9 - process: (tracks: Track[]) => Promise<Track[] | null>; 9 + process: (args: { tracks: Track[]; disabledUris: string[] }) => Promise<Track[] | null>; 10 10 progress: () => Progress; 11 11 };
+14 -6
src/components/orchestrator/process-tracks/worker.js
··· 34 34 ) => /** @type {ActionsWithTunnel<Actions>["process"]} */ (async ( 35 35 { data, ports }, 36 36 ) => { 37 - const cachedTracks = data; 37 + const { tracks: cachedTracks, disabledUris } = data; 38 38 39 39 // Reset progress 40 40 $progress.value = { processed: 0, total: 0 }; ··· 48 48 ports.input.start(); 49 49 ports.metadata.start(); 50 50 51 - // List 52 - const tracks = await input.list(cachedTracks); 51 + // Split disabled tracks out — they are preserved as-is and skipped for listing/metadata 52 + const isDisabled = (/** @type {Track} */ t) => 53 + disabledUris.some((/** @type {string} */ uri) => t.uri.startsWith(uri)); 54 + const disabledTracks = cachedTracks.filter(isDisabled); 55 + const enabledCachedTracks = cachedTracks.filter((t) => !isDisabled(t)); 56 + 57 + // List from enabled sources only 58 + const tracks = await input.list(enabledCachedTracks); 53 59 54 60 // Persist the full track list immediately so that an interrupted metadata 55 61 // processing run doesn't lose discovered tracks. On next run they'll come 56 62 // back as cachedTracks and only the ones without metadata need reprocessing. 57 - announce("list", tracks, context); 63 + announce("list", [...tracks, ...disabledTracks], context); 58 64 59 65 // Reset progress 60 66 $progress.value = { processed: 0, total: tracks.length }; ··· 91 97 Promise.resolve([]), 92 98 ); 93 99 100 + const allTracks = [...tracksWithMetadata, ...disabledTracks]; 101 + 94 102 // Changed? 95 - const diff = deepDiff.diff(tracksWithMetadata, cachedTracks); 103 + const diff = deepDiff.diff(allTracks, cachedTracks); 96 104 const changed = !!diff; 97 105 98 106 // Save if changed 99 - if (changed) return tracksWithMetadata; 107 + if (changed) return allTracks; 100 108 return null; 101 109 }); 102 110
+34
src/components/orchestrator/sources/common.js
··· 1 + import { DISABLED_KEY } from "./constants.js"; 2 + 3 + /** 4 + * @import {Setting} from "~/definitions/types.d.ts" 5 + */ 6 + 7 + /** 8 + * Strips query params from a URI, returning the key used to store/compare disabled state. 9 + * 10 + * @param {string} uri 11 + * @returns {string} 12 + */ 13 + export function uriKey(uri) { 14 + const q = uri.indexOf("?"); 15 + return q === -1 ? uri : uri.slice(0, q); 16 + } 17 + 18 + /** 19 + * Parses the disabled source URIs list from a settings array. 20 + * Returns an empty array if the setting is absent or malformed. 21 + * 22 + * @param {Setting[]} settings 23 + * @returns {string[]} 24 + */ 25 + export function parseDisabledUris(settings) { 26 + const setting = settings.find((s) => s.key === DISABLED_KEY); 27 + if (!setting) return []; 28 + try { 29 + const parsed = JSON.parse(setting.value); 30 + return Array.isArray(parsed) ? parsed : []; 31 + } catch { 32 + return []; 33 + } 34 + }
+5 -23
src/components/orchestrator/sources/element.js
··· 6 6 import { signal } from "~/common/signal.js"; 7 7 8 8 import { DISABLED_KEY } from "./constants.js"; 9 + import { parseDisabledUris, uriKey } from "./common.js"; 9 10 10 11 /** 11 12 * @import {InputElement, Source} from "~/components/input/types.d.ts" ··· 41 42 * @returns {boolean} 42 43 */ 43 44 isDisabled(uri) { 44 - const q = uri.indexOf("?"); 45 - const key = q === -1 ? uri : uri.slice(0, q); 46 - return this.#disabled.get().includes(key); 45 + return this.#disabled.get().includes(uriKey(uri)); 47 46 } 48 47 49 48 /** 50 49 * @param {string} uri 51 50 */ 52 51 async toggle(uri) { 53 - const q = uri.indexOf("?"); 54 - const key = q === -1 ? uri : uri.slice(0, q); 52 + const key = uriKey(uri); 55 53 56 54 const output = this.#output.value; 57 55 if (!output) { ··· 62 60 const settings = await Output.data(output.settings); 63 61 const existing = settings.find((s) => s.key === DISABLED_KEY); 64 62 65 - /** @type {string[]} */ 66 - let disabled = []; 67 - if (existing) { 68 - try { 69 - const parsed = JSON.parse(existing.value); 70 - disabled = Array.isArray(parsed) ? parsed : []; 71 - } catch { 72 - disabled = []; 73 - } 74 - } 63 + let disabled = parseDisabledUris(settings); 75 64 76 65 if (disabled.includes(key)) { 77 66 disabled = disabled.filter((u) => u !== key); ··· 124 113 this.effect(() => { 125 114 const col = output.settings.collection(); 126 115 if (col.state !== "loaded") { this.#disabled.value = []; return; } 127 - const setting = col.data.find((s) => s.key === DISABLED_KEY); 128 - if (!setting) { this.#disabled.value = []; return; } 129 - try { 130 - const parsed = JSON.parse(setting.value); 131 - this.#disabled.value = Array.isArray(parsed) ? parsed : []; 132 - } catch { 133 - this.#disabled.value = []; 134 - } 116 + this.#disabled.value = parseDisabledUris(col.data); 135 117 }); 136 118 137 119 // Single input mode + dependencies