ToolListContainer.vue 46 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306
  1. <template>
  2. <ContentContainer>
  3. <template #header>
  4. <slot name="header"></slot>
  5. </template>
  6. <template #search>
  7. <div class="flex">
  8. <div class="flex-between complex-search">
  9. <el-select
  10. class="complex-search__left"
  11. v-model="search_type"
  12. style="width: 90px"
  13. @change="search_type_change"
  14. >
  15. <el-option :label="$t('common.creator')" value="create_user"/>
  16. <el-option :label="$t('common.name')" value="name"/>
  17. </el-select>
  18. <el-input
  19. v-if="search_type === 'name'"
  20. v-model="search_form.name"
  21. @change="searchHandle"
  22. :placeholder="$t('common.searchBar.placeholder')"
  23. style="width: 190px"
  24. clearable
  25. />
  26. <el-select
  27. v-else-if="search_type === 'create_user'"
  28. v-model="search_form.create_user"
  29. @change="searchHandle"
  30. filterable
  31. clearable
  32. style="width: 190px"
  33. >
  34. <el-option v-for="u in user_options" :key="u.id" :value="u.id" :label="u.nick_name"/>
  35. </el-select>
  36. </div>
  37. <span
  38. class="ml-8"
  39. v-if="!isShared && (permissionPrecise.batchMove() || permissionPrecise.batchDelete())"
  40. >
  41. <el-button @click="batchSelectedHandle(true)" v-if="isBatch === false">
  42. <AppIcon iconName="app-batch-delete" class="mr-4"/>
  43. {{ $t('views.paragraph.setting.batchSelected') }}
  44. </el-button>
  45. <el-button @click="batchSelectedHandle(false)" v-if="isBatch === true">
  46. <AppIcon iconName="app-batch-delete" class="mr-4"/>
  47. {{ $t('views.paragraph.setting.cancelSelected') }}
  48. </el-button>
  49. </span>
  50. <div v-if="isBatch === false">
  51. <span class="ml-8" v-show="false" v-if="!isShared && permissionPrecise.create()">
  52. <el-button @click="openToolStoreDialog()">
  53. <AppIcon iconName="app-tool-store" class="mr-4"/>
  54. {{ $t('views.tool.toolStore.title') }}
  55. </el-button>
  56. </span>
  57. <el-dropdown trigger="click">
  58. <el-button type="primary" class="ml-8" v-if="!isShared && permissionPrecise.create()">
  59. {{ $t('common.create') }}
  60. <el-icon class="el-icon--right">
  61. <arrow-down/>
  62. </el-icon>
  63. </el-button>
  64. <template #dropdown>
  65. <el-dropdown-menu class="create-dropdown">
  66. <el-dropdown-item @click="openCreateDialog()">
  67. <div class="flex align-center">
  68. <el-avatar class="avatar-green" shape="square" :size="32">
  69. <img src="@/assets/tool/icon_tool.svg" style="width: 58%" alt=""/>
  70. </el-avatar>
  71. <div class="pre-wrap ml-8">
  72. <div class="lighter">{{ $t('views.tool.title') }}</div>
  73. </div>
  74. </div>
  75. </el-dropdown-item>
  76. <el-dropdown-item @click="openCreateWorkflowDialog()">
  77. <div class="flex align-center">
  78. <el-avatar class="avatar-green mt-4" shape="square" :size="32">
  79. <img src="@/assets/workflow/logo_workflow.svg" style="width: 60%" alt=""/>
  80. </el-avatar>
  81. <div class="pre-wrap ml-8">
  82. <div class="lighter">{{ $t('workflow.workflow') }}</div>
  83. </div>
  84. </div>
  85. </el-dropdown-item>
  86. <el-dropdown-item @click="openCreateSkillDialog()">
  87. <div class="flex align-center">
  88. <el-avatar shape="square" :size="32">
  89. <img src="@/assets/tool/icon_skill.svg" style="width: 58%" alt=""/>
  90. </el-avatar>
  91. <div class="pre-wrap ml-8">
  92. <div class="lighter">Skills</div>
  93. </div>
  94. </div>
  95. </el-dropdown-item>
  96. <el-dropdown-item @click="openCreateMcpDialog()">
  97. <div class="flex align-center">
  98. <el-avatar shape="square" :size="32">
  99. <img src="@/assets/tool/icon_mcp.svg" style="width: 75%" alt=""/>
  100. </el-avatar>
  101. <div class="pre-wrap ml-8">
  102. <div class="lighter">MCP</div>
  103. </div>
  104. </div>
  105. </el-dropdown-item>
  106. <el-dropdown-item @click="openCreateDataSourceDialog()">
  107. <div class="flex align-center">
  108. <el-avatar class="avatar-purple" shape="square" :size="32">
  109. <img src="@/assets/tool/icon_datasource.svg" style="width: 58%" alt=""/>
  110. </el-avatar>
  111. <div class="pre-wrap ml-8">
  112. <div class="lighter">{{ $t('views.tool.dataSource.title') }}</div>
  113. </div>
  114. </div>
  115. </el-dropdown-item>
  116. <el-upload
  117. ref="elUploadRef"
  118. :file-list="[]"
  119. action="#"
  120. multiple
  121. :auto-upload="false"
  122. :show-file-list="false"
  123. :limit="1"
  124. :on-change="(file: any, fileList: any) => importTool(file)"
  125. class="import-button"
  126. >
  127. <el-dropdown-item v-if="permissionPrecise.import()">
  128. <div class="flex align-center w-full">
  129. <el-avatar shape="square" :size="32" style="background: none">
  130. <img src="@/assets/icon_import.svg" alt=""/>
  131. </el-avatar>
  132. <div class="pre-wrap ml-8">
  133. <div class="lighter">{{ $t('common.importCreate') }}</div>
  134. </div>
  135. </div>
  136. </el-dropdown-item>
  137. </el-upload>
  138. <el-dropdown-item @click="openCreateFolder" divided v-if="apiType === 'workspace'">
  139. <div class="flex align-center">
  140. <AppIcon iconName="app-folder" style="font-size: 32px"></AppIcon>
  141. <div class="pre-wrap ml-4">
  142. <div class="lighter">
  143. {{ $t('components.folder.addFolder') }}
  144. </div>
  145. </div>
  146. </div>
  147. </el-dropdown-item>
  148. </el-dropdown-menu>
  149. </template>
  150. </el-dropdown>
  151. </div>
  152. </div>
  153. </template>
  154. <div
  155. v-loading.fullscreen.lock="paginationConfig.current_page === 1 && loading"
  156. style="max-height: calc(100vh - 120px)"
  157. >
  158. <InfiniteScroll
  159. :size="tool.toolList.length"
  160. :total="paginationConfig.total"
  161. :page_size="paginationConfig.page_size"
  162. v-model:current_page="paginationConfig.current_page"
  163. @load="getList"
  164. :loading="loading"
  165. >
  166. <el-checkbox-group v-model="multipleSelection" @change="handleCheckedChatChange">
  167. <el-row v-if="tool.toolList.length > 0" :gutter="15" class="w-full">
  168. <template v-for="(item, index) in tool.toolList" :key="index">
  169. <el-col :xs="24" :sm="12" :md="12" :lg="8" :xl="6" class="mb-16">
  170. <CardBox
  171. :title="item.name"
  172. :description="item.desc"
  173. class="cursor"
  174. :class="[multipleSelection.includes(item.id) ? 'border-active' : '']"
  175. @click.stop="openEditDialog(item)"
  176. :disabled="!permissionPrecise.edit(item.id) || isBatch"
  177. >
  178. <template #icon>
  179. <el-avatar v-if="item?.icon" shape="square" :size="32" style="background: none">
  180. <img :src="resetUrl(item?.icon)" alt=""/>
  181. </el-avatar>
  182. <ToolIcon v-else :size="32" :type="item?.tool_type"/>
  183. </template>
  184. <template #title>
  185. <div class="flex align-center">
  186. <span class="ellipsis-1" :title="item.name">
  187. {{ item.name }}
  188. </span>
  189. <el-tag
  190. v-if="item.version"
  191. class="ml-4"
  192. size="small"
  193. type="info"
  194. effect="plain"
  195. >
  196. {{ item.version }}
  197. </el-tag>
  198. </div>
  199. </template>
  200. <template #subTitle>
  201. <el-text class="color-secondary lighter flex align-center" size="small">
  202. <span
  203. :title="i18n_name(item.nick_name)"
  204. class="ellipsis"
  205. style="max-width: 90px"
  206. >
  207. {{ i18n_name(item.nick_name) }}
  208. </span>
  209. <span class="ml-4 mr-4"> {{ $t('common.createdIn') }}</span>
  210. <span> {{ dateFormat(item.create_time) }}</span>
  211. </el-text>
  212. </template>
  213. <template #tag="{ hoverShow }">
  214. <el-checkbox :value="item.id" v-if="isBatch" @change="checkboxChange(item)"/>
  215. <div v-else>
  216. <el-tag v-if="isShared" size="small" type="info" class="info-tag">
  217. {{ t('views.shared.title') }}
  218. </el-tag>
  219. <el-tooltip
  220. effect="dark"
  221. :content="$t('views.tool.updatedVersion')"
  222. v-if="
  223. showUpdateStoreTool(item) && !isShared && permissionPrecise.edit(item.id)
  224. "
  225. >
  226. <el-button text @click.stop="updateStoreTool(item)">
  227. <el-icon v-if="hoverShow">
  228. <Refresh/>
  229. </el-icon>
  230. <div v-else class="dot-success"></div>
  231. </el-button>
  232. </el-tooltip>
  233. </div>
  234. </template>
  235. <template #footer>
  236. <div v-if="item.is_active" class="flex align-center">
  237. <el-icon class="color-success mr-8" style="font-size: 16px">
  238. <SuccessFilled/>
  239. </el-icon>
  240. <span class="color-secondary">
  241. {{ $t('common.status.enabled') }}
  242. </span>
  243. </div>
  244. <div v-else class="flex align-center">
  245. <AppIcon iconName="app-disabled" class="color-secondary mr-8"></AppIcon>
  246. <span class="color-secondary">
  247. {{ $t('common.status.disabled') }}
  248. </span>
  249. </div>
  250. </template>
  251. <template #mouseEnter>
  252. <div @click.stop v-if="!isShared && MoreFieldPermission(item.id)">
  253. <el-switch
  254. v-model="item.is_active"
  255. :before-change="() => changeState(item)"
  256. size="small"
  257. class="mr-4"
  258. v-if="permissionPrecise.switch(item.id)"
  259. />
  260. <el-tooltip effect="dark" :content="$t('views.tool.statistics.title')" placement="top">
  261. <el-button text @click.stop="openStatistics(item)" size="small">
  262. <AppIcon iconName="app-operate-log" class="color-secondary"></AppIcon>
  263. </el-button>
  264. </el-tooltip>
  265. <el-divider direction="vertical"/>
  266. <el-dropdown trigger="click">
  267. <el-button text @click.stop>
  268. <AppIcon iconName="app-more" class="color-secondary"></AppIcon>
  269. </el-button>
  270. <template #dropdown>
  271. <el-dropdown-menu>
  272. <el-dropdown-item
  273. v-if="item.tool_type === 'MCP'"
  274. @click.stop="showMcpConfig(item)"
  275. >
  276. <AppIcon iconName="app-operate-log" class="color-secondary"></AppIcon>
  277. {{ $t('views.tool.mcp.mcpConfig') }}
  278. </el-dropdown-item>
  279. <el-dropdown-item
  280. v-if="item.template_id && permissionPrecise.edit(item.id)"
  281. @click.stop="addInternalTool(item, true)"
  282. >
  283. <AppIcon iconName="app-edit" class="color-secondary"></AppIcon>
  284. {{ $t('common.edit') }}
  285. </el-dropdown-item>
  286. <el-dropdown-item
  287. v-else-if="
  288. item.tool_type === 'WORKFLOW' && permissionPrecise.edit(item.id)
  289. "
  290. @click.stop="openCreateWorkflowDialog(item)"
  291. >
  292. <AppIcon iconName="app-edit" class="color-secondary"></AppIcon>
  293. {{ $t('common.edit') }}
  294. </el-dropdown-item>
  295. <el-dropdown-item
  296. v-else-if="permissionPrecise.edit(item.id)"
  297. @click.stop="openEditDialog(item)"
  298. >
  299. <AppIcon iconName="app-edit" class="color-secondary"></AppIcon>
  300. {{ $t('common.edit') }}
  301. </el-dropdown-item>
  302. <el-dropdown-item
  303. v-if="item.tool_type === 'WORKFLOW'"
  304. @click.stop="toWorkflow(item)"
  305. >
  306. <AppIcon iconName="app-workflow" class="color-secondary"></AppIcon>
  307. {{ $t('workflow.workflow') }}
  308. </el-dropdown-item>
  309. <el-dropdown-item
  310. v-if="!item.template_id && permissionPrecise.copy(item.id)"
  311. @click.stop="copyTool(item)"
  312. >
  313. <AppIcon iconName="app-copy" class="color-secondary"></AppIcon>
  314. {{ $t('common.copy') }}
  315. </el-dropdown-item>
  316. <el-dropdown-item
  317. v-if="
  318. item.init_field_list?.length > 0 && permissionPrecise.edit(item.id)
  319. "
  320. @click.stop="configInitParams(item)"
  321. >
  322. <AppIcon iconName="app-operation" class="color-secondary"></AppIcon>
  323. {{ $t('common.param.initParam') }}
  324. </el-dropdown-item>
  325. <el-dropdown-item
  326. @click.stop="openAuthorization(item)"
  327. v-if="apiType === 'workspace' && permissionPrecise.auth(item.id)"
  328. >
  329. <AppIcon
  330. iconName="app-resource-authorization"
  331. class="color-secondary"
  332. ></AppIcon>
  333. {{ $t('views.system.resourceAuthorization.title') }}
  334. </el-dropdown-item>
  335. <el-dropdown-item
  336. @click.stop="openTriggerDrawer(item)"
  337. v-if="
  338. ['workspace', 'systemManage'].includes(apiType) &&
  339. (item.tool_type === 'CUSTOM' || item.tool_type === 'WORKFLOW') &&
  340. permissionPrecise.trigger_read(item.id)
  341. "
  342. >
  343. <AppIcon iconName="app-trigger" class="color-secondary"></AppIcon>
  344. {{ $t('views.trigger.title') }}
  345. </el-dropdown-item>
  346. <el-dropdown-item
  347. text
  348. @click.stop="openResourceMappingDrawer(item)"
  349. v-if="permissionPrecise.relate_map(item.id)"
  350. >
  351. <AppIcon
  352. iconName="app-resource-mapping"
  353. class="color-secondary"
  354. ></AppIcon>
  355. {{ $t('views.system.resourceMapping.title') }}
  356. </el-dropdown-item>
  357. <el-dropdown-item
  358. text
  359. @click.stop="openToolRecordDrawer(item)"
  360. v-if="
  361. (item.tool_type === 'CUSTOM' || item.tool_type === 'WORKFLOW') &&
  362. permissionPrecise.record(item.id)
  363. "
  364. >
  365. <AppIcon
  366. iconName="app-schedule-report"
  367. class="color-secondary"
  368. ></AppIcon>
  369. {{ $t('common.ExecutionRecord.subTitle') }}
  370. </el-dropdown-item>
  371. <el-dropdown-item
  372. @click.stop="openMoveToDialog(item)"
  373. v-if="permissionPrecise.copy(item.id) && apiType === 'workspace'"
  374. >
  375. <AppIcon iconName="app-migrate" class="color-secondary"></AppIcon>
  376. {{ $t('common.moveTo') }}
  377. </el-dropdown-item>
  378. <el-dropdown-item
  379. v-if="isSystemShare"
  380. @click.stop="openAuthorizedWorkspaceDialog(item)"
  381. >
  382. <AppIcon iconName="app-lock" class="color-secondary"></AppIcon>
  383. {{ $t('views.shared.authorized_workspace') }}
  384. </el-dropdown-item>
  385. <el-dropdown-item
  386. v-if="!item.template_id && permissionPrecise.export(item.id)"
  387. @click.stop="exportTool(item)"
  388. >
  389. <AppIcon iconName="app-export" class="color-secondary"></AppIcon>
  390. {{ $t('common.export') }}
  391. </el-dropdown-item>
  392. <el-dropdown-item
  393. v-if="permissionPrecise.delete(item.id)"
  394. divided
  395. @click.stop="deleteTool(item)"
  396. >
  397. <AppIcon iconName="app-delete" class="color-secondary"></AppIcon>
  398. {{ $t('common.delete') }}
  399. </el-dropdown-item>
  400. </el-dropdown-menu>
  401. </template>
  402. </el-dropdown>
  403. </div>
  404. </template>
  405. </CardBox>
  406. </el-col>
  407. </template>
  408. </el-row>
  409. <el-empty :description="$t('common.noData')" v-else/>
  410. </el-checkbox-group>
  411. </InfiniteScroll>
  412. </div>
  413. <!-- 批量操作拦 -->
  414. <div class="mul-operation border-t w-full flex align-center" v-if="isBatch">
  415. <el-checkbox
  416. v-model="checkAll"
  417. :indeterminate="isIndeterminate"
  418. @change="handleCheckAllChange"
  419. >
  420. {{ $t('common.allCheck') }}
  421. </el-checkbox>
  422. <el-button
  423. class="ml-16"
  424. :disabled="multipleSelection.length === 0"
  425. @click="openMoveToDialog()"
  426. v-if="permissionPrecise.batchMove()"
  427. >
  428. {{ $t('common.moveTo') }}
  429. </el-button>
  430. <el-button
  431. :disabled="multipleSelection.length === 0"
  432. @click="deleteMulTool"
  433. v-if="permissionPrecise.batchDelete()"
  434. >
  435. {{ $t('common.delete') }}
  436. </el-button>
  437. <span class="color-secondary ml-24 mr-16">
  438. {{ $t('common.selected') }} {{ multipleSelection.length }}/{{ paginationConfig.total }}
  439. {{ $t('views.document.items') }}
  440. </span>
  441. <el-button link type="primary" @click="batchSelectedHandle(false)">
  442. {{ $t('views.paragraph.setting.cancelSelected') }}
  443. </el-button>
  444. </div>
  445. <InitParamDrawer ref="InitParamDrawerRef" @refresh="refresh"/>
  446. <ToolFormDrawer ref="ToolFormDrawerRef" @refresh="refresh" :title="ToolDrawertitle"/>
  447. <McpToolFormDrawer ref="McpToolFormDrawerRef" @refresh="refresh" :title="McpToolDrawertitle"/>
  448. <SkillToolFormDrawer
  449. ref="SkillToolFormDrawerRef"
  450. @refresh="refresh"
  451. :title="SkillToolDrawertitle"
  452. />
  453. <DataSourceToolFormDrawer
  454. ref="DataSourceToolFormDrawerRef"
  455. @refresh="refresh"
  456. :title="DataSourceToolDrawertitle"
  457. />
  458. <CreateFolderDialog ref="CreateFolderDialogRef" v-if="!isShared" @refresh="refreshFolder"/>
  459. <ToolStoreDialog ref="toolStoreDialogRef" :api-type="apiType" @refresh="refresh"/>
  460. <AddInternalToolDialog ref="AddInternalToolDialogRef" @refresh="confirmAddInternalTool"/>
  461. <McpToolConfigDialog ref="McpToolConfigDialogRef" @refresh="refresh"/>
  462. <AuthorizedWorkspace
  463. ref="AuthorizedWorkspaceDialogRef"
  464. v-if="isSystemShare"
  465. ></AuthorizedWorkspace>
  466. <MoveToDialog
  467. ref="MoveToDialogRef"
  468. :source="SourceTypeEnum.TOOL"
  469. @refresh="refreshToolList"
  470. v-if="apiType === 'workspace'"
  471. />
  472. <ResourceAuthorizationDrawer
  473. :type="SourceTypeEnum.TOOL"
  474. ref="ResourceAuthorizationDrawerRef"
  475. v-if="apiType === 'workspace'"
  476. />
  477. <ToolStoreDescDrawer ref="toolStoreDescDrawerRef"/>
  478. <ResourceMappingDrawer ref="resourceMappingDrawerRef"></ResourceMappingDrawer>
  479. <ResourceTriggerDrawer
  480. ref="resourceTriggerDrawerRef"
  481. :source="SourceTypeEnum.TOOL"
  482. ></ResourceTriggerDrawer>
  483. <ExecutionRecordDrawer ref="toolRecordDrawerRef"/>
  484. <ToolStatisticsDrawer ref="ToolStatisticsDrawerRef"/>
  485. <WorkflowFormDialog
  486. ref="workflowFormDialogRef"
  487. @refresh="refresh"
  488. :title="workflowFormDialogTitle"
  489. ></WorkflowFormDialog>
  490. </ContentContainer>
  491. </template>
  492. <script lang="ts" setup>
  493. import {onMounted, ref, reactive, computed, watch} from 'vue'
  494. import {cloneDeep} from 'lodash'
  495. import {useRoute, onBeforeRouteLeave, useRouter} from 'vue-router'
  496. import type {CheckboxValueType} from 'element-plus'
  497. import InitParamDrawer from '@/views/tool/component/InitParamDrawer.vue'
  498. import ToolFormDrawer from '@/views/tool/ToolFormDrawer.vue'
  499. import McpToolFormDrawer from '@/views/tool/McpToolFormDrawer.vue'
  500. import SkillToolFormDrawer from '@/views/tool/SkillToolFormDrawer.vue'
  501. import DataSourceToolFormDrawer from '@/views/tool/DataSourceToolFormDrawer.vue'
  502. import CreateFolderDialog from '@/components/folder-tree/CreateFolderDialog.vue'
  503. import AuthorizedWorkspace from '@/views/system-shared/AuthorizedWorkspaceDialog.vue'
  504. import ToolStoreDialog from '@/views/tool/tool-store/ToolStoreDialog.vue'
  505. import AddInternalToolDialog from '@/views/tool/tool-store/AddInternalToolDialog.vue'
  506. import MoveToDialog from '@/components/folder-tree/MoveToDialog.vue'
  507. import ResourceAuthorizationDrawer from '@/components/resource-authorization-drawer/index.vue'
  508. import McpToolConfigDialog from '@/views/tool/component/McpToolConfigDialog.vue'
  509. import ResourceTriggerDrawer from '@/views/trigger/ResourceTriggerDrawer.vue'
  510. import ToolStoreDescDrawer from '@/views/tool/component/ToolStoreDescDrawer.vue'
  511. import ResourceMappingDrawer from '@/components/resource_mapping/index.vue'
  512. import WorkflowFormDialog from '../WorkflowFormDialog.vue'
  513. import ToolStatisticsDrawer from '@/views/tool/component/ToolStatisticsDrawer.vue'
  514. import ExecutionRecordDrawer from '@/views/tool-workflow/execution-record/ExecutionRecordDrawer.vue'
  515. import ToolStoreApi from '@/api/tool/store.ts'
  516. import {resetUrl, i18n_name} from '@/utils/common'
  517. import {MsgSuccess, MsgConfirm, MsgError} from '@/utils/message'
  518. import {SourceTypeEnum} from '@/enums/common'
  519. import {dateFormat} from '@/utils/time'
  520. import {loadSharedApi} from '@/utils/dynamics-api/shared-api'
  521. import permissionMap from '@/permission'
  522. import useStore from '@/stores'
  523. import {t} from '@/locales'
  524. import bus from '@/bus'
  525. const router = useRouter()
  526. const route = useRoute()
  527. const {folder, user, tool} = useStore()
  528. onBeforeRouteLeave((to, from) => {
  529. tool.setToolList([])
  530. })
  531. const emit = defineEmits(['refreshFolder'])
  532. const apiType = computed(() => {
  533. if (route.path.includes('shared')) {
  534. return 'systemShare'
  535. } else if (route.path.includes('resource-management')) {
  536. return 'systemManage'
  537. } else {
  538. return 'workspace'
  539. }
  540. })
  541. const isShared = computed(() => {
  542. return folder.currentFolder.id === 'share'
  543. })
  544. const isSystemShare = computed(() => {
  545. return apiType.value === 'systemShare'
  546. })
  547. const permissionPrecise = computed(() => {
  548. return permissionMap['tool'][apiType.value]
  549. })
  550. const MoreFieldPermission = (id: any) => {
  551. return (
  552. permissionPrecise.value.edit(id) ||
  553. permissionPrecise.value.export(id) ||
  554. permissionPrecise.value.delete(id) ||
  555. permissionPrecise.value.auth(id) ||
  556. permissionPrecise.value.relate_map(id) ||
  557. permissionPrecise.value.trigger_read(id) ||
  558. permissionPrecise.value.record(id) ||
  559. isSystemShare.value
  560. )
  561. }
  562. const resourceTriggerDrawerRef = ref<InstanceType<typeof ResourceTriggerDrawer>>()
  563. const openTriggerDrawer = (data: any) => {
  564. resourceTriggerDrawerRef.value?.open(data)
  565. }
  566. const resourceMappingDrawerRef = ref<InstanceType<typeof ResourceMappingDrawer>>()
  567. const openResourceMappingDrawer = (tool: any) => {
  568. resourceMappingDrawerRef.value?.open('TOOL', tool)
  569. }
  570. const ResourceAuthorizationDrawerRef = ref()
  571. function openAuthorization(item: any) {
  572. ResourceAuthorizationDrawerRef.value.open(item.id)
  573. }
  574. const toolRecordDrawerRef = ref<InstanceType<typeof ExecutionRecordDrawer>>()
  575. const ToolStatisticsDrawerRef = ref<InstanceType<typeof ToolStatisticsDrawer>>()
  576. const openToolRecordDrawer = (data: any) => {
  577. toolRecordDrawerRef.value?.open(data)
  578. }
  579. const InitParamDrawerRef = ref()
  580. const search_type = ref('name')
  581. const search_form = ref<any>({
  582. name: '',
  583. create_user: '',
  584. })
  585. const user_options = ref<any[]>([])
  586. const loading = ref(false)
  587. const changeStateloading = ref(false)
  588. const paginationConfig = reactive({
  589. current_page: 1,
  590. page_size: 30,
  591. total: 0,
  592. })
  593. const search_type_change = () => {
  594. search_form.value = {name: '', create_user: ''}
  595. }
  596. const ToolFormDrawerRef = ref()
  597. const McpToolFormDrawerRef = ref()
  598. const SkillToolFormDrawerRef = ref()
  599. const DataSourceToolFormDrawerRef = ref()
  600. const ToolDrawertitle = ref('')
  601. const McpToolDrawertitle = ref('')
  602. const SkillToolDrawertitle = ref('')
  603. const DataSourceToolDrawertitle = ref('')
  604. // 批量操作
  605. const isBatch = ref(false)
  606. const multipleSelection = ref<any[]>([])
  607. const checkAll = ref(false)
  608. const isIndeterminate = computed(() => {
  609. return multipleSelection.value.length > 0 && multipleSelection.value.length < tool.toolList.length
  610. })
  611. function batchSelectedHandle(bool: boolean) {
  612. isBatch.value = bool
  613. multipleSelection.value = []
  614. checkAll.value = false
  615. }
  616. const handleCheckAllChange = (val: CheckboxValueType) => {
  617. let bool
  618. if (isIndeterminate.value) {
  619. bool = true
  620. } else {
  621. bool = val as boolean
  622. }
  623. multipleSelection.value = bool ? tool.toolList.map((v) => v.id) : []
  624. checkAll.value = bool as boolean
  625. }
  626. const handleCheckedChatChange = (value: CheckboxValueType[]) => {
  627. const checkedCount = value.length
  628. checkAll.value = checkedCount === tool.toolList.length
  629. }
  630. const checkboxChange = (data?: any) => {
  631. const index = multipleSelection.value.indexOf(data?.id)
  632. if (index === -1) {
  633. multipleSelection.value.push(data?.id)
  634. } else {
  635. multipleSelection.value.splice(index, 1)
  636. }
  637. checkAll.value = multipleSelection.value.length === tool.toolList.length
  638. }
  639. function deleteMulTool() {
  640. MsgConfirm(
  641. `${t('views.document.delete.confirmTitle1')} ${multipleSelection.value.length} ${t('views.tool.delete.confirmTitle2')}`,
  642. t('views.paragraph.delete.confirmMessage'),
  643. {
  644. confirmButtonText: t('common.confirm'),
  645. confirmButtonClass: 'danger',
  646. },
  647. )
  648. .then(() => {
  649. loadSharedApi({type: 'tool', systemType: apiType.value})
  650. .delMulTool(multipleSelection.value, loading)
  651. .then(() => {
  652. batchSelectedHandle(false)
  653. paginationConfig.current_page = 1
  654. tool.setToolList([])
  655. getList()
  656. MsgSuccess(t('views.document.delete.successMessage'))
  657. })
  658. })
  659. .catch(() => {
  660. })
  661. }
  662. function openStatistics(data: any) {
  663. ToolStatisticsDrawerRef.value?.open({ id: data.id, name: data.name })
  664. }
  665. function openEditDialog(data?: any) {
  666. if (isBatch.value) {
  667. const index = multipleSelection.value.indexOf(data?.id)
  668. if (index === -1) {
  669. multipleSelection.value.push(data?.id)
  670. } else {
  671. multipleSelection.value.splice(index, 1)
  672. }
  673. checkAll.value = multipleSelection.value.length === tool.toolList.length
  674. return
  675. }
  676. // 有template_id的不允许编辑,是模板转换来的
  677. if (data?.template_id) {
  678. return
  679. }
  680. // 共享过来的工具不让编辑
  681. if (isShared.value) {
  682. return
  683. }
  684. if (data) {
  685. bus.emit('select_node', data.folder_id)
  686. }
  687. // 有版本号的展示readme,是商店更新过来的
  688. if (data?.version) {
  689. let readMe = ''
  690. storeTools.value
  691. .filter((item) => item.id === data.template_id)
  692. .forEach((item) => {
  693. readMe = item.readMe
  694. })
  695. toolStoreDescDrawerRef.value?.open(readMe, data)
  696. return
  697. }
  698. // mcp工具
  699. if (data?.tool_type === 'MCP') {
  700. openCreateMcpDialog(data)
  701. return
  702. }
  703. // 数据源工具
  704. if (data?.tool_type === 'DATA_SOURCE') {
  705. openCreateDataSourceDialog(data)
  706. return
  707. }
  708. // 技能
  709. if (data?.tool_type === 'SKILL') {
  710. openCreateSkillDialog(data)
  711. return
  712. }
  713. // 工作流
  714. if (data?.tool_type === 'WORKFLOW') {
  715. toWorkflow(data)
  716. return
  717. }
  718. ToolDrawertitle.value = t('views.tool.editTool')
  719. if (data) {
  720. loadSharedApi({type: 'tool', systemType: apiType.value})
  721. .getToolById(data?.id, loading)
  722. .then((res: any) => {
  723. ToolFormDrawerRef.value.open(res.data)
  724. })
  725. }
  726. }
  727. const MoveToDialogRef = ref()
  728. function openMoveToDialog(data?: any) {
  729. let obj
  730. if (isBatch.value) {
  731. obj = {
  732. id_list: multipleSelection.value,
  733. }
  734. } else {
  735. obj = {
  736. id: data.id,
  737. folder_id: data.folder,
  738. }
  739. }
  740. MoveToDialogRef.value?.open(obj)
  741. }
  742. function refreshToolList(row: any) {
  743. if (row) {
  744. // 不是根目录才会移除
  745. if (folder.currentFolder?.parent_id) {
  746. const list = cloneDeep(tool.toolList)
  747. const index = list.findIndex((v) => v.id === row.id)
  748. list.splice(index, 1)
  749. tool.setToolList(list)
  750. }
  751. } else {
  752. batchSelectedHandle(false)
  753. paginationConfig.current_page = 1
  754. tool.setToolList([])
  755. getList()
  756. }
  757. }
  758. const AuthorizedWorkspaceDialogRef = ref()
  759. function openAuthorizedWorkspaceDialog(row: any) {
  760. if (AuthorizedWorkspaceDialogRef.value) {
  761. AuthorizedWorkspaceDialogRef.value.open(row, 'Tool')
  762. }
  763. }
  764. const toolStoreDescDrawerRef = ref<InstanceType<typeof ToolStoreDescDrawer>>()
  765. function openCreateDialog() {
  766. ToolDrawertitle.value = t('views.tool.createTool')
  767. ToolFormDrawerRef.value.open()
  768. }
  769. function openCreateMcpDialog(data?: any) {
  770. // 有template_id的不允许编辑,是模板转换来的
  771. if (data?.template_id) {
  772. return
  773. }
  774. // 共享过来的工具不让编辑
  775. if (isShared.value) {
  776. return
  777. }
  778. McpToolDrawertitle.value = data
  779. ? t('views.tool.mcp.editMcpTool')
  780. : t('views.tool.mcp.createMcpTool')
  781. if (data) {
  782. loadSharedApi({type: 'tool', systemType: apiType.value})
  783. .getToolById(data?.id, loading)
  784. .then((res: any) => {
  785. McpToolFormDrawerRef.value.open(res.data)
  786. })
  787. } else {
  788. McpToolFormDrawerRef.value.open(data)
  789. }
  790. }
  791. function openCreateSkillDialog(data?: any) {
  792. // 有版本号的展示readme,是商店更新过来的
  793. if (data?.version) {
  794. let readMe = ''
  795. storeTools.value
  796. .filter((item) => item.id === data.template_id)
  797. .forEach((item) => {
  798. readMe = item.readMe
  799. })
  800. toolStoreDescDrawerRef.value?.open(readMe, data)
  801. return
  802. }
  803. // 有template_id的不允许编辑,是模板转换来的
  804. if (data?.template_id) {
  805. return
  806. }
  807. // 共享过来的工具不让编辑
  808. if (isShared.value) {
  809. return
  810. }
  811. SkillToolDrawertitle.value = data
  812. ? t('views.tool.skill.editSkillTool')
  813. : t('views.tool.skill.createSkillTool')
  814. if (data) {
  815. loadSharedApi({type: 'tool', systemType: apiType.value})
  816. .getToolById(data?.id, loading)
  817. .then((res: any) => {
  818. SkillToolFormDrawerRef.value.open(res.data)
  819. })
  820. } else {
  821. SkillToolFormDrawerRef.value.open(data)
  822. }
  823. }
  824. function toWorkflow(data: any) {
  825. const folderId = data.scope === 'SHARED' ? 'shared' : data.folder_id
  826. router.push({name: 'ToolWorkflow', params: {id: data.id, folderId: folderId}})
  827. }
  828. const workflowFormDialogRef = ref<InstanceType<typeof WorkflowFormDialog>>()
  829. const workflowFormDialogTitle = ref('')
  830. const openCreateWorkflowDialog = (data?: any) => {
  831. // 有template_id的不允许编辑,是模板转换来的
  832. if (data?.template_id) {
  833. return
  834. }
  835. // 共享过来的工具不让编辑
  836. if (isShared.value) {
  837. return
  838. }
  839. workflowFormDialogTitle.value = data
  840. ? t('common.edit')
  841. : t('views.tool.toolWorkflow.creatToolWorkflow')
  842. if (data) {
  843. loadSharedApi({type: 'tool', systemType: apiType.value})
  844. .getToolById(data?.id, loading)
  845. .then((res: any) => {
  846. workflowFormDialogRef.value?.open(res.data)
  847. })
  848. } else {
  849. workflowFormDialogRef.value?.open(data)
  850. }
  851. }
  852. function openCreateDataSourceDialog(data?: any) {
  853. // 有template_id的不允许编辑,是模板转换来的
  854. if (data?.template_id) {
  855. return
  856. }
  857. // 共享过来的工具不让编辑
  858. if (isShared.value) {
  859. return
  860. }
  861. DataSourceToolDrawertitle.value = data
  862. ? t('views.tool.dataSource.editDataSource')
  863. : t('views.tool.dataSource.createDataSource')
  864. if (data) {
  865. loadSharedApi({type: 'tool', systemType: apiType.value})
  866. .getToolById(data?.id, loading)
  867. .then((res: any) => {
  868. DataSourceToolFormDrawerRef.value.open(res.data)
  869. })
  870. } else {
  871. DataSourceToolFormDrawerRef.value.open(data)
  872. }
  873. }
  874. async function changeState(row: any) {
  875. if (row.is_active) {
  876. MsgConfirm(
  877. `${t('views.tool.disabled.confirmTitle')}${row.name} ?`,
  878. t('views.tool.disabled.confirmMessage'),
  879. {
  880. confirmButtonText: t('common.status.disable'),
  881. confirmButtonClass: 'danger',
  882. },
  883. ).then(() => {
  884. const obj = {
  885. is_active: !row.is_active,
  886. }
  887. loadSharedApi({type: 'tool', systemType: apiType.value})
  888. .putTool(row.id, obj, changeStateloading)
  889. .then(() => {
  890. const list = cloneDeep(tool.toolList)
  891. const index = list.findIndex((v) => v.id === row.id)
  892. list[index].is_active = !row.is_active
  893. tool.setToolList(list)
  894. return true
  895. })
  896. .catch(() => {
  897. return false
  898. })
  899. })
  900. } else {
  901. const res = await loadSharedApi({type: 'tool', systemType: apiType.value}).getToolById(
  902. row.id,
  903. changeStateloading,
  904. )
  905. if (row.tool_type === 'WORKFLOW' && !res.data.is_publish) {
  906. MsgConfirm(t('common.tip'), t('views.tool.toolWorkflow.toActiveTip')).then(() => {
  907. toWorkflow(row)
  908. })
  909. return
  910. }
  911. if (
  912. (!res.data.init_params || Object.keys(res.data.init_params).length === 0) &&
  913. res.data.init_field_list &&
  914. res.data.init_field_list.length > 0 &&
  915. res.data.init_field_list.filter((item: any) => item.default_value && item.show_default_value)
  916. .length !== res.data.init_field_list.length
  917. ) {
  918. InitParamDrawerRef.value.open(res.data, !row.is_active)
  919. return false
  920. }
  921. const obj = {
  922. is_active: !row.is_active,
  923. }
  924. loadSharedApi({type: 'tool', systemType: apiType.value})
  925. .putTool(row.id, obj, changeStateloading)
  926. .then(() => {
  927. const list = cloneDeep(tool.toolList)
  928. const index = list.findIndex((v) => v.id === row.id)
  929. list[index].is_active = !row.is_active
  930. tool.setToolList(list)
  931. return true
  932. })
  933. .catch(() => {
  934. return false
  935. })
  936. }
  937. }
  938. async function copyTool(row: any) {
  939. // mcp工具
  940. if (row?.tool_type === 'MCP') {
  941. bus.emit('select_node', row.folder_id)
  942. await copyMcpTool(row)
  943. return
  944. }
  945. // 数据源工具
  946. if (row?.tool_type === 'DATA_SOURCE') {
  947. bus.emit('select_node', row.folder_id)
  948. await copyDataSource(row)
  949. return
  950. }
  951. // 技能
  952. if (row?.tool_type === 'SKILL') {
  953. bus.emit('select_node', row.folder_id)
  954. await copySkillTool(row)
  955. return
  956. }
  957. if (row?.tool_type === 'WORKFLOW') {
  958. workflowFormDialogTitle.value = t('views.tool.toolWorkflow.copyToolWorkflow')
  959. const res = await loadSharedApi({type: 'tool', systemType: apiType.value}).getToolById(
  960. row.id,
  961. changeStateloading,
  962. )
  963. const obj = cloneDeep(res.data)
  964. delete obj['id']
  965. obj['name'] = obj['name'] + ` ${t('common.copyTitle')}`
  966. workflowFormDialogRef.value?.open(obj)
  967. return
  968. }
  969. ToolDrawertitle.value = t('views.tool.copyTool')
  970. const res = await loadSharedApi({type: 'tool', systemType: apiType.value}).getToolById(
  971. row.id,
  972. changeStateloading,
  973. )
  974. const obj = cloneDeep(res.data)
  975. delete obj['id']
  976. obj['name'] = obj['name'] + ` ${t('common.copyTitle')}`
  977. ToolFormDrawerRef.value.open(obj)
  978. }
  979. async function copyMcpTool(row: any) {
  980. McpToolDrawertitle.value = t('views.tool.mcp.copyMcpTool')
  981. const res = await loadSharedApi({type: 'tool', systemType: apiType.value}).getToolById(
  982. row.id,
  983. changeStateloading,
  984. )
  985. const obj = cloneDeep(res.data)
  986. delete obj['id']
  987. obj['name'] = obj['name'] + ` ${t('common.copyTitle')}`
  988. McpToolFormDrawerRef.value.open(obj)
  989. }
  990. async function copyDataSource(row: any) {
  991. DataSourceToolDrawertitle.value = t('views.tool.dataSource.copyDataSource')
  992. const res = await loadSharedApi({type: 'tool', systemType: apiType.value}).getToolById(
  993. row.id,
  994. changeStateloading,
  995. )
  996. const obj = cloneDeep(res.data)
  997. delete obj['id']
  998. obj['name'] = obj['name'] + ` ${t('common.copyTitle')}`
  999. DataSourceToolFormDrawerRef.value.open(obj)
  1000. }
  1001. async function copySkillTool(row: any) {
  1002. SkillToolDrawertitle.value = t('views.tool.skill.copySkillTool')
  1003. const res = await loadSharedApi({type: 'tool', systemType: apiType.value}).getToolById(
  1004. row.id,
  1005. changeStateloading,
  1006. )
  1007. const obj = cloneDeep(res.data)
  1008. delete obj['id']
  1009. obj['name'] = obj['name'] + ` ${t('common.copyTitle')}`
  1010. SkillToolFormDrawerRef.value.open(obj)
  1011. }
  1012. function exportTool(row: any) {
  1013. loadSharedApi({type: 'tool', systemType: apiType.value})
  1014. .exportTool(row.id, row.name, loading)
  1015. .catch((e: any) => {
  1016. if (e.response.status !== 403) {
  1017. e.response.data.text().then((res: string) => {
  1018. MsgError(`${t('views.application.tip.ExportError')}:${JSON.parse(res).message}`)
  1019. })
  1020. }
  1021. })
  1022. }
  1023. function deleteTool(row: any) {
  1024. MsgConfirm(
  1025. `${t('views.tool.delete.confirmTitle')}:${row.name} ?`,
  1026. row.resource_count > 0 ? t('views.tool.delete.resourceCountMessage', row.resource_count) : '',
  1027. {
  1028. confirmButtonText: t('common.confirm'),
  1029. cancelButtonText: t('common.cancel'),
  1030. confirmButtonClass: 'danger',
  1031. },
  1032. )
  1033. .then(() => {
  1034. loadSharedApi({type: 'tool', systemType: apiType.value})
  1035. .delTool(row.id, loading)
  1036. .then(() => {
  1037. const list = cloneDeep(tool.toolList)
  1038. const index = list.findIndex((v) => v.id === row.id)
  1039. list.splice(index, 1)
  1040. tool.setToolList(list)
  1041. MsgSuccess(t('common.deleteSuccess'))
  1042. })
  1043. })
  1044. .catch(() => {
  1045. })
  1046. }
  1047. function configInitParams(item: any) {
  1048. loadSharedApi({type: 'tool', systemType: apiType.value})
  1049. .getToolById(item?.id, changeStateloading)
  1050. .then((res: any) => {
  1051. InitParamDrawerRef.value.open(res.data)
  1052. })
  1053. }
  1054. const toolStoreDialogRef = ref<InstanceType<typeof ToolStoreDialog>>()
  1055. function openToolStoreDialog() {
  1056. toolStoreDialogRef.value?.open(folder.currentFolder.id)
  1057. }
  1058. const AddInternalToolDialogRef = ref<InstanceType<typeof AddInternalToolDialog>>()
  1059. function addInternalTool(data?: any, isEdit?: boolean) {
  1060. AddInternalToolDialogRef.value?.open(data, isEdit)
  1061. }
  1062. function confirmAddInternalTool(data?: any, isEdit?: boolean) {
  1063. if (isEdit) {
  1064. loadSharedApi({type: 'tool', systemType: apiType.value})
  1065. .putTool(data?.id as string, {name: data.name}, loading)
  1066. .then((res: any) => {
  1067. MsgSuccess(t('common.saveSuccess'))
  1068. refresh()
  1069. })
  1070. }
  1071. }
  1072. const storeTools = ref<any[]>([])
  1073. function getStoreToolList() {
  1074. ToolStoreApi.getStoreToolList({name: ''}, loading).then((res: any) => {
  1075. storeTools.value = res.data.apps
  1076. })
  1077. }
  1078. function showUpdateStoreTool(item: any) {
  1079. for (const tool of storeTools.value) {
  1080. if (tool.id === item.template_id && tool.version !== item.version) {
  1081. item.downloadUrl = tool.downloadUrl
  1082. item.downloadCallbackUrl = tool.downloadCallbackUrl
  1083. item.icon = tool.icon
  1084. item.versions = tool.versions
  1085. item.label = tool.label
  1086. return true
  1087. }
  1088. }
  1089. }
  1090. function updateStoreTool(item: any) {
  1091. MsgConfirm(
  1092. t('views.tool.toolStore.confirmTip') + item.name,
  1093. t('views.tool.toolStore.updateStoreToolMessage'),
  1094. {
  1095. cancelButtonText: t('common.cancel'),
  1096. confirmButtonText: t('common.confirm'),
  1097. },
  1098. )
  1099. .then(() => {
  1100. const obj = {
  1101. download_url: item.downloadUrl,
  1102. download_callback_url: item.downloadCallbackUrl,
  1103. icon: item.icon,
  1104. versions: item.versions,
  1105. label: item.label,
  1106. }
  1107. loadSharedApi({type: 'tool', systemType: apiType.value})
  1108. .updateStoreTool(item.id, obj, loading)
  1109. .then(async (res: any) => {
  1110. if (res?.data) {
  1111. tool.setToolList([])
  1112. return user.profile().then(() => {
  1113. getList()
  1114. })
  1115. }
  1116. })
  1117. })
  1118. .catch(() => {
  1119. })
  1120. }
  1121. const elUploadRef = ref()
  1122. function importTool(file: any) {
  1123. const formData = new FormData()
  1124. formData.append('file', file.raw, file.name)
  1125. formData.append('folder_id', folder.currentFolder.id || user.getWorkspaceId())
  1126. elUploadRef.value.clearFiles()
  1127. loadSharedApi({type: 'tool', systemType: apiType.value})
  1128. .postImportTool(formData, loading)
  1129. .then(async (res: any) => {
  1130. if (res?.data) {
  1131. tool.setToolList([])
  1132. return user.profile().then(() => {
  1133. getList()
  1134. })
  1135. }
  1136. })
  1137. .catch((e: any) => {
  1138. if (e.code === 400) {
  1139. MsgConfirm(t('common.tip'), t('views.application.tip.professionalMessage'), {
  1140. cancelButtonText: t('common.confirm'),
  1141. confirmButtonText: t('common.professional'),
  1142. }).then(() => {
  1143. window.open('https://maxkb.cn/pricing.html', '_blank')
  1144. })
  1145. }
  1146. })
  1147. }
  1148. const McpToolConfigDialogRef = ref()
  1149. function showMcpConfig(item: any) {
  1150. loadSharedApi({type: 'tool', systemType: apiType.value})
  1151. .getToolById(item?.id, loading)
  1152. .then((res: any) => {
  1153. McpToolConfigDialogRef.value.open(res.data)
  1154. })
  1155. }
  1156. function refresh(data?: any) {
  1157. if (data) {
  1158. const list = cloneDeep(tool.toolList)
  1159. const index = list.findIndex((v) => v.id === data.id)
  1160. list.splice(index, 1, data)
  1161. tool.setToolList(list)
  1162. } else {
  1163. paginationConfig.total = 0
  1164. paginationConfig.current_page = 1
  1165. tool.setToolList([])
  1166. getList()
  1167. }
  1168. }
  1169. // 文件夹相关
  1170. const CreateFolderDialogRef = ref()
  1171. function openCreateFolder() {
  1172. CreateFolderDialogRef.value.open(SourceTypeEnum.TOOL, folder.currentFolder.id)
  1173. }
  1174. watch(
  1175. () => folder.currentFolder,
  1176. (newValue) => {
  1177. if (newValue && newValue.id) {
  1178. batchSelectedHandle(false)
  1179. paginationConfig.current_page = 1
  1180. tool.setToolList([])
  1181. getList()
  1182. }
  1183. },
  1184. {deep: true, immediate: true},
  1185. )
  1186. watch(
  1187. () => tool.tool_type,
  1188. () => {
  1189. paginationConfig.current_page = 1
  1190. tool.setToolList([])
  1191. getList()
  1192. },
  1193. )
  1194. function getList() {
  1195. const params: any = {
  1196. folder_id: folder.currentFolder?.id || user.getWorkspaceId(),
  1197. scope: apiType.value === 'systemShare' ? 'SHARED' : 'WORKSPACE',
  1198. tool_type: tool.tool_type || '',
  1199. }
  1200. if (search_form.value[search_type.value]) {
  1201. params[search_type.value] = search_form.value[search_type.value]
  1202. }
  1203. loadSharedApi({type: 'tool', isShared: isShared.value, systemType: apiType.value})
  1204. .getToolListPage(paginationConfig, params, loading)
  1205. .then((res: any) => {
  1206. paginationConfig.total = res.data?.total
  1207. tool.setToolList([...tool.toolList, ...res.data?.records])
  1208. })
  1209. }
  1210. function refreshFolder() {
  1211. emit('refreshFolder')
  1212. }
  1213. function searchHandle() {
  1214. paginationConfig.current_page = 1
  1215. tool.setToolList([])
  1216. getList()
  1217. }
  1218. onMounted(() => {
  1219. if (apiType.value !== 'workspace') {
  1220. getList()
  1221. }
  1222. loadSharedApi({type: 'workspace', isShared: isShared.value, systemType: apiType.value})
  1223. .getAllMemberList(user.getWorkspaceId(), loading)
  1224. .then((res: any) => {
  1225. user_options.value = res.data
  1226. })
  1227. getStoreToolList()
  1228. })
  1229. </script>
  1230. <style lang="scss" scoped></style>