diff --git a/CHANGELOG.md b/CHANGELOG.md
index cc99efcb..10ccc3f8 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -10,6 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/lang/zh-CN/
### Fixed
- 修复在评论议题后立即关闭拉取请求,拉取请求会被再次创建的问题
+- 修复插件元数据缺失时不报错的问题
## [4.2.3] - 2024-12-30
diff --git a/src/providers/validation/models.py b/src/providers/validation/models.py
index 98d9b275..d29d9ca8 100644
--- a/src/providers/validation/models.py
+++ b/src/providers/validation/models.py
@@ -317,7 +317,7 @@ def plugin_test_metadata_validator(
if context is None:
raise PydanticCustomError("validation_context", "未获取到验证上下文")
- if v is None:
+ if not v:
raise PydanticCustomError(
"plugin.metadata",
"插件无法获取到元数据",
@@ -383,7 +383,7 @@ class ValidationDict(BaseModel):
@property
def valid(self) -> bool:
- return not self.errors
+ return self.info is not None
@property
def name(self) -> str:
diff --git a/tests/plugins/github/publish/process/test_publish_check.py b/tests/plugins/github/publish/process/test_publish_check.py
index 1c3b5e48..e0b9e5ce 100644
--- a/tests/plugins/github/publish/process/test_publish_check.py
+++ b/tests/plugins/github/publish/process/test_publish_check.py
@@ -352,524 +352,6 @@ async def test_adapter_process_publish_check(
assert mocked_api["homepage"].called
-async def test_plugin_process_publish_check(
- app: App,
- mocker: MockerFixture,
- mocked_api: MockRouter,
- tmp_path: Path,
- mock_installation,
-) -> None:
- """测试插件的发布流程"""
- from src.plugins.github import plugin_config
- from src.providers.docker_test import Metadata
-
- mock_subprocess_run = mock_subprocess_run_with_side_effect(mocker)
-
- mock_issue = MockIssue(body=MockBody(type="plugin").generate()).as_mock(mocker)
-
- mock_event = mocker.MagicMock()
- mock_event.issue = mock_issue
-
- mock_issues_resp = mocker.MagicMock()
- mock_issues_resp.parsed_data = mock_issue
-
- mock_comment = mocker.MagicMock()
- mock_comment.body = "Plugin: name"
- mock_list_comments_resp = mocker.MagicMock()
- mock_list_comments_resp.parsed_data = [mock_comment]
-
- mock_pull = mocker.MagicMock()
- mock_pull.number = 2
- mock_pulls_resp = mocker.MagicMock()
- mock_pulls_resp.parsed_data = mock_pull
-
- mock_test_result = mocker.MagicMock()
- mock_test_result.metadata = Metadata(
- name="name",
- desc="desc",
- homepage="https://nonebot.dev",
- type="application",
- supported_adapters=None,
- )
- mock_test_result.load = True
- mock_test_result.version = "1.0.0"
- mock_test_result.output = ""
- mock_docker = mocker.patch("src.providers.docker_test.DockerPluginTest.run")
- mock_docker.return_value = mock_test_result
-
- with open(tmp_path / "plugins.json5", "w") as f:
- json.dump([], f)
-
- check_json_data(plugin_config.input_config.plugin_path, [])
-
- async with app.test_matcher() as ctx:
- adapter, bot = get_github_bot(ctx)
- event = get_mock_event(IssuesOpened)
- event.payload.issue.labels = get_issue_labels(["Plugin", "Publish"])
-
- ctx.should_call_api(
- "rest.apps.async_get_repo_installation",
- {"owner": "he0119", "repo": "action-test"},
- mock_installation,
- )
- ctx.should_call_api(
- "rest.issues.async_get",
- {"owner": "he0119", "repo": "action-test", "issue_number": 80},
- mock_issues_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "body": """\
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [x] 🔥插件测试中,请稍后\
-""",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_list_comments",
- {"owner": "he0119", "repo": "action-test", "issue_number": 80},
- mock_list_comments_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "body": """\
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
-""",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_list_comments",
- {"owner": "he0119", "repo": "action-test", "issue_number": 80},
- mock_list_comments_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_create_comment",
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "body": snapshot(
- """\
-# 📃 商店发布检查结果
-
-> Plugin: name
-
-**✅ 所有测试通过,一切准备就绪!**
-
-
-
-详情
-✅ 项目 主页 返回状态码 200。✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件类型: application。✅ 插件支持的适配器: 所有。✅ 插件 加载测试 通过。✅ 版本号: 1.0.0。✅ 发布时间:2023-09-01 08:00:00 CST。
-
-
----
-
-💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
-💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
-
-♻️ 评论已更新至最新检查结果
-
-💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
-
-"""
- ),
- },
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "title": "Plugin: name",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.pulls.async_create",
- {
- "owner": "he0119",
- "repo": "action-test",
- "title": snapshot("Plugin: name"),
- "body": "resolve #80",
- "base": "master",
- "head": "publish/issue80",
- },
- mock_pulls_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_add_labels",
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 2,
- "labels": ["Publish", "Plugin"],
- },
- True,
- )
-
- ctx.receive_event(bot, event)
-
- # 测试 git 命令
- assert_subprocess_run_calls(
- mock_subprocess_run,
- [
- ["git", "config", "--global", "safe.directory", "*"],
- ["git", "switch", "-C", "publish/issue80"],
- ["git", "ls-remote", "--heads", "origin", "publish/issue80"],
- ["git", "config", "--global", "user.name", "test"],
- [
- "git",
- "config",
- "--global",
- "user.email",
- "test@users.noreply.github.com",
- ],
- ["git", "add", "-A"],
- ["git", "commit", "-m", ":beers: publish plugin name (#80)"],
- ["git", "fetch", "origin"],
- ["git", "diff", "origin/publish/issue80", "publish/issue80"],
- ["git", "push", "origin", "publish/issue80", "-f"],
- ],
- )
-
- # 检查文件是否正确
- check_json_data(
- plugin_config.input_config.plugin_path,
- [
- snapshot(
- {
- "module_name": "module_name",
- "project_link": "project_link",
- "author_id": 1,
- "tags": [{"label": "test", "color": "#ffffff"}],
- "is_official": False,
- }
- )
- ],
- )
-
- assert mocked_api["homepage"].called
- mock_docker.assert_called_once_with("3.12")
-
-
-async def test_plugin_process_publish_check_re_run(
- app: App,
- mocker: MockerFixture,
- mocked_api: MockRouter,
- tmp_path: Path,
- mock_installation,
-) -> None:
- """测试插件的发布流程,重新运行插件测试"""
- from src.plugins.github import plugin_config
- from src.providers.docker_test import Metadata
-
- mock_subprocess_run = mock_subprocess_run_with_side_effect(mocker)
-
- # 这次运行时,议题内容已经包含了插件测试按钮
- mock_issue = MockIssue(
- body=MockBody(type="plugin", test_button=True).generate()
- ).as_mock(mocker)
-
- mock_event = mocker.MagicMock()
- mock_event.issue = mock_issue
-
- mock_issues_resp = mocker.MagicMock()
- mock_issues_resp.parsed_data = mock_issue
-
- mock_comment = mocker.MagicMock()
- mock_comment.body = "Plugin: name"
- mock_list_comments_resp = mocker.MagicMock()
- mock_list_comments_resp.parsed_data = [mock_comment]
-
- mock_pull = mocker.MagicMock()
- mock_pull.number = 2
- mock_pulls_resp = mocker.MagicMock()
- mock_pulls_resp.parsed_data = mock_pull
-
- mock_test_result = mocker.MagicMock()
- mock_test_result.metadata = Metadata(
- name="name",
- desc="desc",
- homepage="https://nonebot.dev",
- type="application",
- supported_adapters=None,
- )
- mock_test_result.load = True
- mock_test_result.version = "1.0.0"
- mock_test_result.output = ""
- mock_docker = mocker.patch("src.providers.docker_test.DockerPluginTest.run")
- mock_docker.return_value = mock_test_result
-
- with open(tmp_path / "plugins.json5", "w") as f:
- json.dump([], f)
-
- check_json_data(plugin_config.input_config.plugin_path, [])
-
- async with app.test_matcher() as ctx:
- adapter, bot = get_github_bot(ctx)
- event = get_mock_event(IssuesOpened)
- event.payload.issue.labels = get_issue_labels(["Plugin", "Publish"])
-
- ctx.should_call_api(
- "rest.apps.async_get_repo_installation",
- {"owner": "he0119", "repo": "action-test"},
- mock_installation,
- )
- ctx.should_call_api(
- "rest.issues.async_get",
- {"owner": "he0119", "repo": "action-test", "issue_number": 80},
- mock_issues_resp,
- )
- # 测试前,将插件测试状态修改为插件测试中,提示用户
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "body": """\
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [x] 🔥插件测试中,请稍后\
-""",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_list_comments",
- {"owner": "he0119", "repo": "action-test", "issue_number": 80},
- mock_list_comments_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "body": """\
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
-""",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_list_comments",
- {"owner": "he0119", "repo": "action-test", "issue_number": 80},
- mock_list_comments_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_create_comment",
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "body": snapshot(
- """\
-# 📃 商店发布检查结果
-
-> Plugin: name
-
-**✅ 所有测试通过,一切准备就绪!**
-
-
-
-详情
-✅ 项目 主页 返回状态码 200。✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件类型: application。✅ 插件支持的适配器: 所有。✅ 插件 加载测试 通过。✅ 版本号: 1.0.0。✅ 发布时间:2023-09-01 08:00:00 CST。
-
-
----
-
-💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
-💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
-
-♻️ 评论已更新至最新检查结果
-
-💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
-
-"""
- ),
- },
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 80,
- "title": "Plugin: name",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.pulls.async_create",
- {
- "owner": "he0119",
- "repo": "action-test",
- "title": snapshot("Plugin: name"),
- "body": "resolve #80",
- "base": "master",
- "head": "publish/issue80",
- },
- mock_pulls_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_add_labels",
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 2,
- "labels": ["Publish", "Plugin"],
- },
- True,
- )
-
- ctx.receive_event(bot, event)
-
- # 测试 git 命令
- assert_subprocess_run_calls(
- mock_subprocess_run,
- [
- ["git", "config", "--global", "safe.directory", "*"],
- ["git", "switch", "-C", "publish/issue80"],
- ["git", "ls-remote", "--heads", "origin", "publish/issue80"],
- ["git", "config", "--global", "user.name", "test"],
- [
- "git",
- "config",
- "--global",
- "user.email",
- "test@users.noreply.github.com",
- ],
- ["git", "add", "-A"],
- ["git", "commit", "-m", ":beers: publish plugin name (#80)"],
- ["git", "fetch", "origin"],
- ["git", "diff", "origin/publish/issue80", "publish/issue80"],
- ["git", "push", "origin", "publish/issue80", "-f"],
- ],
- )
-
- # 检查文件是否正确
- check_json_data(
- plugin_config.input_config.plugin_path,
- [
- snapshot(
- {
- "module_name": "module_name",
- "project_link": "project_link",
- "author_id": 1,
- "tags": [{"label": "test", "color": "#ffffff"}],
- "is_official": False,
- }
- )
- ],
- )
-
- assert mocked_api["homepage"].called
- mock_docker.assert_called_once_with("3.12")
-
-
async def test_edit_title(
app: App,
mocker: MockerFixture,
@@ -1414,266 +896,6 @@ async def test_comment_by_self(
mock_subprocess_run.assert_not_called()
-async def test_skip_plugin_check(
- app: App,
- mocker: MockerFixture,
- mocked_api: MockRouter,
- tmp_path: Path,
- mock_installation,
-) -> None:
- """测试手动跳过插件测试的流程"""
- from src.plugins.github import plugin_config
-
- mock_subprocess_run = mocker.patch(
- "subprocess.run", side_effect=lambda *args, **kwargs: mocker.MagicMock()
- )
-
- mock_issue = MockIssue(number=70, body=MockBody("plugin").generate()).as_mock(
- mocker
- )
-
- mock_event = mocker.MagicMock()
- mock_event.issue = mock_issue
-
- mock_issues_resp = mocker.MagicMock()
- mock_issues_resp.parsed_data = mock_issue
-
- mock_comment = mocker.MagicMock()
- mock_comment.body = "/skip"
- mock_comment.author_association = "OWNER"
- mock_list_comments_resp = mocker.MagicMock()
- mock_list_comments_resp.parsed_data = [mock_comment]
-
- mock_pulls_resp = mocker.MagicMock()
- mock_pulls_resp.parsed_data = []
-
- with open(tmp_path / "plugins.json5", "w") as f:
- json.dump([], f)
-
- check_json_data(plugin_config.input_config.plugin_path, [])
-
- async with app.test_matcher() as ctx:
- adapter, bot = get_github_bot(ctx)
- event = get_mock_event(IssueCommentCreated, "issue-comment-skip")
-
- ctx.should_call_api(
- "rest.apps.async_get_repo_installation",
- {"owner": "he0119", "repo": "action-test"},
- mock_installation,
- )
- ctx.should_call_api(
- "rest.issues.async_get",
- {"owner": "he0119", "repo": "action-test", "issue_number": 70},
- mock_issues_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 70,
- "body": """\
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [x] 🔥插件测试中,请稍后\
-""",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_list_comments",
- {"owner": "he0119", "repo": "action-test", "issue_number": 70},
- mock_list_comments_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 70,
- "body": """\
-### 插件名称
-
-### 插件描述
-
-### 插件项目仓库/主页链接
-
-### 插件类型
-
-### 插件支持的适配器
-
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [x] 🔥插件测试中,请稍后\
-""",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 70,
- "body": snapshot(
- """\
-### 插件名称
-
-### 插件描述
-
-### 插件项目仓库/主页链接
-
-### 插件类型
-
-### 插件支持的适配器
-
-### PyPI 项目名
-
-project_link
-
-### 插件 import 包名
-
-module_name
-
-### 标签
-
-[{"label": "test", "color": "#ffffff"}]
-
-### 插件配置项
-
-```dotenv
-log_level=DEBUG
-```
-
-### 插件测试
-
-- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
-"""
- ),
- },
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_list_comments",
- {"owner": "he0119", "repo": "action-test", "issue_number": 70},
- mock_list_comments_resp,
- )
- ctx.should_call_api(
- "rest.issues.async_create_comment",
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 70,
- "body": snapshot(
- """\
-# 📃 商店发布检查结果
-
-> Plugin: project_link
-
-**⚠️ 在发布检查过程中,我们发现以下问题:**
-
-
⚠️ 名称: 无法匹配到数据。请确保填写该数据项。⚠️ 描述: 无法匹配到数据。请确保填写该数据项。⚠️ 项目仓库/主页链接: 无法匹配到数据。请确保填写该数据项。⚠️ 插件类型: 无法匹配到数据。请确保填写该数据项。⚠️ 插件支持的适配器: 无法匹配到数据。请确保填写该数据项。
-
-
-详情
-✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件 加载测试 已跳过。✅ 版本号: 0.0.1。✅ 发布时间:2023-09-01 08:00:00 CST。
-
-
----
-
-💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
-💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
-
-♻️ 评论已更新至最新检查结果
-
-💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
-
-"""
- ),
- },
- True,
- )
- ctx.should_call_api(
- "rest.issues.async_update",
- snapshot(
- {
- "owner": "he0119",
- "repo": "action-test",
- "issue_number": 70,
- "title": "Plugin: project_link",
- }
- ),
- True,
- )
- ctx.should_call_api(
- "rest.pulls.async_list",
- {
- "owner": "he0119",
- "repo": "action-test",
- "head": "he0119:publish/issue70",
- },
- mock_pulls_resp,
- )
-
- ctx.receive_event(bot, event)
-
- # 测试 git 命令
- mock_subprocess_run.assert_has_calls(
- [
- mocker.call(
- ["git", "config", "--global", "safe.directory", "*"],
- check=True,
- capture_output=True,
- ), # type: ignore
- ]
- )
-
- # 检查文件是否正确
- check_json_data(plugin_config.input_config.plugin_path, [])
-
- assert mocked_api["pypi_project_link"].called
-
-
async def test_convert_pull_request_to_draft(
app: App,
mocker: MockerFixture,
diff --git a/tests/plugins/github/publish/process/test_publish_check_plugin.py b/tests/plugins/github/publish/process/test_publish_check_plugin.py
new file mode 100644
index 00000000..a8fd11ef
--- /dev/null
+++ b/tests/plugins/github/publish/process/test_publish_check_plugin.py
@@ -0,0 +1,998 @@
+import json
+from pathlib import Path
+
+from inline_snapshot import snapshot
+from nonebot.adapters.github import IssueCommentCreated, IssuesOpened
+from nonebug import App
+from pytest_mock import MockerFixture
+from respx import MockRouter
+
+from tests.plugins.github.event import get_mock_event
+from tests.plugins.github.utils import (
+ MockBody,
+ MockIssue,
+ assert_subprocess_run_calls,
+ check_json_data,
+ generate_issue_body_plugin,
+ get_github_bot,
+ get_issue_labels,
+ mock_subprocess_run_with_side_effect,
+ should_call_apis,
+)
+
+
+async def test_plugin_process_publish_check(
+ app: App,
+ mocker: MockerFixture,
+ mocked_api: MockRouter,
+ tmp_path: Path,
+ mock_installation,
+) -> None:
+ """测试插件的发布流程"""
+ from src.plugins.github import plugin_config
+ from src.providers.docker_test import Metadata
+
+ mock_subprocess_run = mock_subprocess_run_with_side_effect(mocker)
+
+ mock_issue = MockIssue(body=MockBody(type="plugin").generate()).as_mock(mocker)
+
+ mock_event = mocker.MagicMock()
+ mock_event.issue = mock_issue
+
+ mock_issues_resp = mocker.MagicMock()
+ mock_issues_resp.parsed_data = mock_issue
+
+ mock_comment = mocker.MagicMock()
+ mock_comment.body = "Plugin: name"
+ mock_list_comments_resp = mocker.MagicMock()
+ mock_list_comments_resp.parsed_data = [mock_comment]
+
+ mock_pull = mocker.MagicMock()
+ mock_pull.number = 2
+ mock_pulls_resp = mocker.MagicMock()
+ mock_pulls_resp.parsed_data = mock_pull
+
+ mock_test_result = mocker.MagicMock()
+ mock_test_result.metadata = Metadata(
+ name="name",
+ desc="desc",
+ homepage="https://nonebot.dev",
+ type="application",
+ supported_adapters=None,
+ )
+ mock_test_result.load = True
+ mock_test_result.version = "1.0.0"
+ mock_test_result.output = ""
+ mock_docker = mocker.patch("src.providers.docker_test.DockerPluginTest.run")
+ mock_docker.return_value = mock_test_result
+
+ with open(tmp_path / "plugins.json5", "w") as f:
+ json.dump([], f)
+
+ check_json_data(plugin_config.input_config.plugin_path, [])
+
+ async with app.test_matcher() as ctx:
+ adapter, bot = get_github_bot(ctx)
+ event = get_mock_event(IssuesOpened)
+ event.payload.issue.labels = get_issue_labels(["Plugin", "Publish"])
+
+ ctx.receive_event(bot, event)
+ should_call_apis(
+ ctx,
+ [
+ {
+ "api": "rest.apps.async_get_repo_installation",
+ "result": mock_installation,
+ },
+ {
+ "api": "rest.issues.async_get",
+ "result": mock_issues_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_create_comment",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.pulls.async_create",
+ "result": mock_pulls_resp,
+ },
+ {
+ "api": "rest.issues.async_add_labels",
+ "result": None,
+ },
+ ],
+ snapshot(
+ {
+ 0: {"owner": "he0119", "repo": "action-test"},
+ 1: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 2: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [x] 🔥插件测试中,请稍后\
+""",
+ },
+ 3: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 4: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
+""",
+ },
+ 5: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 6: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+# 📃 商店发布检查结果
+
+> Plugin: name
+
+**✅ 所有测试通过,一切准备就绪!**
+
+
+
+详情
+✅ 项目 主页 返回状态码 200。✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件类型: application。✅ 插件支持的适配器: 所有。✅ 插件 加载测试 通过。✅ 版本号: 1.0.0。✅ 发布时间:2023-09-01 08:00:00 CST。
+
+
+---
+
+💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
+💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
+
+♻️ 评论已更新至最新检查结果
+
+💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
+
+""",
+ },
+ 7: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "title": "Plugin: name",
+ },
+ 8: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "title": "Plugin: name",
+ "body": "resolve #80",
+ "base": "master",
+ "head": "publish/issue80",
+ },
+ 9: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 2,
+ "labels": ["Publish", "Plugin"],
+ },
+ }
+ ),
+ )
+
+ # 测试 git 命令
+ assert_subprocess_run_calls(
+ mock_subprocess_run,
+ [
+ ["git", "config", "--global", "safe.directory", "*"],
+ ["git", "switch", "-C", "publish/issue80"],
+ ["git", "ls-remote", "--heads", "origin", "publish/issue80"],
+ ["git", "config", "--global", "user.name", "test"],
+ [
+ "git",
+ "config",
+ "--global",
+ "user.email",
+ "test@users.noreply.github.com",
+ ],
+ ["git", "add", "-A"],
+ ["git", "commit", "-m", ":beers: publish plugin name (#80)"],
+ ["git", "fetch", "origin"],
+ ["git", "diff", "origin/publish/issue80", "publish/issue80"],
+ ["git", "push", "origin", "publish/issue80", "-f"],
+ ],
+ )
+
+ # 检查文件是否正确
+ check_json_data(
+ plugin_config.input_config.plugin_path,
+ [
+ snapshot(
+ {
+ "module_name": "module_name",
+ "project_link": "project_link",
+ "author_id": 1,
+ "tags": [{"label": "test", "color": "#ffffff"}],
+ "is_official": False,
+ }
+ )
+ ],
+ )
+
+ assert mocked_api["homepage"].called
+ mock_docker.assert_called_once_with("3.12")
+
+
+async def test_plugin_process_publish_check_re_run(
+ app: App,
+ mocker: MockerFixture,
+ mocked_api: MockRouter,
+ tmp_path: Path,
+ mock_installation,
+) -> None:
+ """测试插件的发布流程,重新运行插件测试"""
+ from src.plugins.github import plugin_config
+ from src.providers.docker_test import Metadata
+
+ mock_subprocess_run = mock_subprocess_run_with_side_effect(mocker)
+
+ # 这次运行时,议题内容已经包含了插件测试按钮
+ mock_issue = MockIssue(
+ body=MockBody(type="plugin", test_button=True).generate()
+ ).as_mock()
+
+ mock_event = mocker.MagicMock()
+ mock_event.issue = mock_issue
+
+ mock_issues_resp = mocker.MagicMock()
+ mock_issues_resp.parsed_data = mock_issue
+
+ mock_comment = mocker.MagicMock()
+ mock_comment.body = "Plugin: name"
+ mock_list_comments_resp = mocker.MagicMock()
+ mock_list_comments_resp.parsed_data = [mock_comment]
+
+ mock_pull = mocker.MagicMock()
+ mock_pull.number = 2
+ mock_pulls_resp = mocker.MagicMock()
+ mock_pulls_resp.parsed_data = mock_pull
+
+ mock_test_result = mocker.MagicMock()
+ mock_test_result.metadata = Metadata(
+ name="name",
+ desc="desc",
+ homepage="https://nonebot.dev",
+ type="application",
+ supported_adapters=None,
+ )
+ mock_test_result.load = True
+ mock_test_result.version = "1.0.0"
+ mock_test_result.output = ""
+ mock_docker = mocker.patch("src.providers.docker_test.DockerPluginTest.run")
+ mock_docker.return_value = mock_test_result
+
+ with open(tmp_path / "plugins.json5", "w") as f:
+ json.dump([], f)
+
+ check_json_data(plugin_config.input_config.plugin_path, [])
+
+ async with app.test_matcher() as ctx:
+ adapter, bot = get_github_bot(ctx)
+ event = get_mock_event(IssuesOpened)
+ event.payload.issue.labels = get_issue_labels(["Plugin", "Publish"])
+
+ ctx.receive_event(bot, event)
+ should_call_apis(
+ ctx,
+ [
+ {
+ "api": "rest.apps.async_get_repo_installation",
+ "result": mock_installation,
+ },
+ {
+ "api": "rest.issues.async_get",
+ "result": mock_issues_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_create_comment",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.pulls.async_create",
+ "result": mock_pulls_resp,
+ },
+ {
+ "api": "rest.issues.async_add_labels",
+ "result": None,
+ },
+ ],
+ snapshot(
+ {
+ 0: {"owner": "he0119", "repo": "action-test"},
+ 1: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 2: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [x] 🔥插件测试中,请稍后\
+""",
+ },
+ 3: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 4: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
+""",
+ },
+ 5: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 6: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+# 📃 商店发布检查结果
+
+> Plugin: name
+
+**✅ 所有测试通过,一切准备就绪!**
+
+
+
+详情
+✅ 项目 主页 返回状态码 200。✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件类型: application。✅ 插件支持的适配器: 所有。✅ 插件 加载测试 通过。✅ 版本号: 1.0.0。✅ 发布时间:2023-09-01 08:00:00 CST。
+
+
+---
+
+💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
+💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
+
+♻️ 评论已更新至最新检查结果
+
+💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
+
+""",
+ },
+ 7: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "title": "Plugin: name",
+ },
+ 8: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "title": "Plugin: name",
+ "body": "resolve #80",
+ "base": "master",
+ "head": "publish/issue80",
+ },
+ 9: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 2,
+ "labels": ["Publish", "Plugin"],
+ },
+ }
+ ),
+ )
+
+ # 测试 git 命令
+ assert_subprocess_run_calls(
+ mock_subprocess_run,
+ [
+ ["git", "config", "--global", "safe.directory", "*"],
+ ["git", "switch", "-C", "publish/issue80"],
+ ["git", "ls-remote", "--heads", "origin", "publish/issue80"],
+ ["git", "config", "--global", "user.name", "test"],
+ [
+ "git",
+ "config",
+ "--global",
+ "user.email",
+ "test@users.noreply.github.com",
+ ],
+ ["git", "add", "-A"],
+ ["git", "commit", "-m", ":beers: publish plugin name (#80)"],
+ ["git", "fetch", "origin"],
+ ["git", "diff", "origin/publish/issue80", "publish/issue80"],
+ ["git", "push", "origin", "publish/issue80", "-f"],
+ ],
+ )
+
+ # 检查文件是否正确
+ check_json_data(
+ plugin_config.input_config.plugin_path,
+ [
+ snapshot(
+ {
+ "module_name": "module_name",
+ "project_link": "project_link",
+ "author_id": 1,
+ "tags": [{"label": "test", "color": "#ffffff"}],
+ "is_official": False,
+ }
+ )
+ ],
+ )
+
+ assert mocked_api["homepage"].called
+ mock_docker.assert_called_once_with("3.12")
+
+
+async def test_plugin_process_publish_check_missing_metadata(
+ app: App,
+ mocker: MockerFixture,
+ mocked_api: MockRouter,
+ tmp_path: Path,
+ mock_installation,
+) -> None:
+ """测试发布检查不通过,测试缺少插件元数据"""
+ from src.plugins.github import plugin_config
+
+ mock_subprocess_run = mock_subprocess_run_with_side_effect(mocker)
+
+ mock_issue = MockIssue(
+ title="Plugin: test",
+ body=generate_issue_body_plugin(),
+ ).as_mock()
+
+ mock_issues_resp = mocker.MagicMock()
+ mock_issues_resp.parsed_data = mock_issue
+
+ mock_pulls_resp = mocker.MagicMock()
+ mock_pulls_resp.parsed_data = []
+
+ mock_comment = mocker.MagicMock()
+ mock_comment.body = "Plugin: test"
+ mock_list_comments_resp = mocker.MagicMock()
+ mock_list_comments_resp.parsed_data = [mock_comment]
+
+ mock_test_result = mocker.MagicMock()
+ mock_test_result.metadata = None
+ mock_test_result.load = True
+ mock_test_result.version = "1.0.0"
+ mock_test_result.output = ""
+ mock_docker = mocker.patch("src.providers.docker_test.DockerPluginTest.run")
+ mock_docker.return_value = mock_test_result
+
+ with open(tmp_path / "plugins.json5", "w") as f:
+ json.dump([], f)
+
+ check_json_data(plugin_config.input_config.plugin_path, [])
+
+ async with app.test_matcher() as ctx:
+ adapter, bot = get_github_bot(ctx)
+ event = get_mock_event(IssuesOpened)
+ event.payload.issue.labels = get_issue_labels(["Plugin", "Publish"])
+
+ ctx.receive_event(bot, event)
+ should_call_apis(
+ ctx,
+ [
+ {
+ "api": "rest.apps.async_get_repo_installation",
+ "result": mock_installation,
+ },
+ {
+ "api": "rest.issues.async_get",
+ "result": mock_issues_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_create_comment",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.pulls.async_list",
+ "result": mock_pulls_resp,
+ },
+ ],
+ snapshot(
+ {
+ 0: {"owner": "he0119", "repo": "action-test"},
+ 1: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 2: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [x] 🔥插件测试中,请稍后\
+""",
+ },
+ 3: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 4: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
+""",
+ },
+ 5: {"owner": "he0119", "repo": "action-test", "issue_number": 80},
+ 6: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "body": """\
+# 📃 商店发布检查结果
+
+> Plugin: project_link
+
+**⚠️ 在发布检查过程中,我们发现以下问题:**
+
+⚠️ 无法获取到插件元数据。请确保插件正常加载。
+
+
+详情
+✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件 加载测试 通过。✅ 版本号: 1.0.0。✅ 发布时间:2023-09-01 08:00:00 CST。
+
+
+---
+
+💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
+💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
+
+♻️ 评论已更新至最新检查结果
+
+💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
+
+""",
+ },
+ 7: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 80,
+ "title": "Plugin: project_link",
+ },
+ 8: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "head": "he0119:publish/issue80",
+ },
+ }
+ ),
+ )
+
+ # 测试 git 命令
+ assert_subprocess_run_calls(
+ mock_subprocess_run,
+ [
+ ["git", "config", "--global", "safe.directory", "*"],
+ ],
+ )
+
+ # 检查文件是否正确
+ check_json_data(plugin_config.input_config.plugin_path, [])
+
+ assert not mocked_api["homepage"].called
+
+
+async def test_skip_plugin_check(
+ app: App,
+ mocker: MockerFixture,
+ mocked_api: MockRouter,
+ tmp_path: Path,
+ mock_installation,
+) -> None:
+ """测试手动跳过插件测试的流程"""
+ from src.plugins.github import plugin_config
+
+ mock_subprocess_run = mock_subprocess_run_with_side_effect(mocker)
+
+ mock_issue = MockIssue(number=70, body=MockBody("plugin").generate()).as_mock()
+
+ mock_event = mocker.MagicMock()
+ mock_event.issue = mock_issue
+
+ mock_issues_resp = mocker.MagicMock()
+ mock_issues_resp.parsed_data = mock_issue
+
+ mock_comment = mocker.MagicMock()
+ mock_comment.body = "/skip"
+ mock_comment.author_association = "OWNER"
+ mock_list_comments_resp = mocker.MagicMock()
+ mock_list_comments_resp.parsed_data = [mock_comment]
+
+ mock_pulls_resp = mocker.MagicMock()
+ mock_pulls_resp.parsed_data = []
+
+ with open(tmp_path / "plugins.json5", "w") as f:
+ json.dump([], f)
+
+ check_json_data(plugin_config.input_config.plugin_path, [])
+
+ async with app.test_matcher() as ctx:
+ adapter, bot = get_github_bot(ctx)
+ event = get_mock_event(IssueCommentCreated, "issue-comment-skip")
+
+ ctx.receive_event(bot, event)
+ should_call_apis(
+ ctx,
+ [
+ # 获取安装信息
+ {
+ "api": "rest.apps.async_get_repo_installation",
+ "result": mock_installation,
+ },
+ # 获取议题信息
+ {
+ "api": "rest.issues.async_get",
+ "result": mock_issues_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_list_comments",
+ "result": mock_list_comments_resp,
+ },
+ {
+ "api": "rest.issues.async_create_comment",
+ "result": None,
+ },
+ {
+ "api": "rest.issues.async_update",
+ "result": None,
+ },
+ {
+ "api": "rest.pulls.async_list",
+ "result": mock_pulls_resp,
+ },
+ ],
+ snapshot(
+ {
+ 0: {"owner": "he0119", "repo": "action-test"},
+ 1: {"owner": "he0119", "repo": "action-test", "issue_number": 70},
+ 2: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 70,
+ "body": """\
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [x] 🔥插件测试中,请稍后\
+""",
+ },
+ 3: {"owner": "he0119", "repo": "action-test", "issue_number": 70},
+ 4: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 70,
+ "body": """\
+### 插件名称
+
+### 插件描述
+
+### 插件项目仓库/主页链接
+
+### 插件类型
+
+### 插件支持的适配器
+
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [x] 🔥插件测试中,请稍后\
+""",
+ },
+ 5: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 70,
+ "body": """\
+### 插件名称
+
+### 插件描述
+
+### 插件项目仓库/主页链接
+
+### 插件类型
+
+### 插件支持的适配器
+
+### PyPI 项目名
+
+project_link
+
+### 插件 import 包名
+
+module_name
+
+### 标签
+
+[{"label": "test", "color": "#ffffff"}]
+
+### 插件配置项
+
+```dotenv
+log_level=DEBUG
+```
+
+### 插件测试
+
+- [ ] 如需重新运行插件测试,请勾选左侧勾选框\
+""",
+ },
+ 6: {"owner": "he0119", "repo": "action-test", "issue_number": 70},
+ 7: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 70,
+ "body": """\
+# 📃 商店发布检查结果
+
+> Plugin: project_link
+
+**⚠️ 在发布检查过程中,我们发现以下问题:**
+
+⚠️ 名称: 无法匹配到数据。请确保填写该数据项。⚠️ 描述: 无法匹配到数据。请确保填写该数据项。⚠️ 项目仓库/主页链接: 无法匹配到数据。请确保填写该数据项。⚠️ 插件类型: 无法匹配到数据。请确保填写该数据项。⚠️ 插件支持的适配器: 无法匹配到数据。请确保填写该数据项。⚠️ 无法获取到插件元数据。请确保插件正常加载。
+
+
+详情
+✅ 项目 project_link 已发布至 PyPI。✅ 标签: test-#ffffff。✅ 插件 加载测试 已跳过。✅ 版本号: 0.0.1。✅ 发布时间:2023-09-01 08:00:00 CST。
+
+
+---
+
+💡 如需修改信息,请直接修改 issue,机器人会自动更新检查结果。
+💡 当插件加载测试失败时,请发布新版本后勾选插件测试勾选框重新运行插件测试。
+
+♻️ 评论已更新至最新检查结果
+
+💪 Powered by [NoneFlow](https://github.com/nonebot/noneflow)
+
+""",
+ },
+ 8: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "issue_number": 70,
+ "title": "Plugin: project_link",
+ },
+ 9: {
+ "owner": "he0119",
+ "repo": "action-test",
+ "head": "he0119:publish/issue70",
+ },
+ }
+ ),
+ )
+
+ # 测试 git 命令
+ assert_subprocess_run_calls(
+ mock_subprocess_run,
+ [
+ ["git", "config", "--global", "safe.directory", "*"],
+ ],
+ )
+
+ # 检查文件是否正确
+ check_json_data(plugin_config.input_config.plugin_path, [])
+
+ assert mocked_api["pypi_project_link"].called
diff --git a/tests/plugins/github/publish/render/test_publish_render.py b/tests/plugins/github/publish/render/test_publish_render.py
index ad9ded06..d2861800 100644
--- a/tests/plugins/github/publish/render/test_publish_render.py
+++ b/tests/plugins/github/publish/render/test_publish_render.py
@@ -1,15 +1,18 @@
from inline_snapshot import snapshot
from nonebug import App
+from tests.providers.validation.utils import generate_bot_data
+
async def test_render_empty(app: App):
"""测试没有数据和错误时的输出"""
from src.plugins.github.plugins.publish.render import render_comment
- from src.providers.validation import PublishType, ValidationDict
+ from src.providers.validation import BotPublishInfo, PublishType, ValidationDict
result = ValidationDict(
type=PublishType.BOT,
raw_data={"name": "name"},
+ info=BotPublishInfo.model_construct(**generate_bot_data()),
)
comment = await render_comment(result)
@@ -38,11 +41,12 @@ async def test_render_empty(app: App):
async def test_render_reuse(app: App):
"""复用评论"""
from src.plugins.github.plugins.publish.render import render_comment
- from src.providers.validation import PublishType, ValidationDict
+ from src.providers.validation import BotPublishInfo, PublishType, ValidationDict
result = ValidationDict(
type=PublishType.BOT,
raw_data={"name": "name"},
+ info=BotPublishInfo.model_construct(**generate_bot_data()),
)
comment = await render_comment(result, True)
diff --git a/tests/plugins/github/publish/render/test_publish_render_data.py b/tests/plugins/github/publish/render/test_publish_render_data.py
index 2fac3e94..56ea8688 100644
--- a/tests/plugins/github/publish/render/test_publish_render_data.py
+++ b/tests/plugins/github/publish/render/test_publish_render_data.py
@@ -2,6 +2,8 @@
from nonebug import App
from pytest_mock import MockFixture
+from tests.providers.validation.utils import generate_plugin_data
+
async def test_render_data_bot(app: App):
"""机器人验证数据"""
@@ -211,7 +213,7 @@ async def test_render_data_plugin(app: App, mocker: MockFixture):
async def test_render_data_plugin_supported_adapters(app: App, mocker: MockFixture):
"""插件支持的适配器"""
from src.plugins.github.plugins.publish.render import render_comment
- from src.providers.validation import PublishType, ValidationDict
+ from src.providers.validation import PluginPublishInfo, PublishType, ValidationDict
result = ValidationDict(
type=PublishType.PLUGIN,
@@ -228,7 +230,7 @@ async def test_render_data_plugin_supported_adapters(app: App, mocker: MockFixtu
"load": True,
"skip_test": False,
},
- info=None,
+ info=PluginPublishInfo.model_construct(**generate_plugin_data()),
errors=[],
)
diff --git a/tests/plugins/github/utils.py b/tests/plugins/github/utils.py
index 2e77dda2..f6221d4c 100644
--- a/tests/plugins/github/utils.py
+++ b/tests/plugins/github/utils.py
@@ -204,8 +204,11 @@ class MockIssue:
pull_request: Any = None
user: MockUser = field(default_factory=MockUser)
- def as_mock(self, mocker: MockFixture):
- mocker_issue = mocker.MagicMock(spec=Issue)
+ def as_mock(self, mocker: MockFixture | None = None):
+ if mocker is None:
+ mocker_issue = MagicMock(spec=Issue)
+ else:
+ mocker_issue = mocker.MagicMock(spec=Issue)
mocker_issue.configure_mock(**self.__dict__)
return mocker_issue
diff --git a/tests/providers/store_test/test_validate_plugin.py b/tests/providers/store_test/test_validate_plugin.py
index c3a27e2f..0024fa38 100644
--- a/tests/providers/store_test/test_validate_plugin.py
+++ b/tests/providers/store_test/test_validate_plugin.py
@@ -324,14 +324,45 @@ async def test_validate_plugin_skip_test_plugin_test_failed(
StoreTestResult(
config="",
outputs={
- "validation": None,
+ "validation": {
+ "data": {
+ "module_name": "nonebot_plugin_treehelp",
+ "project_link": "nonebot-plugin-treehelp",
+ "time": "2024-07-13T04:41:40.905441Z",
+ "version": "0.3.9",
+ "name": "帮助",
+ "desc": "获取插件帮助信息",
+ "author": "he0119",
+ "author_id": 1,
+ "homepage": "https://nonebot.dev/",
+ "tags": [],
+ "is_official": False,
+ "type": "application",
+ "supported_adapters": None,
+ "load": True,
+ "skip_test": True,
+ "test_output": """\
+创建测试目录 plugin_test
+ For further information visit https://errors.pydantic.dev/2.9/v/model_type\x1b[0m\
+""",
+ },
+ "errors": [
+ {
+ "type": "plugin.metadata",
+ "loc": ("metadata",),
+ "msg": "无法获取到插件元数据",
+ "input": False,
+ "ctx": {"load": None},
+ }
+ ],
+ },
"load": """\
创建测试目录 plugin_test
For further information visit https://errors.pydantic.dev/2.9/v/model_type\x1b[0m\
""",
"metadata": None,
},
- results={"validation": True, "load": False, "metadata": False},
+ results={"validation": False, "load": False, "metadata": False},
test_env={"python==3.12.7": True},
version="0.3.9",
)
@@ -350,7 +381,7 @@ async def test_validate_plugin_skip_test_plugin_test_failed(
tags=[],
time="2024-07-13T04:41:40.905441Z",
type="application",
- valid=True,
+ valid=False,
version="0.3.9",
)
)
@@ -424,7 +455,6 @@ async def test_validate_plugin_failed_with_previous(
"is_official": True,
"type": "application",
"supported_adapters": None,
- "metadata": False,
"skip_test": False,
"version": "0.3.9",
"test_output": """\
@@ -444,7 +474,14 @@ async def test_validate_plugin_failed_with_previous(
For further information visit https://errors.pydantic.dev/2.9/v/model_type\x1b[0m\
"""
},
- }
+ },
+ {
+ "type": "plugin.metadata",
+ "loc": ("metadata",),
+ "msg": "无法获取到插件元数据",
+ "input": False,
+ "ctx": {"load": None},
+ },
],
},
"load": """\
diff --git a/tests/providers/validation/fields/test_missing.py b/tests/providers/validation/fields/test_missing.py
index d3b67008..b1c9a314 100644
--- a/tests/providers/validation/fields/test_missing.py
+++ b/tests/providers/validation/fields/test_missing.py
@@ -33,7 +33,6 @@ async def test_fields_missing_plugin(mocked_api: MockRouter) -> None:
"author_id": 1,
"tags": [{"label": "test", "color": "#ffffff"}],
"supported_adapters": None,
- "metadata": False,
"skip_test": False,
"test_output": "error",
}
@@ -138,6 +137,13 @@ async def test_fields_missing_plugin(mocked_api: MockRouter) -> None:
"input": False,
"ctx": {"output": "error"},
},
+ {
+ "type": "plugin.metadata",
+ "loc": ("metadata",),
+ "msg": "无法获取到插件元数据",
+ "input": False,
+ "ctx": {"load": None},
+ },
]
)
diff --git a/tests/providers/validation/test_plugin.py b/tests/providers/validation/test_plugin.py
index 35def94a..d3949eaf 100644
--- a/tests/providers/validation/test_plugin.py
+++ b/tests/providers/validation/test_plugin.py
@@ -155,7 +155,14 @@ async def test_plugin_info_validation_plugin_load_failed(
"msg": "插件无法正常加载",
"input": False,
"ctx": {"output": "test_output"},
- }
+ },
+ {
+ "type": "plugin.metadata",
+ "loc": ("metadata",),
+ "msg": "无法获取到插件元数据",
+ "input": False,
+ "ctx": {"load": None},
+ },
],
info=None,
raw_data={
@@ -189,7 +196,6 @@ async def test_plugin_info_validation_plugin_load_failed(
"tags": [{"label": "test", "color": "#ffffff"}],
"type": "application",
"supported_adapters": None,
- "metadata": False,
"skip_test": False,
"version": "0.0.1",
"test_output": "test_output",