98890b9581
Tests cover curation, Lyria, queue, and API routes. Setting max_new_songs_per_day to 0 disables the limit; generate-batch runs 20 curated multilingual vocal directions. Co-authored-by: Cursor <cursoragent@cursor.com>
98 lines
2.7 KiB
Python
98 lines
2.7 KiB
Python
from __future__ import annotations
|
|
|
|
import json
|
|
from pathlib import Path
|
|
|
|
import pytest
|
|
|
|
from ozan_radio.dj import TrackPlan
|
|
from ozan_radio.settings import LyriaSettings
|
|
|
|
|
|
@pytest.fixture
|
|
def sample_plan() -> TrackPlan:
|
|
return TrackPlan(
|
|
id="abc12345",
|
|
title="Test Transmission",
|
|
mood="hypnotic test mood",
|
|
dj_line="Testing on air.",
|
|
lyria_prompt="Instrumental. 85 BPM desert dub with saz and ney. No vocals.",
|
|
)
|
|
|
|
|
|
@pytest.fixture
|
|
def lyria_mix() -> LyriaSettings:
|
|
return LyriaSettings(
|
|
model="lyria-3-pro-preview",
|
|
vocal_mode="mix",
|
|
language="auto",
|
|
singer_profile="",
|
|
output_format="mp3",
|
|
prefer_instrumental=False,
|
|
)
|
|
|
|
|
|
@pytest.fixture
|
|
def lyria_instrumental() -> LyriaSettings:
|
|
return LyriaSettings(
|
|
model="lyria-3-pro-preview",
|
|
vocal_mode="instrumental",
|
|
language="auto",
|
|
singer_profile="",
|
|
output_format="mp3",
|
|
prefer_instrumental=True,
|
|
)
|
|
|
|
|
|
@pytest.fixture
|
|
def songs_dir(tmp_path: Path) -> Path:
|
|
"""Minimal song library with one keeper and one skip-rated track."""
|
|
d = tmp_path / "songs"
|
|
d.mkdir()
|
|
keeper = {
|
|
"id": "11111111",
|
|
"title": "Sahara Test",
|
|
"mood": "warm",
|
|
"dj_line": "Test line.",
|
|
"lyria_prompt": "saz and ney",
|
|
"lyrics": "",
|
|
"file": "11111111_Sahara_Test.mp3",
|
|
"saved_at": "2026-06-07T12:00:00+00:00",
|
|
"curation": {
|
|
"rating": "love",
|
|
"shuffle_weight": 1.5,
|
|
"public_playlist": True,
|
|
"listener": "test",
|
|
"notes": "Gold template.",
|
|
"loved": ["saz", "ney"],
|
|
"disliked": ["fuzz guitar"],
|
|
"avoid_in_successors": ["electric guitar"],
|
|
"clone_prompt_hints": "saz first",
|
|
},
|
|
}
|
|
skipped = {
|
|
"id": "22222222",
|
|
"title": "Bad Intro",
|
|
"mood": "",
|
|
"dj_line": "",
|
|
"lyria_prompt": "",
|
|
"lyrics": "",
|
|
"file": "22222222_Bad_Intro.mp3",
|
|
"saved_at": "2026-06-06T12:00:00+00:00",
|
|
"curation": {
|
|
"rating": "skip",
|
|
"public_playlist": False,
|
|
"listener": "test",
|
|
"notes": "Removed.",
|
|
"loved": [],
|
|
"disliked": ["thin intro"],
|
|
"avoid_in_successors": [],
|
|
"clone_prompt_hints": "",
|
|
},
|
|
}
|
|
(d / "11111111_Sahara_Test.mp3").write_bytes(b"ID3fake")
|
|
(d / "22222222_Bad_Intro.mp3").write_bytes(b"ID3fake")
|
|
(d / "11111111.meta.json").write_text(json.dumps(keeper), encoding="utf-8")
|
|
(d / "22222222.meta.json").write_text(json.dumps(skipped), encoding="utf-8")
|
|
return d
|