| | |
| | | <template slot="title"> |
| | | <a-space class="operator"> |
| | | <span class="title">SOP</span> |
| | | <a-upload |
| | | v-if="canUpload" |
| | | :before-upload="beforeUpload" |
| | | :showUploadList="false" |
| | | @change="uploadChange" |
| | | accept=".xls,.xlsx" |
| | | <a-button v-if="canUpload" type="primary" @click="showUpload" |
| | | >新增</a-button |
| | | > |
| | | <a-button type="primary">新增</a-button> |
| | | </a-upload> |
| | | </a-space> |
| | | </template> |
| | | <template slot="action" slot-scope="{ record }"> |
| | | <a-popover title="" trigger="hover"> |
| | | <a-popover v-if="!record.currentFlag" title="" trigger="hover"> |
| | | <div class="" slot="content" style="width: 450px"> |
| | | <a-table |
| | | size="small" |
| | |
| | | :expandRowByClick="true" |
| | | :row-key="(record1, index) => index" |
| | | > |
| | | <!-- <template slot="action" slot-scope="record1"> |
| | | 123{{ record1 }} |
| | | </template> --> |
| | | </a-table> |
| | | </div> |
| | | <a>适用产品</a> |
| | | </a-popover> |
| | | <a-tag v-else class="tag-all" color="#f50"> 适用全部 </a-tag> |
| | | <template v-if="canDownload"> |
| | | <a-divider type="vertical"></a-divider> |
| | | <a @click="downloadFile(record)">下载</a> |
| | | </template> |
| | | <a-divider type="vertical"></a-divider> |
| | | <!-- <a class="action-button" @click="viewPdf(record)">预览</a> --> |
| | | <a class="action-button" @click="downloadFile(record)">下载</a> |
| | | <!-- <a class="action-button" @click="viewHistory(record)">历史详情</a> --> |
| | | <a-popover title="" trigger="hover"> |
| | | <a-space class="btn-grp" direction="vertical" slot="content"> |
| | | <a-button |
| | | v-if="canUpload" |
| | | type="primary" |
| | | @click="updateDesc(record)" |
| | | >更新说明</a-button |
| | | > |
| | | <!-- <a-button |
| | | v-if="canLock" |
| | | type="primary" |
| | | @click="lock(record)" |
| | | >{{ record.lockFlag ? "解锁" : "锁定" }}</a-button |
| | | > --> |
| | | <a-button |
| | | v-if="canUpload" |
| | | type="primary" |
| | | @click="handleEmailShow(record)" |
| | | >邮件通知</a-button |
| | | > |
| | | </a-space> |
| | | <a>更多</a> |
| | | </a-popover> |
| | | </template> |
| | | </advance-table> |
| | | </a-card> |
| | | </a-spin> |
| | | </div> |
| | | <!-- 弹窗 解析结果 --> |
| | | <a-modal |
| | | :visible="resShow" |
| | | title="解析结果" |
| | | :destroyOnClose="true" |
| | | :maskClosable="false" |
| | | :width="800" |
| | | okText="提交" |
| | | @cancel="resCancel" |
| | | @ok="uploadOk" |
| | | > |
| | | <desc-res :info="resObj"></desc-res> |
| | | </a-modal> |
| | | <pop |
| | | :visible.sync="popVisible" |
| | | :x="popPosition.x" |
| | |
| | | :position="popPosition.dir" |
| | | :info="popInfo" |
| | | ></pop> |
| | | <a-modal |
| | | :visible="uploadShow" |
| | | :footer="null" |
| | | :width="800" |
| | | title="上传软件" |
| | | :destroyOnClose="true" |
| | | :maskClosable="false" |
| | | @cancel="uploadCancel" |
| | | > |
| | | <div class=""> |
| | | <template v-if="!onlyXls"> |
| | | <a-row type="flex" class="row"> |
| | | <a-col flex="6em" class="label">sop包</a-col> |
| | | <a-col :flex="1"> |
| | | <a-upload |
| | | class="upload" |
| | | :before-upload="beforeUpload" |
| | | @change="uploadChange" |
| | | accept=".zip,.rar" |
| | | > |
| | | <a-button type="primary">选压缩包</a-button> |
| | | </a-upload> |
| | | </a-col> |
| | | </a-row> |
| | | </template> |
| | | <a-row type="flex" class="row"> |
| | | <a-col flex="6em" class="label">SOP说明</a-col> |
| | | <a-col :flex="1"> |
| | | <a-upload |
| | | class="upload" |
| | | :before-upload="beforeUpload" |
| | | @change="uploadChange1" |
| | | accept=".xls,.xlsx" |
| | | > |
| | | <a-button type="primary">说明文件</a-button> |
| | | </a-upload> |
| | | </a-col> |
| | | </a-row> |
| | | <div class="sub-title">说明文件解析结果</div> |
| | | <div class="res-content"> |
| | | <desc-res :info="resObj"></desc-res> |
| | | </div> |
| | | <div class="modal-footer"> |
| | | <a-button type="danger" @click="uploadCancel"> 取消 </a-button> |
| | | <a-button v-if="!onlyXls" type="primary" @click="uploadSop"> |
| | | 提交 |
| | | </a-button> |
| | | <a-button v-else type="primary" @click="applyModel"> 提交 </a-button> |
| | | </div> |
| | | </div> |
| | | </a-modal> |
| | | <a-modal |
| | | :visible="emailShow" |
| | | :footer="null" |
| | | :width="760" |
| | | title="邮件发送" |
| | | :destroyOnClose="true" |
| | | :maskClosable="false" |
| | | @cancel="emailCancel" |
| | | > |
| | | <email-card |
| | | :visible.sync="emailShow" |
| | | :users="userList" |
| | | :title="emailInfo.title" |
| | | :content="emailInfo.content" |
| | | v-if="emailShow" |
| | | ></email-card> |
| | | </a-modal> |
| | | </div> |
| | | </template> |
| | | |
| | |
| | | import checkPermit from "@/assets/js/tools/checkPermit"; |
| | | import PERMITS from "@/assets/js/const/const_permits"; |
| | | import { mapGetters } from "vuex"; |
| | | import { fileParse, addSop, getList, getSopType1, getSopType2 } from "./apis"; |
| | | import EmailCard from "../../components/emailCard"; |
| | | import { getUserList } from "../../permission/apis"; |
| | | import { |
| | | fileParse, |
| | | addSop, |
| | | getList, |
| | | getSopType1, |
| | | getSopType2, |
| | | updateSop, |
| | | } from "./apis"; |
| | | import offset from "@/assets/js/tools/offset"; |
| | | import Pop from "./pop"; |
| | | import DescRes from "./descRes"; |
| | |
| | | AdvanceTable, |
| | | Pop, |
| | | DescRes, |
| | | EmailCard, |
| | | }, |
| | | name: "list", |
| | | data() { |
| | | return { |
| | | emailShow: false, |
| | | emailInfo: { |
| | | title: "", |
| | | content: "", |
| | | }, |
| | | userList: [], |
| | | onlyXls: false, |
| | | uploadShow: false, |
| | | webUrl: getWebUrl(), |
| | | prodsColumns: [ |
| | | { |
| | |
| | | align: "center", |
| | | width: 180, |
| | | }, |
| | | // { |
| | | // title: "操作", |
| | | // dataIndex: "operation", |
| | | // align: "center", |
| | | // width: 180, |
| | | // scopedSlots: { customRender: "action" }, |
| | | // }, |
| | | ], |
| | | file: null, |
| | | file1: null, |
| | | resObj: {}, |
| | | popInfo: {}, |
| | | resShow: false, |
| | | popVisible: false, |
| | | popPosition: { |
| | | x: 500, |
| | |
| | | title: "操作", |
| | | dataIndex: "operation", |
| | | align: "center", |
| | | width: 140, |
| | | width: 200, |
| | | fixed: "right", |
| | | scopedSlots: { customRender: "action" }, |
| | | noSearch: true, |
| | |
| | | }, |
| | | computed: { |
| | | ...mapGetters("account", ["permits"]), |
| | | ...mapGetters("setting", ["affixed"]), |
| | | canUpload() { |
| | | return checkPermit(PERMITS.uploadSoftware, this.permits); |
| | | }, |
| | | canDownload() { |
| | | return checkPermit(PERMITS.downloadSoftware, this.permits); |
| | | }, |
| | | canLock() { |
| | | return checkPermit(PERMITS.lockOther, this.permits); |
| | | }, |
| | | }, |
| | | watch: { |
| | |
| | | }, |
| | | }, |
| | | methods: { |
| | | searchAllUserList() { |
| | | getUserList() |
| | | .then((res) => { |
| | | let rs = res.data; |
| | | if (rs.code && rs.data) { |
| | | this.userList = rs.data2; |
| | | } |
| | | }) |
| | | .catch((error) => { |
| | | console.log(error); |
| | | }); |
| | | }, |
| | | showUpload() { |
| | | this.file = null; |
| | | this.file1 = null; |
| | | this.resObj = {}; |
| | | this.onlyXls = false; |
| | | this.uploadShow = true; |
| | | }, |
| | | updateDesc(row) { |
| | | this.file = null; |
| | | this.file1 = null; |
| | | this.resObj = { rowId: row.id }; |
| | | this.onlyXls = true; |
| | | this.uploadShow = true; |
| | | }, |
| | | uploadCancel() { |
| | | this.uploadShow = false; |
| | | }, |
| | | handleEmailShow(record) { |
| | | this.emailInfo.title = |
| | | "[sop发布记录]" + record.fileName + " 版本号:" + record.fileVersion; |
| | | this.emailInfo.content = record.releaseNotes; |
| | | this.emailShow = true; |
| | | }, |
| | | emailCancel() { |
| | | this.emailShow = false; |
| | | }, |
| | | uploadSop() { |
| | | if (!this.file) { |
| | | this.$message.error("请选择要上传的压缩包"); |
| | | return false; |
| | | } |
| | | if (!this.file1) { |
| | | this.$message.error("请选择sop说明文件"); |
| | | return false; |
| | | } |
| | | if (!this.resObj.fileName) { |
| | | this.$message.error("sop说明文件解析异常"); |
| | | return false; |
| | | } |
| | | // let info = this.resData[0]; |
| | | // if(!info.boardNumber || !info.type) { |
| | | // this.$error({ |
| | | // title: '系统提示', |
| | | // content: '缺少板号或软件类型,请输入板号和软件类型', |
| | | // }); |
| | | // return false; |
| | | // } |
| | | let loading = this.$layer.loading(); |
| | | |
| | | const formData = new FormData(); |
| | | formData.append("multipartFile", this.file); |
| | | // formData.append("file2", this.file1); |
| | | formData.append("sopStr", JSON.stringify(this.resObj)); |
| | | addSop(formData) |
| | | .then((res) => { |
| | | let { code, data, msg } = res.data; |
| | | if (code) { |
| | | this.uploadShow = false; |
| | | this.$message.success("上传成功"); |
| | | this.searchData(); |
| | | } else { |
| | | this.$message.error("解析失败"); |
| | | } |
| | | this.$layer.close(loading); |
| | | }) |
| | | .catch((error) => { |
| | | this.$layer.close(loading); |
| | | console.log(error); |
| | | }); |
| | | }, |
| | | applyModel() { |
| | | if (!this.file1) { |
| | | this.$message.error("请选择sop说明文件"); |
| | | return false; |
| | | } |
| | | if (!this.resObj.fileName) { |
| | | this.$message.error("sop说明文件解析异常"); |
| | | return false; |
| | | } |
| | | let loading = this.$layer.loading(); |
| | | updateSop(this.resObj) |
| | | .then((res) => { |
| | | let { code, data, msg } = res.data; |
| | | if (code) { |
| | | this.uploadShow = false; |
| | | this.$message.success("上传成功"); |
| | | this.searchData(); |
| | | } else { |
| | | this.$message.error("解析失败"); |
| | | } |
| | | this.$layer.close(loading); |
| | | }) |
| | | .catch((error) => { |
| | | this.$layer.close(loading); |
| | | console.log(error); |
| | | }); |
| | | }, |
| | | getSopType1() { |
| | | getSopType1() |
| | | .then((res) => { |
| | |
| | | return false; |
| | | }, |
| | | uploadChange(data) { |
| | | const { file, fileList } = data; |
| | | if (fileList.length > 1) { |
| | | fileList.shift(); |
| | | } |
| | | if (fileList.length) { |
| | | this.file = fileList[0].originFileObj; |
| | | } else { |
| | | this.file = null; |
| | | } |
| | | }, |
| | | uploadChange1(data) { |
| | | const { file, fileList } = data; |
| | | if (fileList.length > 1) { |
| | | fileList.shift(); |
| | | } |
| | | if (fileList.length) { |
| | | this.file1 = fileList[0].originFileObj; |
| | | } else { |
| | | this.file1 = null; |
| | | this.resObj = []; |
| | | return false; |
| | | } |
| | | let loading = this.$layer.loading(); |
| | | const formData = new FormData(); |
| | | formData.append("multipartFile", data.file); |
| | | formData.append("multipartFile", this.file1); |
| | | fileParse(formData) |
| | | .then((res) => { |
| | | this.$layer.close(loading); |
| | | let { code, data, data2 } = res.data; |
| | | if (code && data) { |
| | | let rowId = this.resObj.rowId; |
| | | this.resObj = data2; |
| | | this.resShow = true; |
| | | this.resObj.id = rowId; |
| | | this.$message.success("解析成功"); |
| | | } else { |
| | | this.$message.error("解析失败"); |
| | |
| | | console.log(error); |
| | | }); |
| | | }, |
| | | resCancel() { |
| | | this.resShow = false; |
| | | }, |
| | | uploadOk() { |
| | | addSop(this.resObj).then((res) => { |
| | | let { code, data, msg } = res.data; |
| | | if (code) { |
| | | this.$message.success("上传成功"); |
| | | this.resShow = false; |
| | | this.searchData(); |
| | | } else { |
| | | this.$message.error(msg); |
| | | } |
| | | }); |
| | | }, |
| | | resize() { |
| | | setTimeout(() => { |
| | | this.update = Math.random(); |
| | | }, 200); |
| | | }, |
| | | activeFN() { |
| | | this.resize(); |
| | | }, |
| | | onSearch(conditions, searchOptions, col) { |
| | | // console.log(conditions); |
| | |
| | | parentTypeChange(val) { |
| | | let _search = this.columns[1].search; |
| | | _search.value = []; |
| | | this.conditions['chileType'] = []; |
| | | this.conditions["chileType"] = []; |
| | | this.getSopType2(val); |
| | | }, |
| | | searchData() { |
| | | const { pageCurr, pageSize, conditions, columns } = this; |
| | | let params = {}; |
| | | let params = { pageCurr, pageSize }; |
| | | let data = {}; |
| | | Object.keys(conditions).forEach((v) => { |
| | | switch (v) { |
| | |
| | | getList(params, params2) |
| | | .then((res) => { |
| | | let { code, data, data2 } = res.data; |
| | | let total = 0; |
| | | if (code && data) { |
| | | // console.log(data2); |
| | | list = data2; |
| | | list = data2.list; |
| | | total = data2.total; |
| | | } |
| | | this.dataSource = list; |
| | | this.total = total; |
| | | this.getSopType1(); |
| | | if (-1 == this.update) { |
| | | this.update = Math.random(); |
| | |
| | | }, |
| | | mounted() { |
| | | this.searchData(); |
| | | this.searchAllUserList(); |
| | | this.getSopType1(); |
| | | window.addEventListener("resize", this.resize); |
| | | }, |
| | | destroyed() { |
| | | window.removeEventListener("resize", this.resize); |
| | | }, |
| | | }; |
| | | </script> |
| | |
| | | /deep/table { |
| | | table-layout: fixed; |
| | | } |
| | | .modal-footer { |
| | | text-align: right; |
| | | button + button { |
| | | margin-left: 8px; |
| | | } |
| | | } |
| | | .label { |
| | | display: flex; |
| | | justify-content: flex-end; |
| | | align-items: center; |
| | | padding-right: 0.4em; |
| | | height: 32px; |
| | | &::after { |
| | | content: ":"; |
| | | } |
| | | } |
| | | .row ~ .row { |
| | | margin-top: 10px; |
| | | } |
| | | .sub-title { |
| | | font-size: 14px; |
| | | font-weight: 700; |
| | | margin-top: 10px; |
| | | } |
| | | .res-content { |
| | | max-height: 260px; |
| | | overflow-y: auto; |
| | | margin-bottom: 10px; |
| | | } |
| | | .btn-grp button { |
| | | width: 6.4em; |
| | | } |
| | | .tag-all { |
| | | margin: 0; |
| | | } |
| | | /deep/ .ant-table-fixed-right { |
| | | .ant-table-body-outer { |
| | | margin-bottom: 0 !important; |
| | | } |
| | | .ant-table-body-inner { |
| | | overflow-x: hidden; |
| | | } |
| | | overflow-x: hidden; |
| | | } |
| | | } |
| | | </style> |