<template>
  <div class="wrapper-container">
    <el-row :gutter="10">
      <el-col :span="6" style="width: 286px">
        <el-card class="group">
          <div slot="header">
            分组管理
            <el-tooltip class="item" effect="dark" content="添加根节点" placement="top-start">
              <el-button class="pull-right" type="text" @click="add('0')" icon="el-icon-plus"></el-button>
            </el-tooltip>
          </div>
          <el-row>
            <el-col :span="24">
              <el-tree :data="treeData" ref="scriptTree" node-key="id" :props="defaultProps" :highlight-current="true" :check-on-click-node="true" @node-click="handleNodeClick">
                <span class="custom-tree-node" slot-scope="{ node, data }">
                  <div class="custom-tree-node-wrapper">
                    <span class="custom-tree-node-label">
                      {{ node.label }}
                    </span>
                    <span class="operate-btns">
                      <dot-dropdown :events="dropMenuEvents" :data="{ node, data }" @addNode="addNode" @editNode="editNode" @removeNode="removeNode" />
                    </span>
                  </div>
                </span>
              </el-tree>
            </el-col>
          </el-row>
        </el-card>
      </el-col>
      <el-col :span="18" style="width: calc(100% - 286px)">
        <el-card>
          <el-tabs v-model="typeName" @tab-click="handleSearch">
            <el-tab-pane name="Ansible" label="Ansible">
              <cb-advance-table :data="list" :card-border="false" :searchConfigs="searchConfigs" :params="params" :total="total" :columns="ansibleColumns" :get-list="getList" :loading="loading" ref="ansibleTableRef" @select="handleSelectItem" @select-all="handleSelectAll">
                <!-- <template #action>
                  <el-button type="primary" :disabled="!selectList.length" @click.native="handleConfig({}, 'exclude')"> 排除 </el-button>
                  <el-button type="primary" :disabled="!selectList.length" @click.native="handleConfig({}, 'recovery')"> 恢复 </el-button>
                  <el-button type="primary" @click.native="handleDeployGaia"> 扩容 </el-button>
                </template> -->
                <template #name="val, record">
                  <span class="detail-href" @click="getDetail(record.id)">{{ val }}</span>
                </template>
                <template #isSuper="val">
                  {{ val == null ? '--' : val ? '是' : '否' }}
                </template>
                <template #deleted="deleted">
                  {{ deleted == null ? '--' : deleted ? '异常' : '正常' }}
                </template>
                <template #isExclude="val">
                  {{ val == null ? '--' : val ? '是' : '否' }}
                </template>
                <template #level="level">
                  <cb-status-icon :type="level | levelFilter('color')">{{ level | levelFilter('name') }} </cb-status-icon>
                </template>
                <template #operate="val, record">
                  <el-button type="text" @click.native="setting(record)" :disabled="record.deleted"> 配置 </el-button>
                  <!-- <div class="action-divider"></div>
                  <el-button type="text" @click.native="handleConfig(record)" :disabled="record.deleted"> {{ record.isExclude ? '恢复' : '排除' }} </el-button>
                  <div class="action-divider"></div>
                  <el-dropdown trigger="click">
                    <span class="el-dropdown-link"> 更多<i class="el-icon-arrow-down el-icon--right"></i> </span>
                    <template #dropdown>
                      <el-dropdown-menu>
                        <el-dropdown-item @click.native="handleDelGaia(record)" :disabled="record.deleted"> 缩容 </el-dropdown-item>
                      </el-dropdown-menu>
                    </template>
                  </el-dropdown> -->
                </template>
              </cb-advance-table>
            </el-tab-pane>
            <!-- <el-tab-pane name="SaltMaster" label="SaltMaster">
              <cb-advance-table
                :card-border="false"
                :data="saltMasterList"
                :searchConfigs="saltMasterSearchConfigs"
                :params="paramt"
                :total="saltMasterTotal"
                :columns="saltMasterColumns"
                :get-list="getSaltMasterList"
                :loading="saltMasterLoading"
                ref="saltTableRef"
                @select="handleSelectItem"
                @select-all="handleSelectAll"
              >
                <template #action>
                  <el-button @click="handleCreate(null, 1)" type="primary" icon="el-icon-plus">新增 </el-button>
                </template>
                <template #name="val, record">
                  <span class="detail-href" @click="getDetail(record.id)">{{ val }}</span>
                </template>
                <template #level="level">
                  <cb-status-icon :type="level | levelFilter('color')">{{ level | levelFilter('name') }} </cb-status-icon>
                </template>
                <template #operate="val, record">
                  <el-button icon="el-icon-edit" type="text" @click="handleCreate(record, 2)"> 编辑 </el-button>
                  <div class="action-divider"></div>
                  <el-button icon="el-icon-delete" type="text" @click="handleDelete(record.id)"> 删除 </el-button>
                  <div class="action-divider"></div>
                  <el-dropdown trigger="click">
                    <span class="el-dropdown-link"> 更多<i class="el-icon-arrow-down el-icon--right"></i> </span>
                    <el-dropdown-menu slot="dropdown">
                      <el-dropdown-item @click.native="syncMinion(record)"> minion同步 </el-dropdown-item>
                    </el-dropdown-menu>
                  </el-dropdown>
                </template>
              </cb-advance-table>
            </el-tab-pane> -->
          </el-tabs>
        </el-card>
      </el-col>
    </el-row>
    <!--新增编辑worker分组-->
    <cb-dialog :title="textMap1[dialogStatus]" :close-on-click-modal="false" v-if="addScriptGroupVisible" :visible.sync="addScriptGroupVisible" width="35%">
      <cb-form :model="addScriptGroup" ref="addScriptGroup">
        <cb-form-item label="分组名称：" prop="name" validate="required">
          <el-input v-model="addScriptGroup.name" auto-complete="off"></el-input>
        </cb-form-item>
        <cb-form-item label="分组描述：" prop="remark">
          <el-input type="textarea" :autosize="{ minRows: 3, maxRows: 6 }" v-model="addScriptGroup.remark" auto-complete="off"></el-input>
        </cb-form-item>
      </cb-form>
      <div slot="footer" class="dialog-footer">
        <el-button type="ghost" @click.native="addScriptGroupVisible = false">取消</el-button>
        <el-button type="primary" @click.native="addScriptGroupSubmit">确定</el-button>
      </div>
    </cb-dialog>
    <!--新增编辑worker-->
    <cb-dialog :title="textMap2[dialogStatus]" :close-on-click-modal="false" v-if="addWorkerVisible" :visible.sync="addWorkerVisible" width="35%">
      <cb-form :model="addWorkerData" ref="addWorkerData" label-width="150px">
        <cb-form-item label="SaltMaster地址：" prop="instance" validate="required">
          <el-input v-model="addWorkerData.instance" auto-complete="off"></el-input>
        </cb-form-item>
        <cb-form-item label="协议类型：" prop="protocol" validate="required">
          <el-input v-model="addWorkerData.protocol" auto-complete="off"></el-input>
        </cb-form-item>
        <cb-form-item label="用户名：" prop="username" validate="required">
          <el-input v-model="addWorkerData.username"></el-input>
        </cb-form-item>
        <cb-form-item label="密码：" prop="password" validate="required">
          <el-input v-model="addWorkerData.password" show-password auto-complete="new-password"></el-input>
        </cb-form-item>
      </cb-form>
      <div slot="footer" class="dialog-footer">
        <el-button type="ghost" @click.native="addWorkerVisible = false">取消</el-button>
        <el-button type="primary" @click.native="addWorkerSubmit">确定</el-button>
      </div>
    </cb-dialog>
    <set-group :set-data="setData" v-if="setData.dialog" @setOk="handleSearch"></set-group>
    <GaiaDialog :dialog="gaiaDialog" v-if="gaiaDialog.visible" @back="handleSearch"></GaiaDialog>
  </div>
</template>

<script>
import SetGroup from '@/views/resource-manage/components/setGroup'
import { createBsmHostGroup, deleteBsmHostGroup, getBsmHostGroup, getWorkers, getWorkerDetail, updateBsmHostGroup, createBsmHostWorker, updateBsmHostWorker, deleteBsmHostWorker, updateWorkersConfig, syncMinionApi } from '@/services/task/resource'
import DotDropdown from 'views/repository/component/dotDropdown.vue'
import crypto from 'utils/crypto.js'
import GaiaDialog from './GaiaDialog.vue'
export default {
  components: {
    SetGroup,
    DotDropdown,
    GaiaDialog,
  },
  data() {
    return {
      loading: false,
      searchConfigs: [
        { label: '实例', value: 'instance', type: 'Input' },
        { value: 'category', initValue: 'Ansible', type: 'Const' },
      ],
      saltMasterSearchConfigs: [
        { label: '实例', value: 'instance', type: 'Input' },
        { value: 'category', initValue: 'SaltMaster', type: 'Const' },
      ],
      ansibleColumns: [
        {
          type: 'selection',
          selectable(row, index) {
            return !row.deleted
          },
        },
        { label: '实例', prop: 'instance', scopedSlots: { customRender: 'instance' } },
        { label: '心跳状态', prop: 'deleted', scopedSlots: { customRender: 'deleted' } },
        { label: '超级worker', prop: 'isSuper', scopedSlots: { customRender: 'isSuper' } },
        { label: '所属分组', prop: 'groupName' },
        { label: '任务数量', prop: 'tasks' },
        { label: '是否排除', prop: 'isExclude', scopedSlots: { customRender: 'isExclude' } },
        { label: '操作', disabled: true, width: '200px', scopedSlots: { customRender: 'operate' } },
      ],
      saltMasterColumns: [
        { type: 'selection' },
        { label: '实例', prop: 'instance', scopedSlots: { customRender: 'instance' } },
        { label: '类型', prop: 'category' },
        { label: '协议类型', prop: 'protocol' },
        { label: '所属分组', prop: 'groupName' },
        { label: '操作', disabled: true, width: '200px', scopedSlots: { customRender: 'operate' } },
      ],
      list: [],
      saltMasterList: [],
      saltMasterLoading: false,
      total: null,
      saltMasterTotal: null,
      paramt: {
        page: 1,
        rows: 20,
      },
      params: {
        page: 1,
        rows: 20,
      },
      listQuery: {
        name: '',
        version: '',
      },
      groupId: null,
      parentId: null,
      nodedata: {},
      // 树形菜单
      treeData: [],
      defaultProps: {
        children: 'childrenList',
        label: 'name',
      },
      dropMenuEvents: [
        { label: '编辑', funcName: 'editNode' },
        { label: '删除', funcName: 'removeNode' },
        // { label: '新建子节点', funcName: 'addNode' }
      ],
      // 详情
      detailFlag: false,
      detailData: [],
      // 新增编辑worker分组
      dialogStatus: '',
      textMap1: {
        update: '编辑分组',
        create: '新增分组',
      },
      addScriptGroup: {},
      addScriptGroupVisible: false,
      props: {
        value: 'id',
        children: 'childrenList',
        label: 'name',
        checkStrictly: true,
      },
      addScript: {
        name: '',
      },
      flag: null,
      // 树
      operate: false,
      chartObject: {},
      setData: {
        dialog: false,
        data: {},
      },
      // 新增编辑worker
      textMap2: {
        update: '编辑代理',
        create: '新增代理',
      },
      addWorkerVisible: false,
      addWorkerData: {},
      typeName: 'Ansible',
      selectList: [],
      idList: [],
      timer: null,
      gaiaDialog: {
        visible: false,
        record: {},
      },
    }
  },
  created() {
    this.getTreeData()
    this.startInterval()
    // this.handleSearch()
  },
  destroyed() {
    clearInterval(this.timer)
  },
  methods: {
    startInterval() {
      this.timer = setInterval(this.handleSearch, 1000 * 10)
    },
    addNode({ node, data }) {
      this.addScriptGroup = {}
      this.dialogStatus = 'create'
      this.parentId = data.id
      this.addScriptGroupVisible = true
    },
    editNode({ node, data }) {
      this.addScriptGroup = Object.assign({}, data)
      this.dialogStatus = 'update'
      this.addScriptGroupVisible = true
    },
    removeNode({ node, data }) {
      this.$confirm('您确定要删除该分组吗?', '提示', {
        type: 'warning',
      })
        .then(() => {
          deleteBsmHostGroup(data.id).then((data) => {
            if (data.success) {
              this.$message.success({
                message: data.message,
                type: 'success',
              })
              this.getTreeData()
              this.groupId = null
            }
          })
        })
        .catch(() => {})
    },
    setting(row) {
      this.setData = {
        dialog: true,
        data: {
          ...row,
        },
      }
    },
    syncMinion({ id }) {
      this.$confirm('您确定要执行同步吗？', '提示', {
        type: 'warning',
      })
        .then(async () => {
          const res = await syncMinionApi(id)
          if (res.success) {
            this.$message.success(res.message)
            this.getSaltMasterList()
          }
        })
        .catch(() => {})
    },
    async getTreeData() {
      const that = this
      const data = await getBsmHostGroup({ parentId: 0 })
      if (data.success) {
        that.treeData = data.data
        setTimeout(function () {
          if (that.groupId) {
            that.$refs.scriptTree.setCurrentKey(that.groupId)
          }
        }, 10)
      }
    },
    async getList() {
      this.selectList = []
      this.refreshId()
      this.loading = true
      const data = await getWorkers(this.params)
      if (data.success) {
        this.list = data.data.rows
        this.total = data.data.total
        this.loading = false
      }
    },
    handleNodeClick(node) {
      this.groupId = node.id
      this.nodedata = node
      this.handleSearch()
    },
    // 查询
    handleSearch() {
      this.selectList = []
      this.refreshId()
      const { ansibleTableRef, saltTableRef } = this.$refs
      if (this.typeName == 'Ansible') ansibleTableRef.handleSearch()
      else saltTableRef.handleSearch()
    },
    // 新增worker分组
    add(flag) {
      this.flag = flag
      this.addScriptGroup = {}
      this.dialogStatus = 'create'
      this.parentId = '0'
      this.addScriptGroupVisible = true
    },
    // 保存新增的worker分组
    addScriptGroupSubmit() {
      const that = this
      this.$refs.addScriptGroup.validate((valid) => {
        if (valid) {
          const editObj = ['name', 'code', 'remark']
          const param = {}
          for (const a in editObj) {
            const attr = editObj[a]
            param[attr] = that.addScriptGroup[attr]
          }
          let service = ''
          if (that.dialogStatus === 'update') {
            service = updateBsmHostGroup
            param.id = this.groupId
          } else {
            service = createBsmHostGroup
          }
          service(param).then((data) => {
            if (data.success) {
              that.$notify({
                message: data.message,
                type: 'success',
              })
              that.addScriptGroupVisible = false
              if (that.flag === '2') {
                that.nodedata = param
              }
              that.getTreeData()
            }
          })
        }
      })
    },
    // 详情
    getDetail(id) {
      this.listQuery.version = ''
      this.activeName = 'storage'
      getWorkerDetail(id).then((data) => {
        if (data.success) {
          this.addScript = Object.assign({}, data.data)
          this.addScript.id = id
          this.addScript.groupIds = [this.addScript.groupIds]
          this.detailFlag = true
        }
      })
    },
    goBack() {
      this.detailFlag = false
    },
    async getSaltMasterList() {
      this.selectList = []
      this.refreshId()
      this.saltMasterLoading = true
      const data = await getWorkers(this.paramt)
      if (data.success) {
        this.saltMasterList = data.data.rows
        this.saltMasterTotal = data.data.total
        this.saltMasterLoading = false
      }
    },
    // 新增编辑
    handleCreate(row, flag) {
      this.addWorkerData = {
        content: '',
      }
      this.source = '1'
      switch (flag) {
        case 1:
          this.dialogStatus = 'create'
          this.addWorkerData = {
            instance: '',
            category: 'SaltMaster',
            protocol: '',
            username: '',
            password: '',
          }
          break
        case 2:
          this.dialogStatus = 'update'
          this.addWorkerData = row
          this.addWorkerData.password = crypto.decrypt(this.addWorkerData.password)
          break
      }
      this.addWorkerVisible = true
    },
    handleDelete(id) {
      this.$confirm('您确定要删除该网段吗？', '提示', {
        type: 'warning',
      })
        .then(() => {
          deleteBsmHostWorker(id).then((data) => {
            if (data.success) {
              this.$message.success({
                message: data.message,
                type: 'success',
              })
              this.getSaltMasterList()
            }
          })
        })
        .catch(() => {})
    },
    // 保存worker
    addWorkerSubmit() {
      const that = this
      this.$refs.addWorkerData.validate((valid) => {
        if (valid) {
          const password = crypto.encrypt(this.addWorkerData.password)
          let service
          switch (this.dialogStatus) {
            case 'create':
              service = createBsmHostWorker
              break
            case 'update':
              service = updateBsmHostWorker
              break
          }
          service({ ...this.addWorkerData, password }).then((data) => {
            if (data.success) {
              this.$message({
                message: data.message,
                type: 'success',
              })
              that.addWorkerVisible = false
              that.getSaltMasterList()
            }
          })
        }
      })
    },
    refreshId() {
      this.idList = []
      this.selectList.forEach((item) => {
        this.idList.push(item.id)
      })
    },
    // 单选
    handleSelectItem(selection, row) {
      this.refreshId()
      if (this.idList.indexOf(row.id) > -1) {
        for (let j = 0; j < this.selectList.length; j++) {
          const item = this.selectList[j]
          if (item.id == row.id) {
            this.selectList.splice(j, 1)
            break
          }
        }
      } else {
        this.selectList.push(row)
      }
    },
    // 全选
    handleSelectAll(selection) {
      this.refreshId()
      if (selection.length) {
        // 全选情况下
        selection.forEach((item) => {
          if (this.idList.indexOf(item.id) == -1) {
            this.selectList.push(item)
          }
        })
      } else {
        // 全不选情况下
        this.list.forEach((item) => {
          if (this.idList.indexOf(item.id) > -1) {
            for (let j = 0; j < this.selectList.length; j++) {
              const row = this.selectList[j]
              if (item.id == row.id) {
                this.selectList.splice(j, 1)
                break
              }
            }
          }
        })
      }
    },
    // 排除恢复
    handleConfig(row, type) {
      this.refreshId()
      const { isExclude = type } = row
      this.$confirm(`您确定要${(!type && isExclude) || type == 'recovery' ? '恢复' : '排除'}吗?`, '提示', {
        confirmButtonClass: 'el-button--danger',
        type: 'warning',
      })
        .then(async () => {
          const { success, message } = await updateWorkersConfig((!type && isExclude) || type == 'recovery' ? 'recovery' : 'exclude', {
            workerIds: type ? this.idList : [row.id],
          })
          if (!success) return
          this.$message.success({
            message: message,
            type: 'success',
          })
          this.selectList = []
          this.getList()
        })
        .catch(() => {})
    },
    handleDeployGaia() {
      this.gaiaDialog = {
        visible: true,
        record: {},
        isDeploy: true,
      }
    },
    handleDelGaia(row) {
      this.gaiaDialog = {
        visible: true,
        record: { ...row },
      }
    },
  },
}
</script>

<style scoped="scoped" lang="scss">
.code-type {
  height: 35px;
  padding-left: 15px;
  line-height: 35px;
  border: 1px solid #ddd;
}
.operate {
  position: absolute !important;
  z-index: 99;
}
.content {
  font-size: 14px;
  border: 1px solid #cccccc;
  min-height: 50px;
  max-height: 300px;
  padding: 10px;
  overflow: auto;
}
.item {
  color: rgb(64 158 255);
  font-size: 16px;
}
::v-deep .tree .el-tree-node__expand-icon.expanded {
  -webkit-transform: rotate(0deg);
  transform: rotate(0deg);
}
::v-deep .el-icon-caret-right:before {
  content: '\e6e0';
  font-size: 14px;
}
::v-deep .el-tree-node__content {
  position: relative;
  height: 32px;
  line-height: 32px;
  .operate-btns {
    position: absolute;
    right: 2px;
    display: none;
  }
  // 鼠标悬停时，展示
  &:hover,
  :focus-within {
    .operate-btns {
      display: inline;
    }
  }
}
</style>
