module.go 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278
  1. package plugin
  2. import (
  3. "fmt"
  4. "html/template"
  5. "os"
  6. "path/filepath"
  7. "github.com/langgenius/dify-plugin-daemon/internal/core/plugin_packager/decoder"
  8. "github.com/langgenius/dify-plugin-daemon/internal/types/entities/constants"
  9. "github.com/langgenius/dify-plugin-daemon/internal/utils/log"
  10. )
  11. const TOOL_MODULE_TEMPLATE = `
  12. ========== {{.Identity.Name}} ==========
  13. Author: {{.Identity.Author}}
  14. Label: {{.Identity.Label.EnUS}}
  15. Description: {{.Description.Human.EnUS}}
  16. Parameters:
  17. {{- range .Parameters}}
  18. - Name: {{.Name}}
  19. Type: {{.Type}}
  20. Required: {{.Required}}
  21. Description: {{.HumanDescription.EnUS}}
  22. {{- if .Default}}
  23. Default: {{.Default}}
  24. {{- end}}
  25. {{- if .Options}}
  26. Options:
  27. {{- range .Options}}
  28. - Value: {{.Value}}
  29. Label: {{.Label.EnUS}}
  30. {{- end}}
  31. {{- end}}
  32. {{- end}}
  33. `
  34. const MODEL_MODULE_TEMPLATE = `
  35. ========== {{.Model}} ==========
  36. Name: {{.Model}}
  37. Type: {{.ModelType}}
  38. Label: {{.Label.EnUS}}
  39. Parameters:
  40. {{- range .ParameterRules}}
  41. - Name: {{.Name}}
  42. Type: {{.Type}}
  43. Required: {{.Required}}
  44. Description: {{.Help.EnUS}}
  45. {{- if .Default}}
  46. Default: {{.Default}}
  47. {{- end}}
  48. {{- if .Min}}
  49. Min: {{.Min}}
  50. {{- end}}
  51. {{- if .Max}}
  52. Max: {{.Max}}
  53. {{- end}}
  54. {{- if .Options}}
  55. Options: {{range .Options}}{{.}}, {{end}}
  56. {{- end}}
  57. {{- end}}
  58. `
  59. const ENDPOINT_MODULE_TEMPLATE = `
  60. ========== Endpoints ==========
  61. Path: {{.Path}}
  62. Method: {{.Method}}
  63. `
  64. const PLUGIN_MODULE_TEMPLATE = `
  65. ========== Plugin ==========
  66. Name: {{.Name}}
  67. Version: {{.Version}}
  68. Description: {{.Description.EnUS}}
  69. Author: {{.Author}}
  70. Icon: {{.Icon}}
  71. Tags: {{range .Tags}}{{.}}, {{end}}
  72. Category: {{.Category}}
  73. Resource:
  74. Memory: {{.Resource.Memory}} bytes
  75. Permissions:
  76. {{- if .Resource.Permission.Tool}}
  77. Tool: {{.Resource.Permission.Tool.Enabled}}
  78. {{- end}}
  79. {{- if .Resource.Permission.Model}}
  80. Model:
  81. Enabled: {{.Resource.Permission.Model.Enabled}}
  82. LLM: {{.Resource.Permission.Model.LLM}}
  83. TextEmbedding: {{.Resource.Permission.Model.TextEmbedding}}
  84. Rerank: {{.Resource.Permission.Model.Rerank}}
  85. TTS: {{.Resource.Permission.Model.TTS}}
  86. Speech2text: {{.Resource.Permission.Model.Speech2text}}
  87. Moderation: {{.Resource.Permission.Model.Moderation}}
  88. {{- end}}
  89. {{- if .Resource.Permission.Node}}
  90. Node: {{.Resource.Permission.Node.Enabled}}
  91. {{- end}}
  92. {{- if .Resource.Permission.Endpoint}}
  93. Endpoint: {{.Resource.Permission.Endpoint.Enabled}}
  94. {{- end}}
  95. {{- if .Resource.Permission.App}}
  96. App: {{.Resource.Permission.App.Enabled}}
  97. {{- end}}
  98. {{- if .Resource.Permission.Storage}}
  99. Storage:
  100. Enabled: {{.Resource.Permission.Storage.Enabled}}
  101. Size: {{.Resource.Permission.Storage.Size}} bytes
  102. {{- end}}
  103. `
  104. func ModuleList(pluginPath string) {
  105. decoder, err := decoder.NewFSPluginDecoder(pluginPath)
  106. if err != nil {
  107. log.Error("your plugin is not a valid plugin: %s", err)
  108. return
  109. }
  110. manifest, err := decoder.Manifest()
  111. if err != nil {
  112. log.Error("failed to get manifest: %s", err)
  113. return
  114. }
  115. if manifest.Tool != nil {
  116. for _, tool := range manifest.Tool.Tools {
  117. tmpl, err := template.New("tool").Parse(TOOL_MODULE_TEMPLATE)
  118. if err != nil {
  119. log.Error("failed to parse template: %s", err)
  120. return
  121. }
  122. err = tmpl.Execute(os.Stdout, tool)
  123. if err != nil {
  124. log.Error("failed to execute template: %s", err)
  125. return
  126. }
  127. }
  128. }
  129. if manifest.Model != nil {
  130. for _, model := range manifest.Model.Models {
  131. tmpl, err := template.New("model").Parse(MODEL_MODULE_TEMPLATE)
  132. if err != nil {
  133. log.Error("failed to parse template: %s", err)
  134. return
  135. }
  136. err = tmpl.Execute(os.Stdout, model)
  137. if err != nil {
  138. log.Error("failed to execute template: %s", err)
  139. return
  140. }
  141. }
  142. }
  143. if manifest.Endpoint != nil {
  144. for _, endpoint := range manifest.Endpoint.Endpoints {
  145. tmpl, err := template.New("endpoint").Parse(ENDPOINT_MODULE_TEMPLATE)
  146. if err != nil {
  147. log.Error("failed to parse template: %s", err)
  148. return
  149. }
  150. err = tmpl.Execute(os.Stdout, endpoint)
  151. if err != nil {
  152. log.Error("failed to execute template: %s", err)
  153. return
  154. }
  155. }
  156. }
  157. }
  158. func ModuleAppendTools(pluginPath string) {
  159. decoder, err := decoder.NewFSPluginDecoder(pluginPath)
  160. if err != nil {
  161. log.Error("your plugin is not a valid plugin: %s", err)
  162. return
  163. }
  164. manifest, err := decoder.Manifest()
  165. if err != nil {
  166. log.Error("failed to get manifest: %s", err)
  167. return
  168. }
  169. if manifest.Tool != nil {
  170. log.Error("you have already declared tools in this plugin, " +
  171. "you can add new tool by modifying the `provider.yaml` file to add new tools, " +
  172. "this command is used to create new module that never been declared in this plugin.")
  173. return
  174. }
  175. if manifest.Model != nil {
  176. log.Error("model plugin dose not support declare tools.")
  177. return
  178. }
  179. if manifest.Plugins.Tools == nil {
  180. manifest.Plugins.Tools = []string{}
  181. }
  182. manifest.Plugins.Tools = append(manifest.Plugins.Tools, fmt.Sprintf("provider/%s.yaml", manifest.Name))
  183. if manifest.Meta.Runner.Language == constants.Python {
  184. if err := createPythonTool(pluginPath, &manifest); err != nil {
  185. log.Error("failed to create python tool: %s", err)
  186. return
  187. }
  188. if err := createPythonToolProvider(pluginPath, &manifest); err != nil {
  189. log.Error("failed to create python tool provider: %s", err)
  190. return
  191. }
  192. }
  193. // save manifest
  194. manifest_file := marshalYamlBytes(manifest.PluginDeclarationWithoutAdvancedFields)
  195. if err := writeFile(filepath.Join(pluginPath, "manifest.yaml"), string(manifest_file)); err != nil {
  196. log.Error("failed to save manifest: %s", err)
  197. return
  198. }
  199. log.Info("created tool module successfully")
  200. }
  201. func ModuleAppendEndpoints(pluginPath string) {
  202. decoder, err := decoder.NewFSPluginDecoder(pluginPath)
  203. if err != nil {
  204. log.Error("your plugin is not a valid plugin: %s", err)
  205. return
  206. }
  207. manifest, err := decoder.Manifest()
  208. if err != nil {
  209. log.Error("failed to get manifest: %s", err)
  210. return
  211. }
  212. if manifest.Endpoint != nil {
  213. log.Error("you have already declared endpoints in this plugin, " +
  214. "you can add new endpoint by modifying the `provider.yaml` file to add new endpoints, " +
  215. "this command is used to create new module that never been declared in this plugin.")
  216. return
  217. }
  218. if manifest.Model != nil {
  219. log.Error("model plugin dose not support declare endpoints.")
  220. return
  221. }
  222. if manifest.Plugins.Endpoints == nil {
  223. manifest.Plugins.Endpoints = []string{}
  224. }
  225. manifest.Plugins.Endpoints = append(manifest.Plugins.Endpoints, fmt.Sprintf("group/%s.yaml", manifest.Name))
  226. if manifest.Meta.Runner.Language == constants.Python {
  227. if err := createPythonEndpoint(pluginPath, &manifest); err != nil {
  228. log.Error("failed to create python endpoint: %s", err)
  229. return
  230. }
  231. if err := createPythonEndpointGroup(pluginPath, &manifest); err != nil {
  232. log.Error("failed to create python group: %s", err)
  233. return
  234. }
  235. }
  236. // save manifest
  237. manifest_file := marshalYamlBytes(manifest.PluginDeclarationWithoutAdvancedFields)
  238. if err := writeFile(filepath.Join(pluginPath, "manifest.yaml"), string(manifest_file)); err != nil {
  239. log.Error("failed to save manifest: %s", err)
  240. return
  241. }
  242. log.Info("created endpoint module successfully")
  243. }