田源
2024-12-17 1b84a05dd84e535284ac6e2d2b360d76a4b8e7ac
Source/plt-web/plt-web-ui/src/views/authority/ui/dataAuthorization/index.vue
@@ -1,33 +1,17 @@
<template>
  <el-container>
    <el-aside>
      <basic-container>
        <div ref="TreeBox" style="height: calc(100vh - 144px);!important;">
          <div class="headerCon">
            <el-button icon="el-icon-plus" plain size="small" type="primary" @click="addClickHandler">创建
            </el-button>
            <el-button icon="el-icon-edit" plain size="small" type="primary" @click="editClickHandler">修改
            </el-button>
            <el-button icon="el-icon-delete" plain size="small" type="danger" @click="delClickHandler">删除
            </el-button>
            <el-button icon="el-icon-download" plain size="small" type="primary" @click="exportClickHandler">导出
            </el-button>
            <el-button icon="el-icon-upload2" plain size="small" type="primary" @click="uploadClickHandler">导入
            </el-button>
            <el-button class="smallBtn" plain size="small" type="primary"
                       @click="checkViewClickHandler">查看使用范围
            </el-button>
          </div>
        <div ref="TreeBox" style="height: calc(100vh - 154px);!important;">
          <!-- 左侧树         -->
          <div style="height:  calc(100vh - 280px);">
          <div style="height:  calc(100vh - 190px);">
            <avue-tree :data="treeData" :option="treeOption" @node-click="nodeClick">
          <span slot-scope="{ node, data }" class="el-tree-node__label">
           <span style="font-size: 15px">
              <i class="el-icon-s-promotion"></i>
                {{ (node || {}).label }}
            </span>
          </span>
              <span slot-scope="{ node, data }" class="el-tree-node__label">
               <span style="font-size: 15px">
                  <i class="el-icon-s-promotion"></i>
                    {{ (node || {}).label }}
                </span>
              </span>
            </avue-tree>
          </div>
        </div>
@@ -35,7 +19,107 @@
    </el-aside>
    <el-main>
      <basic-container>
      <basic-container cardBodyStyle="padding-bottom:0;">
        <avue-crud
          ref="crud"
          :data="data"
          :option="option"
          :table-loading="tableLoading"
          @refresh-change="handleRefresh"
          @current-row-change="rowClickHandler">
          <template slot="menuLeft">
            <el-button v-if="permissionList.addBtn" icon="el-icon-plus" size="small" type="primary" @click="addHandler">添加</el-button>
            <el-button v-if="permissionList.editBtn" icon="el-icon-plus" size="small" type="primary" @click="editHandler">修改</el-button>
            <el-button v-if="permissionList.delBtn" icon="el-icon-delete" plain size="small" type="danger" @click="delHandler">删除</el-button>
            <!--<el-button icon="el-icon-view" plain size="small" type="primary" @click="viewAuthHandler">查看授权结果</el-button>-->
          </template>
        </avue-crud>
        <div style="margin-top: 15px;">
          <data-view key="dataView" :btmNode="nodeRow" :actionMap="actionMap" :selectRow="selectRow" :readOnly="true" :height="clientHeight-260-220"></data-view>
        </div>
        <!-- 新增 && 编辑 -->
        <el-dialog
          v-dialogDrag
          :title="title === 'add' ? '创建' : '修改'"
          :visible.sync="visible"
          append-to-body="true"
          class="avue-dialog"
          width="70%"
          @close="addDialogClose">
            <div>
              <data-view ref="editView" key="editView" :btmNode="nodeRow" :actionMap="actionMap" :selectRow="title === 'add'?{}:selectRow" :readOnly="false" :height="clientHeight-260"></data-view>
            </div>
            <span slot="footer" class="dialog-footer">
               <el-button size="small" type="primary" @click="addDialogSavaHandler">保 存</el-button>
               <el-button size="small" @click="addDialogClose">取 消</el-button>
            </span>
        </el-dialog>
        <!-- 查看授权结果    -->
        <el-dialog
          v-dialogDrag
          :visible.sync="authResultVisible"
          append-to-body="true"
          class="avue-dialog"
          title="查看授权结果"
          width="60%"
        >
          <el-form ref="form" :inline="true" size="mini" :model="form" label-width="80px">
            <el-form-item label="业务对象" prop="objectoid">
              <el-input v-model="form.objectoid" style="width:300px;"></el-input>
            </el-form-item>
            <el-form-item>
              <el-button type="primary" @click="queryBtm" style="padding: 6px 15px;">查询业务对象</el-button>
            </el-form-item>
            <fieldset style="width: 99.5%">
              <legend>&nbsp;用户信息 </legend>
              <div>
                <el-form-item label="用户">
                  <el-select v-model="form.userOid">
                    <el-option v-for="item in userDic" :label="item.name+'('+item.id+')'" :value="item.oid"></el-option>
                  </el-select>
                </el-form-item>
                <el-form-item label="角色">
                  <el-select v-model="form.roleOid">
                    <el-option v-for="item in roleDic" :label="item.name" :value="item.oid"></el-option>
                  </el-select>
                </el-form-item>
                <el-form-item label="用户组">
                  <el-select v-model="form.deptOid">
                    <el-option v-for="item in deptDic" :label="item.name" :value="item.oid"></el-option>
                  </el-select>
                </el-form-item>
              </div>
            </fieldset>
            <el-dialog
              v-dialogDrag
              :visible.sync="btmObjVisible"
              append-to-body="true"
              class="avue-dialog"
              title="业务对象列表"
              width="90%"
            >
              <avue-crud
                ref="btmObjCrud"
                :data="btmObjData"
                :option="btmObjOption"
                @current-row-change="btmObjClickHandler"
              >
              </avue-crud>
            </el-dialog>
          </el-form>
          <fieldset style="width: 99.5%;margin-top: 10px;">
            <legend>&nbsp;授权结果: </legend>
            <div>
              <avue-crud
                ref="authResultCrud"
                :data="authResultData"
                :option="authResultOption"
              >
              </avue-crud>
            </div>
          </fieldset>
        </el-dialog>
      </basic-container>
    </el-main>
@@ -43,8 +127,368 @@
</template>
<script>
import {getBizTree} from "@/api/UI/uiDefine";
import basicOption from "@/util/basic-option";
import dataView from "./dataView";
import {getData,saveGrand,delGrand,authResult,queryBusiness} from "@/api/authority/ui/dataAuthor";
import {listUserByUserType, listRoleByUserOid, listDeptByUserOid} from "@/api/system/user/api";
import func from "@/util/func";
import {mapGetters} from "vuex";
export default {
  name: "index"
  name: "index",
  components:{dataView},
  data:function (){
    return{
      clientHeight:Math.max(document.body.clientHeight,700),
      treeOption: {
        height: 'auto',
        defaultExpandAll: true,
        menu: false,
        addBtn: false,
        props: {
          label: 'text',
          value: 'oid',
          children: 'children'
        }
      },
      nodeRow: {},
      treeData: [],
      tableLoading: false,
      selectRow: {},
      option: {
        ...basicOption,
        height:280,
        highlightCurrentRow:true,
        addBtn: false,
        editBtn: false,
        delBtn: false,
        filterBtn:false,
        columnBtn:false,
        gridBtn:false,
        tip: false,
        index:false,
        selection:false,
        menu:false,
        align:'center',
        column: [{
          label: '规则名称',
          prop: 0,
          overHidden: true
        },{
          label: '规则类型',
          prop: 1,
          overHidden: true
        }]
      },
      data: [],
      title: '',
      visible: false,
      form:{
        objectoid:'',
        userOid:'',
        roleOid:'',
        deptOid:''
      },
      userDic:[],
      roleDic:[],
      deptDic:[],
      actionMap:{},
      switchDic:[{
        label:'',
        value:false
      },{
        label:'',
        value:true
      }],
      authResultVisible:false,
      authResultData:[],
      authResultOption:{
        ...basicOption,
        height:300,
        tip: false,
        index:false,
        selection:false,
        menu:false,
        header:false,
        column: [{
          label: '名称',
          prop: 'name',
          overHidden: true
        }]
      },
      //业务对象列表
      btmObjVisible:false,
      btmObjData:[],
      btmObjOption:{
        ...basicOption,
        height:500,
        tip: false,
        selection:false,
        menu:false,
        header:false,
        column: []
      }
    }
  },
  computed:{
    ...mapGetters(["permission"]),
    permissionList() {
      return {
        addBtn: this.vaildData(this.permission[this.$route.query.id].ADD, false),
        delBtn: this.vaildData(this.permission[this.$route.query.id].DELETE, false),
        editBtn: this.vaildData(this.permission[this.$route.query.id].EDIT, false),
      };
    },
  },
  created() {
    this.getTreeList();
  },
  watch:{
    'form.userOid':{
      handler(val) {
        /*if(val){
          listRoleByUserOid(val).then(res => {
            // 组装好穿梭框可用数据
            this.roleDic = res.data.data;
            if(this.roleDic.length>0){
              this.form.roleOid=this.roleDic[0].oid
            }else{
              this.form.roleOid=''
            }
          })
          listDeptByUserOid(val).then(res => {
            this.deptDic = res.data.data;
            if(this.deptDic.length>0){
              this.form.deptOid=this.deptDic[0].oid
            }else {
              this.form.deptOid='';
            }
          })
        }else{
          this.roleDic=[];
          this.deptDic=[];
          this.form.roleOid=''
          this.form.deptOid='';
        }*/
      },
      immediate: true,
      deep: true
    }
  },
  methods: {
    //树表查询
    getTreeList() {
      const loading = this.$loading({});
      getBizTree().then(res => {
        this.treeData = [res.data.obj];
        loading.close();
      }).catch(error => {
        loading.close();
      })
    },
    // 树点击
    nodeClick(row) {
      if (row.oid) {
        this.nodeRow = row;
        this.getTableList();
      }
    },
    getTableList() {
      getData(this.nodeRow.attributes.name).then(res => {
        if(typeof res.data == 'string'){
          res.data=eval('('+res.data +')')
        }
        if(res.data.obj.tableHeader){
          this.option.column=[ {
            label: '规则名称',
            prop: 0,
            overHidden: true
          },{
              label: '规则类型',
              prop: 1,
              overHidden: true
            }];
          res.data.obj.tableHeader.forEach((item,i)=>{
            if(i<=1) return;
            if(i=='rules') return;
            this.option.column.push({
              label: item,
              prop: i,
              overHidden: true,
              width:(this.stringLength(item) *6+35)+'px',
              html:true,
              formatter:(val)=> {
                return '<label class="el-checkbox is-disabled ' + (val[i] == true ? 'is-checked' : '') + '"><span class="el-checkbox__input is-disabled ' + (val[i] == true ? 'is-checked' : '') + '"><span class="el-checkbox__inner"></span><input type="checkbox" aria-hidden="false" class="el-checkbox__original" value="' + val[i] + '"></span></label>'
              }
            })
          })
        }
        this.data = res.data.obj.rowList;
        this.tableLoading = false;
        this.actionMap=res.data.obj.actionMap;
        this.$refs.crud.setCurrentRow( );
      })
    },
    stringLength(str) {
      let len = 0;
      for (let i = 0; i < str.length; i++) {
        let code = str.charCodeAt(i);
        if (code >= 0 && code <= 127) {
          len += 1; // 英文字符
        } else {
          len += 2; // 中文字符
        }
      }
      return len;
    },
    handleRefresh() {
      this.getTableList();
    },
    // 行点击
    rowClickHandler(row) {
      this.selectRow=row
    },
    //创建
    addHandler(){
      if (func.isEmptyObject(this.nodeRow)) {
        this.$message.error('请选择要添加的节点');
        return;
      }
      this.title = 'add';
      this.visible = true;
    },
    //修改
    editHandler(){
      if (func.isEmptyObject(this.selectRow)) {
        this.$message.error('请选择一条数据');
        return;
      }
      this.title = 'edit';
      this.visible = true;
    },
    // 新增编辑保存
    addDialogSavaHandler() {
      let form = this.$refs.editView.form;
      if (form.ruleName == '') {
        this.$message.error('客体请输入规则名称');
        return;
      }
      form.users = ''
      form.userGroups = '';
      form.roles = ''
      this.$refs.editView.authData.forEach(item => {
        let infos = item.name.split(', ');
        infos[0] = infos[0].replace('{', '')
        if (infos[2] == 'user}') {
          form.users += infos[0] + ','
        }
        if (infos[2] == 'userGroup}') {
          form.userGroups += infos[0] + ','
        }
        if (infos[2] == 'role}') {
          form.roles += infos[0] + ','
        }
      });
      let data = [];
      for (var i in this.actionMap) {
        data.push({
          ...form,
          identifier: this.nodeRow.attributes.name + '_' + this.actionMap[i],
          isGrand: this.$refs.editView.actionForm.some(item => {
            return item == this.actionMap[i]
          }) ? 49 : 48
        })
      }
      saveGrand(data).then(res => {
        if (res.data.code === 200) {
          this.$message.success(res.data.obj);
          this.getTableList();
          this.addDialogClose();
        }
      })
    },
    // 新增编辑对话框取消
    addDialogClose() {
      this.visible = false;
    },
    //删除
    delHandler(){
      if (func.isEmptyObject(this.selectRow)) {
        this.$message.error('请选择数据');
        return;
      }
      this.$confirm('您确定要删除所选择的数据吗?', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        delGrand({typeName:this.nodeRow.attributes.name,ruleName:this.selectRow.rules[0].ruleName}).then(res => {
          if (res.data.code === 200) {
            this.$message.success(res.data.obj);
            this.getTableList();
          }
        })
      }).catch(() => {
        this.$message({
          type: 'info',
          message: '已取消删除'
        });
      });
    },
    // 查看授权结果
    viewAuthHandler() {
      if (func.isEmptyObject(this.nodeRow)) {
        this.$message.warning('请选择类型树信息');
        return;
      }
      this.authResultVisible = true;
      listUserByUserType({type:1}).then(res => {
        // 组装好穿梭框可用数据
        this.userDic = res.data.data;
        if(this.userDic.length>0){
          this.form.userOid=this.userDic[0].oid
        }else{
          this.form.userOid=''
        }
      })
      this.getAuthResultData()
    },
    getAuthResultData(){
      authResult({biztype: this.nodeRow.attributes.name,objectoid:this.form.objectoid}).then(res => {
        if (res.data.code === 200) {
          this.authResultData = res.data.data;
        }
      })
    },
    //查询业务对象
    queryBtm(){
      queryBusiness({btmName: this.nodeRow.attributes.name,boFlag:true,btmType:'btm'}).then(res => {
        if (res.data.code === 200) {
          if(res.data.obj.tableHeader){
            this.btmObjOption.column=[];
            res.data.obj.tableHeader.forEach((item,i)=>{
              this.btmObjOption.column.push({
                label: item,
                prop: i,
                overHidden: true,
                width:(this.stringLength(item) *8+30)+'px',
              })
            })
          }
          this.btmObjData = res.data.obj.tableValues;
        }
      })
      this.btmObjVisible=true;
    },
    btmObjClickHandler(row){
      this.form.objectoid=row[0];
      this.getAuthResultData()
      this.btmObjVisible=false;
    }
  }
}
</script>
@@ -53,40 +497,10 @@
  .el-scrollbar__wrap {
    overflow: auto !important;
  }
  .headerCon{
    .el-button{
      width: 82px;
    }
  }
}
.headerCon {
  display: flex;
  flex-wrap: wrap;
  margin-bottom: 5px;
  .el-button + .el-button {
    margin-left: 5px;
  }
  .el-button {
    margin-top: 5px;
  }
fieldset {
  padding: 10px 6px;
  margin: 0;
  border: 1px solid #EBEEF5;
}
.headerCon > .el-button:nth-child(4) {
  margin-left: 0;
}
.headerCon > .el-button:nth-child(7) {
  margin-left: 0;
}
.smallBtn {
  width: 82px;
  text-align: center;
  padding-left: 4.5px;
}
</style>