mirror of
https://github.com/langbot-app/LangBot.git
synced 2026-08-12 13:50:59 +00:00
Merge pull request #1203 from IGCrystal/master
fix: Fix SSL certificate verification error during GitHub plugin installation
This commit is contained in:
@@ -33,6 +33,7 @@ required_deps = {
|
|||||||
"dingtalk_stream": "dingtalk_stream",
|
"dingtalk_stream": "dingtalk_stream",
|
||||||
"dashscope": "dashscope",
|
"dashscope": "dashscope",
|
||||||
"telegram": "python-telegram-bot",
|
"telegram": "python-telegram-bot",
|
||||||
|
"certifi": "certifi",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ import re
|
|||||||
import os
|
import os
|
||||||
import shutil
|
import shutil
|
||||||
import zipfile
|
import zipfile
|
||||||
|
import ssl
|
||||||
|
import certifi
|
||||||
|
|
||||||
import aiohttp
|
import aiohttp
|
||||||
import aiofiles
|
import aiofiles
|
||||||
@@ -21,44 +23,39 @@ class GitHubRepoInstaller(installer.PluginInstaller):
|
|||||||
|
|
||||||
def get_github_plugin_repo_label(self, repo_url: str) -> list[str]:
|
def get_github_plugin_repo_label(self, repo_url: str) -> list[str]:
|
||||||
"""获取username, repo"""
|
"""获取username, repo"""
|
||||||
|
|
||||||
# 提取 username/repo , 正则表达式
|
|
||||||
repo = re.findall(
|
repo = re.findall(
|
||||||
r"(?:https?://github\.com/|git@github\.com:)([^/]+/[^/]+?)(?:\.git|/|$)",
|
r"(?:https?://github\.com/|git@github\.com:)([^/]+/[^/]+?)(?:\.git|/|$)",
|
||||||
repo_url,
|
repo_url,
|
||||||
)
|
)
|
||||||
|
if len(repo) > 0:
|
||||||
if len(repo) > 0: # github
|
|
||||||
return repo[0].split("/")
|
return repo[0].split("/")
|
||||||
else:
|
else:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
async def download_plugin_source_code(self, repo_url: str, target_path: str, task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder()) -> str:
|
async def download_plugin_source_code(self, repo_url: str, target_path: str, task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder()) -> str:
|
||||||
"""下载插件源码(全异步)"""
|
"""下载插件源码(全异步)"""
|
||||||
|
|
||||||
# 提取 username/repo , 正则表达式
|
|
||||||
repo = self.get_github_plugin_repo_label(repo_url)
|
repo = self.get_github_plugin_repo_label(repo_url)
|
||||||
|
|
||||||
target_path += repo[1]
|
|
||||||
|
|
||||||
if repo is None:
|
if repo is None:
|
||||||
raise errors.PluginInstallerError('仅支持GitHub仓库地址')
|
raise errors.PluginInstallerError('仅支持GitHub仓库地址')
|
||||||
|
|
||||||
|
target_path += repo[1]
|
||||||
self.ap.logger.debug("正在下载源码...")
|
self.ap.logger.debug("正在下载源码...")
|
||||||
task_context.trace("下载源码...", "download-plugin-source-code")
|
task_context.trace("下载源码...", "download-plugin-source-code")
|
||||||
|
|
||||||
zipball_url = f"https://api.github.com/repos/{'/'.join(repo)}/zipball/HEAD"
|
zipball_url = f"https://api.github.com/repos/{'/'.join(repo)}/zipball/HEAD"
|
||||||
|
|
||||||
zip_resp: bytes = None
|
zip_resp: bytes = None
|
||||||
|
|
||||||
|
# 创建自定义SSL上下文,使用certifi提供的根证书
|
||||||
|
ssl_context = ssl.create_default_context(cafile=certifi.where())
|
||||||
|
|
||||||
async with aiohttp.ClientSession(trust_env=True) as session:
|
async with aiohttp.ClientSession(trust_env=True) as session:
|
||||||
async with session.get(
|
async with session.get(
|
||||||
url=zipball_url,
|
url=zipball_url,
|
||||||
timeout=aiohttp.ClientTimeout(total=300)
|
timeout=aiohttp.ClientTimeout(total=300),
|
||||||
|
ssl=ssl_context # 使用自定义SSL上下文来验证证书
|
||||||
) as resp:
|
) as resp:
|
||||||
if resp.status != 200:
|
if resp.status != 200:
|
||||||
raise errors.PluginInstallerError(f"下载源码失败: {resp.text}")
|
raise errors.PluginInstallerError(f"下载源码失败: {await resp.text()}")
|
||||||
|
|
||||||
zip_resp = await resp.read()
|
zip_resp = await resp.read()
|
||||||
|
|
||||||
if await aiofiles_os.path.exists("temp/" + target_path):
|
if await aiofiles_os.path.exists("temp/" + target_path):
|
||||||
@@ -80,15 +77,11 @@ class GitHubRepoInstaller(installer.PluginInstaller):
|
|||||||
await aiofiles_os.remove("temp/" + target_path + "/source.zip")
|
await aiofiles_os.remove("temp/" + target_path + "/source.zip")
|
||||||
|
|
||||||
import glob
|
import glob
|
||||||
|
|
||||||
unzip_dir = glob.glob("temp/" + target_path + "/*")[0]
|
unzip_dir = glob.glob("temp/" + target_path + "/*")[0]
|
||||||
|
|
||||||
await aioshutil.copytree(unzip_dir, target_path + "/")
|
await aioshutil.copytree(unzip_dir, target_path + "/")
|
||||||
|
|
||||||
await aioshutil.rmtree(unzip_dir)
|
await aioshutil.rmtree(unzip_dir)
|
||||||
|
|
||||||
self.ap.logger.debug("源码下载完成。")
|
self.ap.logger.debug("源码下载完成。")
|
||||||
|
|
||||||
return repo[1]
|
return repo[1]
|
||||||
|
|
||||||
async def install_requirements(self, path: str):
|
async def install_requirements(self, path: str):
|
||||||
@@ -100,20 +93,14 @@ class GitHubRepoInstaller(installer.PluginInstaller):
|
|||||||
plugin_source: str,
|
plugin_source: str,
|
||||||
task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder(),
|
task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder(),
|
||||||
):
|
):
|
||||||
"""安装插件
|
"""安装插件"""
|
||||||
"""
|
|
||||||
task_context.trace("下载插件源码...", "install-plugin")
|
task_context.trace("下载插件源码...", "install-plugin")
|
||||||
|
|
||||||
repo_label = await self.download_plugin_source_code(plugin_source, "plugins/", task_context)
|
repo_label = await self.download_plugin_source_code(plugin_source, "plugins/", task_context)
|
||||||
|
|
||||||
task_context.trace("安装插件依赖...", "install-plugin")
|
task_context.trace("安装插件依赖...", "install-plugin")
|
||||||
|
|
||||||
await self.install_requirements("plugins/" + repo_label)
|
await self.install_requirements("plugins/" + repo_label)
|
||||||
|
|
||||||
task_context.trace("完成.", "install-plugin")
|
task_context.trace("完成.", "install-plugin")
|
||||||
|
|
||||||
await self.ap.plugin_mgr.setting.record_installed_plugin_source(
|
await self.ap.plugin_mgr.setting.record_installed_plugin_source(
|
||||||
"plugins/"+repo_label+'/', plugin_source
|
"plugins/" + repo_label + '/', plugin_source
|
||||||
)
|
)
|
||||||
|
|
||||||
async def uninstall_plugin(
|
async def uninstall_plugin(
|
||||||
@@ -121,10 +108,8 @@ class GitHubRepoInstaller(installer.PluginInstaller):
|
|||||||
plugin_name: str,
|
plugin_name: str,
|
||||||
task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder(),
|
task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder(),
|
||||||
):
|
):
|
||||||
"""卸载插件
|
"""卸载插件"""
|
||||||
"""
|
|
||||||
plugin_container = self.ap.plugin_mgr.get_plugin_by_name(plugin_name)
|
plugin_container = self.ap.plugin_mgr.get_plugin_by_name(plugin_name)
|
||||||
|
|
||||||
if plugin_container is None:
|
if plugin_container is None:
|
||||||
raise errors.PluginInstallerError('插件不存在或未成功加载')
|
raise errors.PluginInstallerError('插件不存在或未成功加载')
|
||||||
else:
|
else:
|
||||||
@@ -135,24 +120,18 @@ class GitHubRepoInstaller(installer.PluginInstaller):
|
|||||||
async def update_plugin(
|
async def update_plugin(
|
||||||
self,
|
self,
|
||||||
plugin_name: str,
|
plugin_name: str,
|
||||||
plugin_source: str=None,
|
plugin_source: str = None,
|
||||||
task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder(),
|
task_context: taskmgr.TaskContext = taskmgr.TaskContext.placeholder(),
|
||||||
):
|
):
|
||||||
"""更新插件
|
"""更新插件"""
|
||||||
"""
|
|
||||||
task_context.trace("更新插件...", "update-plugin")
|
task_context.trace("更新插件...", "update-plugin")
|
||||||
|
|
||||||
plugin_container = self.ap.plugin_mgr.get_plugin_by_name(plugin_name)
|
plugin_container = self.ap.plugin_mgr.get_plugin_by_name(plugin_name)
|
||||||
|
|
||||||
if plugin_container is None:
|
if plugin_container is None:
|
||||||
raise errors.PluginInstallerError('插件不存在或未成功加载')
|
raise errors.PluginInstallerError('插件不存在或未成功加载')
|
||||||
else:
|
else:
|
||||||
if plugin_container.plugin_source:
|
if plugin_container.plugin_source:
|
||||||
plugin_source = plugin_container.plugin_source
|
plugin_source = plugin_container.plugin_source
|
||||||
|
|
||||||
task_context.trace("转交安装任务.", "update-plugin")
|
task_context.trace("转交安装任务.", "update-plugin")
|
||||||
|
|
||||||
await self.install_plugin(plugin_source, task_context)
|
await self.install_plugin(plugin_source, task_context)
|
||||||
|
|
||||||
else:
|
else:
|
||||||
raise errors.PluginInstallerError('插件无源码信息,无法更新')
|
raise errors.PluginInstallerError('插件无源码信息,无法更新')
|
||||||
@@ -32,6 +32,7 @@ gewechat-client
|
|||||||
dingtalk_stream
|
dingtalk_stream
|
||||||
dashscope
|
dashscope
|
||||||
python-telegram-bot
|
python-telegram-bot
|
||||||
|
certifi
|
||||||
|
|
||||||
# indirect
|
# indirect
|
||||||
taskgroup==0.0.0a4
|
taskgroup==0.0.0a4
|
||||||
Reference in New Issue
Block a user