import { describe, expect, it } from "vitest"; import { classifyTmdb, DEFAULT_CLASSIFICATION_YAML, parseClassificationYaml } from "./classification.ts"; const config = parseClassificationYaml(DEFAULT_CLASSIFICATION_YAML); describe("ordered TMDB classification", () => { it("defaults honor genre priority and normalize raw movie and TV facts", () => { expect(classifyTmdb(config, "movie", { genres: [{ id: 16 }], original_language: "zh" })).toEqual({ category: "动画电影", matchedFields: ["genre_ids"], fallback: false, }); expect(classifyTmdb(config, "movie", { genres: [{ id: 10402 }] }).category).toBe("演唱会"); for (const language of ["zh", "cn", "bo", "za"]) expect(classifyTmdb(config, "movie", { original_language: language }).category).toBe("华语电影"); for (const country of ["JP", "VN", "IR", "SA"]) { expect(classifyTmdb(config, "movie", { production_countries: [{ iso_3166_1: country }] }).category).toBe( "亚洲电影", ); expect(classifyTmdb(config, "tv", { origin_country: [country] }).category).toBe("亚洲剧集"); } expect(classifyTmdb(config, "tv", { genres: [{ id: 16 }, { id: 10762 }], origin_country: ["CN"] }).category).toBe( "儿童剧集", ); expect(classifyTmdb(config, "tv", { genre_ids: [10764], origin_country: ["CN"] }).category).toBe("综艺"); expect(classifyTmdb(config, "tv", { origin_country: ["TW"] }).category).toBe("华语剧集"); expect(classifyTmdb(config, "movie", { original_language: "en" })).toEqual({ category: "欧美电影", matchedFields: [], fallback: true, }); }); it("AND fields, OR scalar/list values, exclusions and year ranges", () => { const c = parseClassificationYaml(`movie: 合作: original_language: [en, fr] production_countries: 'JP,!US' release_year: '2000-2010,2020' adult: false 其它: null tv: 年份: release_year: '!2000-2010' `); const raw = { original_language: "en", production_countries: [{ iso_3166_1: "JP" }], release_date: "2010-02-03", adult: false, }; expect(classifyTmdb(c, "movie", raw).matchedFields).toEqual([ "original_language", "production_countries", "release_year", "adult", ]); expect(classifyTmdb(c, "movie", { ...raw, adult: true }).category).toBe("其它"); expect( classifyTmdb(c, "movie", { ...raw, production_countries: [{ iso_3166_1: "JP" }, { iso_3166_1: "US" }] }).category, ).toBe("其它"); expect(classifyTmdb(c, "movie", { ...raw, release_date: "2020-01-01" }).category).toBe("合作"); expect(classifyTmdb(c, "tv", { first_air_date: "2011-01-01" }).category).toBe("年份"); expect(classifyTmdb(c, "tv", { title: "Missing date" }).category).toBeNull(); }); it("supports arbitrary first-level scalar/list fields and numeric category ordering", () => { const c = parseClassificationYaml(`movie: '20': custom: [true, 3] '1': custom: true tv: {}`); expect(c.movie.map((r) => r.category)).toEqual(["20", "1"]); expect(classifyTmdb(c, "movie", { custom: [true, 4] }).category).toBe("20"); }); it("no fallback without actual raw data, missing exclusions do not match", () => { expect(classifyTmdb(config, "movie", null).category).toBeNull(); expect(classifyTmdb(config, "movie", {}).category).toBeNull(); const c = parseClassificationYaml("movie:\n 未排除:\n original_language: '!zh'\ntv: {}\n"); expect(classifyTmdb(c, "movie", { title: "Unknown" }).category).toBeNull(); expect(classifyTmdb(c, "movie", { original_language: "" }).category).toBeNull(); }); it.each([ "movie: {}\nmovie: {}\ntv: {}", "movie:\n 重复: null\n 重复: null\ntv: {}", "movie:\n 分类:\n genre_ids: 16\n genre_ids: 99\ntv: {}", "movie:\n ../逃逸: null\ntv: {}", "movie:\n 无条件: null\n 动画:\n genre_ids: 16\ntv: {}", "movie:\n 条件:\n release_year: '2020-2000'\ntv: {}", "movie:\n 条件:\n nested: {invalid: value}\ntv: {}", "movies: {}\ntv: {}", ])("rejects invalid config: %s", (yaml) => expect(() => parseClassificationYaml(yaml)).toThrow()); });