研发图纸文件管理系统-前端项目
he wei
2025-03-13 ec8d9f802eac6841165425b228ef56474636fa9a
src/pages/resourceManage/software/list.vue
@@ -3,59 +3,124 @@
    <div class="inner" ref="wraper">
      <a-spin class="" :spinning="spinning" tip="拼命加载中...">
        <a-card>
          <advance-table ref="table" class="doc-center-table" :data-source="dataSource" :columns="columns" title=""
            :row-key="(record, index) => index" @search="onSearch" @refresh="onRefresh" @reset="onReset"
            :format-conditions="true" :scroll="{ x: 2020, y }" :pagination="{
                                current: pageCurr,
                                pageSize: pageSize,
                                total: total,
                                showSizeChanger: true,
                                showLessItems: true,
                                showQuickJumper: true,
                                pageSizeOptions: ['10', '20', '50', '100'],
                                showTotal: (total, range) =>
                                  `第 ${range[0]}-${range[1]} 条,总计 ${total} 条`,
                                onChange: onPageChange,
                                onShowSizeChange: onSizeChange,
                              }" :rowClassName="rowClassFn">
          <advance-table
            ref="table"
            class="doc-center-table"
            :data-source="dataSource"
            :columns="columns"
            title=""
            :row-key="(record, index) => index"
            @search="onSearch"
            @refresh="onRefresh"
            @reset="onReset"
            :format-conditions="true"
            :scroll="{ x: 2020, y }"
            :pagination="{
                                  current: pageCurr,
                                  pageSize: pageSize,
                                  total: total,
                                  showSizeChanger: true,
                                  showLessItems: true,
                                  showQuickJumper: true,
                                  pageSizeOptions: ['10', '20', '50', '100'],
                                  showTotal: (total, range) =>
                                    `第 ${range[0]}-${range[1]} 条,总计 ${total} 条`,
                                  onChange: onPageChange,
                                  onShowSizeChange: onSizeChange,
                                }"
            :rowClassName="rowClassFn"
          >
            <template slot="dataIndex" slot-scope="{ index }">
              {{ index + 1 }}
            </template>
            <template slot="title">
              <a-space>
                <span class="title">软件中心</span>
                <a-button v-if="canUploadSoftware" type="primary" @click="showUpload">上传软件</a-button>
                <a-button
                  v-if="canUploadSoftware"
                  type="primary"
                  @click="showUpload"
                  >上传软件</a-button
                >
              </a-space>
            </template>
            <template slot="tags" slot-scope="tags">
              <a-tag :color="tags.record.codeFlag ? 'green' : 'red'">{{ tags.text }}</a-tag>
              <a-tag
                :color="tags.record.codeFlag ? 'green' : 'red'"
                >{{ tags.text }}</a-tag
              >
            </template>
            <template slot="action" slot-scope="{ record }">
              <a-popover title="" trigger="hover">
                <div class="" slot="content" style="width: 450px">
                  <a-table size="small" :scroll="{ y: 300 }" bordered :columns="prodsColumns" :data-source="record.links"
                    :pagination="false" :expandRowByClick="true" :row-key="(record1, index) => index">
                  <a-table
                    size="small"
                    :scroll="{ y: 300 }"
                    bordered
                    :columns="prodsColumns"
                    :data-source="record.links"
                    :pagination="false"
                    :expandRowByClick="true"
                    :row-key="(record1, index) => index"
                  >
                  </a-table>
                </div>
                <a>适用机型</a>
              </a-popover>
              <template v-if="canDownloadSoftware">
                <a-divider type="vertical"></a-divider>
                <a :disabled="!!record.soft.lockFlag && !isTester" @click="download(record)">下载</a>
                <a
                  :disabled="!!record.soft.lockFlag && !isTester"
                  @click="download(record)"
                  >下载</a
                >
                <a-divider type="vertical"></a-divider>
              </template>
              <a-popover title="" trigger="hover">
                <a-space class="btn-grp" direction="vertical" slot="content">
                  <a-button v-if="canUploadSoftware" :disabled="!!record.soft.lockFlag" type="primary"
                    @click="updateDesc(record)">更新说明</a-button>
                  <a-button v-if="record.soft.lockFlag !== -1 ? canLock : isTester" type="primary"
                    @click="lock(record)">{{ record.soft.lockFlag ? "解锁" : "锁定" }}</a-button>
                  <a-button v-if="canUploadSoftware" type="primary" @click="handleEmailShow(record)">邮件通知</a-button>
                  <a-button type="primary" :disabled="!isTester" @click="handleConfirmDelete(record)">删除</a-button>
                  <template v-if="isCoder">
                    <a-button type="primary" v-if="record.codeFlag" @click="downloadSource(record)">下载源码</a-button>
                    <a-button type="primary" @click="uploadSourceClick(record)">上传源码</a-button>
                  </template>
                  <a-button
                    v-if="canUploadSoftware"
                    :disabled="!!record.soft.lockFlag"
                    type="primary"
                    @click="updateDesc(record)"
                    >更新说明</a-button
                  >
                  <a-button
                    v-if="record.soft.lockFlag !== -1 ? canLock : isTester"
                    type="primary"
                    @click="lock(record)"
                    >{{ record.soft.lockFlag ? "解锁" : "锁定" }}</a-button
                  >
                  <a-button
                    v-if="canUploadSoftware"
                    type="primary"
                    @click="handleEmailShow(record)"
                    >邮件通知</a-button
                  >
                  <a-button
                    type="primary"
                    :disabled="!isTester"
                    @click="handleConfirmDelete(record)"
                    >删除</a-button
                  >
                  <a-button
                    type="primary"
                    v-if="isCoderDown && record.codeFlag"
                    @click="downloadSource(record)"
                    >下载源码</a-button
                  >
                  <a-button
                    type="primary"
                    v-if="isCoderUp && record.soft.owner == user.name && record.codeFlag"
                    @click="connectSource(record)"
                    >共享源码</a-button
                  >
                  <a-button
                    type="primary"
                    v-if="isCoderUp && record.soft.owner == user.name"
                    @click="uploadSourceClick(record)"
                    >上传源码</a-button
                  >
                </a-space>
                <a>更多</a>
              </a-popover>
@@ -65,22 +130,39 @@
      </a-spin>
    </div>
    <!-- 上传软件 -->
    <a-modal :visible="uploadShow" :footer="null" :width="760" :title="onlyXls ? '更新发布说明' : '上传软件'" :destroyOnClose="true"
      :maskClosable="false" @cancel="uploadCancel">
    <a-modal
      :visible="uploadShow"
      :footer="null"
      :width="760"
      :title="onlyXls ? '更新发布说明' : '上传软件'"
      :destroyOnClose="true"
      :maskClosable="false"
      @cancel="uploadCancel"
    >
      <div class="">
        <template v-if="!onlyXls">
          <a-row type="flex" class="row">
            <a-col flex="6em" class="label">更新时间</a-col>
            <a-col :flex="1">
              <a-date-picker format="YYYY-MM-DD HH:mm:ss" valueFormat="YYYY-MM-DD HH:mm:ss" :allowClear="false"
                :disabled-date="disabledDate" :show-time="{ defaultValue: moment('00:00:00', 'HH:mm:ss') }"
                v-model="versionTime" />
              <a-date-picker
                format="YYYY-MM-DD HH:mm:ss"
                valueFormat="YYYY-MM-DD HH:mm:ss"
                :allowClear="false"
                :disabled-date="disabledDate"
                :show-time="{ defaultValue: moment('00:00:00', 'HH:mm:ss') }"
                v-model="versionTime"
              />
            </a-col>
          </a-row>
          <a-row type="flex" class="row">
            <a-col flex="6em" class="label">软件包</a-col>
            <a-col :flex="1">
              <a-upload class="upload" :before-upload="beforeUpload" @change="uploadChange" accept=".zip,.rar">
              <a-upload
                class="upload"
                :before-upload="beforeUpload"
                @change="uploadChange"
                accept=".zip,.rar"
              >
                <a-button type="primary">选择软件</a-button>
              </a-upload>
            </a-col>
@@ -89,7 +171,12 @@
        <a-row type="flex" class="row">
          <a-col flex="6em" class="label">软件说明</a-col>
          <a-col :flex="1">
            <a-upload class="upload" :before-upload="beforeUpload" @change="uploadChange1" accept=".xls,.xlsx">
            <a-upload
              class="upload"
              :before-upload="beforeUpload"
              @change="uploadChange1"
              accept=".xls,.xlsx"
            >
              <a-button type="primary">说明文件</a-button>
            </a-upload>
          </a-col>
@@ -107,34 +194,81 @@
        </div>
      </div>
    </a-modal>
    <pop :visible.sync="popVisible" :x="popPosition.x" :y="popPosition.y" :info="popInfo" :position="popPosition.dir">
    <pop
      :visible.sync="popVisible"
      :x="popPosition.x"
      :y="popPosition.y"
      :info="popInfo"
      :position="popPosition.dir"
    >
    </pop>
    <!-- 操作原因 -->
    <a-modal :visible="reasonVisible" :width="460" title="操作原因" :destroyOnClose="true" :maskClosable="false"
      @cancel="reasonCancel" @ok="reasonOk">
    <a-modal
      :visible="reasonVisible"
      :width="460"
      title="操作原因"
      :destroyOnClose="true"
      :maskClosable="false"
      @cancel="reasonCancel"
      @ok="reasonOk"
    >
      <a-form-model-item ref="name" label="操作原因">
        <a-input type="textarea" v-model="reason" placeHolder="请输入操作原因" />
        <a-input
          type="textarea"
          v-model="reason"
          placeHolder="请输入操作原因"
        />
      </a-form-model-item>
    </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
      :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>
    <!-- 上传源码包 -->
    <a-modal :visible="uploadSourceShow" :footer="null" :width="760" title="上传软件源码包" :destroyOnClose="true"
      :maskClosable="false" @cancel="uploadSourceCancel">
    <a-modal
      :visible="uploadSourceShow"
      :footer="null"
      :width="760"
      title="上传软件源码包"
      :destroyOnClose="true"
      :maskClosable="false"
      @cancel="uploadSourceCancel"
    >
      <div class="">
        <template>
          <a-row type="flex" class="row">
            <a-col flex="6em" class="label">对应软件</a-col>
            <a-col :flex="1">
              <a-select mode="multiple" placeholder="请选择对应的软件" show-search v-model="names" style="width: 36em;">
                <a-select-option v-for="(item, idx) in otherSoftList" :key="'soft_' + idx" :value="item.fileName">
                  {{ item.fileName }} <span class="version">({{ item.version }})</span>
              <a-select
                mode="multiple"
                placeholder="请选择对应的软件"
                show-search
                v-model="names"
                style="width: 36em;"
              >
                <a-select-option
                  v-for="(item, idx) in otherSoftList"
                  :key="'soft_' + idx"
                  :value="item.fileName"
                >
                  {{ item.fileName }}
                  <span class="version">({{ item.version }})</span>
                </a-select-option>
              </a-select>
            </a-col>
@@ -142,16 +276,63 @@
          <a-row type="flex" class="row">
            <a-col flex="6em" class="label">软件源码包</a-col>
            <a-col :flex="1">
              <a-upload class="upload" :before-upload="beforeUpload" @change="sourceUploadChange" accept=".zip,.rar">
              <a-upload
                class="upload"
                :before-upload="beforeUpload"
                @change="sourceUploadChange"
                accept=".zip,.rar"
              >
                <a-button type="primary">选择软件</a-button>
              </a-upload>
            </a-col>
          </a-row>
        </template>
        <div class="modal-footer">
          <a-button type="danger" @click="uploadSourceCancel"> 取消 </a-button>
          <a-button type="primary" @click="uploadSource"> 提交 </a-button>
        </div>
      </div>
    </a-modal>
    <!-- 共享源码包 -->
    <a-modal
      :visible="connectSourceShow"
      :footer="null"
      :width="760"
      title="共享软件源码包"
      :destroyOnClose="true"
      :maskClosable="false"
      @cancel="connectSourceCancel"
    >
      <div class="">
        <template>
          <a-row type="flex" class="row">
            <a-col flex="10em" class="label">要共享该源码的软件</a-col>
            <a-col :flex="1">
              <a-select
                mode="multiple"
                placeholder="请选择对应的软件"
                show-search
                v-model="fileNames"
                style="width: 36em;"
              >
                <a-select-option
                  v-for="(item, idx) in otherSoftList"
                  :key="'soft_' + idx"
                  :value="item.fileName"
                >
                  {{ item.fileName }}
                  <span class="version">({{ item.version }})</span>
                </a-select-option>
              </a-select>
            </a-col>
          </a-row>
        </template>
        <div class="modal-footer">
          <a-button type="danger" @click="connectSourceCancel"> 取消 </a-button>
          <a-button type="primary" @click="connectSourceSubmit"> 提交 </a-button>
        </div>
      </div>
    </a-modal>
@@ -159,869 +340,955 @@
</template>
<script>
   import AdvanceTable from "@/components/table/advance/AdvanceTable";
   import checkPermit from "@/assets/js/tools/checkPermit";
   import PERMITS from "@/assets/js/const/const_permits";
   import DescRes from "./descRes";
   import Pop from "./pop";
   import offset from "@/assets/js/tools/offset";
   import moment from "moment";
   import { getUserList } from "../../permission/apis";
import AdvanceTable from "@/components/table/advance/AdvanceTable";
import checkPermit from "@/assets/js/tools/checkPermit";
import PERMITS from "@/assets/js/const/const_permits";
import DescRes from "./descRes";
import Pop from "./pop";
import offset from "@/assets/js/tools/offset";
import moment from "moment";
import { getUserList } from "../../permission/apis";
   import { message, Modal } from "ant-design-vue";
import { message, Modal } from "ant-design-vue";
   import {
      getList,
      downLoadSoftware,
      excelParse,
      productSoftwareSubmit,
      applyModel,
      updateSoftwareLock,
      deleteSoftwareApi,
      downLoadCode,
      getFileNameByCreateTime,
      uploadCode,
   } from "./apis";
   import { mapGetters } from "vuex";
   import EmailCard from "../../components/emailCard";
   import {
      searchDefaultMailUser,
      sendMail,
   } from "../../components/emailCard/apis";
import {
   getList,
   downLoadSoftware,
   excelParse,
   productSoftwareSubmit,
   applyModel,
   updateSoftwareLock,
   deleteSoftwareApi,
   downLoadCode,
   getFileNameByCreateTime,
   uploadCode,
  connectCode,
  getFileNameByOwner,
} from "./apis";
import { mapGetters } from "vuex";
import EmailCard from "../../components/emailCard";
import {
   searchDefaultMailUser,
   sendMail,
} from "../../components/emailCard/apis";
   import { getRoleUser } from "@/pages/user/apis";
   // TODO
   // const tester = ["李桂华"];
import { getRoleUser } from "@/pages/user/apis";
// TODO
// const tester = ["李桂华"];
   export default {
      name: "",
      data() {
         return {
            mailList: [],
            tester: [],
            versionTime: moment().format("YYYY-MM-DD HH:mm:ss"),
            reasonVisible: false,
            reason: "",
            currentObj: null,
            popVisible: false,
            uploadSourceShow: false,
            names: [],
            otherSoftList: [],
            popPosition: {
               x: 0,
               y: 0,
               dir: "bottom",
export default {
   name: "",
   data() {
      return {
      connectSourceShow: false,
      fileNames: [],
         mailList: [],
         tester: [],
         coderDown: [],
         coderUp: [],
         versionTime: moment().format("YYYY-MM-DD HH:mm:ss"),
         reasonVisible: false,
         reason: "",
         currentObj: null,
         popVisible: false,
         uploadSourceShow: false,
         names: [],
         otherSoftList: [],
         popPosition: {
            x: 0,
            y: 0,
            dir: "bottom",
         },
         popInfo: [],
         onlyXls: false,
         resData: [],
         file: null,
         file1: null,
         sourceFile: null,
         uploadShow: false,
         spinning: false,
         loading: false,
         pageCurr: 1,
         pageSize: 10,
         total: 0,
         y: 400,
         update: -1,
         conditions: {},
         columns: [
            {
               fixed: "left",
               title: "序号",
               dataIndex: "dataIndex",
               key: "dataIndex",
               align: "center",
               width: 60,
               noSearch: true,
               scopedSlots: { customRender: "dataIndex" },
            },
            popInfo: [],
            onlyXls: false,
            resData: [],
            file: null,
            file1: null,
            sourceFile: null,
            uploadShow: false,
            spinning: false,
            loading: false,
            pageCurr: 1,
            pageSize: 10,
            total: 0,
            y: 400,
            update: -1,
            conditions: {},
            columns: [
               {
                  fixed: "left",
                  title: "序号",
                  dataIndex: "dataIndex",
                  key: "dataIndex",
                  align: "center",
                  width: 60,
                  noSearch: true,
                  scopedSlots: { customRender: "dataIndex" },
            {
               title: "状态",
               dataIndex: "soft.lockFlag",
               dataType: "select",
               align: "center",
               width: 140,
               visible: false,
               searchAble: true,
               noSearch: true,
               search: {
                  default: 0,
                  selectOptions: [
                     {
                        title: "全部",
                        value: 11,
                     },
                     {
                        title: "可用",
                        value: 0,
                     },
                     {
                        title: "不可用",
                        value: 12,
                     },
                     {
                        title: "待测试",
                        value: -1,
                     },
                  ],
               },
               {
                  title: "状态",
                  dataIndex: "soft.lockFlag",
                  dataType: "select",
                  align: "center",
                  width: 140,
                  visible: false,
                  searchAble: true,
                  noSearch: true,
                  search: {
                     default: 0,
                     selectOptions: [
                        {
                           title: "全部",
                           value: 11,
                        },
                        {
                           title: "可用",
                           value: 0,
                        },
                        {
                           title: "不可用",
                           value: 12,
                        },
                        {
                           title: "待测试",
                           value: -1,
                        },
                     ],
                  },
                  // customCell: this.customCell,
               },
               {
                  title: "名称",
                  dataIndex: "soft.fileName",
                  align: "center",
                  searchAble: true,
                  customCell: this.customCell,
               },
               {
                  title: "上传日期",
                  dataIndex: "soft.createTime",
                  align: "center",
                  noSearch: true,
                  customCell: this.customCell,
               },
               {
                  title: "是否已上传源码",
                  dataIndex: "codeFlagStr",
                  align: "center",
                  noSearch: true,
                  customCell: this.customCell,
            scopedSlots: { customRender: 'tags' },
               },
          {
                  title: "源码包名称",
                  dataIndex: "codeName",
                  align: "center",
                  width: 180,
                  noSearch: true,
                  customCell: this.customCell,
               },
               {
                  title: "类型",
                  dataIndex: "soft.type",
                  align: "center",
                  width: 180,
                  noSearch: true,
                  customCell: this.customCell,
               },
               {
                  title: "版本",
                  dataIndex: "soft.version",
                  align: "center",
                  searchAble: true,
                  customCell: this.customCell,
               },
               {
                  title: "负责人",
                  dataIndex: "soft.owner",
                  align: "center",
                  searchAble: true,
                  width: 160,
                  customCell: this.customCell,
               },
               {
                  title: "适用机型号",
                  dataIndex: "applyModel",
                  align: "center",
                  searchAble: true,
                  visible: false,
               },
               {
                  title: "适用机料号",
                  dataIndex: "applyMaterialCode",
                  align: "center",
                  searchAble: true,
                  visible: false,
               },
               {
                  title: "板号",
                  dataIndex: "soft.boardNumber",
                  align: "center",
                  searchAble: true,
                  customCell: this.customCell,
               },
               {
                  title: "升级说明",
                  dataIndex: "soft.releaseNotes",
                  align: "center",
                  noSearch: true,
                  customCell: this.customCell,
               },
               {
                  title: "最后一次操作原因",
                  dataIndex: "soft.localReason",
                  align: "center",
                  noSearch: true,
                  customCell: this.customCell,
               },
               {
                  title: "操作",
                  dataIndex: "operation",
                  align: "center",
                  width: 228,
                  fixed: "right",
                  scopedSlots: { customRender: "action" },
                  noSearch: true,
               },
            ],
            dataSource: [],
            prodsColumns: [
               {
                  title: "型号",
                  dataIndex: "applyModel",
                  align: "center",
                  searchAble: true,
               },
               {
                  title: "料号",
                  dataIndex: "applyMaterialCode",
                  align: "center",
                  width: 180,
                  noSearch: true,
               },
            ],
            emailShow: false,
            emailInfo: {
               title: "",
               content: "",
               // customCell: this.customCell,
            },
            userList: [],
         };
            {
               title: "名称",
               dataIndex: "soft.fileName",
               align: "center",
               searchAble: true,
               customCell: this.customCell,
            },
            {
               title: "上传日期",
               dataIndex: "soft.createTime",
               align: "center",
               noSearch: true,
               customCell: this.customCell,
            },
            {
               title: "是否已上传源码",
               dataIndex: "codeFlagStr",
               align: "center",
               noSearch: true,
               customCell: this.customCell,
               scopedSlots: { customRender: 'tags' },
            },
            {
               title: "源码包名称",
               dataIndex: "codeName",
               align: "center",
               width: 180,
               noSearch: true,
               customCell: this.customCell,
            },
            {
               title: "类型",
               dataIndex: "soft.type",
               align: "center",
               width: 180,
               noSearch: true,
               customCell: this.customCell,
            },
            {
               title: "版本",
               dataIndex: "soft.version",
               align: "center",
               searchAble: true,
               customCell: this.customCell,
            },
            {
               title: "负责人",
               dataIndex: "soft.owner",
               align: "center",
               searchAble: true,
               width: 160,
               customCell: this.customCell,
            },
            {
               title: "适用机型号",
               dataIndex: "applyModel",
               align: "center",
               searchAble: true,
               visible: false,
            },
            {
               title: "适用机料号",
               dataIndex: "applyMaterialCode",
               align: "center",
               searchAble: true,
               visible: false,
            },
            {
               title: "板号",
               dataIndex: "soft.boardNumber",
               align: "center",
               searchAble: true,
               customCell: this.customCell,
            },
            {
               title: "升级说明",
               dataIndex: "soft.releaseNotes",
               align: "center",
               noSearch: true,
               customCell: this.customCell,
            },
            {
               title: "最后一次操作原因",
               dataIndex: "soft.localReason",
               align: "center",
               noSearch: true,
               customCell: this.customCell,
            },
            {
               title: "操作",
               dataIndex: "operation",
               align: "center",
               width: 228,
               fixed: "right",
               scopedSlots: { customRender: "action" },
               noSearch: true,
            },
         ],
         dataSource: [],
         prodsColumns: [
            {
               title: "型号",
               dataIndex: "applyModel",
               align: "center",
               searchAble: true,
            },
            {
               title: "料号",
               dataIndex: "applyMaterialCode",
               align: "center",
               width: 180,
               noSearch: true,
            },
         ],
         emailShow: false,
         emailInfo: {
            title: "",
            content: "",
         },
         userList: [],
      };
   },
   components: {
      EmailCard,
      AdvanceTable,
      DescRes,
      Pop,
   },
   methods: {
      moment,
      rowClassFn(record) {
         let classList = [];
         if (record.soft.lockFlag == -1) {
            classList.push("locked");
         }
         return classList;
      },
      components: {
         EmailCard,
         AdvanceTable,
         DescRes,
         Pop,
      disabledDate(current) {
         // Can not select days before today and today
         return current > moment().endOf("day");
      },
      methods: {
         moment,
         rowClassFn(record) {
            let classList = [];
            if (record.soft.lockFlag == -1) {
               classList.push("locked");
      onSearch(conditions, searchOptions) {
         // console.log(conditions);
         // console.log(searchOptions, "options");
         this.pageCurr = 1;
         this.conditions = conditions;
         this.searchData();
      },
      onPageChange(page, pageSize) {
         this.pageCurr = page;
         this.pageSize = pageSize;
         this.searchData();
      },
      onSizeChange(current, size) {
         this.pageCurr = 1;
         this.pageSize = size;
         this.searchData();
      },
      onRefresh(conditions) {
         this.conditions = conditions;
         this.searchData();
      },
      onReset(conditions) {
         // console.log(conditions, "reset");
         this.conditions = conditions;
         this.searchData();
      },
      searchData() {
         const { pageCurr, pageSize, conditions } = this;
         let params = {};
         if (undefined == conditions["soft.lockFlag"]) {
            conditions["soft.lockFlag"] = 11;
         }
         Object.keys(conditions).forEach((v) => {
            switch (v) {
               case "soft.lockFlag":
                  params["lockFlag"] = conditions[v];
                  break;
               case "soft.fileName":
                  params["fileName"] = conditions[v];
                  break;
               case "soft.owner":
                  params["owner"] = conditions[v];
                  break;
               case "soft.boardNumber":
                  params["boardNumber"] = conditions[v];
                  break;
               case "soft.version":
                  params["version"] = conditions[v];
                  break;
               default:
                  params[v] = conditions[v];
                  break;
            }
            return classList;
         },
         disabledDate(current) {
            // Can not select days before today and today
            return current > moment().endOf("day");
         },
         onSearch(conditions, searchOptions) {
            // console.log(conditions);
            // console.log(searchOptions, "options");
            this.pageCurr = 1;
            this.conditions = conditions;
            this.searchData();
         },
         onPageChange(page, pageSize) {
            this.pageCurr = page;
            this.pageSize = pageSize;
            this.searchData();
         },
         onSizeChange(current, size) {
            this.pageCurr = 1;
            this.pageSize = size;
            this.searchData();
         },
         onRefresh(conditions) {
            this.conditions = conditions;
            this.searchData();
         },
         onReset(conditions) {
            // console.log(conditions, "reset");
            this.conditions = conditions;
            this.searchData();
         },
         searchData() {
            const { pageCurr, pageSize, conditions } = this;
            let params = {};
            if (undefined == conditions["soft.lockFlag"]) {
               conditions["soft.lockFlag"] = 11;
         });
         getList(pageCurr, pageSize, params).then((res) => {
            res = res.data;
            // console.log(res);
            let data = [];
            let total = 0;
            if (res.code && res.data) {
               data = res.data2.list.map((v) => {
                  let soft = v.softwares[0];
                  return {
              ...v,
                     id: soft.id,
                     fileName: v.fileName,
                     codeFlag: v.codeFlag,
                     codeName: v.codeName || '--',
                     codeFlagStr: v.codeFlag ? '已上传源码' : '未上传源码',
                     soft,
                     links: v.softwares,
                  };
               });
               total = res.data2.total;
            }
            Object.keys(conditions).forEach((v) => {
               switch (v) {
                  case "soft.lockFlag":
                     params["lockFlag"] = conditions[v];
                     break;
                  case "soft.fileName":
                     params["fileName"] = conditions[v];
                     break;
                  case "soft.owner":
                     params["owner"] = conditions[v];
                     break;
                  case "soft.boardNumber":
                     params["boardNumber"] = conditions[v];
                     break;
                  case "soft.version":
                     params["version"] = conditions[v];
                     break;
                  default:
                     params[v] = conditions[v];
                     break;
               }
            });
            getList(pageCurr, pageSize, params).then((res) => {
               res = res.data;
               // console.log(res);
               let data = [];
               let total = 0;
               if (res.code && res.data) {
                  data = res.data2.list.map((v) => {
                     let soft = v.softwares[0];
                     return {
                        id: soft.id,
                        fileName: v.fileName,
                        codeFlag: v.codeFlag,
                codeName: v.codeName || '--',
                        codeFlagStr: v.codeFlag ? '已上传源码' : '未上传源码',
                        soft,
                        links: v.softwares,
                     };
                  });
                  total = res.data2.total;
               }
               this.dataSource = data;
               this.total = total;
               if (-1 == this.update) {
                  this.update = Math.random();
               }
            });
         },
         download(obj) {
            const { id } = obj;
            let loading = this.$layer.loading();
            downLoadSoftware(id).then((res) => {
               // console.log(res, "===========");
               let { headers, data, status } = res;
               if (200 == status && data) {
                  let url = window.URL.createObjectURL(data);
                  const matchRes = /filename=(.*)/.exec(headers["content-disposition"]);
                  const fileName = matchRes
                     ? decodeURI(matchRes[1].trim())
                     : "未知文件名.zip";
                  let link = document.createElement("a");
                  link.style.display = "none";
                  link.href = url;
                  link.download = fileName;
                  document.body.appendChild(link);
                  link.click();
                  this.$layer.close(loading);
                  document.body.removeChild(link);
                  window.URL.revokeObjectURL(url);
               } else {
                  this.$layer.close(loading);
                  this.$message.error("操作失败");
               }
            });
         },
         resize() {
            setTimeout(() => {
            this.dataSource = data;
            this.total = total;
            if (-1 == this.update) {
               this.update = Math.random();
            }, 200);
         },
         activeFN() {
            this.resize();
         },
         showUpload() {
            }
         });
      },
      download(obj) {
         const { id } = obj;
         let loading = this.$layer.loading();
         downLoadSoftware(id).then((res) => {
            // console.log(res, "===========");
            let { headers, data, status } = res;
            if (200 == status && data) {
               let url = window.URL.createObjectURL(data);
               const matchRes = /filename=(.*)/.exec(headers["content-disposition"]);
               const fileName = matchRes
                  ? decodeURI(matchRes[1].trim())
                  : "未知文件名.zip";
               let link = document.createElement("a");
               link.style.display = "none";
               link.href = url;
               link.download = fileName;
               document.body.appendChild(link);
               link.click();
               this.$layer.close(loading);
               document.body.removeChild(link);
               window.URL.revokeObjectURL(url);
            } else {
               this.$layer.close(loading);
               this.$message.error("操作失败");
            }
         });
      },
      resize() {
         setTimeout(() => {
            this.update = Math.random();
         }, 200);
      },
      activeFN() {
         this.resize();
      },
      showUpload() {
         this.file = null;
         this.file1 = null;
         this.resData = [];
         this.onlyXls = false;
         this.versionTime = moment().format("YYYY-MM-DD HH:mm:ss");
         this.uploadShow = true;
      },
      updateDesc() {
         this.file = null;
         this.file1 = null;
         this.resData = [];
         this.onlyXls = true;
         this.uploadShow = true;
      },
      beforeUpload() {
         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.resData = [];
            this.onlyXls = false;
            this.versionTime = moment().format("YYYY-MM-DD HH:mm:ss");
            this.uploadShow = true;
         },
         updateDesc() {
            this.file = null;
            this.file1 = null;
            this.resData = [];
            this.onlyXls = true;
            this.uploadShow = true;
         },
         beforeUpload() {
            return false;
         },
         uploadChange(data) {
            const { file, fileList } = data;
            if (fileList.length > 1) {
               fileList.shift();
            }
            if (fileList.length) {
               this.file = fileList[0].originFileObj;
         }
         const formData = new FormData();
         formData.append("multipartFile", this.file1);
         excelParse(formData).then((res) => {
            const { code, data, data2, msg } = res.data;
            let list = [];
            if (code && data) {
               list = data2;
               this.$message.success(msg);
            } else {
               this.file = null;
               this.$message.error("解析失败");
            }
         },
         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.resData = [];
               return false;
            }
            const formData = new FormData();
            formData.append("multipartFile", this.file1);
            excelParse(formData).then((res) => {
               const { code, data, data2, msg } = res.data;
               let list = [];
               if (code && data) {
                  list = data2;
            this.resData = list;
         });
      },
      uploadCancel() {
         this.uploadShow = false;
      },
      uploadSoftware() {
         if (!this.file) {
            this.$message.error("请选择要上传的软件包");
            return false;
         }
         if (!this.file1) {
            this.$message.error("请选择软件说明文件");
            return false;
         }
         if (!this.resData.length) {
            this.$message.error("软件说明文件解析异常");
            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("file1", this.file);
         formData.append("file2", this.file1);
         formData.append("fontUpdateTime", this.versionTime);
         formData.append("softwareStr", JSON.stringify(this.resData));
         productSoftwareSubmit(formData)
            .then((res) => {
               let { code, data, msg } = res.data;
               if (code) {
                  this.uploadShow = false;
                  this.$message.success(msg);
                  this.searchData();
               } else {
                  this.$message.error(msg);
               }
               this.$layer.close(loading);
            })
            .catch((error) => {
               this.$layer.close(loading);
               console.log(error);
            });
      },
      applyModel() {
         if (!this.file1) {
            this.$message.error("请选择软件说明文件");
            return false;
         }
         if (!this.resData.length) {
            this.$message.error("软件说明文件解析异常");
            return false;
         }
         let loading = this.$layer.loading();
         const formData = new FormData();
         formData.append("multipartFile", this.file1);
         formData.append("softwareStr", JSON.stringify(this.resData));
         applyModel(formData)
            .then((res) => {
               let { code, data, msg } = res.data;
               if (code) {
                  this.uploadShow = false;
                  this.$message.success(msg);
                  this.searchData();
               } else {
                  this.$message.error("解析失败");
               }
               this.resData = list;
               this.$layer.close(loading);
            })
            .catch((error) => {
               this.$layer.close(loading);
               console.log(error);
            });
         },
         uploadCancel() {
            this.uploadShow = false;
         },
         uploadSoftware() {
            if (!this.file) {
               this.$message.error("请选择要上传的软件包");
               return false;
            }
            if (!this.file1) {
               this.$message.error("请选择软件说明文件");
               return false;
            }
            if (!this.resData.length) {
               this.$message.error("软件说明文件解析异常");
               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("file1", this.file);
            formData.append("file2", this.file1);
            formData.append("fontUpdateTime", this.versionTime);
            formData.append("softwareStr", JSON.stringify(this.resData));
            productSoftwareSubmit(formData)
               .then((res) => {
                  let { code, data, msg } = res.data;
                  if (code) {
                     this.uploadShow = false;
                     this.$message.success(msg);
                     this.searchData();
                  } else {
                     this.$message.error(msg);
                  }
                  this.$layer.close(loading);
               })
               .catch((error) => {
                  this.$layer.close(loading);
                  console.log(error);
               });
         },
         applyModel() {
            if (!this.file1) {
               this.$message.error("请选择软件说明文件");
               return false;
            }
            if (!this.resData.length) {
               this.$message.error("软件说明文件解析异常");
               return false;
            }
            let loading = this.$layer.loading();
            const formData = new FormData();
            formData.append("multipartFile", this.file1);
            formData.append("softwareStr", JSON.stringify(this.resData));
            applyModel(formData)
               .then((res) => {
                  let { code, data, msg } = res.data;
                  if (code) {
                     this.uploadShow = false;
                     this.$message.success(msg);
                     this.searchData();
                  } else {
                     this.$message.error("解析失败");
                  }
                  this.$layer.close(loading);
               })
               .catch((error) => {
                  this.$layer.close(loading);
                  console.log(error);
               });
         },
         cellMouseenter(e, obj) {
            // console.log("enter", e, obj);
            const wraper = this.$refs.wraper;
            const { clientHeight, clientWidth } = wraper;
            const { target, clientX, clientY } = e;
            let { left: x, top: y } = offset(wraper);
            x = clientX - x;
            y = clientY - y;
            // 如果clientHeight 小于380 * 2 则左右布局
            let dir = "bottom";
            if (clientHeight < 380 * 2) {
               if (x + 420 + 18 > clientWidth) {
                  dir = "left";
               } else {
                  dir = "right";
               }
               if (y < 180) {
                  y = 180;
               } else if (y > clientHeight - 378) {
                  y = clientHeight / 2;
               }
      },
      cellMouseenter(e, obj) {
         // console.log("enter", e, obj);
         const wraper = this.$refs.wraper;
         const { clientHeight, clientWidth } = wraper;
         const { target, clientX, clientY } = e;
         let { left: x, top: y } = offset(wraper);
         x = clientX - x;
         y = clientY - y;
         // 如果clientHeight 小于380 * 2 则左右布局
         let dir = "bottom";
         if (clientHeight < 380 * 2) {
            if (x + 420 + 18 > clientWidth) {
               dir = "left";
            } else {
               if (y + 18 + 360 > clientHeight) {
                  // y = clientHeight - 378;
                  dir = "top";
               } else {
                  dir = "bottom";
               }
               if (x < 300) {
                  x = 300;
               }
               if (x + 300 > clientWidth) {
                  x = clientWidth - 300;
               }
               dir = "right";
            }
            this.popPosition.x = x;
            this.popPosition.y = y;
            this.popPosition.dir = dir;
            this.popInfo = obj.links;
            this.popVisible = true;
         },
         cellMouseleave(e, obj) {
            // console.log("leave", obj);
            this.popVisible = false;
         },
         customCell(record) {
            if (y < 180) {
               y = 180;
            } else if (y > clientHeight - 378) {
               y = clientHeight / 2;
            }
         } else {
            if (y + 18 + 360 > clientHeight) {
               // y = clientHeight - 378;
               dir = "top";
            } else {
               dir = "bottom";
            }
            if (x < 300) {
               x = 300;
            }
            if (x + 300 > clientWidth) {
               x = clientWidth - 300;
            }
         }
         this.popPosition.x = x;
         this.popPosition.y = y;
         this.popPosition.dir = dir;
         this.popInfo = obj.links;
         this.popVisible = true;
      },
      cellMouseleave(e, obj) {
         // console.log("leave", obj);
         this.popVisible = false;
      },
      customCell(record) {
         return {
            on: {
               mouseenter: (e) => this.cellMouseenter(e, record),
               mouseleave: (e) => this.cellMouseleave(e, record),
            },
         };
      },
      reasonCancel() {
         this.reasonVisible = false;
      },
      reasonOk() {
         let {
            soft: { fileUrl, lockFlag },
         } = this.currentObj;
         // 多传一个当前状态
         let lockFlagNow = lockFlag;
         lockFlag = !lockFlag * 1;
         let params = {
            fileUrl,
            localReason: this.reason,
            lockFlag,
            lockFlagNow,
         };
         updateSoftwareLock(params).then((res) => {
            const { code, data } = res.data;
            if (code && data) {
               this.$message.success("操作成功");
               this.reasonVisible = false;
               // 如果是测试人员解锁确认 则自动发送邮件
               if (lockFlagNow == -1 && this.isTester) {
                  this.sendEmail();
               }
               this.searchData();
            } else {
               this.$message.error("操作失败");
            }
         });
      },
      sendEmail() {
         let { title, content } = this.handleEmailShow(this.currentObj, true);
         let params = { mailList: this.mailList, title, content };
         sendMail(params);
      },
      lock(record) {
         this.reason = "";
         this.currentObj = record;
         this.reasonVisible = true;
      },
      handleEmailShow(record, get) {
         this.emailInfo.title =
            "[软件发布记录]" +
            record.soft.fileName +
            " 版本号:" +
            record.soft.version;
         let { soft, links } = record;
         let content = [];
         content.push("软件基本信息");
         content.push("文件名称: " + soft.fileName);
         content.push("板号: " + soft.boardNumber);
         content.push("软件类型: " + soft.type);
         content.push("软件版本: " + soft.version);
         content.push("软件基于版本: " + soft.basedVersion);
         content.push("软件负责人: " + soft.owner);
         content.push("归档日期: " + soft.filingDate);
         content.push("软件类型: " + soft.type);
         content.push("软件适用机型");
         links.forEach((v) => {
            content.push(
               "物料编码: " + v.applyMaterialCode + " 规格型号: " + v.applyModel
            );
         });
         content.push("发布说明: " + soft.releaseNotes);
         this.emailInfo.content = content.join("\n");
         if (get) {
            return {
               on: {
                  mouseenter: (e) => this.cellMouseenter(e, record),
                  mouseleave: (e) => this.cellMouseleave(e, record),
               },
               title: this.emailInfo.title,
               content: content.join("\n"),
            };
         },
         reasonCancel() {
            this.reasonVisible = false;
         },
         reasonOk() {
            let {
               soft: { fileUrl, lockFlag },
            } = this.currentObj;
            // 多传一个当前状态
            let lockFlagNow = lockFlag;
            lockFlag = !lockFlag * 1;
            let params = {
               fileUrl,
               localReason: this.reason,
               lockFlag,
               lockFlagNow,
            };
            updateSoftwareLock(params).then((res) => {
               const { code, data } = res.data;
               if (code && data) {
                  this.$message.success("操作成功");
                  this.reasonVisible = false;
                  // 如果是测试人员解锁确认 则自动发送邮件
                  if (lockFlagNow == -1 && this.isTester) {
                     this.sendEmail();
                  }
                  this.searchData();
               } else {
                  this.$message.error("操作失败");
               }
            });
         },
         sendEmail() {
            let { title, content } = this.handleEmailShow(this.currentObj, true);
            let params = { mailList: this.mailList, title, content };
            sendMail(params);
         },
         lock(record) {
            this.reason = "";
            this.currentObj = record;
            this.reasonVisible = true;
         },
         handleEmailShow(record, get) {
            this.emailInfo.title =
               "[软件发布记录]" +
               record.soft.fileName +
               " 版本号:" +
               record.soft.version;
            let { soft, links } = record;
            let content = [];
            content.push("软件基本信息");
            content.push("文件名称: " + soft.fileName);
            content.push("板号: " + soft.boardNumber);
            content.push("软件类型: " + soft.type);
            content.push("软件版本: " + soft.version);
            content.push("软件基于版本: " + soft.basedVersion);
            content.push("软件负责人: " + soft.owner);
            content.push("归档日期: " + soft.filingDate);
            content.push("软件类型: " + soft.type);
            content.push("软件适用机型");
            links.forEach((v) => {
               content.push(
                  "物料编码: " + v.applyMaterialCode + " 规格型号: " + v.applyModel
               );
            });
            content.push("发布说明: " + soft.releaseNotes);
            this.emailInfo.content = content.join("\n");
            if (get) {
               return {
                  title: this.emailInfo.title,
                  content: content.join("\n"),
               };
            }
            this.emailShow = true;
         },
         emailCancel() {
            this.emailShow = false;
         },
         searchAllUserList() {
            getUserList()
               .then((res) => {
                  let rs = res.data;
                  if (rs.code && rs.data) {
                     this.userList = rs.data2;
                     this.searchDefaultMailUser();
                  }
               })
               .catch((error) => {
                  console.log(error);
               });
         },
         searchDefaultMailUser() {
            // 软件 type为1
            let type = 1;
            searchDefaultMailUser(type).then((res) => {
         }
         this.emailShow = true;
      },
      emailCancel() {
         this.emailShow = false;
      },
      searchAllUserList() {
         getUserList()
            .then((res) => {
               let rs = res.data;
               let data = [];
               if (rs.code === 1) {
                  data = rs.data.map((item) => {
                     return item.user;
                  });
               if (rs.code && rs.data) {
                  this.userList = rs.data2;
                  this.searchDefaultMailUser();
               }
               this.mailList = this.userList
                  .filter((o) => data.includes(o.name) && o.mail)
                  .map((item) => {
                     return item.mail;
                  });
            })
            .catch((error) => {
               console.log(error);
            });
         },
         getRoleUser() {
            getRoleUser(0)
               .then((res) => {
                  let { code, data, data2 } = res.data;
                  let list = [];
                  if (code && data) {
                     // console.log(data);
                     list = data2.map((v) => v.name);
                  }
                  this.tester = list;
               })
               .catch((err) => {
                  console.log(err);
      },
      searchDefaultMailUser() {
         // 软件 type为1
         let type = 1;
         searchDefaultMailUser(type).then((res) => {
            let rs = res.data;
            let data = [];
            if (rs.code === 1) {
               data = rs.data.map((item) => {
                  return item.user;
               });
         },
         handleConfirmDelete(obj) {
            Modal.confirm({
               content: () => "删除当前软件,删除后无法恢复,请注意!!!",
               onOk: async () => {
                  try {
                     const res = await deleteSoftwareApi(
                        obj.soft.fileName,
                        obj.soft.version
                     );
                     const rs = res.data;
                     if (rs.code === 1 && rs.data) {
                        this.$message.success("删除成功。");
                     } else {
                        this.$message.error("删除失败!!!");
                     }
                     this.searchData();
                  } catch (e) {
                     this.$message.error("删除失败,请联系开发人员!!!");
                     console.log(e);
                  }
               },
            });
         },
         // 查询其他版本 与当前软件上传日期前三天内的列表
         getOtherSoft(date) {
            return getFileNameByCreateTime(date).then((res) => {
            }
            this.mailList = this.userList
               .filter((o) => data.includes(o.name) && o.mail)
               .map((item) => {
                  return item.mail;
               });
         });
      },
      getRoleUser() {
         getRoleUser(0)
            .then((res) => {
               let { code, data, data2 } = res.data;
               let list = [];
               if (code && data) {
                  console.log(data);
                  list = data2;
                  // console.log(data);
                  list = data2.map((v) => v.name);
               }
               this.otherSoftList = list;
               return list;
               this.tester = list;
            })
               .catch((err) => {
                  console.log(err);
                  return [];
               });
         },
         sourceUploadChange(data) {
            const { file, fileList } = data;
            if (fileList.length > 1) {
               fileList.shift();
            }
            if (fileList.length) {
               this.sourceFile = fileList[0].originFileObj;
            } else {
               this.sourceFile = null;
            }
         },
         // 上传源码包
         uploadSource(record) {
            if (!this.sourceFile) {
               this.$message.error("请选择要上传的源码包");
               return false;
            }
            if (!this.names.length) {
               this.$message.error("请选择源码包对应的软件");
               return false;
            }
            let loading = this.$layer.loading();
            const formData = new FormData();
            formData.append("file", this.sourceFile);
            formData.append("fileNames", this.names.join(','));
            uploadCode(formData)
               .then((res) => {
                  let { code, data, msg } = res.data;
                  if (code) {
                     this.uploadSourceShow = false;
                     this.$message.success('上传成功');
                     this.searchData();
                  } else {
                     this.$message.error('上传失败');
                  }
                  this.$layer.close(loading);
               })
               .catch((error) => {
                  this.$layer.close(loading);
                  console.log(error);
               });
         },
         // 下载源码包
         downloadSource(record) {
            let loading = this.$layer.loading();
            downLoadCode(record.fileName).then((res) => {
               let { headers, data, status } = res;
               if (200 == status && data) {
                  let url = window.URL.createObjectURL(data);
                  const matchRes = /filename=(.*)/.exec(headers["content-disposition"]);
                  const fileName = matchRes
                     ? decodeURI(matchRes[1].trim())
                     : "未知文件名.zip";
                  let link = document.createElement("a");
                  link.style.display = "none";
                  link.href = url;
                  link.download = fileName;
                  document.body.appendChild(link);
                  link.click();
                  this.$layer.close(loading);
                  document.body.removeChild(link);
                  window.URL.revokeObjectURL(url);
               } else {
                  this.$layer.close(loading);
                  this.$message.error("操作失败");
               }
            .catch((err) => {
               console.log(err);
            });
         },
         async uploadSourceClick(obj) {
            console.log('obj', obj, '=============');
            this.currentObj = obj;
            let date = obj.soft.createTime.split(' ')[0];
            await this.getOtherSoft(date);
            this.names = [obj.fileName];
            this.uploadSourceShow = true;
         },
         uploadSourceCancel() {
            this.uploadSourceShow = false;
         },
         // 上传源码人员列表
         getRoleUser(3)
            .then((res) => {
               let { code, data, data2 } = res.data;
               let list = [];
               if (code && data) {
                  // console.log(data);
                  list = data2.map((v) => v.name);
               }
               this.coderUp = list;
            })
            .catch((err) => {
               console.log(err);
            });
         // 下载源码人员列表
         getRoleUser(2)
            .then((res) => {
               let { code, data, data2 } = res.data;
               let list = [];
               if (code && data) {
                  // console.log(data);
                  list = data2.map((v) => v.name);
               }
               this.coderDown = list;
            })
            .catch((err) => {
               console.log(err);
            });
      },
      watch: {
         update(n) {
            if (-1 != n && !this._inactive) {
               this.$nextTick(() => {
                  const table = this.$refs.table;
                  const header = document.querySelectorAll(
                     ".doc-center-table .ant-table-header"
                  )[0].clientHeight;
                  const bar = document.querySelectorAll(".header-bar")[0].clientHeight;
                  if (table.fullScreen) {
                     this.y = table.$el.clientHeight - bar - header - 64;
      handleConfirmDelete(obj) {
         Modal.confirm({
            content: () => "删除当前软件,删除后无法恢复,请注意!!!",
            onOk: async () => {
               try {
                  const res = await deleteSoftwareApi(
                     obj.soft.fileName,
                     obj.soft.version
                  );
                  const rs = res.data;
                  if (rs.code === 1 && rs.data) {
                     this.$message.success("删除成功。");
                  } else {
                     const wraper = this.$refs.wraper.clientHeight;
                     const card = document.querySelectorAll(".ant-card-body")[0];
                     const { paddingBottom, paddingTop } = getComputedStyle(card, null);
                     const h =
                        wraper -
                        header -
                        64 -
                        bar -
                        parseInt(paddingBottom) -
                        parseInt(paddingTop);
                     // console.log(h, "h",wraper, header, bar );
                     this.y = h;
                     this.$message.error("删除失败!!!");
                  }
               });
            }
         },
         affixed() {
            setTimeout(() => {
               this.update = Math.random();
            }, 200);
         },
                  this.searchData();
               } catch (e) {
                  this.$message.error("删除失败,请联系开发人员!!!");
                  console.log(e);
               }
            },
         });
      },
      computed: {
         ...mapGetters("account", ["permits", "user"]),
         ...mapGetters("setting", ["affixed"]),
         canUploadSoftware() {
            return checkPermit(PERMITS.uploadSoftware, this.permits);
         },
         canDownloadSoftware() {
            return checkPermit(PERMITS.downloadSoftware, this.permits);
         },
         canLock() {
            return checkPermit(PERMITS.lockOther, this.permits);
         },
         isTester() {
            return this.tester.some((v) => v == this.user.name);
         },
         isCoder() {
            return '李文涛' == this.user.name;
      // 查询其他版本 与当前软件上传日期前三天内的列表
      getOtherSoft(date) {
         return getFileNameByCreateTime(date).then((res) => {
            let { code, data, data2 } = res.data;
            let list = [];
            if (code && data) {
               console.log(data);
               list = data2;
            }
            this.otherSoftList = list;
            return list;
         })
            .catch((err) => {
               console.log(err);
               return [];
            });
      },
      sourceUploadChange(data) {
         const { file, fileList } = data;
         if (fileList.length > 1) {
            fileList.shift();
         }
         if (fileList.length) {
            this.sourceFile = fileList[0].originFileObj;
         } else {
            this.sourceFile = null;
         }
      },
      mounted() {
         this.getRoleUser();
         this.searchData();
         this.searchAllUserList();
         window.addEventListener("resize", this.resize);
      // 上传源码包
      uploadSource(record) {
         if (!this.sourceFile) {
            this.$message.error("请选择要上传的源码包");
            return false;
         }
         if (!this.names.length) {
            this.$message.error("请选择源码包对应的软件");
            return false;
         }
         let loading = this.$layer.loading();
         const formData = new FormData();
         formData.append("file", this.sourceFile);
         formData.append("fileNames", this.names.join(','));
         uploadCode(formData)
            .then((res) => {
               let { code, data, msg } = res.data;
               if (code) {
                  this.uploadSourceShow = false;
                  this.$message.success('上传成功');
                  this.searchData();
               } else {
                  this.$message.error('上传失败');
               }
               this.$layer.close(loading);
            })
            .catch((error) => {
               this.$layer.close(loading);
               console.log(error);
            });
      },
      destroyed() {
         window.removeEventListener("resize", this.resize);
      // 下载源码包
      downloadSource(record) {
         let loading = this.$layer.loading();
         downLoadCode(record.fileName).then((res) => {
            let { headers, data, status } = res;
            if (200 == status && data) {
               let url = window.URL.createObjectURL(data);
               const matchRes = /filename=(.*)/.exec(headers["content-disposition"]);
               const fileName = matchRes
                  ? decodeURI(matchRes[1].trim())
                  : "未知文件名.zip";
               let link = document.createElement("a");
               link.style.display = "none";
               link.href = url;
               link.download = fileName;
               document.body.appendChild(link);
               link.click();
               this.$layer.close(loading);
               document.body.removeChild(link);
               window.URL.revokeObjectURL(url);
            } else {
               this.$layer.close(loading);
               this.$message.error("操作失败");
            }
         });
      },
   };
      async uploadSourceClick(obj) {
         // console.log('obj', obj, '=============');
         this.currentObj = obj;
         let date = obj.soft.createTime.split(' ')[0];
         await this.getOtherSoft(date);
         this.names = [obj.fileName];
         this.uploadSourceShow = true;
      },
    // 共享源码
    async connectSource(record) {
      let loading = this.$layer.loading();
      this.currentObj = record;
      this.fileNames = [];
      await this.getSoftwareList(record.soft.owner);
      this.$layer.close(loading);
      this.connectSourceShow = true;
    },
    // 根据负责人 查询软件列表 未上传源码
    async getSoftwareList(name) {
      let _res = await getFileNameByOwner(name);
      let res = _res.data;
      let list = [];
      if (res.code && res.data) {
        list = res.data2;
      }
      this.otherSoftList = list;
    },
    connectSourceCancel() {
      this.connectSourceShow = false;
    },
    connectSourceSubmit() {
      let num = this.currentObj.codeNum;
      let fileNames = this.fileNames;
      if (!fileNames.length) {
        this.$message.error('请选择要共享源码包的软件');
        return false;
      }
      let loading = this.$layer.loading();
      connectCode(num, fileNames).then((res) => {
        let { code, data } = res.data;
        this.$layer.close(loading);
        if (code && data) {
          this.$message.success('操作成功');
          this.connectSourceShow = false;
          this.searchData();
        } else {
          this.$message.error('操作失败');
        }
      })
      .catch((err) => {
        this.$layer.close(loading);
        console.log(err);
      });
    },
      uploadSourceCancel() {
         this.uploadSourceShow = false;
      },
   },
   watch: {
      update(n) {
         if (-1 != n && !this._inactive) {
            this.$nextTick(() => {
               const table = this.$refs.table;
               const header = document.querySelectorAll(
                  ".doc-center-table .ant-table-header"
               )[0].clientHeight;
               const bar = document.querySelectorAll(".header-bar")[0].clientHeight;
               if (table.fullScreen) {
                  this.y = table.$el.clientHeight - bar - header - 64;
               } else {
                  const wraper = this.$refs.wraper.clientHeight;
                  const card = document.querySelectorAll(".ant-card-body")[0];
                  const { paddingBottom, paddingTop } = getComputedStyle(card, null);
                  const h =
                     wraper -
                     header -
                     64 -
                     bar -
                     parseInt(paddingBottom) -
                     parseInt(paddingTop);
                  // console.log(h, "h",wraper, header, bar );
                  this.y = h;
               }
            });
         }
      },
      affixed() {
         setTimeout(() => {
            this.update = Math.random();
         }, 200);
      },
   },
   computed: {
      ...mapGetters("account", ["permits", "user"]),
      ...mapGetters("setting", ["affixed"]),
      canUploadSoftware() {
         return checkPermit(PERMITS.uploadSoftware, this.permits);
      },
      canDownloadSoftware() {
         return checkPermit(PERMITS.downloadSoftware, this.permits);
      },
      canLock() {
         return checkPermit(PERMITS.lockOther, this.permits);
      },
      isTester() {
         return this.tester.some((v) => v == this.user.name);
      },
      isCoderUp() {
         return this.coderUp.some((v) => v == this.user.name);
      },
      isCoderDown() {
         return this.coderDown.some((v) => v == this.user.name);
      }
   },
   mounted() {
      this.getRoleUser();
      this.searchData();
      this.searchAllUserList();
      window.addEventListener("resize", this.resize);
   },
   destroyed() {
      window.removeEventListener("resize", this.resize);
   },
};
</script>
<style scoped lang="less">
@@ -1043,6 +1310,7 @@
}
.modal-footer {
  margin-top: 16px;
  text-align: right;
  button+button {
@@ -1105,6 +1373,7 @@
/deep/.locked.locked.locked:hover>td {
  background: #fcd583;
}
.version {
  color: #090;
  display: inline-block;