mirror of
https://github.com/langgenius/dify.git
synced 2026-05-04 09:28:04 +08:00
refactor: plugin installation
This commit is contained in:
@ -6,9 +6,10 @@ from pydantic import BaseModel, ConfigDict, Field
|
||||
|
||||
from core.model_runtime.entities.model_entities import AIModelEntity
|
||||
from core.model_runtime.entities.provider_entities import ProviderEntity
|
||||
from core.plugin.entities.base import BasePluginEntity
|
||||
from core.tools.entities.tool_entities import ToolProviderEntityWithPlugin
|
||||
|
||||
T = TypeVar("T", bound=(BaseModel | dict | list | bool))
|
||||
T = TypeVar("T", bound=(BaseModel | dict | list | bool | str))
|
||||
|
||||
|
||||
class PluginDaemonBasicResponse(BaseModel, Generic[T]):
|
||||
@ -106,3 +107,24 @@ class PluginDaemonInnerError(Exception):
|
||||
def __init__(self, code: int, message: str):
|
||||
self.code = code
|
||||
self.message = message
|
||||
|
||||
|
||||
class PluginInstallTaskStatus(str, Enum):
|
||||
Pending = "pending"
|
||||
Running = "running"
|
||||
Success = "success"
|
||||
Failed = "failed"
|
||||
|
||||
|
||||
class PluginInstallTaskPluginStatus(BaseModel):
|
||||
plugin_unique_identifier: str = Field(description="The plugin unique identifier of the install task.")
|
||||
plugin_id: str = Field(description="The plugin ID of the install task.")
|
||||
status: PluginInstallTaskStatus = Field(description="The status of the install task.")
|
||||
message: str = Field(description="The message of the install task.")
|
||||
|
||||
|
||||
class PluginInstallTask(BasePluginEntity):
|
||||
status: PluginInstallTaskStatus = Field(description="The status of the install task.")
|
||||
total_plugins: int = Field(description="The total number of plugins to be installed.")
|
||||
completed_plugins: int = Field(description="The number of plugins that have been installed.")
|
||||
plugins: list[PluginInstallTaskPluginStatus] = Field(description="The status of the plugins.")
|
||||
|
||||
@ -19,7 +19,7 @@ from core.plugin.entities.plugin_daemon import PluginDaemonBasicResponse, Plugin
|
||||
plugin_daemon_inner_api_baseurl = dify_config.PLUGIN_API_URL
|
||||
plugin_daemon_inner_api_key = dify_config.PLUGIN_API_KEY
|
||||
|
||||
T = TypeVar("T", bound=(BaseModel | dict | list | bool))
|
||||
T = TypeVar("T", bound=(BaseModel | dict | list | bool | str))
|
||||
|
||||
|
||||
class BasePluginManager:
|
||||
|
||||
@ -1,16 +1,16 @@
|
||||
import json
|
||||
from collections.abc import Generator, Mapping
|
||||
from typing import Any
|
||||
from collections.abc import Sequence
|
||||
|
||||
from core.plugin.entities.plugin import PluginEntity, PluginInstallationSource
|
||||
from core.plugin.entities.plugin_daemon import InstallPluginMessage
|
||||
from core.plugin.entities.plugin import PluginDeclaration, PluginEntity, PluginInstallationSource
|
||||
from core.plugin.entities.plugin_daemon import PluginInstallTask
|
||||
from core.plugin.manager.base import BasePluginManager
|
||||
|
||||
|
||||
class PluginInstallationManager(BasePluginManager):
|
||||
def fetch_plugin_by_identifier(self, tenant_id: str, identifier: str) -> bool:
|
||||
# urlencode the identifier
|
||||
|
||||
def fetch_plugin_by_identifier(
|
||||
self,
|
||||
tenant_id: str,
|
||||
identifier: str,
|
||||
) -> bool:
|
||||
return self._request_with_plugin_daemon_response(
|
||||
"GET",
|
||||
f"plugin/{tenant_id}/management/fetch/identifier",
|
||||
@ -26,37 +26,34 @@ class PluginInstallationManager(BasePluginManager):
|
||||
params={"page": 1, "page_size": 256},
|
||||
)
|
||||
|
||||
def install_from_pkg(
|
||||
def upload_pkg(
|
||||
self,
|
||||
tenant_id: str,
|
||||
pkg: bytes,
|
||||
source: PluginInstallationSource,
|
||||
meta: Mapping[str, Any],
|
||||
verify_signature: bool = False,
|
||||
) -> Generator[InstallPluginMessage, None, None]:
|
||||
) -> str:
|
||||
"""
|
||||
Install a plugin from a package.
|
||||
Upload a plugin package and return the plugin unique identifier.
|
||||
"""
|
||||
# using multipart/form-data to encode body
|
||||
body = {
|
||||
"dify_pkg": ("dify_pkg", pkg, "application/octet-stream"),
|
||||
}
|
||||
|
||||
data = {
|
||||
"verify_signature": "true" if verify_signature else "false",
|
||||
"source": source.value,
|
||||
"meta": json.dumps(meta),
|
||||
}
|
||||
|
||||
return self._request_with_plugin_daemon_response_stream(
|
||||
return self._request_with_plugin_daemon_response(
|
||||
"POST",
|
||||
f"plugin/{tenant_id}/management/install/pkg",
|
||||
InstallPluginMessage,
|
||||
f"plugin/{tenant_id}/management/install/upload",
|
||||
str,
|
||||
files=body,
|
||||
data=data,
|
||||
)
|
||||
|
||||
def install_from_identifier(self, tenant_id: str, identifier: str) -> bool:
|
||||
def install_from_identifiers(
|
||||
self, tenant_id: str, identifiers: Sequence[str], source: PluginInstallationSource, meta: dict
|
||||
) -> str:
|
||||
"""
|
||||
Install a plugin from an identifier.
|
||||
"""
|
||||
@ -64,13 +61,45 @@ class PluginInstallationManager(BasePluginManager):
|
||||
return self._request_with_plugin_daemon_response(
|
||||
"POST",
|
||||
f"plugin/{tenant_id}/management/install/identifier",
|
||||
bool,
|
||||
str,
|
||||
data={
|
||||
"plugin_unique_identifier": identifier,
|
||||
"plugin_unique_identifiers": identifiers,
|
||||
"source": source,
|
||||
"meta": meta,
|
||||
},
|
||||
headers={"Content-Type": "application/json"},
|
||||
)
|
||||
|
||||
def fetch_plugin_installation_tasks(self, tenant_id: str) -> Sequence[PluginInstallTask]:
|
||||
"""
|
||||
Fetch plugin installation tasks.
|
||||
"""
|
||||
return self._request_with_plugin_daemon_response(
|
||||
"GET",
|
||||
f"plugin/{tenant_id}/management/install/tasks",
|
||||
list[PluginInstallTask],
|
||||
)
|
||||
|
||||
def fetch_plugin_installation_task(self, tenant_id: str, task_id: str) -> PluginInstallTask:
|
||||
"""
|
||||
Fetch a plugin installation task.
|
||||
"""
|
||||
return self._request_with_plugin_daemon_response(
|
||||
"GET",
|
||||
f"plugin/{tenant_id}/management/install/tasks/{task_id}",
|
||||
PluginInstallTask,
|
||||
)
|
||||
|
||||
def fetch_plugin_manifest(self, tenant_id: str, plugin_unique_identifier: str) -> PluginDeclaration:
|
||||
"""
|
||||
Fetch a plugin manifest.
|
||||
"""
|
||||
return self._request_with_plugin_daemon_response(
|
||||
"GET",
|
||||
f"plugin/{tenant_id}/management/fetch/identifier",
|
||||
PluginDeclaration,
|
||||
)
|
||||
|
||||
def uninstall(self, tenant_id: str, plugin_installation_id: str) -> bool:
|
||||
"""
|
||||
Uninstall a plugin.
|
||||
|
||||
Reference in New Issue
Block a user