mirror of
https://github.com/jxxghp/MoviePilot.git
synced 2026-11-11 08:10:39 +08:00
fix: align AniList and TheAudioDB network probes
This commit is contained in:
@@ -8,6 +8,8 @@ from app.foundation.url import UrlUtils
|
||||
|
||||
from .domain import NetworkTestRule, SettingsReader
|
||||
|
||||
_DEFAULT_THEAUDIODB_API_KEY = "123"
|
||||
|
||||
|
||||
def _configured_service_rule(
|
||||
*,
|
||||
@@ -90,7 +92,7 @@ def build_network_rules(
|
||||
rules.extend(_build_metadata_module_rules(settings))
|
||||
rules.extend(_build_notification_module_rules())
|
||||
rules.extend(_build_external_media_rules(settings))
|
||||
rules.extend(_build_music_service_rules())
|
||||
rules.extend(_build_music_service_rules(settings))
|
||||
rules.extend(_build_configured_module_rules(settings))
|
||||
rules.extend(_build_fixed_service_rules(settings, github_proxy))
|
||||
if enabled_module_ids is None:
|
||||
@@ -325,10 +327,16 @@ def _build_external_media_rules(settings: SettingsReader) -> list[NetworkTestRul
|
||||
id="anilist_api",
|
||||
name="AniList 番剧元数据",
|
||||
icon="anilist",
|
||||
url=("https://graphql.anilist.co/?query=%7B%20Media%28id%3A1%29%20%7Bid%7D%20%7D"),
|
||||
url="https://graphql.anilist.co",
|
||||
proxy=True,
|
||||
allowed_redirect_prefixes=("https://graphql.anilist.co/",),
|
||||
module_ids=("AniListModule",),
|
||||
http_method="POST",
|
||||
request_json=(("query", "{ Media(id: 1) { id } }"),),
|
||||
headers=(
|
||||
("Accept", "application/json"),
|
||||
("Content-Type", "application/json"),
|
||||
),
|
||||
),
|
||||
NetworkTestRule(
|
||||
id="anilist_trace",
|
||||
@@ -367,8 +375,8 @@ def _build_external_media_rules(settings: SettingsReader) -> list[NetworkTestRul
|
||||
]
|
||||
|
||||
|
||||
def _build_music_service_rules() -> list[NetworkTestRule]:
|
||||
"""构建 MusicBrainz、ListenBrainz 和 TheAudioDB 服务目标。"""
|
||||
def _build_music_service_rules(settings: SettingsReader) -> list[NetworkTestRule]:
|
||||
"""构建音乐服务目标,并让 TheAudioDB 使用模块当前配置的 API Key。"""
|
||||
return [
|
||||
NetworkTestRule(
|
||||
id="musicbrainz_api",
|
||||
@@ -392,7 +400,11 @@ def _build_music_service_rules() -> list[NetworkTestRule]:
|
||||
id="theaudiodb_api",
|
||||
name="TheAudioDB 音乐信息",
|
||||
icon="theaudiodb",
|
||||
url=("https://www.theaudiodb.com/api/v1/json/123/search.php?s=coldplay"),
|
||||
url=(
|
||||
"https://www.theaudiodb.com/api/v1/json/"
|
||||
f"{settings('THEAUDIODB_API_KEY', _DEFAULT_THEAUDIODB_API_KEY)}"
|
||||
"/search.php?s=coldplay"
|
||||
),
|
||||
proxy=True,
|
||||
allowed_redirect_prefixes=("https://www.theaudiodb.com/",),
|
||||
module_ids=("TheAudioDbModule",),
|
||||
|
||||
84
tests/test_nettest_probe_contract.py
Normal file
84
tests/test_nettest_probe_contract.py
Normal file
@@ -0,0 +1,84 @@
|
||||
"""验证内置网络探针与对应模块请求契约保持一致。"""
|
||||
|
||||
import asyncio
|
||||
from types import SimpleNamespace
|
||||
from unittest.mock import AsyncMock, Mock
|
||||
|
||||
from app.application.network import NetworkTestService
|
||||
|
||||
|
||||
def _network_test_service(transport, **settings) -> NetworkTestService:
|
||||
"""创建读取独立设置快照的网络探测服务。"""
|
||||
values = {"NORMAL_USER_AGENT": "MoviePilot-Test", **settings}
|
||||
return NetworkTestService(
|
||||
transport=transport,
|
||||
settings=lambda key, default=None: values.get(key, default),
|
||||
logger=Mock(),
|
||||
)
|
||||
|
||||
|
||||
def test_anilist_probe_uses_post_graphql_request() -> None:
|
||||
"""AniList 官方 GraphQL 探针应使用模块相同的 POST JSON 协议。"""
|
||||
captured = {}
|
||||
response = SimpleNamespace(
|
||||
status_code=200,
|
||||
headers={},
|
||||
text='{"data":{"Media":{"id":1}}}',
|
||||
aclose=AsyncMock(),
|
||||
)
|
||||
|
||||
async def respond(method, url, **options):
|
||||
"""记录 AniList 探测请求并返回成功响应。"""
|
||||
captured.update(method=method, url=url, **options)
|
||||
return response
|
||||
|
||||
transport = SimpleNamespace(request=AsyncMock(side_effect=respond))
|
||||
result = asyncio.run(
|
||||
_network_test_service(transport).execute(target_id="anilist_api")
|
||||
)
|
||||
|
||||
assert result.success
|
||||
assert captured["method"] == "POST"
|
||||
assert captured["url"] == "https://graphql.anilist.co"
|
||||
assert captured["json_body"] == {"query": "{ Media(id: 1) { id } }"}
|
||||
assert captured["headers"] == {
|
||||
"Accept": "application/json",
|
||||
"Content-Type": "application/json",
|
||||
}
|
||||
|
||||
|
||||
def test_theaudiodb_probe_uses_configured_key_and_module_health_endpoint() -> None:
|
||||
"""TheAudioDB 探针应使用模块配置的 Key 和相同的艺术家搜索接口。"""
|
||||
configured_key = "custom-audio-key"
|
||||
captured = {}
|
||||
response = SimpleNamespace(
|
||||
status_code=200,
|
||||
headers={},
|
||||
text='{"artists":[]}',
|
||||
aclose=AsyncMock(),
|
||||
)
|
||||
|
||||
async def respond(method, url, **options):
|
||||
"""记录 TheAudioDB 探测请求并返回成功响应。"""
|
||||
captured.update(method=method, url=url, **options)
|
||||
return response
|
||||
|
||||
transport = SimpleNamespace(request=AsyncMock(side_effect=respond))
|
||||
service = _network_test_service(
|
||||
transport,
|
||||
THEAUDIODB_API_KEY=configured_key,
|
||||
)
|
||||
|
||||
public_target = next(
|
||||
target for target in service.list_targets() if target.id == "theaudiodb_api"
|
||||
)
|
||||
result = asyncio.run(service.execute(target_id="theaudiodb_api"))
|
||||
|
||||
assert result.success
|
||||
assert public_target.address == "https://www.theaudiodb.com"
|
||||
assert configured_key not in public_target.address
|
||||
assert captured["method"] == "GET"
|
||||
assert captured["url"] == (
|
||||
"https://www.theaudiodb.com/api/v1/json/"
|
||||
"custom-audio-key/search.php?s=coldplay"
|
||||
)
|
||||
Reference in New Issue
Block a user