diff --git a/src/api/publicService/docCenter.js b/src/api/publicService/docCenter.js index 645c017..b72dd7c 100644 --- a/src/api/publicService/docCenter.js +++ b/src/api/publicService/docCenter.js @@ -44,3 +44,74 @@ export function uploadFileTagAPI(data = {}) { data, }) } + +// 删除文档中心 +export function deleteDocCenterAPI(data = {}) { + return request({ + url: '/screen/document/delete', + method: 'POST', + data, + }) +} + +// 移动文档/文件 +export function moveDocCenterAPI(data = {}) { + return request({ + url: '/screen/document/move', + method: 'POST', + data, + }) +} + +// 复制文档/文件 +export function copyDocCenterAPI(data = {}) { + return request({ + url: '/screen/document/copy', + method: 'POST', + data, + }) +} + +// 共享-获取部门树 +export function getShareDeptTreeAPI() { + return request({ + url: '/system/user/deptTree', + method: 'GET', + }) +} + +// 共享-获取角色列表 +export function getShareRoleListAPI(params = { pageSize: 1000, pageNum: 1 }) { + return request({ + url: '/system/role/list', + method: 'GET', + params, + }) +} + +// 共享-根据部门获取人员列表 +export function getShareUserListAPI(params = {}) { + return request({ + url: '/system/user/list', + method: 'GET', + params, + }) +} + +// 共享-根据角色获取人员列表 +export function getShareUserListByRoleAPI(params = {}) { + return request({ + url: '/system/role/authUser/allocatedList', + method: 'GET', + params, + }) +} + +// 共享-提交授权 +export function saveSharePermissionAPI(data = {}) { + return request({ + url: '/screen/document/share', + method: 'POST', + data, + }) +} diff --git a/src/views/publicService/docCenter/components/rightTable.vue b/src/views/publicService/docCenter/components/rightTable.vue index afe6fa7..31ff690 100644 --- a/src/views/publicService/docCenter/components/rightTable.vue +++ b/src/views/publicService/docCenter/components/rightTable.vue @@ -84,33 +84,20 @@ > - @@ -230,7 +218,10 @@ import Move from './tableCom/move.vue' import AddCopy from './tableCom/addCopy.vue' import TagFilter from './tableCom/tagFilter.vue' -import { getDocCenterRightListAPI } from '@/api/publicService/docCenter' +import { + getDocCenterRightListAPI, + deleteDocCenterAPI, +} from '@/api/publicService/docCenter' export default { name: 'RightTable', props: { @@ -267,6 +258,7 @@ export default { searchValue: '', parentId: '', type: '', + labelIds: '', }, tableData: [], @@ -327,6 +319,7 @@ export default { outerVisible: false, outerWidth: '50%', outerComponent: null, + outerComponentProps: {}, }, // 用于下载的文件列表 selectedFilesForDownload: [], @@ -376,7 +369,7 @@ export default { // 获取类型标签样式 getTypeTagType(type) { - if (type === '文件夹') { + if (type == 0) { return 'warning' } else if (type === 'docx') { return 'primary' @@ -409,6 +402,7 @@ export default { this.dialogConfig.outerTitle = '新建文档夹' this.dialogConfig.outerVisible = true this.dialogConfig.outerComponent = 'AddWord' + this.dialogConfig.outerComponentProps = {} }, // 上传 @@ -417,6 +411,7 @@ export default { this.dialogConfig.outerTitle = '上传文件' this.dialogConfig.outerVisible = true this.dialogConfig.outerComponent = 'Upload' + this.dialogConfig.outerComponentProps = {} }, // 移动 @@ -425,6 +420,7 @@ export default { this.dialogConfig.outerTitle = '移动' this.dialogConfig.outerVisible = true this.dialogConfig.outerComponent = 'Move' + this.dialogConfig.outerComponentProps = {} }, // 删除 @@ -444,8 +440,20 @@ export default { type: 'warning', }, ) - .then(() => { - this.$modal.msgSuccess('删除功能待实现') + .then(async () => { + // this.$modal.msgSuccess('删除功能待实现') + + const res = await deleteDocCenterAPI({ + id: this.selectedRows.map((row) => row.id).join(','), + parentId: this.selectedNode?.id, + }) + + if (res.code === 200) { + this.$modal.msgSuccess('删除成功') + this.getTableList() + } else { + this.$modal.msgError(res.message) + } }) .catch(() => { this.$modal.msgInfo('已取消删除') @@ -481,6 +489,10 @@ export default { })) this.dialogConfig.outerTitle = '共享' this.dialogConfig.outerVisible = true + this.dialogConfig.outerComponent = 'SharePermissionForm' + this.dialogConfig.outerComponentProps = { + selectedFiles: this.selectedFilesForShare, + } }, // 添加副本 @@ -488,6 +500,8 @@ export default { // this.$emit('add-copy', this.selectedRows) this.dialogConfig.outerTitle = '添加副本' this.dialogConfig.outerVisible = true + this.dialogConfig.outerComponent = 'AddCopy' + this.dialogConfig.outerComponentProps = {} }, // 查看 @@ -539,7 +553,7 @@ export default { const res = await this.$refs.componentRef.submit() console.log(res, '新增结果') // this.$modal.msgSuccess('操作成功') - // this.dialogConfig.outerVisible = false + this.dialogConfig.outerVisible = false // 刷新列表 this.getTableList() @@ -577,16 +591,20 @@ export default { }, // 处理标签查询 - handleTagQuery(selectedTags) { - console.log('选中的标签:', selectedTags) - // 这里可以根据选中的标签进行数据筛选 - // this.$modal.msgSuccess('标签筛选功能待实现') + handleTagQuery(tagIds) { + this.queryParams.pageNum = 1 + this.queryParams.labelIds = Array.isArray(tagIds) + ? tagIds.join(',') + : '' + this.getTableList() this.tagFilterVisible = false }, // 处理标签重置 handleTagReset() { - console.log('重置标签筛选') + this.queryParams.labelIds = '' + this.queryParams.pageNum = 1 + this.getTableList() this.$modal.msgInfo('已重置标签筛选') }, diff --git a/src/views/publicService/docCenter/components/tableCom/TagSelector.vue b/src/views/publicService/docCenter/components/tableCom/TagSelector.vue index 0708d09..bba31bd 100644 --- a/src/views/publicService/docCenter/components/tableCom/TagSelector.vue +++ b/src/views/publicService/docCenter/components/tableCom/TagSelector.vue @@ -27,7 +27,7 @@
# {{ category.typeName }} #
@@ -124,13 +124,22 @@ export default { // 初始化选中的标签 initSelectedTags() { if (this.selectedTags && this.selectedTags.length > 0) { - this.selectedTagIds = this.selectedTags.map((tag) => { - if (typeof tag === 'object') { - // 使用 categoryName_labelName 作为唯一标识 - return tag.id || `${tag.typeName}_${tag.labelName}` - } - return tag - }) + this.selectedTagIds = this.selectedTags + .map((tag) => { + if (typeof tag === 'object') { + return ( + (tag.id || + tag.typeId || + tag.labelId || + tag.value || + tag.labelCode) ?? + '' + ) + } + return tag ?? '' + }) + .filter((id) => id !== '') + .map((id) => String(id)) } else { this.selectedTagIds = [] } @@ -150,21 +159,32 @@ export default { // 转换为分类数组格式 this.categories = Object.keys(tagsData) - .map((categoryName) => { + .map((categoryName, index) => { const tagList = tagsData[categoryName] || [] - // 从第一个标签获取分类的 typeId(同一分类下的标签 typeId 相同) - const categoryTypeId = - tagList.length > 0 ? tagList[0].typeId : null - return { - typeId: categoryTypeId, + key: `${categoryName}_${index}`, typeName: categoryName, - tags: tagList.map((tag) => ({ - id: `${categoryName}_${tag.labelName}`, - labelName: tag.labelName, - typeId: tag.typeId, - typeName: categoryName, - })), + tags: tagList + .map((tag) => { + const rawId = + tag.id ?? + tag.typeId ?? + tag.labelId ?? + tag.value ?? + tag.labelCode + if (!rawId) { + return null + } + return { + id: String(rawId), + labelName: + tag.labelName ?? tag.name ?? '', + typeId: tag.typeId ?? rawId, + typeName: categoryName, + raw: tag, + } + }) + .filter(Boolean), } }) .filter((category) => category.tags.length > 0) @@ -182,16 +202,17 @@ export default { // 判断标签是否被选中 isTagSelected(tagId) { - return this.selectedTagIds.includes(tagId) + return this.selectedTagIds.includes(String(tagId)) }, // 切换标签选中状态 toggleTag(tag) { - const index = this.selectedTagIds.indexOf(tag.id) + const tagId = String(tag.id) + const index = this.selectedTagIds.indexOf(tagId) if (index > -1) { this.selectedTagIds.splice(index, 1) } else { - this.selectedTagIds.push(tag.id) + this.selectedTagIds.push(tagId) } }, @@ -199,15 +220,15 @@ export default { getSelectedTags() { const selectedTags = [] const typeIdSet = new Set() // 用于收集去重后的 typeId - this.categories.forEach((category) => { category.tags.forEach((tag) => { - if (this.selectedTagIds.includes(tag.id)) { + if (this.selectedTagIds.includes(String(tag.id))) { selectedTags.push({ - id: tag.id, + id: String(tag.id), labelName: tag.labelName, typeId: tag.typeId, typeName: tag.typeName, + raw: tag.raw, }) // 收集 typeId if (tag.typeId) { @@ -217,9 +238,14 @@ export default { }) }) + const tagIds = selectedTags.map((tag) => tag.id) + const tagLabels = selectedTags.map((tag) => tag.labelName) + // 返回选中的标签和去重后的 typeId 数组 return { tags: selectedTags, + tagIds, + tagLabels, typeIds: Array.from(typeIdSet), } }, diff --git a/src/views/publicService/docCenter/components/tableCom/addCopy.vue b/src/views/publicService/docCenter/components/tableCom/addCopy.vue index 6398e03..a162e1c 100644 --- a/src/views/publicService/docCenter/components/tableCom/addCopy.vue +++ b/src/views/publicService/docCenter/components/tableCom/addCopy.vue @@ -1,9 +1,247 @@ - + diff --git a/src/views/publicService/docCenter/components/tableCom/move.vue b/src/views/publicService/docCenter/components/tableCom/move.vue index d749baa..152e302 100644 --- a/src/views/publicService/docCenter/components/tableCom/move.vue +++ b/src/views/publicService/docCenter/components/tableCom/move.vue @@ -1,9 +1,303 @@ - + diff --git a/src/views/publicService/docCenter/components/tableCom/share.vue b/src/views/publicService/docCenter/components/tableCom/share.vue index 3af6bec..26345a4 100644 --- a/src/views/publicService/docCenter/components/tableCom/share.vue +++ b/src/views/publicService/docCenter/components/tableCom/share.vue @@ -1,74 +1,220 @@ diff --git a/src/views/publicService/docCenter/components/tableCom/tagFilter.vue b/src/views/publicService/docCenter/components/tableCom/tagFilter.vue index 60c41f6..49dd3df 100644 --- a/src/views/publicService/docCenter/components/tableCom/tagFilter.vue +++ b/src/views/publicService/docCenter/components/tableCom/tagFilter.vue @@ -1,186 +1,177 @@ @@ -191,14 +182,29 @@ export default { background: #fff; min-height: 100%; box-sizing: border-box; + display: flex; + flex-direction: column; +} + +.search-container { + display: flex; + align-items: center; + gap: 8px; + margin-bottom: 16px; + + .search-input { + flex: 1; + } +} + +.tags-container { + flex: 1; + overflow-y: auto; + padding-right: 4px; } .filter-section { - margin-bottom: 24px; - - &:last-of-type { - margin-bottom: 32px; - } + margin-bottom: 20px; } .section-title { @@ -213,108 +219,94 @@ export default { display: flex; flex-wrap: wrap; gap: 8px; - margin-bottom: 8px; +} - .tag-button { - height: 32px; - padding: 0 16px; - border-radius: 16px; - border: 1px solid #dcdfe6; - background: #f5f7fa; - color: #606266; - font-size: 14px; - transition: all 0.3s; +.tag-button { + min-width: 80px; + height: 32px; + line-height: 32px; + border-radius: 16px; + border: 1px solid #dcdfe6; + background: #f5f7fa; + color: #606266; + font-size: 14px; + text-align: center; + padding: 0 16px; + cursor: pointer; + transition: all 0.3s; + user-select: none; - &:hover { - border-color: #409eff; - color: #409eff; - } - - &.active { - background: #409eff; - border-color: #409eff; - color: #fff; - } + &:hover { + border-color: #409eff; + color: #409eff; } + + &.active { + background: #409eff; + border-color: #409eff; + color: #fff; + } +} + +.load-status { + text-align: center; + color: #909399; + font-size: 12px; + padding: 12px 0 4px; } .action-buttons { display: flex; justify-content: center; gap: 16px; - margin-top: 24px; - padding-top: 20px; + margin-top: 16px; + padding-top: 16px; border-top: 1px solid #e4e7ed; - .query-button { + .query-button, + .reset-button { height: 36px; padding: 0 24px; border-radius: 18px; - background: #409eff; - border-color: #409eff; - color: #fff; - font-size: 14px; - font-weight: 500; display: flex; align-items: center; gap: 6px; + } + + .query-button { + background: #409eff; + border-color: #409eff; + color: #fff; &:hover { background: #66b1ff; border-color: #66b1ff; } - - i { - font-size: 14px; - } } .reset-button { - height: 36px; - padding: 0 24px; - border-radius: 18px; background: #f5f7fa; border-color: #dcdfe6; color: #606266; - font-size: 14px; - display: flex; - align-items: center; - gap: 6px; &:hover { background: #ecf5ff; border-color: #c6e2ff; color: #409eff; } - - i { - font-size: 14px; - } } } -// 响应式设计 @media (max-width: 768px) { .tag-filter-container { padding: 16px; } - .tag-buttons { - .tag-button { - height: 28px; - padding: 0 12px; - font-size: 12px; - } - } - - .action-buttons { - flex-direction: column; - align-items: center; - - .query-button, - .reset-button { - width: 120px; - } + .tag-button { + min-width: 70px; + height: 28px; + line-height: 28px; + font-size: 12px; } } diff --git a/src/views/publicService/docCenter/components/tableCom/upload.vue b/src/views/publicService/docCenter/components/tableCom/upload.vue index fad91f1..5a70e59 100644 --- a/src/views/publicService/docCenter/components/tableCom/upload.vue +++ b/src/views/publicService/docCenter/components/tableCom/upload.vue @@ -41,7 +41,6 @@ action="#" :auto-upload="false" :file-list="fileList" - :before-upload="handleBeforeUpload" :on-change="handleFileChange" :on-remove="handleRemove" :on-exceed="handleExceed" @@ -87,61 +86,45 @@ export default { TagSelector, }, props: { - visible: { - type: Boolean, - default: false, - }, selectedNode: { type: Object, - default: {}, + default: () => ({}), }, }, data() { return { - dialogVisible: false, duplicateHandle: '1', // 重复处理方式:1-跳过,2-覆盖 - selectedTag: '', // 选中的文件标签ID(兼容旧代码) selectedTags: [], // 选中的标签对象数组 + selectedTagIds: [], // 选中的标签ID数组 + selectedTagLabels: [], // 选中的标签名称数组 selectedTypeIds: [], // 选中的去重后的 typeId 数组 tagSelectorVisible: false, // 标签选择弹框显示状态 fileList: [], // 文件列表 uploading: false, // 上传状态 } }, - watch: { - visible: { - handler(val) { - this.dialogVisible = val - }, - immediate: true, - }, - }, computed: { // 选中的标签显示文本 selectedTagText() { - if (this.selectedTags.length === 0) { + if (this.selectedTagLabels.length === 0) { return '' } - return this.selectedTags.map((tag) => tag.labelName).join(',') + return this.selectedTagLabels.join(',') }, }, methods: { - // 关闭对话框 - handleClose() { - this.dialogVisible = false - this.$emit('update:visible', false) - this.resetForm() - }, - // 重置表单 resetForm() { this.duplicateHandle = '1' - this.selectedTag = '' this.selectedTags = [] + this.selectedTagIds = [] + this.selectedTagLabels = [] this.selectedTypeIds = [] this.fileList = [] this.uploading = false - this.$refs.upload && this.$refs.upload.clearFiles() + this.$nextTick(() => { + this.$refs.upload && this.$refs.upload.clearFiles() + }) }, // 打开标签选择弹框 @@ -153,38 +136,56 @@ export default { handleTagConfirm(result) { // result 格式: { tags: [], typeIds: [] } this.selectedTags = result?.tags || [] + this.selectedTagIds = + result?.tagIds || + this.selectedTags.map((tag) => String(tag.id ?? '')) + this.selectedTagLabels = + result?.tagLabels || + this.selectedTags.map((tag) => tag.labelName || '') this.selectedTypeIds = result?.typeIds || [] - // 兼容旧代码,取第一个标签的ID - if (this.selectedTags.length > 0) { - this.selectedTag = this.selectedTags[0].id - } else { - this.selectedTag = '' - } }, - // 上传前校验 - handleBeforeUpload(file) { - // 检查文件格式 - // const allowedTypes = ['rar', 'zip'] - // const fileExtension = file.name.split('.').pop().toLowerCase() + // 校验文件合法性 + validateFile(file, options = {}) { + const { showMessage = true } = options + const rawFile = file?.raw || file + if (!rawFile) { + if (showMessage) { + this.$modal.msgError('文件信息异常,请重新选择文件!') + } + return false + } - // if (!allowedTypes.includes(fileExtension)) { - // this.$modal.msgError('只支持上传rar/zip格式文件!') - // return false - // } + const fileName = rawFile.name || file.name || '' + const fileSize = rawFile.size || file.size || 0 + + // 检查文件格式 + const allowedTypes = ['rar', 'zip'] + const fileExtension = fileName.split('.').pop().toLowerCase() + + if (!allowedTypes.includes(fileExtension)) { + if (showMessage) { + this.$modal.msgError('只支持上传rar/zip格式文件!') + } + return false + } // 检查文件大小 (500kb = 0.5MB) const maxSize = 0.5 - const isLtMaxSize = file.size / 1024 / 1024 < maxSize + const isLtMaxSize = fileSize / 1024 / 1024 < maxSize if (!isLtMaxSize) { - this.$modal.msgError(`文件大小不能超过 ${maxSize}MB!`) + if (showMessage) { + this.$modal.msgError(`文件大小不能超过 ${maxSize}MB!`) + } return false } // 检查文件名是否包含特殊字符 - if (file.name.includes(',')) { - this.$modal.msgError('文件名不能包含英文逗号!') + if (fileName.includes(',')) { + if (showMessage) { + this.$modal.msgError('文件名不能包含英文逗号!') + } return false } @@ -193,6 +194,10 @@ export default { // 文件变化 handleFileChange(file, fileList) { + // if (!this.validateFile(file, { showMessage: true })) { + // this.fileList = fileList.filter((item) => item.uid !== file.uid) + // return + // } this.fileList = fileList }, @@ -215,14 +220,21 @@ export default { async handleConfirm() { if (this.fileList.length === 0) { this.$modal.msgWarning('请选择要上传的文件!') - return + throw new Error('表单验证失败') } if (this.selectedTags.length === 0) { this.$modal.msgWarning('请选择文件标签!') - return + throw new Error('表单验证失败') } + // const hasInvalidFile = this.fileList.some( + // (item) => !this.validateFile(item, { showMessage: true }), + // ) + // if (hasInvalidFile) { + // throw new Error('表单验证失败') + // } + this.uploading = true try { @@ -233,9 +245,12 @@ export default { folderId: this.selectedNode?.id, type: this.selectedNode?.type, repeatType: this.duplicateHandle, - parentId: this.selectedNode?.parentId, - labels: this.selectedTags.map((tag) => tag.id).join(','), - typeIds: this.selectedTypeIds.join(','), // 去重后的 typeId 数组,用逗号连接 + parentId: this.selectedNode?.id, + parentIds: this.selectedNode?.parentIds, + labelIds: this.selectedTagIds.join(','), // 标签ID + labels: this.selectedTagLabels.join(','), // 标签名称 + level: this.selectedNode?.level * 1 + 1, + // typeIds: this.selectedTypeIds.join(','), // 去重后的 typeId 数组,用逗号连接 } // 添加文件 @@ -250,7 +265,24 @@ export default { // 调用上传接口 const response = await uploadFileTagAPI(formData) - console.log(response, '上传结果') + this.$modal.msgSuccess('文件上传成功!') + + const payload = { + success: true, + response, + tagIds: [...this.selectedTagIds], + tagLabels: [...this.selectedTagLabels], + tags: this.selectedTags.map((tag) => ({ + id: String(tag.id ?? ''), + labelName: tag.labelName, + typeId: tag.typeId, + typeName: tag.typeName, + })), + } + + this.$emit('confirm', payload) + this.resetForm() + return payload } catch (error) { this.$modal.msgError('文件上传失败,请重试!') throw error