From 6ac608a0b1ed0c50d7e3be07d27522059bd81d4e Mon Sep 17 00:00:00 2001 From: wisecolt Date: Sun, 1 Feb 2026 18:02:08 +0300 Subject: [PATCH] =?UTF-8?q?feat(movies):=20film=20tekrarlar=C4=B1n=C4=B1?= =?UTF-8?q?=20ve=20=C3=B6nbelle=C4=9Fi=20temizle?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Aynı film için birden fazla önbellek girdisi olduğunda en güncel olanı tutup eski önbellekleri temizleyen mekanizma eklendi. Video yolu bulunamayan filmlerin metadatası otomatik silinir. --- server/server.js | 66 +++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 65 insertions(+), 1 deletion(-) diff --git a/server/server.js b/server/server.js index a0c51c2..1695182 100644 --- a/server/server.js +++ b/server/server.js @@ -7565,7 +7565,7 @@ app.get("/api/movies", requireAuth, (req, res) => { .readdirSync(MOVIE_DATA_ROOT, { withFileTypes: true }) .filter((d) => d.isDirectory()); - const movies = entries + const rawMovies = entries .map((dirent) => { const key = dirent.name; const paths = movieDataPathsByKey(key); @@ -7587,6 +7587,17 @@ app.get("/api/movies", requireAuth, (req, res) => { const dupe = metadata._dupe || {}; const rootFolder = dupe.folder || key; const videoPath = dupe.videoPath || metadata.videoPath || null; + const absVideo = resolveMovieVideoAbsPath(metadata); + if (!absVideo) { + try { + fs.rmSync(paths.dir, { recursive: true, force: true }); + } catch (err) { + console.warn( + `⚠️ Movie metadata temizlenemedi (${paths.dir}): ${err.message}` + ); + } + return null; + } const encodedKey = key .split(path.sep) .map(encodeURIComponent) @@ -7605,6 +7616,14 @@ app.get("/api/movies", requireAuth, (req, res) => { : null); const cacheKey = paths.key; return { + _absVideo: absVideo, + _cacheDir: paths.dir, + _cacheKey: cacheKey, + _dedupeKey: + typeof metadata.id === "number" && metadata.id + ? `id:${metadata.id}` + : `title:${(metadata.title || metadata.matched_title || rootFolder) + .toLowerCase()}-${year || "unknown"}`, folder: rootFolder, cacheKey, id: @@ -7639,6 +7658,51 @@ app.get("/api/movies", requireAuth, (req, res) => { }) .filter(Boolean); + const dedupedMap = new Map(); + for (const item of rawMovies) { + const key = item._dedupeKey; + if (!dedupedMap.has(key)) { + dedupedMap.set(key, item); + continue; + } + const existing = dedupedMap.get(key); + const existingScore = + existing?.metadata?._dupe?.fetchedAt || + existing?.metadata?._dupe?.matchedAt || + existing?.metadata?.matchedAt || + 0; + const nextScore = + item?.metadata?._dupe?.fetchedAt || + item?.metadata?._dupe?.matchedAt || + item?.metadata?.matchedAt || + 0; + if (nextScore > existingScore) { + if (existing?._cacheDir) { + try { + fs.rmSync(existing._cacheDir, { recursive: true, force: true }); + } catch (err) { + console.warn( + `⚠️ Movie metadata temizlenemedi (${existing._cacheDir}): ${err.message}` + ); + } + } + dedupedMap.set(key, item); + } else if (item?._cacheDir) { + try { + fs.rmSync(item._cacheDir, { recursive: true, force: true }); + } catch (err) { + console.warn( + `⚠️ Movie metadata temizlenemedi (${item._cacheDir}): ${err.message}` + ); + } + } + } + + const movies = Array.from(dedupedMap.values()).map((item) => { + const { _absVideo, _cacheDir, _cacheKey, _dedupeKey, ...rest } = item; + return rest; + }); + movies.sort((a, b) => { const yearA = a.year || 0; const yearB = b.year || 0;