Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions ui/src/api/API_README.md
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,25 @@ Action、Drawer 或 Dialog。复用方直接使用 `typeof XxxApi` 约束完整
`typeof ModelApi | typeof SystemSharedModelApi`,不为凑齐类型添加其他范围不存在的接口。
仅展示数据的组件不接收 API。

### 工作流发布历史

`workspace/application/workflow-version.ts` 维护智能体 `application_version` 资源:
`getWorkflowVersions(applicationId)` 返回按创建时间倒序的完整 `WorkflowVersion[]`;
`putWorkflowVersion(applicationId, versionId, payload)` 编辑标题与更新说明,返回更新后的版本。
共用类型 `WorkflowVersion` 和 `WorkflowVersionPayload` 位于 `types/workflow-version.ts`,
通过 `@/api/types` 导出。页面传入完整 API 对象,发布历史面板不推测其他工作流的接口地址。

v3 编辑表单提交 `{ name, description }`,标题上限 64、更新说明上限 1000。
当前仓库后端的版本编辑序列化器只处理 `name`,列表和详情也未返回 `description`;
更新说明的持久化与回显需要后端补齐,前端不将智能体自身的 `desc` 当作版本更新说明。

### 智能体模板中心

`admin/tool-store.ts` 的 `getStoreApplicationList(query)` 查询智能体模板,直接返回
`ApplicationStoreResponse`,不再返回 `unknown`。模板元数据使用 `ApplicationStoreTemplate`,
与响应类型一起维护在 `api/types/application.ts`,经 `@/api/types` 导入。
创建或覆盖工作流时通过已有智能体 API 提交 `work_flow_template`,成功后的刷新与导航由 View 负责。

### 模型选项查询

`workspace/model/model.ts` 的 `getModelListWithShared(query)` 请求
Expand Down
14 changes: 7 additions & 7 deletions ui/src/api/admin/tool-store.ts → ui/src/api/admin/store.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { get, post } from './core/request'
import type { Dict, ToolItem, ToolStoreResponse } from '@/api/types'
import { get } from './core/request'
import type { ApplicationStoreResponse, Dict, ToolItem, ToolStoreResponse } from '@/api/types'

/** 获取系统内置工具。 */
const getInternalToolList = (query?: Dict<unknown>) => {
Expand All @@ -11,6 +11,11 @@ const getStoreToolList = (query?: Dict<unknown>) => {
return get<ToolStoreResponse>('/workspace/store/tool', query)
}

/** 获取应用模板商店列表。 */
const getStoreApplicationList = (query?: Dict<unknown>) => {
return get<ApplicationStoreResponse>('/workspace/store/application_template', query)
}

/** 获取知识库模板商店列表。 */
const getStoreKnowledgeList = (query?: Dict<unknown>) => {
return get<unknown>('/workspace/store/knowledge_template', query)
Expand All @@ -21,9 +26,4 @@ const getStoreToolWorkflowList = (query?: Dict<unknown>) => {
return get<unknown>('/workspace/store/tool_workflow_template', query)
}

/** 获取应用模板商店列表。 */
const getStoreApplicationList = (query?: Dict<unknown>) => {
return get<unknown>('/workspace/store/application_template', query)
}

export default { getInternalToolList, getStoreApplicationList, getStoreKnowledgeList, getStoreToolList, getStoreToolWorkflowList }
14 changes: 14 additions & 0 deletions ui/src/api/admin/workspace/application/workflow-version.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import { get, put } from '../../core/request'
import type { WorkflowVersion, WorkflowVersionPayload } from '@/api/types'
import { getWorkspaceId } from '@/utils/resource-context'

const getPrefix = (applicationId: string) => `/workspace/${getWorkspaceId()}/application/${applicationId}/application_version`

/** 获取智能体发布历史,按发布时间倒序返回完整版本快照。 */
const getWorkflowVersions = (applicationId: string) => get<WorkflowVersion[]>(getPrefix(applicationId))

/** 修改智能体历史版本标题和更新说明,更新说明需要服务端支持 description 字段。 */
const putWorkflowVersion = (applicationId: string, versionId: string, data: WorkflowVersionPayload) =>
put<WorkflowVersionPayload, WorkflowVersion>(`${getPrefix(applicationId)}/${versionId}`, data)

export default { getWorkflowVersions, putWorkflowVersion }
20 changes: 20 additions & 0 deletions ui/src/api/types/application.ts
Original file line number Diff line number Diff line change
Expand Up @@ -84,3 +84,23 @@ export interface PromptGeneratePayload {
messages: PromptGenerateMessage[]
prompt: string
}

/** 智能体模板中心的模板及下载元数据。 */
export interface ApplicationStoreTemplate {
id: string
name: string
desc?: string | null
description?: string | null
icon?: string
label?: string | null
downloads?: number
readMe?: string
downloadUrl?: string
downloadCallbackUrl?: string
[key: string]: unknown
}

export interface ApplicationStoreResponse {
additionalProperties: { tags: { key: string; name: string }[] }
apps: ApplicationStoreTemplate[]
}
1 change: 1 addition & 0 deletions ui/src/api/types/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,4 @@ export type * from './tool'
export type * from './knowledge'
export type * from './trigger'
export type * from './related-resources'
export type * from './workflow-version'
19 changes: 19 additions & 0 deletions ui/src/api/types/workflow-version.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import type LogicFlow from '@logicflow/core'

/** 工作流发布历史的版本快照与展示信息。 */
export interface WorkflowVersion {
id: string
name: string
/** 更新说明;旧版本接口可能不返回。 */
description?: string | null
work_flow: LogicFlow.GraphConfigData
publish_user_name: string
create_time: string
update_time: string
}

/** 发布历史的标题和更新说明编辑内容。 */
export interface WorkflowVersionPayload {
name: string
description: string
}
2 changes: 1 addition & 1 deletion ui/src/assets/iconfont.js

Large diffs are not rendered by default.

7 changes: 6 additions & 1 deletion ui/src/components/COMPONENT_README.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@ import { MkDynamicsForm, MkDynamicsFormConstructor } from '@/components/mk-dynam

## 通用规则

- 按钮组件统一使用 `Button` 前缀:操作按钮按 `Button + 动作 + 对象` 命名,例如
`ButtonAddModel`、`ButtonImportUsers`;功能入口按 `Button + 功能名称` 命名,例如
`ButtonToolStore`、`ButtonDefaultModelSetting`,不添加表示打开弹窗的 `Open`。
此规则适用于公共、页面和画布按钮组件;文件名、导入名、模板标签及已有的
`defineOptions.name` 保持一致,打开方法仍可命名为 `handleOpenXxx`。
- 目录使用 kebab-case,默认入口为 `index.vue`,通过 `defineOptions` 声明 PascalCase 多单词组件名。
Markdown 编辑器、CodeMirror 和 Logo 按下文的专用入口使用。
- Props、Emits、Slots 保持类型化。类型归属遵循 [API_README.md](../api/API_README.md),
Expand Down Expand Up @@ -576,7 +581,7 @@ Skills 场景传入 `[TOOL_TYPE.SKILL]`,并通过 `title` 指定标题。两
通过 Props 与事件回写设置的子组件,应分别发送模型 ID 和参数的局部更新,由父级合并,避免
同次交互连续更新时使用旧 Props 覆盖刚选中的模型。

`canAdd` 默认为 `false`,开启后在下拉列表底部显示“添加模型”,复用 `ModelCreateButton` 的
`canAdd` 默认为 `false`,开启后在下拉列表底部显示“添加模型”,复用 `ButtonAddModel` 的
供应商选择和模型创建流程。组件通过 `isWorkspaceResource()`、`isSystemSharedResource()` 读取
`resourceScope`:Workspace 传入 `ModelApi`,System 共享资源传入 `SystemSharedModelApi`;
其他范围暂不展示创建入口。创建成功后触发 `refresh`,使用方重新加载原业务范围的模型选项,
Expand Down
6 changes: 3 additions & 3 deletions ui/src/components/business/select-model/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { MODEL_STATUS } from '@/api/enums'
import type { ModelProviderItem, ModelItem } from '@/api/types'
import { groupBy } from 'lodash'
import ModelParamsDialog from './ModelParamsDialog.vue'
import ModelCreateButton from '@/views/model/create-model/ModelCreateButton.vue'
import ButtonAddModel from '@/views/model/create-model/ButtonAddModel.vue'
import ModelApi from '@/api/admin/workspace/model/model'
import SystemSharedModelApi from '@/api/admin/system/shared-resources/model'
import { isWorkspaceResource, isSystemSharedResource } from '@/utils/resource-context'
Expand Down Expand Up @@ -159,14 +159,14 @@ function openModelParams() {

<template v-if="canAdd && createModelApi" #footer>
<slot name="footer">
<ModelCreateButton :api="createModelApi" :current-provider="allModelProvider" :providers="providerOptions" @refresh="emit('refresh')">
<ButtonAddModel :api="createModelApi" :current-provider="allModelProvider" :providers="providerOptions" @refresh="emit('refresh')">
<template #default="{ open }">
<el-button type="primary" link :disabled="disabled" @click.stop="handleOpenCreateModel(open)">
<MkIcon name="icon_add_outlined" />
<span>添加模型</span>
</el-button>
</template>
</ModelCreateButton>
</ButtonAddModel>
</slot>
</template>
</el-select>
Expand Down
10 changes: 10 additions & 0 deletions ui/src/router/ROUTE_README.md
Original file line number Diff line number Diff line change
Expand Up @@ -320,3 +320,13 @@ System 共享资源页面:
渲染 `knowledge-detail/setting/KnowledgeSettingView.vue`,使用容器提供的知识库详情。`workflow-entry`
仅作为目录跳转入口,重定向到独立的 `workflow-knowledge` 全屏画布。画布返回知识库详情。
文档详情继续保留原地址,并通过 `detailActiveMenu` 高亮“文档”。

智能体工作流返回通过 `views/workflow/application/navigation.ts` 动态读取详情父路由的 `children`。
Workspace 父路由为 `workspace-application-detail-layout`;System 详情实现时使用
`system-application-detail-layout`。按照菜单的 `meta.order` 顺序选择首个具备名称、标题、未隐藏
且 `meta.canAccess(params)` 返回 true 的子路由;未配置该方法时默认可访问。
`canAccess` 接收目标路由参数,维护本页权限和类型约束;当前只用于详情返回导航,不代替路由守卫或后端鉴权。
概览配置 v3 的 `overviewRead` 权限,简易设置要求 SIMPLE 类型及编辑权限。
新增或调整详情页时在路由中维护这些条件,不在工作流返回函数中新增页面名称分支。
无可访问子页面或详情父路由尚未实现时,分别返回 `workspace-application-list` 或
`system-resource-applications`。
3 changes: 3 additions & 0 deletions ui/src/router/admin/types.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
/** Admin Router 的业务范围和路由元信息声明。 */

import type { RouteParamsGeneric } from 'vue-router'
import type { ResourceAuthorizationType } from '@/api/types'

export type RouteScope = 'workspace' | 'system'
Expand All @@ -22,6 +23,8 @@ declare module 'vue-router' {
hidden?: boolean
/** 系统资源授权页面当前管理的资源类型。 */
resource?: ResourceAuthorizationType
/** 详情返回导航的可访问性判断,由业务路由配置。 */
canAccess?: (params: RouteParamsGeneric) => boolean
title?: string
}
}
18 changes: 16 additions & 2 deletions ui/src/router/admin/workspace/modules/application.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import type { RouteRecordRaw } from 'vue-router'
import { perm } from '@/permission'
import { APPLICATION_TYPE } from '@/api/enums'

export const applicationRoutes: RouteRecordRaw[] = [
{
Expand All @@ -23,13 +25,25 @@ export const applicationRoutes: RouteRecordRaw[] = [
path: 'overview',
name: 'workspace-application-overview',
component: () => import('@/views/application-detail/overview/OverviewView.vue'),
meta: { title: '概览', icon: 'icon_screen_outlined', activeIcon: 'icon_screen_filled', order: 10 },
meta: {
title: '概览',
icon: 'icon_screen_outlined',
activeIcon: 'icon_screen_filled',
order: 10,
canAccess: (params) => perm.application.workspace.overviewRead(String(params.applicationId)),
},
},
{
path: 'setting',
name: 'workspace-application-simple-setting',
component: () => import('@/views/application-detail/setting/SimpleSettingView.vue'),
meta: { title: '设置', icon: 'icon_setting', activeIcon: 'icon_setting_filled', order: 20 },
meta: {
title: '设置',
icon: 'icon_setting',
activeIcon: 'icon_setting_filled',
order: 20,
canAccess: (params) => params.type === APPLICATION_TYPE.SIMPLE && perm.application.workspace.edit(String(params.applicationId)),
},
},
],
},
Expand Down
Loading
Loading