1、工具管理独立处理

2、文档资源管理调整:批量导出、文档资源管理关联附件独立处理
This commit is contained in:
pan 2024-09-05 21:23:42 +08:00
parent 2a933ea8cb
commit f7f98ee723
15 changed files with 1014 additions and 361 deletions

View File

@ -32,36 +32,42 @@
],
"dependencies": {
"@riophae/vue-treeselect": "0.4.0",
"@vue-office/docx": "1.6.1",
"@vue-office/pdf": "1.6.5",
"axios": "0.24.0",
"clipboard": "2.0.8",
"core-js": "3.37.1",
"docxtemplater": "3.50.0",
"docxtemplater-image-module-free": "1.1.1",
"echarts": "5.4.0",
"element-ui": "2.15.14",
"file-save": "0.2.0",
"file-saver": "2.0.5",
"fuse.js": "6.4.3",
"highlight.js": "9.18.5",
"js-base64": "^3.7.7",
"js-cookie": "3.0.1",
"jsencrypt": "3.0.0-rc.1",
"jszip": "3.10.1",
"jszip-utils": "0.1.0",
"nprogress": "0.2.0",
"pizzip": "3.1.7",
"quill": "1.3.7",
"screenfull": "5.0.2",
"sockjs-client": "^1.6.1",
"sortablejs": "1.10.2",
"v-viewer": "1.6.4",
"vue": "2.6.12",
"vue-count-to": "1.0.13",
"vue-cropper": "0.5.5",
"vue-demi": "^0.14.10",
"vue-iframe": "0.0.0",
"vue-json-viewer": "2.2.22",
"vue-meta": "2.4.0",
"vue-router": "3.4.9",
"vue-video-player": "5.0.1",
"vuex": "3.6.0",
"websocket": "^1.0.35",
"jszip": "3.10.1",
"jszip-utils": "0.1.0",
"file-save": "0.2.0",
"pizzip": "3.1.7",
"docxtemplater": "3.50.0",
"docxtemplater-image-module-free": "1.1.1"
"websocket": "^1.0.35"
},
"devDependencies": {
"@vue/cli-plugin-babel": "4.4.6",
@ -80,6 +86,7 @@
"sass-loader": "10.1.1",
"script-ext-html-webpack-plugin": "2.1.5",
"svg-sprite-loader": "5.1.1",
"@vue/composition-api": "1.7.2",
"vue-template-compiler": "2.6.12"
},
"engines": {

View File

@ -65,9 +65,9 @@ export function getStatistics(query) {
// 查询【请填写功能名称】列表
export function listAllDoc(query) {
export function getExportWordList(query) {
return request({
url: '/document/all/list',
url: '/document/export/word/list',
method: 'get',
params: query
})

View File

@ -74,7 +74,7 @@ export function getStatistics(query) {
export function exportWordList(query) {
return request({
url: '/tool/export/word/list',
method: 'get',
params: query
method: 'post',
data: query
})
}

View File

@ -339,7 +339,7 @@ export default {
const data = {
fileName: file.name,
fileSize: file.size,
fileUrl: res.data.filePath,
fileUrl: res.data.url,
filePath: res.data.filePath,
fileOldName: res.data.originalFilename,
fileNewName: res.data.newFileName,

View File

@ -0,0 +1,232 @@
<template>
<el-dialog
:close-on-click-modal="false"
title="预览文件"
:visible.sync="dialogVisible"
width="70%"
:destroy-on-close="true"
:append-to-body="true"
:close-on-press-escape="false"
@close="handleClose"
>
<template v-if="isTxt">
<!-- 在文本框中预览文件内容 -->
<el-input type="textarea" :rows="40" v-model="resultContentObj">
</el-input>
</template>
<template v-if="isDocx">
<vue-office-docx
:src="docxData"
style="height: 100vh;"
@rendered="rendered"
/>
</template>
<template v-if="isPdf">
<vue-office-pdf
:src="pdfFileData"
style="height: 100vh;"
@rendered="renderedHandler"
@error="errorHandler"
/>
</template>
<template v-if="isVideos">
<div class="input_video">
<video-player class="video-player vjs-custom-skin"
ref="videoPlayer"
:playsinline="true"
:options="playerOptions"
></video-player>
</div>
</template>
</el-dialog>
</template>
<script>
import axios from 'axios'
import {
getToken
} from "@/utils/auth";
import { videoPlayer } from "vue-video-player";
export default {
components: { videoPlayer},
props: {
uploadUrl: {
type: String,
required: false
},
//
isMultiple: {
type: Boolean,
default() {
return false
},
required: false
},
//
type: {
type: Array,
default() {
return []
},
required: false
},
//
acceptType: {
type: String,
required: false
},
//
limit: {
type: Number,
default() {
return 1
},
required: false
},
//
dataFile: {
type: [Object, Array, String],
default() {
return ''
},
required: false
},
isDetail: {
type: Boolean,
default: false
},
},
data() {
return {
// txt
dialogVisible:false,
isTxt:false,
resultContentObj:'',
// docx
isDocx:false,
docxData: null,
//pdf
isPdf:false,
pdfFileData: null, //
previewLoading:false,
previewUseFront: "txt,doc,docx,pdf",
isVideos:false,
//
playerOptions : {
playbackRates : [ 0.5, 1.0, 1.5, 2.0 ], //
autoplay : false, //true,
muted : false, //
loop : false, //
preload : 'auto', // <video>auto,
language : 'zh-CN',
aspectRatio : '16:9', // 使 - "16:9""4:3"
fluid : true, // trueVideo.js player
sources : [],
poster : "", //
// width: document.documentElement.clientWidth,
notSupportedMessage : '此视频暂无法播放,请稍后再试', //Video.js
controlBar : {
timeDivider : true,//
durationDisplay : true,//
remainingTimeDisplay : false,//
fullscreenToggle : true //
}
}
};
},
watch: {
},
methods: {
//
frontModulePreview(row){
let self = this
self.initPreviewData()
console.info("row=================", row)
self.previewLoading = true
if(row.fileName.endsWith(".jpg") || row.fileName.endsWith(".png")){
this.$viewerApi({images: [row.fileUrl]})
self.previewLoading = false
return
}
if(row.fileName.endsWith(".mp4")){
this.playerOptions.sources = [
{
src: row.fileUrl,
type: 'video/mp4'
}
]
self.dialogVisible = true
self.isVideos = true;
self.previewLoading = false
return
}
axios({
method: 'post',
url: process.env.VUE_APP_BASE_API + "/common/preview/download",
responseType: 'blob',
data: {
'filePath': row.filePath,
'fileOldName': row.fileOldName
},
headers: { 'Authorization': 'Bearer ' + getToken() }
}).then(res => {
const content = res.data;
if(row.fileName.endsWith(".txt")){
self.dialogVisible = true
self.previewLoading = false
let blob = new Blob([res.data]);
blob.text().then(data =>{
self.resultContentObj = data;
self.isTxt = true;
self.previewLoading = false; //
})
// self.previewLoading = false
}else if (row.fileName.endsWith(".docx")) {
// renderAsync(response.data, self.$refs.file);
self.isDocx = true
self.dialogVisible = true; //
content.arrayBuffer().then(res=>{
self.docxData = res
})
self.previewLoading = false
}else if(row.fileName.endsWith(".doc") || row.fileName.endsWith(".pdf")){
self.isPdf = true
self.dialogVisible = true; //
content.arrayBuffer().then(res=>{
self.pdfFileData = res
})
self.previewLoading = false
}
}).catch(err => {
console.info("err===============", err)
self.previewLoading = false
});
},
//
initPreviewData(){
this.isTxt = false
this.isDocx = false
this.isPdf = false
this.resultcontentObj = ''
this.docxData = null
this.pdfFileData = null
},
rendered(){
console.log("渲染完成1")
},
renderedHandler(){
console.log("pdf渲染完成2")
},
errorHandler(){
console.log("pdf渲染失败3")
},
handleClose(){
this.$emit("previewClose");
}
}
};
</script>

View File

@ -6,6 +6,9 @@
:width="width || '900px'"
:height="height || '650px'"
:before-close="handleClose"
:show-close="false"
:close-on-press-escape="false"
:close-on-click-modal="false"
append-to-body
>
@ -230,11 +233,7 @@
},
methods: {
handleClose(done) {
this.$confirm('确认关闭?')
.then(_ => {
this.cancel();
})
.catch(_ => {});
this.cancel();
},
handleClick(tab, event) {
console.log(tab, event);

View File

@ -42,6 +42,15 @@ import DictData from '@/components/DictData'
// 图形监控组件
import MonitorDrawer from "@/components/MonitorDrawer"
//引入VueOfficeDocx组件
import VueOfficeDocx from '@vue-office/docx'
//引入相关样式
import '@vue-office/docx/lib/index.css'
import VueOfficePdf from '@vue-office/pdf'
//视频组件
import 'video.js/dist/video-js.css'
import 'vue-video-player/src/custom-theme.css'
// 全局方法挂载
Vue.prototype.getDicts = getDicts
Vue.prototype.getConfigKey = getConfigKey
@ -52,6 +61,9 @@ Vue.prototype.selectDictLabel = selectDictLabel
Vue.prototype.selectDictLabels = selectDictLabels
Vue.prototype.download = download
Vue.prototype.handleTree = handleTree
import 'viewerjs/dist/viewer.css'
import Viewer from 'v-viewer'
// 全局组件挂载
Vue.component('DictTag', DictTag)
@ -62,7 +74,14 @@ Vue.component('FileUpload', FileUpload)
Vue.component('ImageUpload', ImageUpload)
Vue.component('ImagePreview', ImagePreview)
Vue.component('MonitorDrawer', MonitorDrawer)
Vue.component('VueOfficeDocx', VueOfficeDocx)
Vue.component('VueOfficePdf', VueOfficePdf)
Vue.use(Viewer, {
defaultOptions: {
zIndex: 9999
}
})
Vue.use(directive)
Vue.use(plugins)
Vue.use(VueMeta)

View File

@ -0,0 +1,148 @@
<template>
<div class="fbox1">
<div class="fl">
<el-tabs v-model="detailActiveName">
<el-tab-pane label="附件信息" name="first">
<el-table :data="attachmentList" style="width: 100%">
<el-table-column label="附件名称" prop="fileName" :show-overflow-tooltip="true" />
<el-table-column label="创建时间" align="center" prop="createTime" width="180">
<template slot-scope="scope">
<span>{{ parseTime(scope.row.createDate) }}</span>
</template>
</el-table-column>
<el-table-column label="操作" align="center" width="180" v-if="docDetail.downloadStatus">
<template slot-scope="scope">
<el-button
size="mini"
type="text"
icon="el-icon-view"
@click="handlePreview(scope.row)"
>预览</el-button>
<el-button type="text" icon="el-icon-download" @click="handleDownload(scope.row)" v-loading="loadingDownload">下载</el-button>
</template>
</el-table-column>
</el-table><!--el-table-->
</el-tab-pane><!--el-tab-pane-->
</el-tabs><!--el-tabs-->
</div><!--fl 左侧页签-->
<preview-util v-if="isPreviewDisable" ref="previewForm" @previewClose="previewClose"></preview-util>
</div><!--fbox1 左右分栏-->
</template>
<script>
import { listAttachment } from "@/api/attachment/attachment";
import previewUtil from '@/components/PreviewUtil/previewUtil.vue'
import { addCount } from "@/api/tool/downloadCount";
export default {
name: 'docDetailFile',
components: { previewUtil},
dicts:[],
props: {
docDetail: {
type: Object,
default: {},
}
},
data(){
return{
detailActiveName: 'first',
attachmentList: [],
queryParams: {
pageNum: 1,
pageSize: 10,
docId: ''
},
previewUrl: '',
viewDialogTitle: "",
viewDialogOpen: false,
open: false,
loadingDownload: false,
discussionContent: null, //
repliesContent: null, //
//
discussionsList: [],
//
repliesList: [],
showReplyForm: [],
replyContent: [],
isPreviewDisable: false,
attFileType: "zip,rar,7z",
}
},
created(){
this.getAttachmentList()
},
methods:{
getAttachmentList() {
this.loading = true;
this.$set(this.queryParams,'del',"0")
this.$set(this.queryParams,'businessId',this.docDetail.docId)
listAttachment(this.queryParams).then(response => {
this.attachmentList = response.rows;
this.total = response.total;
this.loading = false;
}
);
},
handlePreview(row){
this.isPreviewDisable = true
this.$nextTick(() => {
this.$refs.previewForm.frontModulePreview(row)
})
},
/** 关闭预览 **/
previewClose(){
this.isPreviewDisable = false
},
previewAuth(row){
if(row.fileUrl == null || row.fileUrl == '' || row.fileUrl == undefined){
return false
}
let extension = this.getExtension(row.fileUrl);
const acceptedExtensions = this.attFileType.toLowerCase().split(',');
if(acceptedExtensions.includes(extension)){
return false
}
return true
},
getExtension(filePath) {
// '.'
const parts = filePath.split('.');
//
const extension = parts.pop();
return extension;
},
/**
* 处理下载
* **/
handleDownload(row){
let self = this
self.loadingDownload = true
this.$download.resource(row.fileUrl);
//
if(row.businessId){
let formData = {
'businessId': row.businessId,
'businessType': 'doc',
'attId': row.id,
'attName': row.fileOldName
}
addCount(formData).then(res => {
});
}
setTimeout(()=>{
self.loadingDownload = false
},1000)
},
}
}
</script>
<style scoped>
</style>

View File

@ -57,7 +57,23 @@
<!-- <el-input v-model="form.docSource" placeholder="请输入文档来源" maxlength="50" show-word-limit/>-->
</el-form-item>
</el-col>
<el-col :span="24" v-if="relatedTool">
<el-col :span="24">
<el-form-item label="负责人" prop="docPrincipals">
<template v-if="detailBoolean">{{form.docPrincipalsName}}</template>
<template v-else>
<el-input v-model="form.docPrincipalsName" placeholder="请选择负责人" maxlength="11" @focus="toolPrincipalsChoose = true"/>
<!-- <el-input v-model="form.docPrincipals" placeholder="请输入负责人" maxlength="50" show-word-limit/>-->
</template>
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="归属单位" prop="docRespDept">
{{userInfo.dept.deptName}}
<!-- <treeselect v-model="form.docRespDept" :options="deptOptions" :show-count="true"
:disabled="detailBoolean" placeholder="请输入归属单位"/>-->
</el-form-item>
</el-col>
<!-- <el-col :span="24" v-if="relatedTool">
<el-form-item label="关联工具" prop="toolId">
<el-select
v-model="toolDataInfo"
@ -78,22 +94,9 @@
</el-select>
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="负责人" prop="docPrincipals">
<template v-if="detailBoolean">{{form.docPrincipals}}</template>
<template v-else>
<el-input v-model="form.docPrincipals" placeholder="请输入负责人" maxlength="50" show-word-limit/>
</template>
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="归属单位" prop="docRespDept">
<treeselect v-model="form.docRespDept" :options="deptOptions" :show-count="true"
:disabled="detailBoolean" placeholder="请输入归属单位"/>
</el-form-item>
</el-col>
<el-col :span="24">
</el-col>-->
<!-- <el-col :span="24">
<el-form-item label="文件" required>
<uploadVue
:display="editStatus"
@ -108,7 +111,7 @@
@handleError="handleUploadError"
/>
</el-form-item>
</el-col>
</el-col>-->
<el-col :span="24">
<el-form-item label="备注" prop="remark">
<template v-if="detailBoolean">{{form.remark}}</template>
@ -120,6 +123,58 @@
</el-row>
</el-form><!--el-form-->
</div>
<div class="divide double"></div><!--divide 分隔-->
<div class="tboper">
<div class="tit">关联附件</div>
</div>
<div class="el-form-border">
<div class="operate">
<!-- <el-form-item label="文件" required>
</el-form-item>
<el-button type="primary" icon="el-icon-upload2" v-if="editStatus" @click="handleDocAdd">上传</el-button>-->
<template v-if="editStatus && !detailBoolean">
<uploadVue
:display="editStatus"
:uploadUrl="uploadFileUrl"
:type="['.txt','.doc','.docx','.pdf','.mp4','.zip','.rar','.7z','.png','.jpg','.jpeg']"
:acceptType="acceptType"
:isMultiple="true"
:dataFile="dataFile"
:isDetail="detailBoolean"
ref="uploadFile"
@handleSuccess="handleUploadSuccess"
@handleError="handleUploadError"
/>
</template>
<!-- <el-button icon="el-icon-delete">删除</el-button>-->
</div><!--operate 操作按钮-->
<el-table :data="attachmentList" style="width: 100%">
<!-- <el-table-column type="selection" width="50" align="center"> </el-table-column>-->
<el-table-column label="序号" width="60" type="index"></el-table-column>
<el-table-column label="附件名称" prop="fileName" :show-overflow-tooltip="true" />
<el-table-column label="操作" align="center" width="180">
<template slot-scope="scope" v-if="scope.row.roleId !== 1">
<el-button
size="mini"
type="text"
icon="el-icon-view"
v-if="previewAuth(scope.row)"
@click="handlePreview(scope.row)"
>预览</el-button>
<el-button
size="mini"
type="text"
icon="el-icon-delete"
v-if="editStatus && !detailBoolean"
@click="handleDelete(scope.row)"
>删除</el-button>
<el-button type="text" icon="el-icon-download" v-if="isShowOperation(scope.row)" @click="handleDownload(scope.row)" v-loading="loadingDownload">下载</el-button>
</template>
</el-table-column>
</el-table><!--el-table-->
</div>
</div><!--fl 左侧页签-->
<div class="fr" v-if="detailBoolean">
@ -174,27 +229,33 @@
</template>
</div>
</div>
<preview-util v-if="isPreviewDisable" ref="previewForm" @previewClose="previewClose"></preview-util>
<tool-selector ref="toolSelect" @selectHandle="selectHandle"></tool-selector>
<bl-user-selector ref="peopleSelect" :type="'single'" :isCheck="true" :open="toolPrincipalsChoose" :deptFilter="true" @cancel="toolPrincipalsChoose=false" @submit="submitPeople"></bl-user-selector>
</div><!--el-form-border 表单-->
</template>
<script>
import { addDocument, updateDocument, getDocument } from "@/api/document/document";
import axios from 'axios';
import { getToken } from '@/utils/auth'
import { deptTreeSelect } from "@/api/system/user";
import { documentTree } from "@/api/documentCategory/documentCategory.js";
import Treeselect from "@riophae/vue-treeselect";
import uploadProgress from "./uploadProgress";
import uploadVue from '@/components/FileUpload/optimizeUpload.vue'
import uploadVue from '@/components/FileUpload/optimizeToolUpload.vue'
import ToolSelector from '@/components/tool-selector/index.vue'
import { listDiscussions, addDiscussions } from "@/api/tool/discussions.js";
import { listReplies, addReplies} from "@/api/tool/replies.js";
import previewUtil from '@/components/PreviewUtil/previewUtil.vue'
import blUserSelector from '@/components/user-selector/src/user-selector.vue'
import { listAttachment } from "@/api/attachment/attachment";
import { addCount } from "@/api/tool/downloadCount";
export default {
name: 'editDocument',
components: { Treeselect, uploadProgress, uploadVue, ToolSelector},
components: { Treeselect, uploadProgress, uploadVue, ToolSelector, previewUtil, blUserSelector},
dicts:['doc_class','doc_source'],
props: {
tooId: {
@ -235,11 +296,12 @@
docCode: '',
docName: '',
docType: '',
docPrincipals: '',
docRespDept: undefined,
docPrincipals: null,
docPrincipalsName: null,
docRespDept: this.$store.getters.userInfo.deptId,
docSource: '',
toolId: '',
remark: undefined
remark: undefined,
},
fileList: [],
progress: 0,
@ -259,7 +321,13 @@
],
docSource: [
{ required: true, message: "文档来源不能为空", trigger: "blur" }
]
],
docPrincipals: [
{ required: true, message: "负责人不能为空", trigger: ['change','blur'] }
],
docRespDept: [
{ required: true, message: "请选择归属部门", trigger: ['blur','change'] }
],
},
docCategory:[],
deptOptions:[],
@ -281,6 +349,17 @@
showReplyForm: [],
replyContent: [],
detailLoading: false,
attachmentList: [],
attFileType: "zip,rar,7z",
isPreviewDisable: false,
loadingDownload: false,
userInfo: this.$store.getters.userInfo,
toolPrincipalsChoose: false,
docQueryParams: {
pageNum: 1,
pageSize: 10,
},
}
},
created(){
@ -336,47 +415,61 @@
},
/** 提交按钮 */
submitForm: function() {
let self = this
let fileName = []
//
if(this.form.docId && (this.fileList == null || this.fileList.length <= 0 )){
fileName = this.$refs.uploadFile.fileList[0]
this.fileList = this.$refs.uploadFile.fileList
/* if(self.form.docId && (self.fileList == null || self.fileList.length <= 0 )){
fileName = self.$refs.uploadFile.fileList[0]
self.fileList = self.$refs.uploadFile.fileList
}else{
fileName = this.fileList[0]
this.fileList = this.fileList
}
fileName = self.fileList[0]
self.fileList = self.fileList
} */
//
if (this.fileList.length == 0) {
return this.$message.warning('请选取文件后再上传')
if (self.attachmentList.length <= 0) {
return self.$message.warning('最少上传一个附件')
}
/*this.fileList.map(file =>{
this.form.docName = file.name
})*/
if(fileName){
this.$set(this.form,"docUrl", fileName.filePath)
this.$set(this.form,"docStatus", "ysc")
this.$set(this.form,"attachment", fileName)
}
if(this.toolDataInfo && this.toolDataInfo.length > 0){
this.$set(this.form,"toolId", this.toolDataInfo[0].toolId)
/* if(fileName){
self.$set(self.form,"docUrl", fileName.filePath)
self.$set(self.form,"docStatus", "ysc")
} */
self.$set(self.form,"docStatus", "ysc")
if(self.toolDataInfo && self.toolDataInfo.length > 0){
self.$set(self.form,"toolId", self.toolDataInfo[0].toolId)
}
self.$set(self.form,'attachmentList',self.attachmentList)
this.$refs["form"].validate(valid => {
self.$refs["form"].validate(valid => {
if (valid) {
if (this.form.docId) {
updateDocument(this.form).then(res => {
this.$modal.msgSuccess("修改成功");
this.open = false;
this.$emit("submit");
});
} else {
addDocument(this.form).then(res => {
this.$modal.msgSuccess("新增成功");
this.open = false;
// this.confirmSubmit(response.data);
this.$emit("submit");
});
let tipName = '';
if (self.form.docId){
tipName = '更新'
}else{
tipName = '保存'
}
this.$modal.confirm('是否确认' + tipName+ '').then(() => {
if (self.form.docId) {
updateDocument(self.form).then(res => {
self.$modal.msgSuccess("修改成功");
self.open = false;
self.$emit("submit");
});
} else {
addDocument(self.form).then(res => {
self.$modal.msgSuccess("新增成功");
self.open = false;
// self.confirmSubmit(response.data);
self.$emit("submit");
});
}
}).catch((err) => {
console.error(err)
});
}
});
},
@ -442,14 +535,6 @@
getError(message) {
this.$message.error(message);
},
handleUploadSuccess(res) {
this.fileList = []
this.fileList.push(res)
//
},
handleUploadError(error) {
//
},
toolSelect(){
this.$refs.selectHeadTool.blur();
this.$nextTick(()=>{
@ -463,23 +548,32 @@
},
/**初始化 **/
resetForm() {
let self = this
self.form.docPrincipalsName = null
this.$refs.form.resetFields();
this.toolDataInfo = []
this.fileList = []
this.attachmentList = []
this.detailBoolean = false
this.setAllRequiredTrue(true)
this.$nextTick(()=>{
this.$refs.uploadFile.clearFile();
if(self.$refs.uploadFile){
self.$refs.uploadFile.clearFile();
}
})
},
editInit(docId, type){
let self = this
if(type == "detail"){
this.detailBoolean = true
self.setAllRequiredTrue(false)
}
self.$refs.form.resetFields();
self.toolDataInfo = []
self.$nextTick(()=>{
self.$refs.uploadFile.clearFile();
if(self.$refs.uploadFile){
self.$refs.uploadFile.clearFile();
}
getDocument(docId).then(res => {
self.form = res.data
@ -488,12 +582,12 @@
self.toolDataInfo.push(toolInfo)
self.dataFile = []
let fileData = res.data.attachment
/* let fileData = res.data.attachment
self.$set(fileData, "name", fileData.fileOldName)
self.$set(fileData, "size", fileData.fileSize)
self.dataFile.push(fileData)
self.dataFile.push(fileData) */
self.getDiscussionsList()
self.getAttachemntList()
});
})
},
@ -521,7 +615,7 @@
type:'success',  //
duration:1200,  //, 0 1200
});
self.getDiscussionsList()
self.getAttachemntList()
}).catch(err =>{
this.discussionContent = null
console.error("handleDiscussions==err==", err)
@ -529,19 +623,14 @@
});
})
},
getDiscussionsList() {
getAttachemntList() {
let self = this
listDiscussions({businessId:this.form.docId}).then(res => {
self.discussionsList = res.rows
self.discussionsList.forEach(item => {
if(item.repliesList && item.repliesList.length > 0){
self.$set(item, 'showReplyFormSon', new Array(item.repliesList.length).fill(false))
self.$set(item, 'replyContentSon', new Array(item.repliesList.length).fill(''))
}else{
self.$set(item, 'showReplyFormSon', false)
self.$set(item, 'replyContentSon', '')
}
});
this.$set(this.docQueryParams,'del',"0")
this.$set(this.docQueryParams,'businessId',this.form.docId)
listAttachment({businessId:this.form.docId}).then(res => {
self.attachmentList = res.rows;
self.total = res.total;
self.loading = false;
});
},
getFirstChar(value) {
@ -593,7 +682,7 @@
duration:1200,  //, 0 1200
});
self.cancelReplySon(parentIndex, repIndex)
self.getDiscussionsList()
self.getAttachemntList()
}).catch(err =>{
console.error("submitReplySon==err==", err)
self.$modal.msgError("发布失败");
@ -629,7 +718,7 @@
duration:1200,  //, 0 1200
});
self.cancelReply(index)
self.getDiscussionsList()
self.getAttachemntList()
}).catch(err =>{
console.error("handleDiscussions==err==", err)
self.$modal.msgError("发布失败");
@ -640,6 +729,91 @@
this.replyContent[index] = '';
this.showReplyForm[index] = false;
},
previewAuth(row){
if(row.fileUrl == null || row.fileUrl == '' || row.fileUrl == undefined){
return false
}
let extension = this.getExtension(row.fileUrl);
const acceptedExtensions = this.attFileType.toLowerCase().split(',');
if(acceptedExtensions.includes(extension)){
return false
}
return true
},
getExtension(filePath) {
// '.'
const parts = filePath.split('.');
//
const extension = parts.pop();
return extension;
},
handlePreview(row){
this.isPreviewDisable = true
this.$nextTick(() => {
this.$refs.previewForm.frontModulePreview(row)
})
},
/** 关闭预览 **/
previewClose(){
this.isPreviewDisable = false
},
/**
* 处理下载
* **/
handleDownload(row){
let self = this
self.loadingDownload = true
this.$download.resource(row.fileUrl);
//
if(row.businessId){
let formData = {
'businessId': row.businessId,
'businessType': 'doc',
'attId': row.id,
'attName': row.fileOldName
}
addCount(formData).then(res => {
});
}
setTimeout(()=>{
self.loadingDownload = false
},1000)
},
handleDelete(row){
this.attachmentList.splice(row,1)
},
handleBeforeClose() {
this.viewDialogOpen = false
},
handleUploadSuccess(res) {
this.attachmentList.push(res)
//
},
handleUploadError(error) {
//
},
isShowOperation(row){
let self = this
if(row.businessId == null || row.businessId == undefined || row.businessId == ''){
return false
}
return true
},
submitPeople(peopleList){
this.$set(this.form,'docPrincipals',peopleList[0]['userId'])
this.$set(this.form,'docPrincipalsName',peopleList[0]['nickName'])
this.toolPrincipalsChoose = false;
},
setAllRequiredTrue(value) {
Object.keys(this.rules).forEach(key => {
this.rules[key].forEach(rule => {
rule.required = value;
});
});
}
}
}
</script>

View File

@ -115,10 +115,12 @@
<el-button type="primary" icon="el-icon-position" @click="handlePush" v-hasPermi="['document:push']">发布</el-button>
<el-button icon="el-icon-delete" @click="handleDelete" v-hasPermi="['document:batch:remove']">批量删除</el-button>
<el-button icon="el-icon-download" @click="handleOpenExport()" v-hasPermi="['document:export']">导出</el-button>
<el-button icon="el-icon-download" @click="handleOpenBatchExport()" v-hasPermi="['document:batch:export']">批量导出</el-button>
</div><!--operate 操作按钮-->
<el-table v-loading="loading" :data="docList" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="55" align="center" :selectable="isSelectable"/>
<el-table-column type="selection" width="55" align="center" />
<el-table-column label="文档编号" align="center" prop="docCode" width="120" />
<el-table-column label="文档名称" align="center" prop="docName" :show-overflow-tooltip="true" />
<el-table-column label="文档类别" align="center" prop="docType" :show-overflow-tooltip="true" width="80">
@ -126,14 +128,14 @@
<dict-tag :options="dict.type.doc_class" :value="scope.row.docType"/>
</template>
</el-table-column>·
<el-table-column label="负责人" align="center" prop="docPrincipals" :show-overflow-tooltip="true" width="80" />
<el-table-column label="负责人" align="center" prop="docPrincipalsName" :show-overflow-tooltip="true" width="100" />
<el-table-column label="归属单位" align="center" prop="docRespDeptName" :show-overflow-tooltip="true" width="80" />
<el-table-column label="文档来源" align="center" prop="docSource" width="100">
<template slot-scope="scope">
<dict-tag :options="dict.type.doc_source" :value="scope.row.docSource"/>
</template>
</el-table-column>
<el-table-column label="关联工具" align="center" prop="toolName" width="100" />
<!-- <el-table-column label="关联工具" align="center" prop="toolName" width="100" />-->
<el-table-column label="文档状态" align="center" prop="docStatus" width="100" >
<template slot-scope="scope">
<dict-tag :options="dict.type.doc_upload_status" :value="scope.row.docStatus"/>
@ -153,14 +155,14 @@
</el-table-column>
<el-table-column label="操作" align="center" width="180" fixed="right">
<template slot-scope="scope">
<el-button
<!-- <el-button
size="mini"
type="text"
icon="el-icon-view"
v-if="previewAuth(scope.row)"
@click="handlePreview(scope.row)"
v-hasPermi="['document:preview']"
>预览</el-button>
>预览</el-button>-->
<el-button type="text" icon="el-icon-download" @click="handleDownload(scope.row)"
v-if="scope.row.downloadStatus"
v-loading="loadingDownload">下载</el-button>
@ -226,24 +228,27 @@
</span>
</el-dialog>
<el-dialog :title="viewDialogTitle" :visible.sync="viewDialogOpen" fullscreen width="500px" append-to-body :before-close="handleBeforeClose">
<i-frame :src="previewUrl" v-if="viewDialogOpen"/>
</el-dialog>
<el-drawer :visible.sync="open" :modal-append-to-body="false" size="75%" :show-close="false">
<el-drawer :visible.sync="open"
:modal-append-to-body="false" :show-close="false" :close-on-press-escape="false"
size="75%">
<template #title>
<span class="title">{{docTitle}}</span>
<div class="drawer-head-btn" v-if="docDetailDisable">
<el-button type="primary" @click="$refs.editDocumentRef.submitForm()"> </el-button>
<el-button type="primary" @click="docConfrim()"> </el-button>
<el-button @click="docCancel()"> </el-button>
</div><!--drawer-head-btn 抽屉顶部按钮区域-->
<div class="drawer-head-btn" v-else>
<el-button @click="docCancel()"> </el-button>
</div><!--drawer-head-btn 抽屉顶部按钮区域-->
</template>
<edit-document ref="editDocumentRef" @submit="editDocumentSubmit"/>
</el-drawer>
<!-- 工具导出对话框 -->
<el-dialog title="导出" :visible.sync="exportDrawerOpen" width="980px" append-to-body>
<el-dialog :title="exportTitle" :visible.sync="exportDrawerOpen"
:modal-append-to-body="false" :show-close="false" :close-on-press-escape="false"
width="980px" append-to-body>
<div class="el-form-border">
<el-form ref="exportFrom" label-width="180px">
<el-row>
@ -269,8 +274,7 @@
<el-checkbox label="docPrincipals">负责人</el-checkbox>
<el-checkbox label="docRespDeptName">归属单位</el-checkbox>
<el-checkbox label="docSource">文档来源</el-checkbox>
<el-checkbox label="toolName">关联工具</el-checkbox>
<el-checkbox label="docStatus">上传状态</el-checkbox>
<el-checkbox label="docStatus">文档状态</el-checkbox>
<el-checkbox label="createTime">创建时间</el-checkbox>
</el-checkbox-group>
</el-form-item>
@ -284,27 +288,38 @@
</span>
</el-dialog>
<!-- 工具详情对话框 -->
<el-drawer :visible.sync="fileDetailDrawerOpen"
:modal-append-to-body="false" :show-close="false" :close-on-press-escape="false"
size="80%" class="no-padding" @close="handleFileCloseDetail()">
<template #title>
<span>文档附件下载</span>
<div class="drawer-head-btn">
<el-button @click="fileDetailDrawerOpen = false"> </el-button>
</div><!--drawer-head-btn 抽屉顶部按钮区域-->
</template>
<template v-if="fileDetailOpen">
<download-file-detail ref="downloadFileDetailRef" :docDetail="docDetail"/>
</template>
</el-drawer><!--el-drawer 详情-抽屉-->
<!-- <upload-progress/>-->
</div>
</template>
<script>
import { listDocument, getDocument, delDocument, addDocument, updateDocument,pushDoc, listAllDoc} from "@/api/document/document";
import { listDocument, getDocument, delDocument, addDocument, updateDocument,pushDoc, getExportWordList} from "@/api/document/document";
import { deptTreeSelect } from "@/api/system/user";
import { documentTree,addCategory,updateCategory,delCategory,getCategory } from "@/api/documentCategory/documentCategory.js";
import { Base64 } from 'js-base64';
import iFrame from "@/components/iFrame/index"
import editDocument from "./editDocument";
import uploadProgress from "./uploadProgress";
import { w3cwebsocket as WebSocket } from 'websocket';
import Treeselect from "@riophae/vue-treeselect";
import { addCount } from "@/api/tool/downloadCount";
import { exportDocx } from '@/utils/docUtil/docutil.js';
import downloadFileDetail from "./downloadFileDetail.vue";
export default {
name: "Document",
components: { iFrame, editDocument, uploadProgress, Treeselect},
components: { editDocument, uploadProgress, Treeselect, downloadFileDetail},
dicts:['doc_class','doc_source','doc_upload_status'],
data() {
return {
@ -404,7 +419,7 @@ export default {
loadingDownload: false,
acceptType: "zip,rar,7z",
//
columnList: ['docCode', 'docName', 'docType', 'docPrincipals', 'docRespDeptName', 'docSource', 'toolName', 'docStatus', 'createTime'],
columnList: ['docCode', 'docName', 'docType', 'docPrincipals', 'docRespDeptName', 'docSource', 'docStatus', 'createTime'],
checkList: [],
exportDrawerOpen: false,
docTitle: '',
@ -422,6 +437,16 @@ export default {
label: 'word'
}
],
docTipAddOrEdit: null,
//
fileDetailDrawerOpen: false,
fileDetailOpen: false,
toolDetail: {},
//
exportTitle:'',
batchExportFlag: false,
//
selection: undefined,
};
},
created() {
@ -481,6 +506,7 @@ export default {
/** 新增按钮操作 */
handleAdd() {
this.docTitle="新增文档资源"
this.docTipAddOrEdit = 'add'
this.docDetailDisable=true
this.open = true
this.$nextTick(()=>{
@ -489,6 +515,7 @@ export default {
},
handleEdit(row){
this.docTitle="编辑文档资源"
this.docTipAddOrEdit = 'edit'
this.docDetailDisable=true
this.open = true
this.$nextTick(()=>{
@ -497,6 +524,7 @@ export default {
},
handleDetail(row){
this.docTitle="详情"
this.docTipAddOrEdit = 'detail'
this.docDetailDisable=false
this.open = true
this.$nextTick(()=>{
@ -513,6 +541,7 @@ export default {
},
//
handleSelectionChange(selection) {
this.selection=selection
this.ids = selection.map(item => item.docId)
this.single = selection.length!=1
this.multiple = !selection.length
@ -523,11 +552,24 @@ export default {
},
/** 删除按钮操作 */
handleDelete(row) {
let self = this
const docIds = row.docId || this.ids;
if(docIds == null || docIds == undefined || docIds =='' || docIds.length < 0){
this.$modal.msgError(`最少选择一条数据`);
return;
}
//
let delFlag = false;
for(let item of self.selection){
if(!(item.docStatus == 'ysc')){
delFlag = true;
}
}
if(delFlag){
this.$modal.msgError(`只能删除文档状态为[已上传]数据,请重新选择`);
return
}
this.$modal.confirm('是否确认删除?').then(function() {
return delDocument(docIds);
}).then(() => {
@ -600,20 +642,9 @@ export default {
* 处理下载
* **/
handleDownload(row){
let self = this
self.loadingDownload = true
this.$download.resource(row.docUrl);
//
if(row.toolId){
let formData = {
toolId: row.toolId
}
addCount(formData).then(res => {
});
}
setTimeout(()=>{
self.loadingDownload = false
},1000)
this.fileDetailDrawerOpen = true
this.fileDetailOpen = true
this.docDetail = row
},
/** 发布操作 */
handlePush(row) {
@ -631,6 +662,12 @@ export default {
console.error(err)
});
},
/**
* 确认
*/
docConfrim(){
this.$refs.editDocumentRef.submitForm();
},
docCancel(){
this.$refs.editDocumentRef.resetForm();
this.open = false
@ -656,31 +693,64 @@ export default {
isSelectable(row) {
return row.docStatus !== 'yfb' && row.docStatus !== 'shz';
},
/** 批量导出 */
handleOpenBatchExport() {
let self = this
if(self.selection == null || self.selection == '' || self.selection == undefined || self.selection.length <= 0){
this.$modal.msgError(`最少选择一条数据`);
return;
}
if (this.checkList.length<1) {
this.checkList = JSON.parse(JSON.stringify(this.columnList))
}
this.exportTitle = '批量导出'
this.batchExportFlag = true
this.exportDrawerOpen = true
},
/** 导出按钮操作 */
handleOpenExport() {
if (this.checkList.length<1) {
this.checkList = JSON.parse(JSON.stringify(this.columnList))
}
this.exportTitle = '导出'
this.exportDrawerOpen = true
this.batchExportFlag = false
},
/** 导出按钮操作 */
handleExport() {
let self = this
if (this.statevalue == 1) {
let excludeFields = this.columnList.filter(item=>!this.checkList.includes(item))
this.download('/document/export', {
let params = {
...this.queryParams,
downloadCheck:false,
excludeFields:excludeFields,
}, `文档资源信息数据_${new Date().getTime()}.xlsx`)
}
if(this.batchExportFlag){
params = {
downloadCheck:false,
docIdList: self.selection.map(item=>item.docId),
excludeFields:excludeFields,
}
}
this.download('/document/export', params , `文档资源信息数据_${new Date().getTime()}.xlsx`)
}
if (this.statevalue == 2) {
listAllDoc(this.queryParams).then(r => {
let params = {
...this.queryParams
}
if(this.batchExportFlag){
params = {
docIdList: self.selection.map(item=>item.docId)
}
}
getExportWordList(params).then(r => {
if (r.data.length != 0) {
const data = {
form: null,
list: r.data
}
//publicN
exportDocx('document.docx', data, `document.docx`)
} else {
this.$message.error('没有数据');
@ -704,10 +774,22 @@ export default {
case "handleDelete":
this.handleDelete(row);
break;
case "handleDetail":
this.handleDetail(row);
break;
default:
break;
}
},
/** 关闭详情 **/
handleFileCloseDetail(){
this.fileDetailDrawerOpen = false;
this.fileDetailOpen = false;
this.$refs.downloadFileDetailRef.$destroy(); //
this.$nextTick(() => {
this.$refs.downloadFileDetailRef = null; //
});
},
}
};

View File

@ -2,7 +2,7 @@
<div class="fbox1">
<div class="fl">
<el-tabs v-model="detailActiveName">
<el-tab-pane label="件信息" name="first">
<el-tab-pane label="件信息" name="first">
<el-table :data="attachmentList" style="width: 100%">
<el-table-column label="附件名称" prop="fileName" :show-overflow-tooltip="true" />
<el-table-column label="创建时间" align="center" prop="createTime" width="180">
@ -16,7 +16,8 @@
size="mini"
type="text"
icon="el-icon-view"
@click="handlePriew(scope.row)"
v-if="previewAuth(scope.row)"
@click="handlePreview(scope.row)"
>预览</el-button>
<el-button type="text" icon="el-icon-download" @click="handleDownload(scope.row)" v-loading="loadingDownload">下载</el-button>
</template>
@ -26,28 +27,20 @@
</el-tabs><!--el-tabs-->
</div><!--fl 左侧页签-->
<el-dialog :title="viewDialogTitle" :visible.sync="viewDialogOpen" fullscreen width="500px" append-to-body :before-close="handleBeforeClose">
<i-frame :src="previewUrl" v-if="viewDialogOpen"/>
</el-dialog>
<preview-util v-if="isPreviewDisable" ref="previewForm" @previewClose="previewClose"></preview-util>
</div><!--fbox1 左右分栏-->
</template>
<script>
import { listDocument, getDocument, delDocument, addDocument, updateDocument } from "@/api/document/document";
import { listDiscussions, addDiscussions } from "@/api/tool/discussions.js";
import { listReplies, addReplies} from "@/api/tool/replies.js";
import { addCount } from "@/api/tool/downloadCount";
import AddDoc from './AddDoc'
import editDocument from "../document/editDocument";
import { Base64 } from 'js-base64';
import iFrame from "@/components/iFrame/index"
import { listAttachment } from "@/api/attachment/attachment";
import previewUtil from '@/components/PreviewUtil/previewUtil.vue'
export default {
name: 'toolDetail',
components: { editDocument, AddDoc, iFrame },
dicts:['sys_normal_disable','tool_type','tool_source','tool_status','doc_class','doc_source'],
components: { previewUtil},
dicts:[],
props: {
toolDetail: {
type: Object,
@ -77,17 +70,13 @@
repliesList: [],
showReplyForm: [],
replyContent: [],
isPreviewDisable: false,
attFileType: "zip,rar,7z",
}
},
created(){
this.getAttachmentList()
this.getDiscussionsList()
},
watch: {
discussionsList(newList) {
this.showReplyForm = new Array(newList.length).fill(false);
this.replyContent = new Array(newList.length).fill('');
}
},
methods:{
getAttachmentList() {
@ -101,27 +90,33 @@
}
);
},
handleAdd(){
this.open = true
handlePreview(row){
this.isPreviewDisable = true
this.$nextTick(() => {
this.$refs.previewForm.frontModulePreview(row)
})
},
editDocumentSubmit(){
this.open = false
this.getAttachmentList()
/** 关闭预览 **/
previewClose(){
this.isPreviewDisable = false
},
handlePriew(row){
this.previewUrl = process.env.VUE_APP_TOOL_TECH_FILE_VIEW_API + '/onlinePreview?url=' + encodeURIComponent(Base64.encode(process.env.VUE_APP_BASE_API + row.docUrl));
this.viewDialogTitle = '文档在线预览'
this.viewDialogOpen = true;
previewAuth(row){
if(row.fileUrl == null || row.fileUrl == '' || row.fileUrl == undefined){
return false
}
let extension = this.getExtension(row.fileUrl);
const acceptedExtensions = this.attFileType.toLowerCase().split(',');
if(acceptedExtensions.includes(extension)){
return false
}
return true
},
/** 删除按钮操作 */
handleDelete(row) {
const docIds = row.docId || this.ids;
this.$modal.confirm('是否确认删除?').then(function() {
return delDocument(docIds);
}).then(() => {
this.getList();
this.$modal.msgSuccess("删除成功");
}).catch(() => {});
getExtension(filePath) {
// '.'
const parts = filePath.split('.');
//
const extension = parts.pop();
return extension;
},
/**
* 处理下载
@ -147,155 +142,6 @@
self.loadingDownload = false
},1000)
},
getDiscussionsList() {
let self = this
listDiscussions({businessId:this.toolDetail.toolId}).then(res => {
self.discussionsList = res.rows
self.discussionsList.forEach(item => {
if(item.repliesList && item.repliesList.length > 0){
self.$set(item, 'showReplyFormSon', new Array(item.repliesList.length).fill(false))
self.$set(item, 'replyContentSon', new Array(item.repliesList.length).fill(''))
}else{
self.$set(item, 'showReplyFormSon', false)
self.$set(item, 'replyContentSon', '')
}
});
});
},
/** 评论 **/
handleDiscussions(){
let self = this
if (this.discussionContent == '' || this.discussionContent == null || this.discussionContent == undefined) {
self.$message({
message: '内容不能为空',//
type:'warning',  //
duration:1200,  //, 0 1200
});
return;
}
let data = {
businessId: this.toolDetail.toolId,
content: this.discussionContent,
type: "tool",
}
self.$modal.confirm('是否确认发布?').then(()=> {
addDiscussions(data).then(res => {
this.discussionContent = null
self.$message({
message: '发布成功',//
type:'success',  //
duration:1200,  //, 0 1200
});
self.getDiscussionsList()
}).catch(err =>{
this.discussionContent = null
console.error("handleDiscussions==err==", err)
self.$modal.msgError("发布失败");
});
})
},
getFirstChar(value) {
if(!value){return ''}
return value.charAt(0);
},
toggleReplyForm(index) {
this.$set(this.showReplyForm, index, !this.showReplyForm[index]);
},
cancelReply(index) {
this.$set(this.showReplyForm, index, false);
this.$set(this.replyContent, index, '');
},
/** 回复 **/
submitReply(index, item) {
let self = this
const content = this.replyContent[index];
if (content == '' || content == null || content == undefined) {
self.$message({
message: '回复内容不能为空',//
type:'warning',  //
duration:1200,  //, 0 1200
});
return;
}
let data = {
"discussionId": item.id,
"content": content,
}
self.$modal.confirm('是否确认发布?').then(()=> {
addReplies(data).then(res => {
self.$message({
message: '发布成功',//
type:'success',  //
duration:1200,  //, 0 1200
});
self.cancelReply(index)
self.getDiscussionsList()
}).catch(err =>{
console.error("handleDiscussions==err==", err)
self.$modal.msgError("发布失败");
});
})
//
this.replyContent[index] = '';
this.showReplyForm[index] = false;
},
/** 第二级 **/
toggleReplyFormSon(parentIndex, repIndex) {
const parentItem = this.discussionsList[parentIndex];
this.$set(parentItem.showReplyFormSon, repIndex, !parentItem.showReplyFormSon[repIndex]);
// this.$set(this.showReplyFormSon, index, !this.showReplyFormSon[index]);
},
/** 第二级,取消回复 **/
cancelReplySon(parentIndex, repIndex) {
const parentItem = this.discussionsList[parentIndex];
this.$set(parentItem.showReplyFormSon, repIndex, false);
this.$set(parentItem.replyContentSon, repIndex, '');
},
/** 第二级回复 **/
submitReplySon(parentIndex, repIndex, repItem) {
let self = this
const parentItem = this.discussionsList[parentIndex];
const content = parentItem.replyContentSon[repIndex];
if (content.trim() == '' || content == null || content == undefined) {
self.$message({
message: '回复内容不能为空',//
type:'warning',  //
duration:1200,  //, 0 1200
});
return;
}
let data = {
"discussionId": repItem.id,
"content": content,
}
self.$modal.confirm('是否确认发布?').then(()=> {
addReplies(data).then(res => {
self.$message({
message: '发布成功',//
type:'success',  //
duration:1200,  //, 0 1200
});
self.cancelReplySon(parentIndex, repIndex)
self.getDiscussionsList()
}).catch(err =>{
console.error("submitReplySon==err==", err)
self.$modal.msgError("发布失败");
});
})
//
this.$set(parentItem.replyContentSon, repIndex, '');
this.$set(parentItem.showReplyFormSon, repIndex, false);
},
handleBeforeClose() {
this.viewDialogOpen = false
}
}
}
</script>

View File

@ -91,9 +91,10 @@
>工具发布</el-button>
<el-button icon="el-icon-delete" @click="handleDelete(selection)" v-hasPermi="['tool:batch:remove']">批量删除</el-button>
<el-button icon="el-icon-download" @click="handleOpenExport()" v-hasPermi="['tool:export']">导出</el-button>
<el-button icon="el-icon-download" @click="handleOpenBatchExport()" v-hasPermi="['tool:batch:export']">批量导出</el-button>
</div><!--operate 操作按钮-->
<el-table v-loading="loading" :data="toolList" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="50" align="center" :selectable="selectable"/>
<el-table v-loading="loading" :data="toolList" ref="tableRef" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="50" align="center"/>
<el-table-column label="工具编号" align="center" key="toolCode" prop="toolCode" v-if="columns[0].visible" />
<el-table-column label="工具名称" align="center" key="toolName" prop="toolName" v-if="columns[1].visible" :show-overflow-tooltip="true" />
<el-table-column label="工具类别" align="center" key="toolType" prop="toolType" v-if="columns[2].visible" :show-overflow-tooltip="true" >
@ -113,14 +114,38 @@
<dict-tag :options="dict.type.flow_status" :value="scope.row.recordStatus"/>
</template>
</el-table-column>
<el-table-column label="关联工具" align="center" :show-overflow-tooltip="true">
<!-- <el-table-column label="引用工具" align="center" :show-overflow-tooltip="true">
<template slot-scope="scope">
<span v-if="handleRelationTool(scope.row.relationToolList)">
<el-link target="_blank" v-for="assItem in scope.row.relationToolList" :key="assItem.id" @click="handleToolDetail(assItem)">{{assItem.toolName}}</el-link>
</span>
</template>
</el-table-column>-->
<el-table-column label="引用工具" align="center" :show-overflow-tooltip="true" width="100">
<template slot-scope="scope">
<el-popover
trigger="click"
placement="top-start"
v-if="Array.isArray(scope.row.relationToolList) && scope.row.relationToolList.length > 0"
>
<!-- 这里展示引用工具的详细信息 -->
<ul>
<li v-for="assItem in scope.row.relationToolList" :key="assItem.id">
<el-link target="_blank" @click="handleToolDetail(assItem)">
{{ assItem.toolName }}
</el-link>
</li>
</ul>
<!-- 弹出框触发器 -->
<el-link slot="reference">
引用工具 ({{ scope.row.relationToolList.length }})
</el-link>
</el-popover>
</template>
</el-table-column>
<el-table-column label="创建时间" align="center" prop="createTime" v-if="columns[6].visible" width="160">
<template slot-scope="scope">
<span>{{ parseTime(scope.row.createTime) }}</span>
@ -130,7 +155,7 @@
label="操作"
align="center"
fixed="right"
width="250"
width="270px"
class-name="small-padding fixed-width"
>
<template slot-scope="scope">
@ -159,7 +184,7 @@
</el-card><!--el-card-->
<!-- 工具导出对话框 -->
<el-dialog title="导出" :visible.sync="exoportDrawerOpen" width="980px" append-to-body>
<el-dialog :title="exportTitle" :visible.sync="exoportDrawerOpen" width="980px" append-to-body :close-on-press-escape="false" :close-on-click-modal="false" :show-close="false">
<div class="el-form-border">
<el-form ref="exportFrom" label-width="180px">
<el-row>
@ -203,9 +228,6 @@
</span>
</el-dialog>
<el-drawer
:visible.sync="drawerShow"
direction="rtl"
@ -215,14 +237,19 @@
:show-close="false"
modal-append-to-body
:destroy-on-close="true"
:close-on-press-escape="false"
>
<main-component ref="mainComponent" :code="path + code" :data="data" @close="handleClose"></main-component>
</el-drawer>
<!-- 工具详情对话框 -->
<el-drawer :visible.sync="detailDrawerOpen" :modal-append-to-body="false" size="80%" class="no-padding" @close="handleCloseDetail()">
<el-drawer :visible.sync="detailDrawerOpen" :modal-append-to-body="false" :show-close="false"
size="80%" class="no-padding" :close-on-press-escape="false" @close="handleCloseDetail()">
<template #title>
<span>工具名称</span>
<span>{{toolTitle}}</span>
<div class="drawer-head-btn">
<el-button @click="detailDrawerOpen = false"> </el-button>
</div><!--drawer-head-btn 抽屉顶部按钮区域-->
</template>
<template v-if="detailOpen">
<tool-detail ref="toolDetailRef" :toolDetail="toolDetail"/>
@ -232,15 +259,20 @@
<!-- 工具详情对话框 -->
<el-drawer :visible.sync="fileDetailDrawerOpen" :modal-append-to-body="false" size="80%" class="no-padding" @close="handleFileCloseDetail()">
<el-drawer :visible.sync="fileDetailDrawerOpen" :modal-append-to-body="false" :show-close="false"
size="80%" class="no-padding" :close-on-press-escape="false" @close="handleFileCloseDetail()">
<template #title>
<span>工具下载</span>
<span>工具附件下载</span>
<div class="drawer-head-btn">
<el-button @click="fileDetailDrawerOpen = false"> </el-button>
</div><!--drawer-head-btn 抽屉顶部按钮区域-->
</template>
<template v-if="fileDetailOpen">
<download-file-detail ref="downloadFileDetailRef" :toolDetail="toolDetail"/>
</template>
</el-drawer><!--el-drawer 详情-抽屉-->
</div><!--app-container-->
</template>
@ -255,6 +287,7 @@ import downloadFileDetail from "./downloadFileDetail.vue";
import AddDoc from './AddDoc'
import mainComponent from "@/components/mainComponent/index.vue";
import { exportDocx } from '@/utils/docUtil/docutil.js';
import { addCount } from "@/api/tool/downloadCount";
export default {
name: "User",
@ -369,6 +402,12 @@ export default {
label: 'word'
}
],
//
toolTitle:'',
exportTitle:'',
batchExportFlag: false,
selectedRows: [], //
};
},
watch: {
@ -512,9 +551,10 @@ export default {
this.detailDrawerOpen = true
this.detailOpen = true
this.toolDetail = row
this.toolTitle = '工具详情'
} else {
let status = row.recordStatus === 'draft' ? '1' : '0'
this.handleOpen({type:'tool_release', procInstId:row.procInstId, status:status})
this.handleOpen({type:'tool_release', procInstId:row.procInstId, status:status, title: '工具发布'})
}
},
handleFileDownload(row){
@ -551,11 +591,27 @@ export default {
let _this = this
_this.handleOpen({type:'tool_release',procInstId:row.procInstId,status:'1'})
},
/** 发布按钮操作 */
/** 导出 */
handleOpenExport() {
if (this.checkList.length<1) {
this.checkList = JSON.parse(JSON.stringify(this.columnList))
}
this.exportTitle = '导出'
this.batchExportFlag = false
this.exoportDrawerOpen = true
},
/** 批量导出 */
handleOpenBatchExport() {
let self = this
if(self.selection == null || self.selection == '' || self.selection == undefined || self.selection.length <= 0){
this.$modal.msgError(`最少选择一条数据`);
return;
}
if (this.checkList.length<1) {
this.checkList = JSON.parse(JSON.stringify(this.columnList))
}
this.exportTitle = '批量导出'
this.batchExportFlag = true
this.exoportDrawerOpen = true
},
/** 导出按钮操作 */
@ -563,17 +619,36 @@ export default {
let self = this
if (this.statevalue == 1) {
let excludeFields = this.columnList.filter(item=>!this.checkList.includes(item))
this.download('/tool/export', {
let params = {
...this.queryParams,
downloadCheck:false,
excludeFields:excludeFields,
}, `工具信息数据_${new Date().getTime()}.xlsx`)
}
if(this.batchExportFlag){
params = {
downloadCheck:false,
toolIdList: self.selection.map(item=>item.toolId),
excludeFields:excludeFields,
}
}
this.download('/tool/export',params, `工具信息数据_${new Date().getTime()}.xlsx`)
setTimeout(() => {
if(self.batchExportFlag){
self.clearSelected()
}
self.exoportDrawerOpen = false;
}, 1000);
}
if (this.statevalue == 2) {
exportWordList(this.queryParams).then(r => {
let params = {
...this.queryParams
}
if(this.batchExportFlag){
params = {
toolIdList: self.selection.map(item=>item.toolId)
}
}
exportWordList(params).then(r => {
if (r.data.length != 0) {
const data = {
form: null,
@ -582,6 +657,9 @@ export default {
//publicN
exportDocx('tool.docx', data, `tool.docx`)
setTimeout(() => {
if(self.batchExportFlag){
self.clearSelected()
}
self.exoportDrawerOpen = false;
}, 1000);
} else {
@ -590,6 +668,7 @@ export default {
})
}
},
//
handleFileUploadProgress(event, file, fileList) {
@ -617,6 +696,18 @@ export default {
this.$modal.msgError(`最少选择一条数据`);
return
}
//稿
let delFlag = false;
for(let item of list){
if(!(item.recordStatus == 'draft')){
delFlag = true;
}
}
if(delFlag){
this.$modal.msgError(`只能删除流程状态为[拟稿]数据,请重新选择`);
return
}
_this.$modal.confirm('删除后,该流程待办任务将会被删除,请谨慎操作。是否确认执行?')
.then(async() => {
_this.loading = true
@ -680,9 +771,27 @@ export default {
return true
}
},
clearSelected() {
// tab
this.$refs.tableRef.clearSelection();
},
onPopoverShow(list) {
this.relationToolList = list; //
},
/* handlePageChange(page) {
this.$nextTick(() => {
this.restoreSelection();
});
},
//
restoreSelection() {
this.$refs.tableRef.clearSelection();
this.toolList.forEach(row => {
if (this.selectedRows.some(selected => selected.toolId == row.toolId)) {
this.$refs.tableRef.toggleRowSelection(row, true);
}
});
}, */
}
};

View File

@ -19,7 +19,7 @@
<el-col :span="12"> <el-form-item label="操作说明">{{detailData.operateExplain}}</el-form-item> </el-col>
<el-col :span="12"> <el-form-item label="备注">{{detailData.remark}}</el-form-item> </el-col>
<el-col :span="24">
<el-form-item label="关联工具">
<el-form-item label="引用工具">
<span v-if="detailData.association != null && detailData.association != '' && detailData.association != undefined">
<el-tag :key="tag.toolId" v-for="tag in JSON.parse(detailData.association)" type="info" style="margin-right: 5px">{{tag.toolName}}</el-tag>
</span>
@ -121,6 +121,8 @@
<i-frame :src="previewUrl" v-if="viewDialogOpen"/>
</el-dialog>
<preview-util v-if="isPreviewDisable" ref="previewForm" @previewClose="previewClose"></preview-util>
<!-- 上传 -->
<AddDoc :show.sync="open" :toolId="detailData.toolId" @callback="getAttachmentList"/>
</div><!--fbox1 左右分栏-->
@ -138,10 +140,15 @@
import iFrame from "@/components/iFrame/index"
import { addCount } from "@/api/tool/downloadCount";
import { listAttachment } from "@/api/attachment/attachment";
import axios from 'axios'
import {
getToken
} from "@/utils/auth";
import previewUtil from '@/components/PreviewUtil/previewUtil.vue'
export default {
name: 'toolDetail',
components: { editDocument, AddDoc, iFrame },
components: { editDocument, AddDoc, iFrame, previewUtil },
dicts:['sys_normal_disable','tool_type','tool_source','tool_status','doc_class','doc_source'],
props: {
toolDetail: {
@ -177,6 +184,20 @@
//
detailData:{},
attFileType: "zip,rar,7z",
// json
dialogVisible:false,
isJson:false,
resultContentObj:[],
// docx
isDocx:false,
docxData: null,
//pdf
isPdf:false,
pdfFileData: null, //
previewLoading:false,
previewUseFront: "txt,doc,docx,pdf",
isPreviewDisable: false
}
},
created(){
@ -210,9 +231,14 @@
this.getAttachmentList()
},
handlePreview(row){
this.previewUrl = process.env.VUE_APP_TOOL_TECH_FILE_VIEW_API + '/onlinePreview?url=' + encodeURIComponent(Base64.encode(process.env.VUE_APP_BASE_API + row.docUrl));
this.viewDialogTitle = '文档在线预览'
this.viewDialogOpen = true;
this.isPreviewDisable = true
this.$nextTick(() => {
this.$refs.previewForm.frontModulePreview(row)
})
},
/** 关闭预览 **/
previewClose(){
this.isPreviewDisable = false
},
/** 删除按钮操作 */
handleDelete(row) {

View File

@ -2,7 +2,7 @@
<div v-loading="loading||detailLoading">
<div class="drawer-head">
<div class="cell-title">
<p class="title">工具发布</p>
<p class="title">{{title}}</p>
</div>
<div class="cell-btn">
<el-button type="primary" v-if="pListData && pListData.procInstId" @click="handleMonitor" icon="el-icon-data-line">流程监控</el-button>
@ -191,7 +191,7 @@
</el-row>
<el-row>
<el-col :span="24">
<el-form-item label="关联工具" prop="association">
<el-form-item label="引用工具" prop="association">
<el-select
:disabled="!editStatus"
v-model="form.association"
@ -200,7 +200,7 @@
value-key="toolId"
filterable
remote
placeholder="请选择关联工具"
placeholder="请选择引用工具"
@focus="toolSelect">
<el-option
v-for="item in form.association"
@ -279,6 +279,7 @@
v-loading = flowStepLoading
:close-on-click-modal="false"
:close-on-press-escape="false"
:show-close="false"
>
<processcode
ref="prochild"
@ -301,6 +302,7 @@
<tool-selector ref="toolSelect" @selectHandle="selectHandle"></tool-selector>
<bl-user-selector ref="peopleSelect" :type="'single'" :isCheck="true" :open="toolPrincipalsChoose" :deptFilter="true" @cancel="toolPrincipalsChoose=false" @submit="submitPeople"></bl-user-selector>
<preview-util v-if="isPreviewDisable" ref="previewForm" @previewClose="previewClose"></preview-util>
<el-dialog :title="viewDialogTitle" :visible.sync="viewDialogOpen" fullscreen width="500px" append-to-body :before-close="handleBeforeClose">
<i-frame :src="previewUrl" v-if="viewDialogOpen"/>
@ -325,9 +327,9 @@ import { addUser, deptTreeSelect, updateUser } from '@/api/system/user'
import { addTool, checkToolExist, getInfoByBpmcId, updateTool } from '@/api/tool/tool'
import blUserSelector from '@/components/user-selector/src/user-selector.vue'
import ToolSelector from '@/components/tool-selector/index.vue'
import { Base64 } from 'js-base64'
import uploadVue from '@/components/FileUpload/optimizeToolUpload.vue'
import { addCount } from "@/api/tool/downloadCount";
import previewUtil from '@/components/PreviewUtil/previewUtil.vue'
// PDF
export default {
@ -339,7 +341,8 @@ export default {
WorkflowLogs,
processcode,
iFrame,
uploadVue
uploadVue,
previewUtil
},
name: "Borrow_doc",
props: ['data'],
@ -458,6 +461,8 @@ export default {
detailBoolean: false,
attachmentList: [],
attFileType: "zip,rar,7z",
isPreviewDisable: false,
title: '工具发布'
};
},
computed: {},
@ -472,6 +477,9 @@ export default {
this.curDeptId = this.$store.getters.userInfo.deptId
this.curDeptName = this.$store.getters.userInfo.dept.deptName
if (this.data) {
if(this.data.title){
this.title = this.data.title
}
this.init(this.data)
}
this.getConfigKey("sys.user.initPassword").then(response => {
@ -927,12 +935,14 @@ export default {
return extension;
},
handlePreview(row){
this.viewDialogOpen = true;
this.viewDialogTitle = '文档在线预览'
let protocol = window.location.protocol
let hostname = window.location.hostname;
let getDocUrl = protocol + '//' + hostname + ':8080' + process.env.VUE_APP_BASE_API
this.previewUrl = process.env.VUE_APP_TOOL_TECH_FILE_VIEW_API + '/onlinePreview?url=' + encodeURIComponent(Base64.encode(getDocUrl + row.docUrl));
this.isPreviewDisable = true
this.$nextTick(() => {
this.$refs.previewForm.frontModulePreview(row)
})
},
/** 关闭预览 **/
previewClose(){
this.isPreviewDisable = false
},
/**
* 处理下载

View File

@ -145,6 +145,7 @@
v-loading = flowStepLoading
:close-on-click-modal="false"
:close-on-press-escape="false"
:show-close="false"
>
<processcode
ref="prochild"