feat: 重塑技能库与统一文件工作台

- 统一分类检索、新建导入和发布交互

- 使用单一文件工作台编辑全部 Skill 资源

- 下沉可复用 Markdown 与代码编辑能力
This commit is contained in:
2026-08-14 18:58:20 +08:00
parent 77d66e1b42
commit 5de3b209c1
38 changed files with 2354 additions and 5810 deletions

View File

@@ -1,15 +1,11 @@
import type {
RequestResult,
SkillCapabilityBinding,
SkillCapabilityCandidate,
SkillCapabilityReplaceResult,
SkillCapabilityTools,
SkillCapabilityType,
SkillCategory,
SkillCategoryDraft,
SkillExportFormat,
SkillFileContent,
SkillFileNode,
SkillImportBatchResult,
SkillImportConfirmPayload,
SkillImportPreview,
SkillInfo,
SkillValidationResult,
@@ -17,7 +13,6 @@ import type {
import { api } from '#/api/request';
import { buildCapabilityBindingsPayload } from './skill-capability';
import { buildSkillCategoryPayload } from './skill-category';
import { buildSkillDraftPayload } from './skill-draft';
@@ -60,18 +55,14 @@ export function validateSkillForPublish(id: number | string) {
export function getSkillCategories() {
return api.get<RequestResult<SkillCategory[]>>(
'/api/v1/skill/category/visibleList',
{
params: { sortKey: 'sortNo', sortType: 'asc' },
},
{ params: { sortKey: 'sortNo', sortType: 'asc' } },
);
}
export function getSkillCategoryTree() {
return api.get<RequestResult<SkillCategory[]>>(
'/api/v1/skill/category/tree',
{
params: { sortKey: 'sortNo', sortType: 'asc' },
},
{ params: { sortKey: 'sortNo', sortType: 'asc' } },
);
}
@@ -93,10 +84,13 @@ export function deleteSkillCategory(id: number | string) {
return api.post<RequestResult<void>>('/api/v1/skill/category/remove', { id });
}
export function submitSkillPublishApproval(id: number | string) {
export function submitSkillPublishApproval(
id: number | string,
applicationReason: string,
) {
return api.post<RequestResult<null | number | string>>(
'/api/v1/skill/submitPublishApproval',
{ id },
{ applicationReason, id },
);
}
@@ -123,9 +117,7 @@ export function getSkillFileTree(skillId: number | string) {
export function getSkillFileContent(skillId: number | string, path: string) {
return api.get<RequestResult<SkillFileContent>>(
'/api/v1/skill/file/content',
{
params: { path, skillId },
},
{ params: { path, skillId } },
);
}
@@ -196,9 +188,8 @@ export function uploadSkillFile(
const formData = new FormData();
formData.append('skillId', String(skillId));
formData.append('path', path);
if (expectedContentHash) {
if (expectedContentHash)
formData.append('expectedContentHash', expectedContentHash);
}
formData.append('file', file);
return api.postFile<RequestResult<SkillFileContent>>(
'/api/v1/skill/file/upload',
@@ -218,71 +209,18 @@ export function previewSkillFile(skillId: number | string, path: string) {
});
}
export function getSkillCapabilityBindings(skillId: number | string) {
return api.get<RequestResult<SkillCapabilityBinding[]>>(
'/api/v1/skill/capability/list',
{
params: { skillId },
},
);
}
export function getSkillCapabilityCandidates(
type: SkillCapabilityType,
keyword = '',
) {
return api.get<RequestResult<SkillCapabilityCandidate[]>>(
'/api/v1/skill/capability/candidates',
{ params: { keyword, type } },
);
}
export function getSkillCapabilityTools(targetId: number | string) {
return api.get<RequestResult<SkillCapabilityTools>>(
'/api/v1/skill/capability/tools',
{
params: { targetId },
},
);
}
export function replaceSkillCapabilityBindings(
skillId: number | string,
bindings: SkillCapabilityBinding[],
expectedCapabilityHash: string,
) {
return api.post<RequestResult<SkillCapabilityReplaceResult>>(
'/api/v1/skill/capability/replace',
{
bindings: buildCapabilityBindingsPayload(bindings),
expectedCapabilityHash,
skillId,
},
);
}
export function importSkillPreview(file: File) {
export function importSkillPreviews(files: File[]) {
const formData = new FormData();
formData.append('file', file);
return api.postFile<RequestResult<SkillImportPreview>>(
files.forEach((file) => formData.append('files', file));
return api.postFile<RequestResult<SkillImportPreview[]>>(
'/api/v1/skill/import/preview',
formData,
);
}
export function importSkillConfirm(payload: {
capabilityMappings?: Array<{
bindingKey: string;
disabled?: boolean;
targetId?: number | string;
}>;
categoryId?: number | string;
conflictStrategy: 'OVERWRITE' | 'REJECT' | 'RENAME';
importToken: string;
renames?: Record<string, string>;
}) {
return api.post<RequestResult<SkillInfo[]>>(
'/api/v1/skill/import/confirm',
export function importSkillConfirmBatch(payload: SkillImportConfirmPayload[]) {
return api.post<RequestResult<SkillImportBatchResult[]>>(
'/api/v1/skill/import/confirmBatch',
payload,
);
}
@@ -293,12 +231,9 @@ export function cancelSkillImport(importToken: string) {
});
}
export function exportSkills(
ids: Array<number | string>,
format: SkillExportFormat,
) {
export function exportSkills(ids: Array<number | string>) {
return api.download<Blob>('/api/v1/skill/export', {
data: { format, ids },
data: { ids },
method: 'POST',
});
}