vue用户管理、角色管理和部门管理展示

news2024/9/22 5:35:35

1、用户和角色一对多,用户和部门多对多

2、用户管理

编辑用户时部门层级展示

角色-下拉框展示

 

<template>
  <div class="s">
    <!-- 操作按钮 -->
    <div class="shang">
      <el-input v-model="searchText" placeholder="请输入姓名搜索关键词" style="width: 200px;"></el-input>
      <el-input v-model="userEmailSearchText" placeholder="请输入邮箱号搜索关键词" style="width: 200px;"></el-input>
      <el-select v-model="selectedRoleId" placeholder="请选择角色">
        <el-option v-for="role in roles" :key="role.id" :label="role.role_name" :value="role.id"></el-option>
      </el-select>
      <el-button type="primary" @click="search">搜索</el-button>
      <el-button @click="resetForm">重置</el-button>
    </div>
    <br>
    <el-button type="primary" @click="showAddDialog">新增用户</el-button>
    <el-table :data="filteredTableData" style="width: 100%">
      <el-table-column prop="name" label="姓名"></el-table-column>
      <el-table-column prop="user_email" label="邮箱号"></el-table-column>
      <el-table-column label="角色">
        <template slot-scope="scope">
          {{ scope.row.role_name }}
        </template>
      </el-table-column>

      <el-table-column label="部门">
        <template slot-scope="scope">
          <span v-for="(department, index) in scope.row.department_id" :key="department">
            {{ department.split(' ----- ').pop() }}
          </span>
        </template>
      </el-table-column>

      <el-table-column label="操作">
        <template slot-scope="scope">
          <el-button size="mini" @click="showEditDialog(scope.row)">编辑</el-button>
          <el-button size="mini" type="danger" @click="handleDelete(scope.row.user_id)">删除</el-button>
        </template>
      </el-table-column>
    </el-table>

    <!-- 新增/编辑对话框 -->
    <el-dialog :title="dialogTitle" :visible.sync="isDialogVisible">
      <el-form :model="form">
        <el-form-item label="姓名">
          <el-input v-model="form.name"></el-input>
        </el-form-item>

        <el-form-item label="邮箱号">
          <el-input v-model="form.user_email"></el-input>
        </el-form-item>
        <el-form-item label="角色">
          <br>
          <el-select v-model="form.role" style="width:200px">
            <el-option v-for="role in roles" :key="role.id" :label="role.role_name" :value="role.id"></el-option>
          </el-select>
        </el-form-item>

        <el-form-item label="归属部门">
          <treeselect v-model="form.department_ids" :options="deptOptions" :show-count="true" placeholder="请选择归属部门"
            :normalizer="normalizer" multiple />
        </el-form-item>

      </el-form>
      <div slot="footer" class="dialog-footer">
        <el-button @click="isDialogVisible = false">取消</el-button>
        <el-button type="primary" @click="handleSubmit">确定</el-button>
      </div>
    </el-dialog>
  </div>
</template>

<script>
import axios from 'axios';
import Treeselect from "@riophae/vue-treeselect";
import "@riophae/vue-treeselect/dist/vue-treeselect.css";

export default {
  components: { Treeselect },
  data() {
    return {
      searchText: '',
      userEmailSearchText: '', 
      selectedRoleId: null, 
      selectedDepartment: [], 
      deptOptions: [],
      tableData: [],
      roles: [],
      isDialogVisible: false,
      dialogTitle: '新增用户',
      form: {
        id: '',
        name: '',
        user_email: '',
        role: '',
        department_ids: []
      },
      setRoleDialogVisible: false,
      setDepDialogVisible: false,
      userInfo: []
    };
  },
  mounted() {
    this.handleSearch();
    this.setRole();
    this.setDep();
    this.loadDepartmentOptions(); 
    console.log("deptOptions", this.deptOptions); 
  },
 // 计算属性
computed: {
  filteredTableData() {
    let filteredData = this.tableData;
    if (this.searchText) {
      filteredData = filteredData.filter(user => user.name.includes(this.searchText));
    }
    if (this.userEmailSearchText) {
      filteredData = filteredData.filter(user => user.user_email.includes(this.userEmailSearchText));
    }
    if (this.selectedRoleId) {
      filteredData = filteredData.filter(user => user.role_id === this.selectedRoleId);
    }

    // 为每个用户获取角色和部门名称
    filteredData.forEach(user => {
      user.role_name = this.getRoleName(user.role_id);
      if (user.department_id && Array.isArray(user.department_id)) {
        user.department_names = user.department_id.map(departmentId => {
          const department = this.deptOptions.find(dep => dep.id === departmentId);
          return department? department.name : '';
        });
      } else {
        user.department_names = [];  // 确保没有部门 ID 时,department_names 是一个空数组
      }
    });

    return filteredData;
  }
},
  methods: {
    getRoleName(roleId) {
      const role = this.roles.find(role => role.id === roleId);
      return role? role.role_name : '';
    },
    resetForm() {
      this.searchText = '';
      this.userEmailSearchText = ''; 
      this.selectedRoleId = null; 
      this.selectedDepartment = []; 
      this.handleSearch();
    },
    async search() {
      try {
        const params = {};
        if (this.searchText) {
          params.name = this.searchText;
        }
        if (this.userEmailSearchText) {
          params.user_email = this.userEmailSearchText;
        }
        if (this.selectedRoleId) {
          params.role_id = this.selectedRoleId;
        }
        if (this.selectedDepartment.length > 0) {
          params.departments = this.selectedDepartment.map(department => department.name).join(','); 
        }
        console.log('发送的请求参数params:', params); 
        const usersResponse = await axios.get('http://127.0.0.1:8000/users/search_user_by_params/', {
          params: params
        });
        this.tableData = usersResponse.data;
      } catch (error) {
        console.error('搜索时出错:', error);
      }
    },
    async handleSearch() {
      try {
        const usersResponse = await axios.get('http://127.0.0.1:8000/users/get_user_details_extended/');
        this.tableData = usersResponse.data;
        // 同时获取部门信息
        const deptResponse = await axios.get('http://127.0.0.1:8000/departments/');
        this.deptOptions = deptResponse.data;
        console.log("this.deptOptions部门1", this.deptOptions);
      } catch (error) {
        console.error('Error fetching users:', error);
      }
    },
    async loadDepartmentOptions() { // 加载部门选项的方法
      try {
        const response = await axios.get('http://127.0.0.1:8000/departments/');
        this.departmentOptions = response.data.map(department => ({
          id: department.id, 
          label: department.name, 
          children: department.children 
        }));
      } catch (error) {
        console.error('Error fetching department options:', error);
      }
    },
    async setRole() {
      try {
        const response = await axios.get('http://127.0.0.1:8000/roles/');
        this.roles = response.data;
        this.setRoleDialogVisible = true;
      } catch (error) {
        console.error('Error fetching roles:', error);
      }
    },
    normalizer(node) {
      console.log("node", node);
      console.log("node.children", node.children);
      if (node.children) {
        return {
          id: node.id,
          label: node.name, 
          children: node.children 
        };
      }
      return {
        id: node.id,
        label: node.name,
        children: node.children
      };
    },
    showAddDialog() {
      this.dialogTitle = '新增用户11111';
      this.form = {
        id: '',
        name: '',
        user_email: '',
        role_id: '',
        department_ids: []
      };
      this.isDialogVisible = true;
    },
    async setDep() {
      try {
        const response = await axios.get('http://127.0.0.1:8000/departments/');
        this.deptOptions = response.data.map(department => ({
          id: department.id, 
          name: department.name
        }));
        this.setDepDialogVisible = false;
        console.log("this.deptOptions部门", this.deptOptions);
      } catch (error) {
        console.error('Error fetching departments:', error);
      }
    },
    showEditDialog(row) {
      this.dialogTitle = '编辑用户1111';
      this.form = {
        id: row.user_id,
        name: row.name,
        user_email: row.user_email,
        role: row.role_id
      };
      // 处理部门信息
      // 根据部门名称找到对应的 ID
      if (row.department_id && Array.isArray(row.department_id)) {
        console.log("Row department IDs:", row.department_id);
        console.log("Department Options:", this.deptOptions);
        this.form.department_ids = row.department_id.map(departmentName => {
          const findDepartment = (options) => {
            for (const option of options) {
              if (option.name === departmentName) {
                return option.id;
              }
              if (option.children) {
                const found = findDepartment(option.children);
                if (found) {
                  return found;
                }
              }
            }
            return null;
          };
          return findDepartment(this.deptOptions);
        }).filter(id => id!== null);
      } else {
        this.form.department_ids = [];
      }
      this.isDialogVisible = true;
    },
    async handleSubmit() {
      const payload = {
        id: this.form.id,
        name: this.form.name,
        user_email: this.form.user_email,
        role_id: this.form.role,
        department_ids: this.form.department_ids  
      };
      console.log("用户编辑部分111111111111111111111111", this.form.id);
      if (this.form.id!== "") {
        try {
          await axios.put(`http://127.0.0.1:8000/search/update_user/${this.form.id}`, payload);
          this.$message.success('用户编辑成功');
          this.handleSearch();
        } catch (error) {
          console.error('Error updating user:', error);
        }
      } else {
        try {
          await axios.post('http://127.0.0.1:8000/search/create_user/', payload);
          this.$message.success('新增用户成功');
          this.handleSearch();
        } catch (error) {
          console.error('Error adding user:', error);
        }
      }
      this.isDialogVisible = false;
    },

    async handleDelete(id) {
      try {
        await axios.delete(`http://127.0.0.1:8000/users/${id}/`);
        this.$message.success('用户删除成功');
        this.handleSearch();
      } catch (error) {
        console.error('Error deleting user:', error);
      }
    }
  }
};
</script>

<style>
/* 样式可以按需添加 */
.s {
  margin-left: 20px;
  margin-top: 20px;
}

.shang {
  margin-top: 20px;
}
</style>

3、角色管理

<template>
  <div class="s">
    <!-- 操作按钮 -->

    <div class="shang">

      <el-input v-model="searchText" placeholder="请输入搜索关键词" style="width: 500px;"></el-input>
      <el-button type="primary" @click="search">搜索</el-button>
      <el-button @click="resetForm">重置</el-button>
    </div>
    <br>
    <el-button type="primary" @click="showAddDialog">新增角色</el-button>
    <el-table :data="tableData" style="width: 100%;">

      <el-table-column prop="role_name" label="角色" >
        <template slot-scope="scope">
          <div class="centered-content">{{ scope.row.role_name }}</div>
        </template>
      </el-table-column>
    
      <el-table-column prop="status" label="状态" >
        <template slot-scope="scope">
          <div class="centered-content">
            <el-tag :type="scope.row.status === true? 'success' : 'danger'">
              {{ scope.row.status === true? '激活' : '禁用' }}
            </el-tag>
          </div>
        </template>
      </el-table-column>
      <!-- can_view_files: false, // 添加文件查看权限属性
      can_upload_files: false // 添 -->
      <el-table-column prop="can_upload_files" label="上传文件状态" >
        <template slot-scope="scope">
          <div class="centered-content">
            <el-tag :type="scope.row.can_upload_files === true? 'success' : 'danger'">
              {{ scope.row.can_upload_files === true? '激活' : '禁用' }}
            </el-tag>
          </div>
        </template>
      </el-table-column>
      
      <el-table-column prop="can_view_files" label="查看文件状态" >
        <template slot-scope="scope">
          <div class="centered-content">
            <el-tag :type="scope.row.can_view_files === true? 'success' : 'danger'">
              {{ scope.row.can_view_files === true? '激活' : '禁用' }}
            </el-tag>
          </div>
        </template>
      </el-table-column>
    
      <el-table-column prop="created_at" label="创建时间" >
        <template slot-scope="scope">
          <div class="centered-content">{{ scope.row.created_at | formatDate }}</div>
        </template>
      </el-table-column>
    
      <el-table-column label="操作" >
        <template slot-scope="scope">
          <div class="centered-content">
            <el-button size="mini" type="text" icon="el-icon-edit" @click="showEditDialog(scope.row)">修改</el-button>
            <el-button size="mini" type="text" icon="el-icon-delete" @click="handleDelete(scope.row.id)">删除</el-button>
          </div>
        </template>
      </el-table-column>
    
    </el-table>
    
    


    <!-- 分配用户对话框 -->
    <!-- 分配用户到角色的弹框 -->

    <el-dialog :title="dialogTitle1" :visible.sync="isDialogVisible1">
      <el-table :data="tableData1" style="width: 100%" @selection-change="handleSelectionChange">
        <!-- 复选框列 -->
        <el-table-column type="selection" width="55"></el-table-column>

        <el-table-column prop="name" label="姓名"></el-table-column>
        <el-table-column prop="nickname" label="昵称"></el-table-column>

        <el-table-column prop="phone_number" label="电话"></el-table-column>

      </el-table>
      <span slot="footer" class="dialog-footer">
        <el-button @click="isDialogVisible1 = false">取消</el-button>
        <el-button type="primary" @click="asingnuser">确定</el-button>
        <!-- @click="handleConfirm" -->
      </span>
    </el-dialog>
    <!-- 新增/编辑对话框 -->
    <el-dialog :title="dialogTitle" :visible.sync="isDialogVisible">
      <el-form :model="form">
        <el-form-item label="角色">
          <el-input v-model="form.role_name"></el-input>
        </el-form-item>
    
        <div class="role-permissions">
          <div style="display: flex; align-items: center;">
            <span>状态</span>
            <el-form-item style="margin-left: 20px; flex: 1;">
              <el-switch v-model="form.status" style="float: right;"></el-switch>
            </el-form-item>
          </div>
    
          <div style="display: flex; align-items: center;">
            <span>文件上传权限</span>
            <el-form-item style="margin-left: 20px; flex: 1;">
              <el-switch v-model="form.can_upload_files" style="float: right;"></el-switch>
            </el-form-item>
          </div>
    
          <div style="display: flex; align-items: center;">
            <span>文件查看权限</span>
            <el-form-item style="margin-left: 20px; flex: 1;">
              <el-switch v-model="form.can_view_files" style="float: right;"></el-switch>
            </el-form-item>
          </div>
        </div>
      </el-form>
    
      <div slot="footer" class="dialog-footer">
        <el-button @click="isDialogVisible = false">取消</el-button>
        <el-button type="primary" @click="handleSubmit">确定</el-button>
      </div>
    </el-dialog>

  </div>
</template>

<script>
import axios from 'axios';

export default {
  data() {
    return {
      searchText: '', // 搜索关键词
      tableData: [
        { created_at: '2024-06-21T05:41:57.131606Z' },
      ], // 存储从后端获取的数据
      tableData1: [],
      isDialogVisible: false, // 控制对话框的显示
      dialogTitle: '新增角色', // 对话框标题
      form: { // 表单数据
        id: '',
        role_id: null,
        role_name: '',
        status: true,
        created_at: '',
        can_view_files: false, // 添加文件查看权限属性
        can_upload_files: false // 添加文件上传权限属性
      },
      isDialogVisible1: false, // 控制对话框的显示
      dialogTitle1: '分配用户', // 对话框标题
      form1: { // 表单数据
        id: '',
        role_id: null,
        role_name: '',
        status: true,
        created_at: ''
      },
      showAssignUsers: false,
      selectedUsers: [], // 存储选择的用户数据
      selectedRoles: [], // 存储选择的角色


    };
  },
  mounted() {
    this.handleSearch();
    this.handleSearch1();
  },
  methods: {
    asingnuser() {
      console.log("用户分配成功!!!")
    },
    resetForm() {
      // 重置表单
      this.searchText = '';
      // 重新加载数据或执行其他操作
      // 例如异步获取数据
      this.handleSearch();
    },
    async search() {
      try {
        // 发起搜索请求
        const response = await axios.get('http://127.0.0.1:8000/search/roles/', {
          params: {
            query: this.searchText
          }
        });
        console.log(this.searchText);
        // 更新表格数据
        this.tableData = response.data;
        console.log(this.tableData);
      } catch (error) {
        console.error('搜索时出错:', error);
      }
    },
    handleSelectionChange(selection) {
      this.selectedUsers = selection;
    },

    async handleSearch() {
      try {
        const response = await axios.get('http://127.0.0.1:8000/roles/');
        this.tableData = response.data; // 将返回的用户数据存储在tableData中
      } catch (error) {
        console.error('Error fetching users:', error);
      }
    },
    async handleSearch1() {  // 接收角色 id 作为参数
      try {
        const response = await axios.get(`http://127.0.0.1:8000/users/`);
        this.tableData1 = response.data;
      } catch (error) {
        console.error('Error fetching users:', error);
      }
    },
    showAddDialog() {
      this.dialogTitle = '新增角色';
      this.form = {
        id: '',
        role_id: null,
        role_name: '',
        status: true,
        created_at: ''
      };
      this.isDialogVisible = true;
    },
    showEditDialog(row) {
      this.dialogTitle = '编辑用户';
      this.form = { ...row }; // 将选中的行数据填充到表单中
      this.isDialogVisible = true;
    },
    assignUser(row) {
      this.isDialogVisible1 = true;
      this.dialogTitle1 = '分配用户';
      // 调用获取对应角色用户数据的方法,并传递角色 id
      const role = this.handleSearch1(row.role_id);
      console.log("role角色", role);
    },


    async handleSubmit() {
      if (this.form.id) {
        // 编辑用户
        try {
          await axios.put(`http://127.0.0.1:8000/roles/${this.form.id}/`, this.form);
          this.$message.success('用户更新成功');
          this.handleSearch();
        } catch (error) {
          console.error('Error updating user:', error);

        }
      } else {
        // 新增用户
        try {
          await axios.post('http://127.0.0.1:8000/roles/', this.form);
          this.$message.success('用户新增成功');
          this.handleSearch();
        } catch (error) {
          console.error('Error adding user:', error);
        }
      }
      this.isDialogVisible = false;
    },


    async handleDelete(id) {
      try {
        const confirm = await this.$confirm('确认删除该用户吗?', '提示', {
          confirmButtonText: '确定',
          cancelButtonText: '取消',
          type: 'warning'
        });
        if (confirm) {
          await axios.delete(`http://127.0.0.1:8000/roles/${id}/`);
          this.$message.success('用户删除成功');
          this.handleSearch();
        }
      } catch (error) {
        console.error('Error deleting user:', error);
      }
    },


    /** 分配用户操作 */
    handleAuthUser(row) {
      console.log("rowsaaaaaaaaaaaaaaaaaaaaaaa", row);
      const roleID = row.id;
      console.log("sssssssssssssss", roleID);
      // this.$router.push("/role/authUser/"+roleID);
      // 使用 $router.push 导航到对应的角色授权页面
      this.$router.push({ name: 'authUser', params: { roleID: this.roleID } });
    },



    // // 更多操作触发
    handleCommand(command, row) {
      switch (command) {
        case "handleDataScope":
          this.handleDataScope(row);
          break;
        case "handleAuthUser":
          this.handleAuthUser(row);
          break;
        default:
          break;
      }
    },




  }
};
</script>

<style>
/* 样式可以按需添加 */
.s {

  margin-left: 20px;
  margin-top: 20px;
}
.role-permissions{
  margin-top: 20px;
  display: flex;
  flex-direction:row;
}
.el-switch__core{
  margin-top: 23px;
  margin-right: 60px;

}

</style>

4、部门管理

<template>
  <div class="as">
    <div class="xinzeng">
      <el-row :gutter="10" class="mb8">
        <el-col :span="1.5">
          <el-button type="primary" plain icon="el-icon-plus" size="mini" @click="showAddDialog">新增</el-button>
        </el-col>
        <!-- <el-col :span="1.5">
          <el-button type="info" plain icon="el-icon-sort" size="mini" @click="toggleExpandCollapse">展开/折叠</el-button>
        </el-col> -->
        <!-- <right-toolbar :showSearch.sync="showSearch" @queryTable="fetchData"></right-toolbar> -->
      </el-row>
    </div>
    <div class="tab">
      <el-table v-loading="loading" :data="processedData" row-key="id" :default-expand-all="isExpandAll"
        :tree-props="{ children: 'children', hasChildren: 'hasChildren' }">
        <el-table-column prop="name" label="部门名称" width="260"></el-table-column>
<!-- 
        <el-table-column prop="id" label="id222222222" width="260"></el-table-column>

        <el-table-column prop="parent" label="部门名称1111111111" width="260"></el-table-column>
      -->
        <el-table-column prop="order" label="排序" width="250"></el-table-column>

        <el-table-column prop="status" label="状态" width="260">
          <template slot-scope="scope">
            <el-tag :type="scope.row.status ? 'success' : 'danger'">{{ scope.row.status ? '正常' : '停用' }}</el-tag>
          </template>
        </el-table-column>
        <el-table-column prop="created_at" label="创建时间" width="280">
          <template slot-scope="scope">
            {{ scope.row.created_at | formatDate }}
          </template>
        </el-table-column>
        <el-table-column label="操作" align="center" class-name="small-padding fixed-width">
          <template slot-scope="scope">
            <el-button size="mini" type="text" icon="el-icon-edit" @click="showEditDialog(scope.row)"
         >修改</el-button>
            <!-- <el-button size="mini" type="text" icon="el-icon-plus" @click="showAddDialog">新增</el-button> -->
            <el-button v-if="scope.row.parentId != 0" size="mini" type="text" icon="el-icon-delete"
              @click="handleDelete(scope.row.id)">删除</el-button>
          </template>
        </el-table-column>
      </el-table>

      <!-- 新增/编辑对话框 -->
      <el-dialog :title="dialogTitle" :visible.sync="isDialogVisible">
        <el-form :model="form">

          <el-row>
            <el-col :span="24" v-if="form.parent !== 0">
              <el-form-item label="上级部门" prop="parent">
                <treeselect v-model="form.parent" :options="deptOptions" :normalizer="normalizer" placeholder="选择上级部门" />
              </el-form-item>
            </el-col>
          </el-row>
     
          <el-form-item label="部门名称">
            <el-input v-model="form.name"></el-input>
          </el-form-item>

          <el-form-item label="排序">
            <el-input v-model="form.order"></el-input>
          </el-form-item>

          <el-form-item label="状态">
            <el-switch v-model="form.status"></el-switch>
          </el-form-item>
        </el-form>
        <div slot="footer" class="dialog-footer">
          <el-button @click="isDialogVisible = false">取消</el-button>
          <el-button type="primary" @click="handleSubmit">确定</el-button>
        </div>
      </el-dialog>



    </div>
  </div>
</template>

<script>
import axios from "axios";
import Treeselect from "@riophae/vue-treeselect";
import "@riophae/vue-treeselect/dist/vue-treeselect.css";

export default {
  components: { Treeselect },
  data() {
    return {

      // {
      //     id: "",
      //   name: "",
      //   parent: null,
      //   children: [
      //       {
      //           id: "",
      //           name: "",
      //           parent: "",
      //           children: [
      //             {
      //               name: "",
      //             }
      //           ],
      //           order: "",
      //           status: "",
      //           created_at: ""
      //       }
      //   ],
      //   order: "",
      //   status: "",
      //   created_at: ""
      //   }
      // 部门树选项
      deptOptions: [
       
      ],
      isDialogVisible: false, // 控制对话框的显示
      dialogTitle: '新增部门', // 对话框标题
      form: { // 表单数据a
        id: '',
        name: "",
        parent: "",
        children: [],
        order: 0,
        status: "",
        created_at: ""
      },
      processedData: [],
      loading: false,  // 数据加载状态

      defaultProps: {
        children: "children",
        label: "name"
      },
      dialogVisible: false,  // 对话框的可见性
      currentItem: {  // 当前操作的部门项目
        id: null,
        name: "",
        parent: null
      },
      rules: {
        name: [
          { required: true, message: "请输入名称", trigger: "blur" }
        ],
        parent: [
          { required: true, message: "请选择父级", trigger: "blur" }
        ]
      },
      // 是否展开,默认全部展开
      isExpandAll: true,
      // 重新渲染表格状态
      refreshTable: true,
    };
  },
  created() {
    this.fetchData();
  },
  methods: {/** 转换部门数据结构 */
    normalizer(node) {
      if (node.children && !node.children.length) {
        delete node.children;
      }
      return {
        id: node.id,
        label: node.name,
        children: node.children
      };
    },

    // 获取部门数据
    async fetchData() {
      this.loading = true;  // 开始加载数据时设置加载状态为真
      try {
        const response = await axios.get("http://127.0.0.1:8000/departments/");
        this.processedData = response.data;
        this.deptOptions = response.data;
        console.log(this.processedData)
      } catch (error) {
        console.error("Error fetching data:", error);
      } finally {
        this.loading = false;  // 无论成功与否,结束加载时设置加载状态为假
      }
    },
    // 切换展开/折叠状态
    toggleExpandCollapse() {

      this.isExpandAll = !this.isExpandAll;
    },
    // 显示添加对话框
    showAddDialog() {
      this.dialogTitle = '新增部门';
      this.form = {
        id: '',
        name: "",
        order: '',
        status: true,
        created_at: '',
        parent: null
      };
      this.isDialogVisible = true;
    },
    showEditDialog(row) {
      this.dialogTitle = '编辑部门';
      this.form = { ...row }; // 将选中的行数据填充到表单中
      this.isDialogVisible = true;
    },
    // 表单重置
    reset() {
      this.form = {
        id: undefined,
        parent: undefined,
        name: undefined,
        order: undefined,
        created_at: undefined,

      };
      this.resetForm("form");
    },
    /** 新增按钮操作 */
    async handleAdd(row) {
      this.reset();
      if (row != undefined) {
        this.form.parent = row.id;
      }
      this.isDialogVisible = true;
      this.dialogTitle = "添加部门";
      try {
        await axios.post('http://127.0.0.1:8000/departments/', this.form);
        this.$message.success('用户新增成功');
        this.fetchData();

      } catch (error) {
        console.error('Error adding user:', error);
      }
    },
// // 部门弹框展示数据
//     showEditDialog(row) {
//       this.dialogTitle = '编辑用户';
//       this.form = { ...row }; // 将选中的行数据填充到表单中
//       this.isDialogVisible = true;
//     },
    async handleSubmit() {

      if (this.form.id !== "") {
        // 编辑部门
        try {
          await axios.put(`http://127.0.0.1:8000/departments/${this.form.id}/`, this.form);
          this.$message.success('用户更新成功');
          this.fetchData();
        } catch (error) {
          console.error('Error updating user:', error);
        }
      } else {
        // 新增部门
        try {
          await axios.post('http://127.0.0.1:8000/departments/', this.form);
          this.$message.success('用户新增成功');
          this.fetchData();

        } catch (error) {
          console.error('Error adding user:', error);
        }
      }
      this.isDialogVisible = false;
    },
    // 删除部门节点
    async deleteNode(node) {
      try {
        await axios.delete(`http://127.0.0.1:8000/departments/${node.id}`);
        await this.fetchData();
      } catch (error) {
        console.error("Error deleting node:", error);
      }
    },
    // // 编辑部门节点
    // editNode(node) {
    //   this.currentItem = { ...node };
    //   this.dialogVisible = true;
    // },
    
    // 处理新增子部门
    handleAdd(row) {
      // 这里可以添加具体的新增子部门逻辑
      console.log("新增子部门操作", row);
    },
    /** 展开/折叠操作 */
    toggleExpandAll() {
      this.refreshTable = false;
      this.isExpandAll = !this.isExpandAll;
      this.$nextTick(() => {
        this.refreshTable = true;
      });
    },
    async handleDelete(id) {
      try {
        await axios.delete(`http://127.0.0.1:8000/departments/${id}/`);
        this.$message.success('用户删除成功');
        this.fetchData();
      } catch (error) {
        console.error('Error deleting user:', error);
      }
    },
     
  }
};
</script>

<style scoped>
.xinzeng {
  padding-top: 30px;
  padding-left: 35px;
}


.tab {
  margin-top: 20px;
  margin-left: 20px;
}
</style>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2043418.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

EXTI外部中断之对射式红外传感器计次应用案例

系列文章目录 STM32中断系统之EXTI外部中断 文章目录 系列文章目录前言一、应用案例简介二、电路接线图三、应用案例代码四、应用案例分析4.1 配置外部中断4.1.1 配置RCC时钟4.1.2 配置GPIO4.1.3 配置AFIO4.1.4 配置EXTI4.1.5 配置NVIC 4.2 编写中断函数 前言 提示&#xff1…

泛微OA系统走进腾讯大厦

企业信息化、数字化、网络化、智能化的快速发展带来了无限可能&#xff0c;但同时也带来了系统安全的严峻挑战。您准备好应对了吗? 上月由腾讯安全部、泛微联合举办的“OA 系统安全防护与腾讯iOA 零信任安全策略客户会”在腾讯滨海大厦成功举办&#xff0c;本次活动邀请了60位…

拆开一个断了FPC的墨水屏,是不是像OLED一样驱动芯片在里面

可对比查看一个OLED的屏幕拆解 拆解理由 第一次焊接驱动板时的fpc上下接问题&#xff0c;但焊接到板子上并没有达到正常的显示效果。PI补强也被撕下来。后来拔下来后发现金手指断裂。本来想用一个fpc排线连接在一起&#xff0c;但后来发现并没有达到理想效果&#xff0c;飞线…

【Python学习-UI界面】PyQt5 小部件14-QDock 子窗口

可停靠窗口是一个子窗口&#xff0c;可以保持浮动状态或附加到主窗口的指定位置。 QMainWindow类的主窗口对象保留了一块区域供可停靠窗口使用。该区域位于中央窗口部件周围。 可停靠窗口可以在主窗口内移动&#xff0c;也可以被取消停靠并由用户移动到新的区域。 样式如下: …

MinIO DataPOD 目标锁定 GPU Direct 并行文件系统

MinIO 推出针对 AI 应用的 DataPOD 参考架构 MinIO 设计了一种旨在为 AI 训练提供数据的 exascale DataPOD 参考架构。这家开源对象存储软件供应商正将其可扩展至100 PiB&#xff08;即大约112.6 PB&#xff09;的单元定位为一种替代方案&#xff0c;以取代使用 GPU Direct 技…

新中地2402期GIS特训营学员圆满结业,解锁GIS开发的无限可能!

GIS开发了解 24年8月5日&#xff0c;新中地GIS开发特训营2402期学员迎来了属于自己的结业典礼。 初入特训营&#xff0c;教与学双向奔赴 从24年3月4日开班&#xff0c;面对全新的领域&#xff0c;大家新中既有对未知的忐忑&#xff0c;更有对掌握GIS开发技术的期待 在本期学员…

车辆车载客流统计系统解决方案

车辆车载客流统计系统是一种用于实时监测和分析乘客流量的技术解决方案&#xff0c;它可以帮助公交公司、地铁运营商等交通管理部门优化运营计划、提高服务效率和乘客满意度。以下是一个详细的车载客流统计系统解决方案&#xff1a; 一、系统组成 传感器与设备 摄像头&#xf…

C库函数signal()信号处理

signal()是ANSI C信号处理函数&#xff0c;原型如下&#xff1a; #include <signal.h>typedef void (*sighandler_t)(int); sighandler_t signal(int signum, sighandler_t handler); signal()将信号signum的处置设置为handler&#xff0c;该handler为SIG_IGN&#xff…

脊髓损伤治疗方法和需要那些营养

脊髓损伤作为一种严重的神经系统损伤&#xff0c;其治疗与康复一直是医学界关注的重点。在中医领域&#xff0c;针对脊髓损伤的治疗有着独特的理论和方法&#xff0c;旨在通过调节人体内部环境&#xff0c;促进受损神经的修复与再生。以下将从中医缓解方法与营养支持两个方面进…

Velero 快速上手:使用 Velero 实现 Kubernetes 集群备份与迁移

一、veloro 简介 Velero 是vmware开源的一个云原生的灾难恢复和迁移工具&#xff0c;它本身也是开源的,采用Go语言编写&#xff0c;可以安全的备份、恢复和迁移Kubernetes集群资源数据&#xff1b;Velero 是西班牙语意思是帆船&#xff0c;非常符合Kubernetes社区的命名风格&a…

【Python快速入门和实践017】Python常用脚本-根据文件后缀对其进行分类保存

一、功能介绍 这段代码的功能是将源文件夹中的文件按照它们的文件扩展名分类并移动到不同的子文件夹中。步骤如下&#xff1a; 定义函数&#xff1a;move_files_by_extension函数接收两个参数&#xff1a; source_folder&#xff1a;源文件夹路径。destination_folder&#xff…

LLM + GraphRAG技术,赋能教育培训行业数字化创新

随着人工智能大模型时代的到来&#xff0c;LLM大语言模型、RAG增强检索、Graph知识图谱、Prompt提示词工程等技术的发展日新月异&#xff0c;也让各行各业更加期待技术带来的产业变革。 比如&#xff0c;教育培训行业&#xff0c;教师数量相对有限、学生个体差异较大&#xff…

数据结构第一天

数据结构基础知识 1.1 什么是数据结构 数据结构就是数据的逻辑结构以及存储操作 (类似数据的运算) 数据结构就教会你一件事&#xff1a;如何更有效的存储数据 1.2 数据 数据&#xff1a;不再是单纯的数字&#xff0c;而是类似于集合的概念。 数据元素&#xff1a;是数据的基本单…

怎样卸载python

python卸载干净的具体操作步骤如下&#xff1a; 1、首先打开电脑左下角开始菜单&#xff0c;点击“运行”选项&#xff0c;输入“cmd”。 2、输入“python --version”&#xff0c;得到一个程序的版本&#xff0c;按回车键。 3、点击下图程序。 4、然后在该页面中点击“uninst…

【投融界-注册安全分析报告】

前言 由于网站注册入口容易被黑客攻击&#xff0c;存在如下安全问题&#xff1a; 暴力破解密码&#xff0c;造成用户信息泄露短信盗刷的安全问题&#xff0c;影响业务及导致用户投诉带来经济损失&#xff0c;尤其是后付费客户&#xff0c;风险巨大&#xff0c;造成亏损无底洞…

8 自动类型转换、强制类型转换、整数数据溢出与模运算、浮点数精度丢失、类型转换值截断

目录 1 自动类型转换&#xff08;隐式转换&#xff09; 1.1 运算过程中的自动类型转换 1.1.1 转换规则 1.1.2 转换方向 1.1.3 案例演示 1.2 赋值时的自动类型转换 1.2.1 案例演示 2 强制类型转换&#xff08;显式转换&#xff09; 2.1 介绍 2.2 转换格式 2.3 转换规…

案例分享—国外毛玻璃效果UI设计案例

毛玻璃效果通过模糊和半透明特性&#xff0c;显著增强了UI界面的层次感和深度&#xff0c;使得元素之间界限清晰&#xff0c;同时赋予界面一种现代、高级的质感&#xff0c;提升了整体视觉吸引力。 该效果不仅美观&#xff0c;还通过柔和的色彩和光照效果营造出清新、轻松的氛围…

回归分析系列1-多元线性回归

03 多元线性回归 3.1 简介 多元线性回归是简单线性回归的扩展&#xff0c;允许我们同时研究多个自变量对因变量的影响。多元回归模型可以表示为&#xff1a; 其中&#xff0c;x1,x2,…,xp是 p 个自变量&#xff0c;β0 是截距&#xff0c;β1,β2,…,βp是对应的回归系数&…

【STM32项目】在FreeRtos背景下的实战项目的实现过程(一)

个人主页~ 这篇文章是我亲身经历的&#xff0c;在做完一个项目之后总结的经验&#xff0c;虽然我没有将整个项目给放出来&#xff0c;因为这项目确实也是花了米让导师指导的&#xff0c;但是这个过程对于STM32的实战项目开发都是非常好用的&#xff0c;可以说按照这个过程&…

Layout 布局组件快速搭建

文章目录 设置主题样式变量封装公共布局组件封装 Logo 组件封装 Menu 菜单组件封装 Breadcrumb 面包屑组件封装 TabBar 标签栏组件封装 Main 内容区组件封装 Footer 底部组件封装 Theme 主题组件 经典布局水平布局响应式布局搭建 Layout 布局组件添加 Layout 路由配置启动项目 …