zoukankan      html  css  js  c++  java
  • 工单项目(前端)用于思考

    1 Vue端

    1.1 http

    1.1.1 aips.js
    //将我们http.js中封装好的  get,post.put,delete,patch  导过来
    import { axios_get, axios_post, axios_delete, axios_put, axios_patch } from './index.js'
    
    
    //按照格式确定方法名
    export const user_login = P => axios_post("/user/login/", P)  // 用户登录
    
    // 用户模块
    // 用户信息管理
    export const get_userlist = P => axios_get('/user/user/?page='+P, P)            // 获取用户列表
    export const get_userlist_new = P => axios_get('user/user_get/', P)             // 获取用户列表(不包含分页的接口)
    export const add_user = P => axios_post('/user/register/', P)                   // 注册新用户
    export const search_for = P => axios_get('user/user/', P)                       // 根据用户名查找指定用户信息并展示
    export const delete_user = P => axios_delete('/user/user/' + P + '/')           // 根据获取到的用户id删除用户信息
    export const update_user = P => axios_put('/user/user/'+ P.id +'/', P)          // 根据用户id和提交来的数据修改用户信息
    
    // 角色管理
    export const get_rolelist = P => axios_get('/user/role/?page='+P, P)            // 获取角色列表
    export const get_rolelist_new = P => axios_get('/user/role_get/', P)            // 获取角色列表(不包含分页的接口)
    export const add_role = P => axios_post('/user/role/', P)                       // 注册新角色
    export const search_for_role = P => axios_get('user/role/', P)                  // 根据角色名查找指定角色信息并展示
    export const delete_role = P => axios_delete('/user/role/' + P + '/')           // 根据获取到的角色id删除角色信息
    export const update_role = P => axios_put('/user/role/'+ P.id +'/', P)          // 根据角色id和提交来的数据修改角色信息
    
    // 工单模块---分类工单
    export const get_flowtypelist = P => axios_get('/workflow/flowtype/?page='+P, P)            // 获取模板分类列表
    export const get_flowtypelist_new = P => axios_get('/workflow/flowtype_get/', P)            // 获取模板分类列表(不含分页)
    export const add_flowtype = P => axios_post('/workflow/flowtype/', P)                       // 创建新模板分类
    export const search_for_flowtype = P => axios_get('/workflow/flowtype/', P)                  // 根据模板分类名查找指定模板分类信息并展示
    export const delete_flowtype = P => axios_delete('/workflow/flowtype/' + P + '/')           // 根据获取到的模板分类id删除模板分类信息
    export const update_flowtype = P => axios_put('/workflow/flowtype/'+ P.id +'/', P)          // 根据模板分类id和提交来的数据修改模板分类信息
    
    // 工单模块---工单模板
    export const get_flowconflist = P => axios_get('/workflow/flowconf/?page='+P, P)            // 获取工单模板列表
    export const get_flowconflist_new = P => axios_get('/workflow/flowconf_get/', P)            // 获取工单模板列表(不含分页)
    export const add_flowconf = P => axios_post('/workflow/flowconf/', P)                       // 创建新工单模板
    export const search_for_flowconf = P => axios_get('/workflow/flowconf/', P)                 // 根据工单模板名查找指定工单模板信息并展示
    export const delete_flowconf = P => axios_delete('/workflow/flowconf/' + P + '/')           // 根据获取到的工单模板id删除工单模板信息
    export const update_flowconf = P => axios_put('/workflow/flowconf/'+ P.id +'/', P)          // 根据工单模板id和提交来的数据修改工单模板信息
    
    // 工单模块---配置审批流
    export const get_approveconflist = P => axios_get('/workflow/approveconf/?page='+P, P)            // 获取配置审批流列表
    export const get_approveconflist_new = P =>axios_get('/workflow/approveconf/?flowconf='+P.flowconf, P)      // 获取指定模板的审批流
    export const add_approveconf = P => axios_post('/workflow/approveconf/', P)                       // 配置新审批流
    export const delete_approveconf = P => axios_delete('/workflow/approveconf/' + P + '/')           // 根据审批流id删除审批流信息
    export const update_approveconf = P => axios_put('/workflow/approveconf/'+ P.id +'/', P)          // 根据审批流id和提交来的数据修改审批流信息
    
    // 实例化工单
    export const add_workorder = P => axios_post('/workerorder/workorder/', P)                   // 数据库添加实例化工单
    
    // 工单管理---实例工单页面
    export const get_workerorder = P => axios_get('/workerorder/workorder/', P)                      // 获取实例化工单列表
    export const search_workerorder = P => axios_get('/workerorder/workorder_search/', P)            // 查找我的工单
    // 工单管理---实例子工单页面(由实例工单页面带参跳转)
    export const get_suborder = P => axios_get('/workerorder/suborder_get/', P)                      // 获取实例化工单列表
    export const search_suborder = P => axios_get('/workerorder/suborder_search/', P)            // 查找能审批的工单
    // 获取子工单审批状态
    export const get_suborder_auth = P => axios_get('/workerorder/suborder/', P)
    // 审批子工单
    export const add_suborder = P => axios_post('/workerorder/suborder_get/', P)            // 获取实例化工单列表
    
    // 判断是否是超级管理员
    
    export const is_superuser = P => axios_get('/user/is_superuser/', P)
    
    1.1.2 index.js
    import axios from 'axios'
    
    // 第一步:设置axios
    axios.defaults.baseURL = "http://192.168.56.100:1594/"
    
    //全局设置网络超时
    axios.defaults.timeout = 10000;
    
    //设置请求头信息
    axios.defaults.headers.post['Content-Type'] = 'application/json';
    axios.defaults.headers.put['Content-Type'] = 'application/json';
    
    
    // 第二:设置拦截器
    /**
     * 请求拦截器(当前端发送请求给后端前进行拦截)
     * 例1:请求拦截器获取token设置到axios请求头中,所有请求接口都具有这个功能
     * 例2:到用户访问某一个页面,但是用户没有登录,前端页面自动跳转 /login/ 页面
     */
    axios.interceptors.request.use(
        config => {
            // 每次发送请求之前判断是否存在token,如果存在,则统一在http请求的header都加上token,不用每次请求都手动添加了
            const token = localStorage.getItem("token")
                // console.log(token)
            if (token) {
                config.headers.Authorization = 'JWT ' + token
            }
            return config;
        },
        error => {
            return Promise.error(error);
        })
    
    axios.interceptors.response.use(
        // 请求成功,因为 API返回的状态码有多个,所以一定要在这里写上,不然会无法访问页面
        res => res.status === 200 || 201 || 204 ? Promise.resolve(res) : Promise.reject(res),
        // 请求失败
        error => {
            if (error.response) {
                // 判断一下返回结果的status == 401?  ==401跳转登录页面。  !=401passs
                // console.log(error.response)
                if (error.response.status === 401) {
                    // 跳转不可以使用this.$router.push方法、
                    // this.$router.push({path:'/login'})
                    window.location.href = "http://127.0.0.1:8080/"
                } else {
                    // errorHandle(response.status, response.data.message);
                    return Promise.reject(error.response);
                }
                // 请求已发出,但是不在2xx的范围
            } else {
                // 处理断网的情况
                // eg:请求超时或断网时,更新state的network状态
                // network状态在app.vue中控制着一个全局的断网提示组件的显示隐藏
                // 关于断网组件中的刷新重新获取数据,会在断网组件中说明
                // store.commit('changeNetwork', false);
                return Promise.reject(error.response);
            }
        });
    
    
    // 第三:封装axios请求
    // 3.1 封装get请求
    export function axios_get(url, params) {
        return new Promise(
            (resolve, reject) => {
                axios.get(url, {params:params})
                    .then(res => {
                        // console.log("封装信息的的res", res)
                        resolve(res.data)
                    }).catch(err => {
                        reject(err.data)
                    })
            }
        )
    }
    
    // 3.2 封装post请求
    export function axios_post(url, data) {
        return new Promise(
            (resolve, reject) => {
                // console.log(data)
                axios.post(url, JSON.stringify(data))
                    .then(res => {
                        // console.log("封装信息的的res", res)
                        resolve(res.data)
                    }).catch(err => {
                        reject(err.data)
                    })
            }
        )
    }
    
    // 3.3 封装put请求
    export function axios_put(url, data) {
        return new Promise(
            (resolve, reject) => {
                // console.log(data)
                axios.put(url, JSON.stringify(data))
                    .then(res => {
                        // console.log("封装信息的的 res", res)
                        resolve(res.data)
                    }).catch(err => {
                        reject(err.data)
                    })
            }
        )
    }
    
    // 3.4 封装patch请求(可用于局部修改)
    
    export function axios_patch(url, data) {
        return new Promise(
            (resolve, reject) => {
                // console.log(data)
                axios.patch(url, JSON.stringify(data))
                    .then(res => {
                        // console.log("封装信息的的res", res)
                        resolve(res.data)
                    }).catch(err => {
                        reject(err.data)
                    })
            }
        )
    }
    
    // 3.5 封装delete请求
    export function axios_delete(url, data) {
        return new Promise(
            (resolve, reject) => {
                // console.log(data)
                axios.delete(url, { params: data })
                    .then(res => {
                        // console.log("封装信息的的res", res)
                        resolve(res.data)
                    }).catch(err => {
                        // reject(err.data)
                    })
            }
        )
    }
    

    1.2 router

    1.2.1 index.js
    • 这里采用了子路由,在主页中直接<路由名></路由名>就可以引用组件
    import Vue from 'vue'
    import Router from 'vue-router'
    import Home from '@/components/layout/Home'
    const page = name => () => import('@/views/' + name)
    Vue.use(Router)
    
    export default new Router({
      mode: 'history',
      routes: [
        { path: '/login',component: page('Login'),name: '登录'},
        { path: '/',component: Home,name: 'home',
          children: [
            { path: 'usermanage', component: page('user-manage/index'), name: '信息管理' },
            { path: 'rolemanage', component: page('role-manage/index'), name: '角色管理' },
            { path: 'flowtype', component: page('flowtype-manage/index'), name: '模板分类管理' },
            { path: 'flowconf', component: page('flowconf-manage/index'), name: '工单模板管理' },
            { path: 'approveconf', component: page('approveconf-manage/index'), name: '新建模板管理' },
            { path: 'workorder', component: page('workorder-manage/index'), name: '创建工单' },
            { path: 'flowconfform', component: page('flowconfform-manage/index'), name: '实例化工单form' },
            { path: 'childconfform', component: page('childconfform-manage/index'), name: '实例化子工单form' },
            { path: 'workerorder', component: page('workerorder-manage/index'), name: '查看工单' },
            { path: 'suborder', component: page('suborder-manage/index'), name: '查看子工单' },
            { path: 'start', component: page('StartPage'), name: '首页猫咪' },
            { path: 'baidu', component: page('BaiDu'), name: '跳转百度' },     
          ]
        },
      ]
    })
    
    

    1.3 components

    • 公用组件
    1.3.1 Header.vue
    <template>
            <div><a style="float:right" @click="outLogin">注销登录</a>
              <h3 style="margin-top:20px">           
              欢迎你
               <a-icon type="smile" theme="outlined" style="font-size:20px;color:pink"/>&ensp;
              {{username}}
                <a-icon type="fire" style="font-size:25px;color:pink"/>&ensp;
              </h3>         
            </div>
    </template>
    <script>
    export default{
        data(){
            return{
              username:localStorage.getItem('username')
            }
        },
        methods:{
          outLogin(){
            localStorage.removeItem('token')
            localStorage.removeItem('username')
            localStorage.removeItem('uid')
            alert('注销登录成功,稍后为您跳转登录页面')
            this.$router.push('/login')
          }
        }
    }
    </script>
    
    1.3.2 Home.vue
    <template>
             <div id="components-layout-demo-basic" style="">
                <a-layout>
                    <a-layout-sider style="height:250px;150px">
                        <LeftMenu></LeftMenu>
                        <!-- 以组件发昂视导入左侧菜单 -->
                    </a-layout-sider>
                    <a-layout>
    
                        <a-layout-header  style="height:80px;500px;background:rgb(253,234,254)">
                            <Header/>
                            <!-- 导入头部 -->
                        </a-layout-header>
                        
                            <div style="margin-left:100px">
                                <!-- 这里的 router-view 是绑定的路由 -->
                                <p><router-view></router-view></p>
                            </div>
                            
                    </a-layout>
    
                </a-layout>
            </div>
    </template>
    
    <script>
    // 导入组件
    import LeftMenu from '@/components/layout/LeftMenu'
    import Header from '@/components/layout/Header'
    export default {
        // 注册组件
        components:{
            LeftMenu,
            Header
        },
        data() {
            
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header {
      background: white;
    }
    #components-layout-demo-basic .ant-layout-footer {
      background: rgb(253,234,254);
      color: rgb(253,234,254);
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-sider {
      background: rgb(253,234,254);
      color: rgb(253,234,254);
      line-height: 120px;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: white;
      min-height: 120px;
      line-height: 120px;
    }
    .ant-layout.ant-layout-has-sider{
      1530px;
      height: 722px;
      background:rgb(253,234,254)
    }
    .ant-layout{
      background:rgb(253,234,254);
      800px
    }
    </style>
    
    1.3.3 LeftMenu.vue
    <template>
      <div>
        <a-switch :default-checked="false" @change="changeMode" style="margin-top:70px"/>&emsp;
        <br>
        <a-menu
          style=" 300px;background:rgb(253,234,254)"
          :default-selected-keys="['1']"
          :default-open-keys="['sub1']"
          :mode="mode"
          :theme="theme"
          @click="handleClick"
          
        >
        <!-- 必须定义click方法,handleClick是用来跳转路由的,内置毁掉参数e,包括传递上去的key路由地址 -->
          <a-sub-menu >
            <span slot="title">
              <a-icon type="user" />
              <span>用户模块</span>
            </span>
              
              <a-menu-item key="usermanage" title="用户信息管理" style="background:rgb(253,234,254)">
                信息管理
              </a-menu-item>
              <!-- key是路由地址 -->
    
              <a-menu-item key="rolemanage" title="工单模板" style="background:rgb(253,234,254)">
                角色管理
              </a-menu-item>
    
    
           </a-sub-menu>
          
    
          <a-menu-item key="baidu">
            <a-icon type="calendar" />
            百度翻译
          </a-menu-item>
          <a-sub-menu key="workflow" style="background:rgb(253,234,254)">
            <span slot="title">
              <a-icon type="appstore" />
              <span>模板管理</span>
            </span>
              
              <a-menu-item key="flowtype" title="工单分类" style="background:rgb(253,234,254);">
                模板分类
              </a-menu-item>
    
              <a-menu-item key="flowconf" title="工单模板" style="background:rgb(253,234,254)">
                新建模板
              </a-menu-item>
    
           </a-sub-menu>
        
          <a-sub-menu key="workorder">
            <span slot="title"><a-icon type="setting" /><span>工单管理</span></span>
                  
              <a-menu-item key="workorder" style="background:rgb(253,234,254)">
              新建工单
              </a-menu-item>
    
              <a-menu-item key="workerorder"  style="background:rgb(253,234,254)">
              查看我的工单
              </a-menu-item>
              <a-menu-item key="suborder"  style="background:rgb(253,234,254)">
              查看我的子工单
              </a-menu-item>
    
          </a-sub-menu>
        </a-menu>
      </div>
    </template>
    <script>
    import { is_superuser } from '@/http/apis'
    export default {
      data() {
        return {
          mode: 'inline',
          theme: 'light',
          current: '1'
        };
      },
      methods: {
        changeMode(checked) {
          this.mode = checked ? 'vertical' : 'inline';
        },
        changeTheme(checked) {
          this.theme = checked ? 'dark' : 'light';
        },
         handleClick(e) {
          this.current = e.key;
          console.log(this.current)
          console.log(e.domEvent)
          is_superuser().then(res=>{
            if(res.type == 1 || this.current == 'workorder' || this.current == 'workerorder' || this.current == 'suborder'){
                this.$router.push({path:this.current});
                // click方法默认回调参数中的 key,所以 e.key就是传递来的路由
            }else{
              alert('您不是管理员,没有权限访问哦!')
            }
          })
    
        },
      },
    };
    </script>
    <style>
    .a-menu{
      background:rgb(253,234,254);
         5500px;
    }
    .ul{
      background:rgb(253,234,254)
    }
    .ant-menu-submenu > .ant-menu{
      background-color: rgb(253,234,254);
    
    }
    </style>
    

    1.4 views

    1.4.1 user-manage

    • 用户组件
    • 只允许超级有用户访问
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <BreadCrumb style="float:left"></BreadCrumb>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <a-button type="danger" ghost style="float:left;margin-left:20px;margin-top:16px;color:pink;border-color:pink;font-size:16px" @click="addNew">
                    AddUser
                    </a-button>
                    <EditForm
                        :visible.sync="visible"
                        :userList='userList'
                        :roleList='roleList'
                        @add="add"
                    >
                    <!-- .sync控制组件是否显示 -->
                    </EditForm>
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchList="searchList"
                      @find="find"
                      @getUser="getUser"
                    >
                    </Search>
                    
                </div>
                    <TableList
                      :userListGet="userListGet"
                      :userList="userList"
                      @getUser="getUser"
                      @add="add"
                    >
                    </TableList>
                    <Pagination
                      @getPage="getPage" 
                      :count="count" 
                      style="margin-top:20px; "             
                    ></Pagination>
                    <p></p>
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import Search from "./components/Search";
    import EditForm from "./components/EditForm";
    import Pagination from "./components/Pagination"
    
    import { add_user, search_for, get_userlist, update_user } from '@/http/apis';
    import { delete_user } from '../../http/apis';
    import { get_rolelist_new, add_role_user } from '../../http/apis';
    export default {
        components:{
            BreadCrumb,
            TableList,
            Search,
            EditForm,
            Pagination
        },
        data() {
            return {
                visible:false,
                userList: {
                  'id':'',
                  // 'is_superuser':'',
                  'username': '',
                  'passowrd': '',
                  'password_new': '',
                  'email':'',
                  'mobile':'',
                  'weixin':'',
                  'roles':[]
                  // 没定义roles字段的话,没办法绑定
                },
                roleList: [],
                userListGet:[],
                searchList:{
                    'username':'',
                    'page':1,
                    'page_size':4
    
                },
                updateUserList:[],
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0,
                addRoleList:[]
    
            }
        },
        methods: {
            addNew(){
              this.visible = true
              this.userList = {
                  'id':'',
                  'username': '',
                  'passowrd': '',
                  'password_new': '',
                  'email':'',
                  'mobile':'',
                  'weixin':'',
                  'roles':[],
                }
              // 用于控制组件显示
            },
            add(role_list){
              if(this.userList.id){            
                this.visible = true  
                update_user(this.userList).then(res=>{
                  // alert('修改成功')
                  this.getUser()
                })
    
              }else{
                
                // 添加用户,子组件中编辑的值实际上是写在父组件上面的
                add_user(this.userList).then(res=>{
                  
                  console.log(res)
                  alert('添加新用户成功')
                  this.getUser()
                  
              })   
                this.visible=false       
              }
            },
            find(){
              // 根据用户名查找用户信息
              search_for(this.searchList).then(res=>{
                // 阔落的办法可以解决bug,但是不支持查询出多条数据,因为没办法分页
                // if(this.searchList.username){
                //   // 修复如果没有搜索数据,回车就只能显示一个页面的bug
                //   console.log(res)
                //   this.userListGet = res.results
                //   this.count = res.results.length
                // }else{
                //   this.getUser()
                // }
                this.getUser()
    
              })
            },
            getUser(){
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_userlist(this.searchList).then(res=>{
                this.userListGet = res.results
                this.count = res.count
                console.log(this.count)
                console.log(this.userListGet)
    
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getUser()
            },
            getRole(){
                get_rolelist_new().then(res=>{
                    this.roleList = res
                    console.log(111111)
                    console.log(this.roleList)
                })
            }
        },
        created() {
          this.getRole()
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <br>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                用户模块
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                信息管理页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 EditForm.vue
    <template>
        <div>
            <a-modal
            title="Please write now."
            :visible="visible"
            @ok="handleOk"
            @cancel="handleCancel"
            >
            <!-- @ok控制按钮ok -->
            <!-- @cancel控制按钮cancel -->
                <p v-if="userList.id">UserName:
                    <a-input 
                    style="380px;float:right" 
                    placeholder="username" 
                    v-model="userList.username"
                    disabled="disabled"
                    ></a-input>                
                </p>
                <p v-else>UserName:
                    <a-input 
                    style="380px;float:right" 
                    placeholder="username" 
                    v-model="userList.username"
                    ></a-input>
                </p>
                <br>
                <div v-if="userList.id">
    
                </div>
                <div v-else>
                <p>PassWord:
                    <a-input
                        v-decorator="[
                            'password',
                            { rules: [{ required: true, message: 'Please input your Password!' }] },
                        ]"
                        type="password"
                        placeholder="Password"
                        style="380px;float:right"
                        v-model="userList.password"
                        :disabled = 'false'
                    >
                        <a-icon slot="prefix" type="lock" style="color:rgba(0,0,0,.25)" />
                    </a-input>
                </p>
                <br>
                <p>PassWord Again:
                    <a-input
                        v-decorator="[
                            'password',
                            { rules: [{ required: true, message: 'Please input your Password!' }] },
                        ]"
                        type="password"
                        placeholder="Password"
                        style="340px;float:right"
                        v-model="userList.password_new"
                    >
                        <a-icon slot="prefix" type="lock" style="color:rgba(0,0,0,.25)" />
                    </a-input>
                </p>
                </div>
                <br>
                <p>Email:
                    <a-input style="410px;float:right" placeholder="Email" v-model="userList.email"></a-input>
                </p>
                <br>
                <p>Mobile:
                    <a-input style="410px" placeholder="Mobile" v-model="userList.mobile"></a-input>
                </p>
                <br>
                <p>Weixin:
                    <a-input style="410px" placeholder="WeiXin" v-model="userList.weixin"></a-input>
                </p>
                <br>
                <p v-show="userList.id!=''">Is_superuser:
                    <a-input style="370px" placeholder="SuperUser" v-model="userList.is_superuser" disabled="disabled"></a-input>
                
                </p>
                <br>
                <p>Role:
                 <a-select
                    mode="multiple"               
                    style=" 410px; float:right"
                    placeholder="Please select"
                    @change="handleChange"
                    v-model="userList.roles"
                 >
                    <a-select-option v-for="i in roleList" :key="i.id" >
                    {{ i.zh_name }}
                    </a-select-option>
                </a-select>
                </p>
            </a-modal>
    
        </div>
    </template>
    
    <script>
    export default {
        props:['visible', 'userList', 'roleList'],
        data() {
            return {
            }
        },
        methods: {
            handleOk(e) {
                this.$emit('add', this.role)
                // add方法的调用一定要在关闭弹窗上面,否则方法不执行完毕没有办法关闭弹窗
                // 调用父组件中 add 方法            
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
    
            },
            handleCancel(e) {
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
            },
            handleChange(value) {
                // console.log(`selected ${value}`);
                console.log(value)
                this.userList.roles = value
            },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 Search.vue
    <template>
        <div>
            <a-input-search placeholder="Input the username that you want to search for..." enter-button @search="onSearch" style="float:right;400px;" v-model="searchList.username"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchList'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
                this.$emit('find')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.5 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="userListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
        style="height:430px"
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="roles" slot-scope="roles">
          <a-tag
            v-for="role in roles"
            :key="role.id"
            color="pink"
          >
            {{ role.role__zh_name }}
          </a-tag>
        </p>
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="delUser(text,tags,i)">删除</a-button>
          <a-button @click="updateUser(text,tags,i)">修改</a-button>
        </p>
        
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: 'UserName',
        dataIndex: 'username',
        key: 'username',
        scopedSlots: { customRender: 'username' },
         80,
      },
      {
        title: 'Email',
        dataIndex: 'email',
        key: 'email',
         100,
      },
      {
        title: 'Mobile',
        dataIndex: 'mobile',
        key: 'mobile',
        ellipsis: true,
         100,
      },
      {
        title: 'WeiXin',
        dataIndex: 'weixin',
        key: 'weixin',
        ellipsis: true,
         80,
      },
      {
        title: 'Is SuperUser',
        dataIndex: 'is_superuser',
        key: 'is_superuser',
        ellipsis: true,
         90,
      },
        {
        title: 'Roles',
        dataIndex: 'roles',
        key: 'roles',
        ellipsis: true,
         150,
        scopedSlots : { customRender: 'roles'}
        // 不写的话显示不了标签
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    
    ]
    
    import { delete_user } from '@/http/apis'
    export default {
      props:[ 'userListGet', 'userList'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getUser')
            // 调用父组件中的获取用户列表的方法
        },
        delUser(text,tags,i){
          // 定义变量 isDel来控制 confirm,isDel==true执行的就是对话框的 ok,isDel==false执行的就是对话框的 false
            const isDel = confirm('你确定要删除' + tags.id)
            if(isDel==true){
              delete_user(tags.id).then(
              res=>{
                // 删除回调地址是  http://192.168.56.100:1594/id/
                this.get()
                alert('删除成功啦~')
              })
            }else{
                alert('有需要再叫我哈~')
            }
                 
        },
        updateUser(text,tags,i){
          const roleIds = []
          tags.roles.forEach(item => {
            roleIds.push(item.role__id)
          });
    
          this.userList.id = tags.id
          this.userList.username = tags.username
          this.userList.password = tags.password,
          this.userList.password_new = tags.password
          this.userList.email = tags.email
          this.userList.mobile = tags.mobile
          this.userList.weixin = tags.weixin
          this.userList.is_superuser = tags.is_superuser
          // 传一个角色id的列表给父组件
          this.userList.roles = roleIds     
          this.$emit('add')
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.2 role-manage

    • 角色组件
    • 只允许超级有用户访问
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <p></p>
              <BreadCrumb style="float:left"></BreadCrumb>
              <p></p>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <a-button  type="danger" ghost style="float:left;margin-left:20px;margin-top:16px;color:pink;border-color:pink;font-size:16px" @click="addNew">
                    AddRole
                    </a-button>
                    <p></p>
                    <EditForm
                        :visible.sync="visible"
                        :roleList='roleList'
                        @add="add"
                    >
                    <!-- .sync控制组件是否显示 -->
                    </EditForm>
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchList="searchList"
                      @find="find"
                      @getRole="getRole"
                    >
                    </Search>
                    
                </div>
                    <TableList
                      :roleListGet="roleListGet"
                      :roleList="roleList"
                      @getRole="getRole"
                      @add="add"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"
                      style="margin-top:20px;"              
                    ></Pagination>
                    <p></p>
                    
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import Search from "./components/Search";
    import EditForm from "./components/EditForm";
    import Pagination from "./components/Pagination"
    
    import { add_role, search_for_role, get_rolelist, update_role } from '@/http/apis';
    import { delete_role } from '../../http/apis';
    export default {
        components:{
            BreadCrumb,
            TableList,
            Search,
            EditForm,
            Pagination
        },
        data() {
            return {
                visible:false,
                roleList: {
                  'id':'',
                  'zh_name': '',
                  'en_name': '',
                  'description':''
                },
                roleListGet:[],
                searchList:{
                    'zh_name':'',
                    'page':1,
                    'page_size':4,
                    
                },
                updateRoleList:[],
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0
    
            }
        },
        methods: {
            addNew(){
              this.visible = true
              this.roleList = {
                  'id':'',
                  'zh_name': '',
                  'en_name': '',
                  'description':''
                }
              // 用于控制组件显示
            },
            add(){
              if(this.roleList.id){            
                this.visible = true  
                update_role(this.roleList).then(res=>{
                  // alert('修改成功')
                  this.getRole()
                })
    
              }else{
                // 添加用户,子组件中编辑的值实际上是写在父组件上面的
                add_role(this.roleList).then(res=>{
                  console.log(res)
                  alert('添加新用户成功')
                  this.getRole()
                  
              })   
                this.visible=false       
              }
            },
            find(){
              // 根据用户名查找用户信息
              search_for_role(this.searchList).then(res=>{
                  this.getRole()
                  // 数据解耦性!!!查询和查询某个其实可以调用同一个接口!
                  // 查询所有:http://192.168.56.100:1594/?page=1&zh_name=
                  // 查询某个:http://192.168.56.100:1594/?page=1&zh_name=
                
              })
            },
            getRole(){
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_rolelist(this.searchList).then(res=>{
                this.roleListGet = res.results
                this.count = res.count
                console.log(this.count)
                console.log(this.roleListGet)
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getRole()
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                用户模块
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                角色管理页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 EditForm.vue
    <template>
        <div>
            <a-modal
            title="Please write now."
            :visible="visible"
            @ok="handleOk"
            @cancel="handleCancel"
            >
            <!-- @ok控制按钮ok -->
            <!-- @cancel控制按钮cancel -->
                <p v-if="roleList.id">ZhName:
                    <a-input 
                    style="400px;float:right" 
                    placeholder="zh_rname"
                    v-model="roleList.zh_name"
                    disabled="disabled"
                    ></a-input>                
                </p>
                <p v-else>ZhName:
                    <a-input 
                    style="390px;float:right" 
                    placeholder="zh_name" 
                    v-model="roleList.zh_name"
                    ></a-input>
                </p>
                <br>
                <p>EnName:
                    <a-input style="380px;float:right" placeholder="Description" v-model="roleList.en_name"></a-input>
                </p>
                <br>
                <p>Description:
                    <a-input style="380px;float:right" placeholder="Description" v-model="roleList.description"></a-input>
                </p>
            </a-modal>
    
        </div>
    </template>
    
    <script>
    export default {
        props:['visible', 'roleList'],
        data() {
            return {
            }
        },
        methods: {
            handleOk(e) {
                this.$emit('add')
                // add方法的调用一定要在关闭弹窗上面,否则方法不执行完毕没有办法关闭弹窗
                // 调用父组件中 add 方法            
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
    
            },
            handleCancel(e) {
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
            },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 Search.vue
    <template>
        <div>
            <a-input-search placeholder="Input the rolename that you want to search for..." enter-button @search="onSearch" style="float:right;400px" v-model="searchList.zh_name"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchList'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
                this.$emit('find')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.5 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="roleListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="delRole(text,tags,i)">删除</a-button>
          <a-button @click="updateRole(text,tags,i)">修改</a-button>
        </p>
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: 'ZhName',
        dataIndex: 'zh_name',
        key: 'zh_name',
        scopedSlots: { customRender: 'zh_name' },
         80,
      },
      {
        title: 'EnName',
        dataIndex: 'en_name',
        key: 'en_name',
         100,
      },
        {
        title: 'Description',
        dataIndex: 'description',
        key: 'description',
         100,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    ]
    
    import { delete_role } from '@/http/apis'
    export default {
      props:[ 'roleListGet', 'roleList'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getRole')
            // 调用父组件中的获取用户列表的方法
        },
        delRole(text,tags,i){
          // 定义变量 isDel来控制 confirm,isDel==true执行的就是对话框的 ok,isDel==false执行的就是对话框的 false
            const isDel = confirm('你确定要删除')
            if(isDel==true){
              delete_role(tags.id).then(
              res=>{
                // 删除回调地址是  http://192.168.56.100:1594/id/
                this.get()
                alert('删除成功啦~')
              })
            }else{
                alert('有需要再叫我哈~')
            }
                 
        },
        updateRole(text,tags,i){
          this.roleList.id = tags.id
          this.roleList.zh_name = tags.zh_name
          this.roleList.en_name = tags.en_name,
          this.roleList.description = tags.description     
          this.$emit('add')
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.3 flowtype-manage

    • 工单分类组件
    • 只允许超级有用户访问
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <BreadCrumb style="float:left"></BreadCrumb>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <a-button  type="danger" ghost style="float:left;margin-left:20px;margin-top:16px;color:pink;border-color:pink;font-size:16px" @click="addNew">
                    AddFlowType
                    </a-button>
                    <p></p>
                    <EditForm
                        :visible.sync="visible"
                        :flowTypeList='flowTypeList'
                        @add="add"
                    >
                    <!-- .sync控制组件是否显示 -->
                    </EditForm>
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchList="searchList"
                      @find="find"
                      @getFlowType="getFlowType"
                    >
                    </Search>
                    <p></p>
                    
                </div>
                    <TableList
                      :flowTypeListGet="flowTypeListGet"
                      :flowTypeList="flowTypeList"
                      @getFlowType="getFlowType"
                      @add="add"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"   
                      style="margin-top:20px"           
                    ></Pagination>
                    <p></p>
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import Search from "./components/Search";
    import EditForm from "./components/EditForm";
    import Pagination from "./components/Pagination"
    
    import { add_flowtype, search_for_flowtype, get_flowtypelist, update_flowtype } from '@/http/apis';
    import { delete_flowtype } from '../../http/apis';
    export default {
        components:{
            BreadCrumb,
            TableList,
            Search,
            EditForm,
            Pagination
        },
        data() {
            return {
                visible:false,
                flowTypeList: {
                  'id':'',
                  'name': '',
                  'description':''
                },
                flowTypeListGet:[],
                searchList:{
                    'name':'',
                    'page':1,
                    'page_size':4,
                    
                },
                updateFlowTypeList:[],
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0
    
            }
        },
        methods: {
            addNew(){
              this.visible = true
              this.flowTypeList = {
                  'id':'',
                  'name': '',
                  'description':''
                }
              // 用于控制组件显示
            },
            add(){
              if(this.flowTypeList.id){            
                this.visible = true  
                update_flowtype(this.flowTypeList).then(res=>{
                  // alert('修改成功')
                  this.getFlowType()
                })
    
              }else{
                // 添加用户,子组件中编辑的值实际上是写在父组件上面的
                add_flowtype(this.flowTypeList).then(res=>{
                  console.log(res)
                  alert('添加新用户成功')
                  this.getFlowType()
                  
              })   
                this.visible=false       
              }
            },
            find(){
              // 根据用户名查找用户信息
              search_for_flowtype(this.searchList).then(res=>{
                  this.getFlowType()
                  // 数据解耦性!!!查询和查询某个其实可以调用同一个接口!
                  // 查询所有:http://192.168.56.100:1594/?page=1&zh_name=
                  // 查询某个:http://192.168.56.100:1594/?page=1&zh_name=
                
              })
            },
            getFlowType(){
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_flowtypelist(this.searchList).then(res=>{
                this.flowTypeListGet = res.results
                this.count = res.count
                // console.log(this.count)
                // console.log(this.flowTypeListGet)
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getFlowType()
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单模块
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                分类管理页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 EditForm.vue
    <template>
        <div>
            <a-modal
            title="Please write now."
            :visible="visible"
            @ok="handleOk"
            @cancel="handleCancel"
            >
            <!-- @ok控制按钮ok -->
            <!-- @cancel控制按钮cancel -->
                <p v-if="flowTypeList.id">Name:
                    <a-input 
                    style="400px;float:right" 
                    placeholder="zh_rname"
                    v-model="flowTypeList.name"
                    disabled="disabled"
                    ></a-input>                
                </p>
                <p v-else>Name:
                    <a-input 
                    style="390px;float:right" 
                    placeholder="name" 
                    v-model="flowTypeList.name"
                    ></a-input>
                </p>
                <br>
                <p>Description:
                    <a-input style="380px;float:right" placeholder="Description" v-model="flowTypeList.description"></a-input>
                </p>
            </a-modal>
    
        </div>
    </template>
    
    <script>
    export default {
        props:['visible', 'flowTypeList'],
        data() {
            return {
            }
        },
        methods: {
            handleOk(e) {
                this.$emit('add')
                // add方法的调用一定要在关闭弹窗上面,否则方法不执行完毕没有办法关闭弹窗
                // 调用父组件中 add 方法            
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
    
            },
            handleCancel(e) {
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
            },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 Search.vue
    <template>
        <div>
            <a-input-search placeholder="Input the flowtypename that you want to search for..." enter-button @search="onSearch" style="float:right;400px" v-model="searchList.name"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchList'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
                this.$emit('find')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.5 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="flowTypeListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="delFlowType(text,tags,i)">删除</a-button>
          <a-button @click="updateFlowType(text,tags,i)">修改</a-button>
        </p>
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: 'Name',
        dataIndex: 'name',
        key: 'name',
        scopedSlots: { customRender: 'name' },
         80,
      },
    
        {
        title: 'Description',
        dataIndex: 'description',
        key: 'description',
         100,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    ]
    
    import { delete_flowtype } from '@/http/apis'
    export default {
      props:[ 'flowTypeListGet', 'flowTypeList'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getFlowType')
            // 调用父组件中的获取用户列表的方法
        },
        delFlowType(text,tags,i){
          // 定义变量 isDel来控制 confirm,isDel==true执行的就是对话框的 ok,isDel==false执行的就是对话框的 false
            const isDel = confirm('你确定要删除')
            if(isDel==true){
              delete_flowtype(tags.id).then(
              res=>{
                // 删除回调地址是  http://192.168.56.100:1594/id/
                this.get()
                alert('删除成功啦~')
              })
            }else{
                alert('有需要再叫我哈~')
            }
                 
        },
        updateFlowType(text,tags,i){
          this.flowTypeList.id = tags.id
          this.flowTypeList.name = tags.name
          this.flowTypeList.description = tags.description     
          this.$emit('add')
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.4 flowconf-manage

    • 工单模板组件
    • 只允许超级有用户访问
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <BreadCrumb style="float:left"></BreadCrumb>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <a-button  type="danger" ghost style="float:left;margin-left:20px;margin-top:16px;color:pink;border-color:pink;font-size:16px" @click="addNew">
                    AddFlowConf
                    </a-button>
                    <EditForm
                        :visible.sync="visible"
                        :flowConfList='flowConfList'
                        :flowTypeList='flowTypeList'
                        @add="add"
                    >
                    <!-- .sync控制组件是否显示 -->
                    </EditForm>
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchList="searchList"
                      @find="find"
                      @getFlowConf="getFlowConf"
                    >
                    </Search>
                    
                </div>
                    <TableList
                      :flowConfListGet="flowConfListGet"
                      :flowConfList="flowConfList"
                      
                      @getFlowConf="getFlowConf"
                      @add="add"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"   
                      style="margin-top:20px"           
                    ></Pagination>
                    <p></p>
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import Search from "./components/Search";
    import EditForm from "./components/EditForm";
    import Pagination from "./components/Pagination"
    
    import { add_flowconf, search_for_flowconf, get_flowconflist, update_flowconf } from '@/http/apis';
    import { delete_flowconf, get_flowtypelist_new } from '../../http/apis';
    export default {
        components:{
            BreadCrumb,
            TableList,
            Search,
            EditForm,
            Pagination
        },
        data() {
            return {
                visible:false,
                flowConfList: {
                  'id':'',
                  'name': '',
                  'customfield':'',
                  'flowtype':'',
                  'description':''
                },
                flowTypeList:[],
                flowConfListGet:[],
                searchList:{
                    'name':'',
                    'page':1,
                    'page_size':4,
                    
                },
                updateFlowConfList:[],
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0,
    
    
            }
        },
        methods: {
            addNew(){
              this.visible = true
              this.flowConfList = {
                  'id':'',
                  'name': '',
                  'customfield':'',
                  'flowtype':1,
                  'description':''
                }
              // 用于控制组件显示
            },
            add(){
              if(this.flowConfList.id){            
                this.visible = true  
                update_flowconf(this.flowConfList).then(res=>{
                  // alert('修改成功')
                  this.getFlowConf()
                })
    
              }else{
                // 添加用户,子组件中编辑的值实际上是写在父组件上面的
                add_flowconf(this.flowConfList).then(res=>{
                  console.log(res)
                  alert('添加新用户成功')
                  this.getFlowConf()
                  
              })   
                this.visible=false       
              }
            },
            find(){
              // 根据用户名查找用户信息
              search_for_flowconf(this.searchList).then(res=>{
                  this.getFlowConf()
                  // 数据解耦性!!!查询和查询某个其实可以调用同一个接口!
                  // 查询所有:http://192.168.56.100:1594/?page=1&zh_name=
                  // 查询某个:http://192.168.56.100:1594/?page=1&zh_name=
                
              })
            },
            getFlowConf(){
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_flowconflist(this.searchList).then(res=>{
                this.flowConfListGet = res.results
                this.count = res.count
                // console.log(this.count)
                // console.log(this.flowConfListGet)
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getFlowConf()
            },
            // 获取分类
            getFlowType(){
              get_flowtypelist_new().then(
                res=>{
                this.flowTypeList = res
                console.log('11111',this.flowTypeList)              
                }
    
              )
            }
        },
        created() {
          this.getFlowType()
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单模块
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单模板页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 EditForm.vue
    <template>
        <div>
            <a-modal
            title="Please write now."
            :visible="visible"
            @ok="handleOk"
            @cancel="handleCancel"
            >
            <!-- @ok控制按钮ok -->
            <!-- @cancel控制按钮cancel -->
                <p v-if="flowConfList.id">Name:
                    <a-input 
                    style="400px;float:right" 
                    placeholder="name"
                    v-model="flowConfList.name"
                    disabled="disabled"
                    ></a-input>                
                </p>
                <p v-else>Name:
                    <a-input 
                    style="420px;float:right" 
                    placeholder="name" 
                    v-model="flowConfList.name"
                    ></a-input>
                </p>
                <br>
                <p style="text-align:left">Customfield:<br>
                    <a-textarea style="470px;height:150px" placeholder="Write your customfields..." v-model="flowConfList.customfield"></a-textarea>
                </p>
                <br>FlowType:
                    <a-select        
                        style=" 400px; float:right"
                        @change="handleChange"
                        v-model="flowConfList.flowtype"
                    >
                        <a-select-option v-for="i in flowTypeList" :key="i.id" :value='i.id'>
                        {{ i.name }}
                        </a-select-option>
                    </a-select>
                </p>            
                <br>
                <p>Description:
                    <a-input style="380px;float:right" placeholder="Description" v-model="flowConfList.description"></a-input>
                </p>
            </a-modal>
    
        </div>
    </template>
    
    <script>
    export default {
        props:['visible', 'flowConfList', 'flowTypeList'],
        data() {
            return {
            }
        },
        methods: {
            handleOk(e) {
                this.$emit('add')
                // add方法的调用一定要在关闭弹窗上面,否则方法不执行完毕没有办法关闭弹窗
                // 调用父组件中 add 方法            
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
    
            },
            handleCancel(e) {
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
            },
            handleChange(value) {
                // console.log(`selected ${value.key}`);
                this.flowConfList.flowtype = value
                console.log('111111',this.flowConfList.flowtype)
                // 输出类型为 { key: 2,label: '财务工单' }
            },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 Search.vue
    <template>
        <div>
            <a-input-search placeholder="Input the flowconfname that you want to search for..." enter-button @search="onSearch" style="float:right;400px" v-model="searchList.name"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchList'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
                this.$emit('find')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.5 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="flowConfListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="flowtype_name" slot-scope="flowtype_name">
          <a-tag
            color="pink"
          >
            {{ flowtype_name }}
          </a-tag>
        </p>
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="delFlowConf(text,tags,i)">删除</a-button>
          <a-button @click="updateFlowConf(text,tags,i)">修改</a-button>
          <a-button @click="jump(text,tags,i)">配置审批流</a-button>
        </p>
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: 'Name',
        dataIndex: 'name',
        key: 'name',
        scopedSlots: { customRender: 'name' },
         80,
      },
      {
        title: 'Customfield',
        dataIndex: '',
        key: 'customfield',
        scopedSlots: { customRender: 'customfield' },
         60,    
      },
        {
        title: 'FlowType',
        dataIndex: 'flowtype_name',
        key: 'flowtype_name',
         50,
        scopedSlots: { customRender: 'flowtype_name' },
      },  
        {
        title: 'Description',
        dataIndex: 'description',
        key: 'description',
         150,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    ]
    
    import { delete_flowconf } from '@/http/apis'
    export default {
      props:[ 'flowConfListGet', 'flowConfList'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getFlowConf')
            // 调用父组件中的获取用户列表的方法
        },
        delFlowConf(text,tags,i){
          // 定义变量 isDel来控制 confirm,isDel==true执行的就是对话框的 ok,isDel==false执行的就是对话框的 false
            const isDel = confirm('你确定要删除')
            if(isDel==true){
              delete_flowconf(tags.id).then(
              res=>{
                // 删除回调地址是  http://192.168.56.100:1594/id/
                this.get()
                alert('删除成功啦~')
              })
            }else{
                alert('有需要再叫我哈~')
            }
                 
        },
        updateFlowConf(text,tags,i){
          this.flowConfList.id = tags.id
          this.flowConfList.name = tags.name
          this.flowConfList.flowtype = tags.flowtype
          this.flowConfList.customfield = tags.customfield
          this.flowConfList.description = tags.description     
          this.$emit('add')
          console.log('tags',tags)
        },
        // 跳转配置审批流
        jump(text,tags,i){
          this.$router.push({
            'path':'approveconf',
            // 不写query,写params会报错啊
            'query':{
              'id': tags.id,
              'name': tags.name
            }
          })
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.5 approveconf-manage

    • 配置审批流组件
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <BreadCrumb style="float:left"></BreadCrumb>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <a-button  type="danger" ghost style="float:left;margin-left:20px;margin-top:16px;color:pink;border-color:pink;font-size:16px" @click="addNew">
                    AddApproveConf
                    </a-button>
                    <EditForm
                        :visible.sync="visible"
                        :approveConfList='approveConfList'
                        @add="add"
                    >
                    <!-- .sync控制组件是否显示 -->
                    </EditForm>
                    
                </div>
                    <TableList
                      :approveConfListGet="approveConfListGet"
                      :approveConfList="approveConfList"
                      
                      @getApproveConf="getApproveConf"
                      @add="add"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"   
                      style="margin-top:20px"           
                    ></Pagination>
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import EditForm from "./components/EditForm";
    import Pagination from "./components/Pagination"
    
    import { add_approveconf, search_for_approveconf, get_approveconflist, update_approveconf } from '@/http/apis';
    import { delete_approveconf } from '../../http/apis';
    export default {
        components:{
            BreadCrumb,
            TableList,
            EditForm,
            Pagination
        },
        data() {
            return {
                visible:false,
                approveConfList: {
                  'id':'',
                  'approvetype':'',
                  'approve_type_id':'',
                  'sequence':'',
                  'flowconf':'',
                  'flowconf_name':''
                },
                approveConfListGet:[],
                searchList:{
                    'flowconf':'',
                    'page':1,
                    'page_size':4,
                    
                },
                updateApproveConfList:[],
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0,
                // 获取跳转id
                id:this.$route.query.id,
                flowconf_name: this.$route.query.name
    
    
            }
        },
        methods: {
            addNew(){
              this.visible = true
              this.approveConfList = {
                  'id':'',
                  'approvetype':'',
                  'approve_type_id':'',
                  'sequence':'',
                  'flowconf':this.id,
                  'flowconf_name':this.flowconf_name
                }
              // 用于控制组件显示
            },
            add(){
              if(this.approveConfList.id){            
                this.visible = true  
                update_approveconf(this.approveConfList).then(res=>{
                  // alert('修改成功')
                  this.getApproveConf()
                })
    
              }else{
                // 添加用户,子组件中编辑的值实际上是写在父组件上面的
                add_approveconf(this.approveConfList).then(res=>{
                  console.log(res)
                  alert('添加新用户成功')
                  this.getApproveConf()
                  
              })   
                this.visible=false       
              }
            },
            getApproveConf(){
              this.searchList.page = this.current
              this.searchList.flowconf = this.id
              // 获取用户信息列表,父组件传递给子组件
              get_approveconflist(this.searchList).then(res=>{
                this.approveConfListGet = res.results
                this.count = res.count
                // console.log(this.count)
                // console.log(this.flowConfListGet)
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getApproveConf()
            },
        },
        created() {
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单模块
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                配置审批流页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 EditForm.vue
    <template>
        <div>
            <a-modal
            title="Please write now."
            :visible="visible"
            @ok="handleOk"
            @cancel="handleCancel"
            >
            <!-- @ok控制按钮ok -->
            <!-- @cancel控制按钮cancel -->
                <p>FlowConf:
                    <a-input 
                    style="400px;float:right" 
                    v-model="approveConfList.flowconf_name"
                    disabled="disabled"
                    ></a-input>                
                </p>         
                <br>
                <p>Sequence:
                    <a-input style="380px;float:right" placeholder="Sequence" v-model="approveConfList.sequence"></a-input>
                </p>
                <br>
                <p>
                    审批类型:
                    <a-select
                        style=" 180px"
                        @change="handleChangeRole"
                        v-model="approveConfList.approvetype"
                    >
                        <a-select-option v-for="select in selectList" :key="select.id" :value="select.id">
                        {{ select.name }}
                        </a-select-option>
                    </a-select>
                </p>
                <br>
                <p v-if="approveConfList.approvetype=='2'">审批人员:
                    <a-select
                        style=" 120px"
                        @change="handleChangeUser"
                        v-model="approveConfList.approve_type_id"
                    >
                        <a-select-option v-for="user in userList" :key="user.id" :value="user.id" >
                            {{user.username}}
                        </a-select-option>
                    </a-select>
                </p>
                <p v-else>审批人员:
                    <a-select
                        style=" 120px"
                        @change="handleChangeRole"
                        v-model="approveConfList.approve_type_id"
                    >
                        <a-select-option :value="role.id" v-for="role in roleList" :key="role.id">
                        {{ role.zh_name }}
                        </a-select-option>
                    </a-select>
                </p>
            </a-modal>
    
        </div>
    </template>
    
    <script>
    import { get_userlist_new, get_rolelist_new } from '@/http/apis'
    import { get_rolelist } from '../../../http/apis'
    export default {
        props:['visible', 'approveConfList'],
        data() {
            return {
                userList:[],
                roleList:[],
                selectList:[
                    { 'id':1, 'name':'角色组审批'},
                    { 'id':2, 'name':'指定人员审批'}
                ]
            }
        },
        methods: {
            handleOk(e) {
                this.$emit('add')
                // add方法的调用一定要在关闭弹窗上面,否则方法不执行完毕没有办法关闭弹窗
                // 调用父组件中 add 方法            
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
    
            },
            handleCancel(e) {
                this.$emit('update:visible', false)
                // 把 visible 的值更新为 false,控制组件不显示
            },
             handleChangeUser(value) {
                console.log(value);
            },
             handleChangeRole(value) {
                console.log(value); // { key: "lucy", label: "Lucy (101)" }
            },
            // 获取用户信息列表
            get_user(){
                get_userlist_new().then(res=>{
                    this.userList=res
                    console.log(this.userList)
                })
            },
            // 获取角色信息列表
            get_role(){
                get_rolelist_new().then(res=>{
                    this.roleList=res
                    console.log(this.roleList)
                })
            }
        },
        created() {
            this.get_user()
            this.get_role()
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="approveConfListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="flowtype_name" slot-scope="flowtype_name">
          <a-tag
            color="pink"
          >
            {{ flowtype_name }}
          </a-tag>
        </p>
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="delApproveConf(text,tags,i)">删除</a-button>
          <a-button @click="updateApproveConf(text,tags,i)">修改</a-button>
         
        </p>
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: 'FlowConfName',
        dataIndex: 'flowconf_name',
        key: 'flowconf_name',
        scopedSlots: { customRender: 'flowconf_name' },
         80,
      },
      {
        title: 'ApproveType',
        dataIndex: 'approvetype_name',
        key: 'approvetype_name',
        scopedSlots: { customRender: 'approvetype_name' },
         100,    
      },
        {
        title: 'ApprovePerson',
        dataIndex: 'approve_type_id_name',
        key: 'approve_type_id_name',
         100,
        scopedSlots: { customRender: 'approve_type_id_name' },
      },  
        {
        title: 'Sequence',
        dataIndex: 'sequence',
        key: 'sequence',
         100,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    ]
    
    import { delete_approveconf } from '@/http/apis'
    export default {
      props:[ 'approveConfListGet', 'approveConfList'],
      data() {
        return {
          columns,
    
        }
      },
      methods:{
        get(){
            this.$emit('getApproveConf')
            // 调用父组件中的获取用户列表的方法
        },
        delApproveConf(text,tags,i){
          // 定义变量 isDel来控制 confirm,isDel==true执行的就是对话框的 ok,isDel==false执行的就是对话框的 false
            const isDel = confirm('你确定要删除')
            if(isDel==true){
              delete_approveconf(tags.id).then(
              res=>{
                // 删除回调地址是  http://192.168.56.100:1594/id/
                this.get()
                alert('删除成功啦~')
              })
            }else{
                alert('有需要再叫我哈~')
            }
                 
        },
        updateApproveConf(text,tags,i){
          this.approveConfList.id = tags.id
          this.approveConfList.approvetype_name = tags.approvetype_name
          this.approveConfList.approvetype = tags.approvetype
          this.approveConfList.approve_type_id = tags.approve_type_id
          this.approveConfList.approve_type_id_name = tags.approve_type_id_name
          this.approveConfList.sequence = tags.sequence
          this.approveConfList.flowconf = tags.flowconf 
          this.approveConfList.flowconf_name = tags.flowconf_name      
          this.$emit('add')
          console.log('tags',tags)
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.6 workorder-manage

    • 新建工单,提供模板选择工单组件(让用户选择需要的工单模板)
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <p></p>
              <BreadCrumb style="float:left"></BreadCrumb>
              <p></p>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchES="searchES"
                      @search="search"
                    >
                    </Search>
                    
                </div>
                    <TableList
                      :workerOrderListGet="workerOrderListGet"
                      @getWorkerOrder="getWorkerOrder"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"
                      style="margin-top:20px;"              
                    ></Pagination>
                    <p></p>
                    
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import Search from "./components/Search";
    import Pagination from "./components/Pagination"
    
    import { get_workerorder, search_workerorder } from '@/http/apis';
    
    export default {
        components:{
            BreadCrumb,
            TableList,
            Search,
            Pagination
        },
        data() {
            return {
                visible:false,
                workerOrderListGet:[],
                searchList:{
                    'create_user':'',
                    'page':1,
                    'page_size':4,
                    
                },
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0,
                            // ES查询
                searchES:{
                    'page':1,
                    'page_size':4, 
                    'q':''    
                }
    
            }
        },
        methods: {
            find(){
              // 根据用户名查找用户信息
              get_workerorder(this.searchList).then(res=>{
                  this.getWorkerOrder()
                  // 数据解耦性!!!查询和查询某个其实可以调用同一个接口!
                  // 查询所有:http://192.168.56.100:1594/?page=1&zh_name=
                  // 查询某个:http://192.168.56.100:1594/?page=1&zh_name=
                
              })
            },
            getWorkerOrder(){
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_workerorder(this.searchList).then(res=>{
                this.workerOrderListGet = res.results
                this.count = res.count
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getWorkerOrder()
            },
            search(){
              search_workerorder(this.searchES).then(
                res =>{
                  this.workerOrderListGet = res.results
                  this.count = res.count
                }
              )
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单管理
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                实例工单页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Search.vue
    <template>
        <div>
            <!-- 日期格式请按照:2020 - 12 - 3 -->
            <a-input-search placeholder="Input the rolename that you want to search for..." enter-button @search="onSearch" style="float:right;400px" v-model="searchES.q"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchES'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
                this.$emit('search')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="workerOrderListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="jumpChild(text,tags,i)">查看详情</a-button>
          
        </p>
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: '工单名称',
        dataIndex: 'flowconf_name',
        key: 'flowconf_name',
        scopedSlots: { customRender: 'flowconf_name' },
         80,
      },
      {
        title: '工单状态',
        dataIndex: 'order_status_name',
        key: 'order_status_name',
         100,
      },
        {
        title: '创建者',
        dataIndex: 'create_user_name',
        key: 'create_user_name',
         100,
      },
      {
        title: '创建日期',
        dataIndex: 'create_time',
        key: 'create_time',
         100,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    ]
    
    
    export default {
      props:[ 'workerOrderListGet'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getWorkerOrder')
            // 调用父组件中的获取用户列表的方法
        },
        jumpChild(text,tags,i){
          console.log('tags',tags)
          // 查看详情
          this.$router.push({
            path:'childconfform',
            query:{
              'flowconf':tags.flowconf,
              'id':tags.id
            }
          })
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.7 flowconfform-manage

    • 动态生成工单组件
    1 index.vue
    <template>
        <div>
            <div>
                 <a-row>
                <a-col :span="16" style="height:500px">
                    <CreateForm
                       :msg="flowConf"
                       @addWorkOrder="addWorkOrder" 
                       
                    ></CreateForm>
                </a-col>
                <a-col :span="8" style="height:500px;text-align:left;font-size:20px;color:pink">
                    <br><br><br><br><br><br><br><p>{{flowConf.description}}</p>
                </a-col>
                </a-row>
                <a-row>
                <a-col :span="24" style="height:160px">
                    <Check
                        :flowConf="flowConf"
                        
                    ></Check>
                </a-col>
                </a-row>
            </div>
        </div>
    </template>
    
    <script>
    import Check from '@/views/flowconfform-manage/components/Check'
    import CreateForm from '@/views/flowconfform-manage/components/CreateForm'
    import { add_workorder } from '@/http/apis'
    export default {
        components:{
            Check,
            CreateForm
        },
        data() {
            return {
                flowConf:this.$route.query.flowconf,
                // token:localStorage.getItem('token')
            }
        },
        methods: {
            // json转换
            changeJson(){
                const textJson = this.flowConf.customfield
                console.log('自定义字段', textJson)
                const textJsonChange = JSON.parse(textJson)
                console.log('转换后自定义字段', textJsonChange)
                this.flowConf.customfield = textJsonChange
                console.log(this.flowConf)
            },
            // 添加
            addWorkOrder(){
                let data = {
                    // 'token':this.token,
                    'name':this.flowConf.name,
                    'form':this.flowConf.customfield.field_list,                
                }
                console.log('data',data)
                add_workorder(data).then(res=>{
                    console.log(res.msg)
                    if(res.code==200){
                        alert('实例化工单完成')
                    }
                })
            }
        },
        created() {
        this.changeJson()
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2 components
    2.1 Check.vue
    <template>
        <div>
            <p style="float:left;margin-top:20px;font-size:20px">审批流程&ensp;<a-icon type="heart" theme="twoTone" two-tone-color="#eb2f96" /></p>
            <div v-for="check in checkList" :key="check.id" style="float:left;margin-left:200px;margin-top:50px">
                <p>
                    <a-icon type="user" style="font-size:40px;color:pink"/>
                </p>
                <p>
                {{check.approvetype_name}}:{{check.approve_type_id_name}}&ensp;<a-icon type="forward" theme="filled" style="font-size:20px;color:pink"/>
                </p>
            </div>
    
        </div>
    </template>
    
    <script>
    import { get_approveconflist_new } from '@/http/apis'
    export default {
        props:[ "flowConf" ],
        data() {
            return {
                checkList:[]
            }
        },
        methods: {
            getApproveConf(){
                get_approveconflist_new({'flowconf':this.flowConf.id}).then(res=>{
                    // console.log(res.results)
                    this.checkList = res.results
                })
            }
    
        },
        created() {
            // console.log('AAA', this.flowConf)
            this.getApproveConf()
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 CreateForm.vue
    <template>
        <div>
             <a-form-model :label-col="labelCol" :wrapper-col="wrapperCol">
                <a-form-model-item v-for="(select,item) in msg.customfield.field_list" :key="item">
                
                <p v-if="select.field_type==='input'" style="text-align:left">{{select.verbos_name}}:&emsp;
                    <a-input v-model="select.value" style="200px" @change="giveValue"/>
                </p>
                
                <p v-show="select.field_type==='select'" style="text-align:left">
                    {{select.verbos_name}}:&emsp;
                    <a-select v-model="select.value" placeholder="please select your option" style="200px" @change="giveValue">
                        <a-select-option v-for="s in select.field_datasource" :key="s.value" :value="s.value">
                        {{ s.label }}
                        </a-select-option>
                    </a-select>
                </p>
    
                <p v-show="select.field_type=='textarea'" style="text-align:left">
                    {{select.verbos_name}}:
                    <a-input v-model="select.value" type="textarea" style="700px;height:150px" @change="giveValue"/>
                </p>
                </a-form-model-item>
                <a-form-model-item :wrapper-col="{ span: 14, offset: 4 }">
                    <a-button type="primary" @click="onSubmit">
                    提交
                    </a-button>
                    <a-button style="margin-left: 10px;">
                    取消
                    </a-button>
                </a-form-model-item>
            </a-form-model>
        </div>
    </template>
    <script>
    export default {
      props:[ 'msg' ],
      data() {
        return {  
          labelCol: { span: 4 },
          wrapperCol: { span: 14 },
        };
      },
      methods: {
        // 实例化工单
        onSubmit() {
          console.log('submit!', this.msg);
          this.$emit('addWorkOrder')
        },  
        // giveValue(){
        //     for(var i in this.msg.customfield.form){
        //     const val = this.getInputValue(i);
        //     this.msg.customfield.form[i] = val;
        //   }       
        // },
        // getInputValue(key){
        //     for(var i=0;i<this.msg.customfield.field_list.length;i=i+1){
        //         const fileld_dic = this.msg.customfield.field_list[i];
        //         const k1 = fileld_dic['name'];
        //         if(key == k1){
        //         return fileld_dic['value']
        //     }
        //   }
        //   return ''
        // }
        giveValue(){
            const form_list = Object.keys(this.msg.customfield.form) 
            // 可以获取到所有的key
            for(var i=0;i<this.msg.customfield.field_list.length;i++){
                form_list.forEach(item => {
                    if(this.msg.customfield.field_list[i].name==item){
                        this.msg.customfield.form[item]=this.msg.customfield.field_list[i].value
                    }
                });
            }
            return this.msg
        }
      },
    
    };
    </script>
    
    <style scoped>
    </style>
    

    1.4.8 workerorder-manage

    • 主工单组件
    • 超级管理员身份可以查看全部工单,其他普通用户只能看到自己创建的工单
    • 采用了ES,只能根据状态进行查询(因为主工单和子工单时外键关联的关系,这种索引名一样的,建立索引会出现先后查找混乱的现象)
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <p></p>
              <BreadCrumb style="float:left"></BreadCrumb>
              <p></p>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
                <div style="margin-bottom:80px">
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchES="searchES"
                      @search="search"
                    >
                    </Search>
                    
                </div>
                    <TableList
                      :workerOrderListGet="workerOrderListGet"
                      @getWorkerOrder="getWorkerOrder"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"
                      style="margin-top:20px;"              
                    ></Pagination>
                    <p></p>
                    
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import TableList from "./components/TableList";
    import Search from "./components/Search";
    import Pagination from "./components/Pagination"
    
    import { get_workerorder, search_workerorder } from '@/http/apis';
    
    export default {
        components:{
            BreadCrumb,
            TableList,
            Search,
            Pagination
        },
        data() {
            return {
                visible:false,
                workerOrderListGet:[],
                searchList:{
                    'create_user':'',
                    'page':1,
                    'page_size':4,
                    
                },
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0,
                            // ES查询
                searchES:{
                    'page':1,
                    'page_size':4, 
                    'q':''    
                }
    
            }
        },
        methods: {
            find(){
              // 根据用户名查找用户信息
              get_workerorder(this.searchList).then(res=>{
                  this.getWorkerOrder()
                  // 数据解耦性!!!查询和查询某个其实可以调用同一个接口!
                  // 查询所有:http://192.168.56.100:1594/?page=1&zh_name=
                  // 查询某个:http://192.168.56.100:1594/?page=1&zh_name=
                
              })
            },
            getWorkerOrder(){
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_workerorder(this.searchList).then(res=>{
                this.workerOrderListGet = res.results
                this.count = res.count
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              this.getWorkerOrder()
            },
            search(){
              search_workerorder(this.searchES).then(
                res =>{
                  this.workerOrderListGet = res.results
                  this.count = res.count
                }
              )
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单管理
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                实例工单页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Search.vue
    <template>
        <div>
            <!-- 日期格式请按照:2020 - 12 - 3 -->
            <a-input-search placeholder="Input the rolename that you want to search for..." enter-button @search="onSearch" style="float:right;400px" v-model="searchES.q"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchES'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
                this.$emit('search')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 TableList.vue
    <template>
      <a-table 
        :columns="columns" 
        :data-source="workerOrderListGet" 
        :rowKey="(record,index)=>{return index}"
        :pagination= 'false'
      >
      <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
        <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
        <p slot="tags" slot-scope="text,tags,i">
          <!-- 加入操作的按钮! -->
          <a-button @click="jumpChild(text,tags,i)">查看详情</a-button>
          
        </p>
      </a-table>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
      },
      {
        title: '工单名称',
        dataIndex: 'flowconf_name',
        key: 'flowconf_name',
        scopedSlots: { customRender: 'flowconf_name' },
         80,
      },
      {
        title: '工单状态',
        dataIndex: 'order_status_name',
        key: 'order_status_name',
         100,
      },
        {
        title: '创建者',
        dataIndex: 'create_user_name',
        key: 'create_user_name',
         100,
      },
      {
        title: '创建日期',
        dataIndex: 'create_time',
        key: 'create_time',
         100,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
    
      }
    ]
    
    
    export default {
      props:[ 'workerOrderListGet'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getWorkerOrder')
            // 调用父组件中的获取用户列表的方法
        },
        jumpChild(text,tags,i){
          console.log('tags',tags)
          // 查看详情
          this.$router.push({
            path:'childconfform',
            query:{
              'flowconf':tags.flowconf,
              'id':tags.id
            }
          })
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.9 suborder-manage

    • 子工单组件
    • 超级管理员身份可以看到全部工单,其他普通用户只能看到自己能审批的工单(包括不在当前节点的也能看见)
    • 采用了ES,可以根据显示在 table 中的全部字段进行查询
    1 index.vue
    <template>
    <div>
      <div id="components-layout-demo-basic">
         <a-layout>
            <a-layout-header>
              <p></p>
              <BreadCrumb style="float:left"></BreadCrumb>
              <p></p>
    
            </a-layout-header>
            <a-layout>
                <a-layout-content>
    
                  <div style="margin-bottom:80px">
                    <Search 
                      style="margin-bottom:-20px;margin-top:10px" 
                      :searchES="searchES"
                      @search="search"
                    >
                    </Search>    
                </div>
    
                    <TableList
                      :subOrderListGet="subOrderListGet"
                      @getSubOrder="getSubOrder"
                      :mainorder="mainorder"
                    >
                    </TableList>
    
                    <Pagination
                      @getPage="getPage" 
                      :count="count"
                      style="margin-top:20px;"              
                    ></Pagination>
                    <p></p>
                    
                </a-layout-content>
            </a-layout>
         </a-layout>
      </div>
    </div>
    </template>
    
    <script>
    import BreadCrumb from "./components/BreadCrumb";
    import Pagination from "./components/Pagination";
    import Search from "./components/Search";
    import TableList from "./components/TableList";
    import { get_suborder, search_suborder } from '@/http/apis';
    
    export default {
        components:{
            BreadCrumb,
            TableList,
            Pagination,
            Search,
        },
        data() {
            return {
                mainorder:this.$route.query.id,
                subOrderListGet:[],
                searchList:{
                    'page':1,
                    'page_size':4,               
                },
                // 当前页码
                current:1,
                // 总共的数据多少条
                count:0,
                // ES查询
                searchES:{
                    'page':1,
                    'page_size':4, 
                    'q':''    
                }
    
            }
        },
        methods: {
            getSubOrder(){
              
              this.searchList.page = this.current
              // 获取用户信息列表,父组件传递给子组件
              get_suborder(this.searchList).then(res=>{
                console.log(res)
                this.subOrderListGet = res.results
                this.count = res.count
                
              })
            },
            // 获取页码
            getPage(currentChild){
              // 获取到的currentChild是子组件传递过来是第几页
              this.current = currentChild
              console.log(this.current)
              if(this.subOrderListGet[0].type){
                this.search()
              }else{
                this.getSubOrder()
              }
              
            },
            search(){
              this.searchES['page'] = this.current
              search_suborder(this.searchES).then(
                res =>{
                  console.log('res',res)
                  this.subOrderListGet = res.results
                  this.count = res.count
                  console.log('this.subOrderListGet',this.subOrderListGet)
                }
              )
            }
        },
        created() {
          this.getSubOrder()
        }
    }
    </script>
    
    <style scoped>
    #components-layout-demo-basic {
      text-align: center;
    }
    #components-layout-demo-basic .ant-layout-header,
    #components-layout-demo-basic .ant-layout-footer {
      background: white;
      color: #fff;
    }
    #components-layout-demo-basic .ant-layout-footer {
      line-height: 1.5;
    }
    #components-layout-demo-basic .ant-layout-content {
      background: white;
      color: #fff;
      min-height: 120px;
      line-height: 120px;
    }
    #components-layout-demo-basic > .ant-layout {
      margin-bottom: 48px;
    }
    #components-layout-demo-basic > .ant-layout:last-child {
      margin: 0;
    }
    </style>
    
    2 components
    2.1 BreadCrumb.vue
    <template>
        <div>
            <a-breadcrumb>
                <a-breadcrumb-item href="">
                <a-icon type="home" />
                </a-breadcrumb-item>
    
                <a-breadcrumb-item href="">
                <a-icon type="user" />
                <span>首页</span>
    
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                工单管理
                </a-breadcrumb-item>
                <a-breadcrumb-item>
                子工单页面
                </a-breadcrumb-item>
            </a-breadcrumb>
        </div>
    </template>
    
    <script>
    export default {
        name:"BreadCrumb",
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.2 Search.vue
    <template>
        <div>
            <a-input-search placeholder="Input the rolename that you want to search for..." enter-button @search="onSearch" style="float:right;400px" v-model="searchES.q"/>
        </div>
    </template>
    
    <script>
    export default {
        props:['searchES'],
        data() {
            return {
    
            } 
        },
        methods: {
            onSearch(){
    
                this.$emit('search')
                // 调用父组件中的find方法
            }
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.3 Pagination.vue
    <template>
      <div>
        <a-pagination
          show-quick-jumper
          :default-current="2"
          :pageSize = '4'
          :total="count"
          show-less-items
          @change="onChange"
          v-model="current"
    
        />
      </div>
    </template>
    
    <script>
    export default {
        props:[ 'count' ],
        data() {
            return {
                current:1
            }
        },
        methods: {
            
            onChange() {
                this.$emit('getPage', this.current)
                // this.$emit('getPage')
        },
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
    2.4 TableList.vue
    <template>
      <div>
        <a-table 
          :columns="columns" 
          :data-source="subOrderListGet" 
          :rowKey="(record,index)=>{return index}"
          :pagination='false'
        >
        <!-- 带:的都是属性绑定,不可以更换名字,带 : 就是 js 环境 -->
          <!-- 不写:rowKey="(record,index)=>{return index}"浏览器会发出警告 -->
          <p slot="tags" slot-scope="text,tags,i">
            <a-button @click="jump(text,tags,i)">查看工单审批详情</a-button>
          </p>
        </a-table>
      </div>
    </template>
    
    <script>
    const columns = [
        {
        title: 'ID',
        dataIndex: 'id',
        key: 'id',
        // ellipsis: true,
         50,
        scopedSlots: { customRender: 'id' },
      },
      {
        title: '工单名称',
        dataIndex: 'flowconf_name',
        key: 'flowconf_name',
        scopedSlots: { customRender: 'flowconf_name' },
         80,
      },
      {
        title: '工单状态',
        dataIndex: 'action_status_name',
        key: 'action_status_name',
         100,
      },
      {
        title: '审批人',
        dataIndex: 'approve_user_name',
        key: 'approve_user_name',
         100,
      },
      {
        title: '审批角色',
        dataIndex: 'approbe_user_role',
        key: 'approbe_user_role',
         100,
      },
      {
        title:'操作',
        dataIndex: 'tags',
        key : 'tags',
         100,
        scopedSlots : { customRender: 'tags'}
        // scopedSlots: { customRender: 'tags' },一定不能少不然渲染不了html标签
      }
    ]
    
    
    export default {
      props:[ 'subOrderListGet', 'mainorder'],
      data() {
        return {
          columns,
        }
      },
      methods:{
        get(){
            this.$emit('getSubOrder')
            // 调用父组件中的获取用户列表的方法
        },
        jump(text,tags,i){
          this.$router.push({
            path:'childconfform',
            query:{
              'id':tags.mainorder,
              'flowconf':tags.flowconf
            }
          })
        }
      },
      created(){
        this.get()
      }
    };
    </script>
    

    1.4.10 childconfform-manage

    • 子工单审批
    1 index.vue
    <template>
        <div>
          <a-row>
          <a-col :span="10" style="background:rgb(253,234,254);height:700px">
              <br>
            <CreateChildForm
                :form="form"
            >
            </CreateChildForm>
            <br><br><br><br>
            <div style="float:left">
                <PersonRole
                    :approveConfList="approveConfList"
                ></PersonRole>
            </div>
          </a-col>
          <a-col :span="14" style="height:700px">
            <Approval
                :approveConf="approveConfList"
                :mainorder="mainorder"
            ></Approval>
          </a-col>
        </a-row>
        </div>
    </template>
    
    <script>
    import CreateChildForm from './components/CreateChildForm'
    import PersonRole from './components/PersonRole'
    import Approval from './components/Approval'
    import { get_workerorder,get_suborder } from '@/http/apis'
    import { get_approveconflist_new } from '@/http/apis'
    
    export default {
        
        components:{
            CreateChildForm,
            PersonRole,
            Approval
        },
        data() {
            return {
                mainorder:this.$route.query.id,
                form:{},
                flowconf:this.$route.query.flowconf,
                approveConfList:[]
    
            }
        },
        methods: {
            getForm(){
                get_workerorder({'id': this.mainorder}).then(res=>{
                    const data = res[0].parameter         
                    var dic = data.replace(/'/g, '"')
                    this.form = JSON.parse(dic)
    
                    })
                get_approveconflist_new({'flowconf': this.flowconf}).then(res=>{
                        this.approveConfList = res.results
                        console.log('approveConfList', res.results)
                        })
    
            },
            
    
        },
        created() {
            this.getForm()
        }
    }
    </script>
    
    <style scoped>
    </style>
    
    2 components
    2.1 Approval.vue
    <template>
        <div>
            <div style="float:left">
                <a-icon type="smile" theme="twoTone" style="font-size:15px;" />&ensp;审批详情
                <div v-for=" (approve, item) in approveConf" :key="item" style="margin-top:30px">
    
                    <span style="float:left;font-size:16px;">
                        <a-button style="border-radius: 50%;margin-right:8px;background:lightblue;color:white;border:white">Step{{ approve.sequence }}</a-button>
                        Role:{{ approve.approve_type_id_name }}
                        <br>
                        Status:{{ suborderList[item].suborder_status_name }}
                        <br>
                        Advice:
                
                    </span>
                        <span>
                            
                            <a-textarea
                                v-model="value[item]"
                                placeholder="Write your advice..."
                                :auto-size="{ minRows: 3, maxRows: 8 }"
                                style="height:80px;500px;margin-top:30px"
                                v-if="suborderList[item].type=='1'"
                            />
                            <br>
                            <br>
                            <a-button type="link" style="color:palevioletred;font-size:20px" ghost v-if="suborderList[item].type=='1'" @click="choose(value[item],yes,suborderList[item].id)">
                                √通过
                            </a-button>
                            <a-button type="primary" style="margin-left:30px" ghost v-if="suborderList[item].type=='1'" @click="choose(value[item],returnMsg,suborderList[item].id)">
                                退回
                            </a-button>
                            <a-button type="danger" style="margin-left:30px" ghost v-if="suborderList[item].type=='1'" @click="choose(value[item],no,suborderList[item].id)">拒绝</a-button>
                        </span>
    
                </div>
            </div>
        </div>
    </template>
    
    <script>
    import { get_suborder_auth, add_suborder } from '@/http/apis'
    export default {
        props:[ 'approveConf', 'mainorder' ],
        data() {
            return {
                current:1,
                value:[],
                suborderList:[],
                yes:'2',
                no:'3',
                returnMsg:'4'
            }
        },
        methods: {
            onChange(current) {
                console.log('onChange:', current);
                this.current = current;
                },
            getSuborder(){
                get_suborder_auth({'mainorder':this.mainorder}).then(res=>{
                    this.suborderList = res
                    console.log('suborderList', this.suborderList)
    
                })
            },
            choose(decision, action_status, suborder_id){
                let data={
                    'suborder_id':suborder_id,
                    'decision':decision,
                    'action_status':action_status
                }
                console.log('i am data',data)
                add_suborder(data).then(res=>{
                    if(res.code==200){
                        alert('审批成功')
                        this.getSuborder()
                    }else{
                        alert('审批失败')
                    }
                })
            }
        },
        created() {
            this.getSuborder()
        }
    }
    </script>
    
    <style scoped>
    .a-textarea{
        100;
        min-height:50px;
        max-height: 300px;
    }
    </style>
    
    2.2 CreateChildForm.vue
    <template>
        <div>
            <div>
              <p style="float:left"><a-icon type="smile" theme="twoTone" style="font-size:15px"/>&ensp;用户申请</p><br><br><br>
                <table style="500px;height:150px">
                  <tr>
                    <th>标题</th>
                    <th>数据</th>
                  </tr>
                  <tr v-for="(f,item) in form" :key="item">
                    <td>{{ f.verbos_name }}</td>
                    <td>{{ f.value }}</td>
                  </tr>
                </table>
            </div>
    
        </div>
    </template>
    
    <script>
    export default {
        props:['form'],
        data() {
            return {
                
            }
        },
        methods: {
    
            // get_form(){
            //   this.$emit('getForm')
            // }
        },
        created() {
          // this.get_form()
        }
    }
    </script>
    
    <style scoped>
    .table,th,tr,td{
      border: white 3px solid;
    }
    .table{
       300px;
      height: 300px
    }
    </style>
    
    2.3 PersonRole.vue
    <template>
        <div>
            <p style="float:left"><a-icon type="smile" theme="twoTone" style="font-size:15px"/>&ensp;审批步骤</p><br>
            <br>
            <br>
            <div v-for="person in approveConfList" :key="person.id">          
              <span style="margin-top:40px">
                  <h2 style="color:palevioletred"><a-icon type="user"  style="color:lightblue;"/>&ensp;&ensp;{{ person.approve_type_id_name }}</h2>
                  <h3>.</h3>
              </span>
            </div>
    
        </div>
    </template>
    
    <script>
    export default {
        props:[ 'approveConfList' ],
        data() {
            return {
                
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    

    1.5 BaiDu.vue

    • 自动跳转到百度翻译页面
    <template>
        <div>
    
        </div>
    </template>
    
    <script>
    export default {
        data() {
            return {
    
            }
        },
        methods: {
            goBaiDu(){
                window.location.href = 'https://fanyi.baidu.com/?aldtype=16047#auto/zh'
            }
        },
        created() {
            this.goBaiDu()
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    

    1.6 Login.vue

    • 登录页面
    <template>
      <div>
        <div class="d1">
          <div style="margin-top:150px;height:400px;800px;margin-left:400px;background:pink">
            <br>
            <center><h1 style="margin-top:50px;color:white">登&emsp;录</h1></center>
            <br>
    
            <a-form-item label="用户名" v-bind="formlayout" style="color:pink">
    
              <a-input v-model="username" style="400px"/>
        
            </a-form-item>   
            <a-form-item label="密码" v-bind="formlayout" style="color:pink">
              <a-input-password v-model="password" placeholder="input password" @keyup.enter.native.enter="submit"  style="400px"/>
            </a-form-item>
    
            <a-form-item v-bind="buttonlayout">
    
              <a-button type="primary"  @click="submit" style="color:blue;background:white;border:pink;color:pink">登录</a-button>
    
            </a-form-item>
    
          </div>
        </div>
      </div>
    </template>
    
    <script type="text/javascript">
    import { user_login } from '../http/apis';
    
    export default{
    
      data(){
        return{
          username:"",
          password:'',
          //表单样式
          formlayout:{
            //标签
            labelCol:{
              xs:{span:24},
              sm:{span:8}
            },
            //文本框
            wrapperCol:{
              xs:{span:14},
              sm:{span:6}
            }
          },
          //按钮样式
          buttonlayout:{
            //按钮
            wrapperCol:{
              xs:{
                span:24,
                offset:0
              },
              sm:{span:16,offset:8}
            }
          }
        }
    
      },
      //自定义方法
      methods:{
        submit:function(){
          var data={'username':this.username,'password':this.password}
          user_login(data).then(resp => {
            console.log(resp)
            if(resp.token){
              // 如果返还token值,就储存 token username uid
              localStorage.setItem('token',resp.token)
              localStorage.setItem('username',resp.username)
              localStorage.setItem('uid',resp.id)
              this.$router.push('/start')
            }
          }).catch(err=>{
            console.log(err)
            alert('登录失败')
          })
    
        }
      }
    };
    
    
    </script>
    
    <style type="text/css">
    </style>
    

    1.7 StartPage.vue

    • 初始界面
    <template>
        <div>
            <img src="static	mg.png" style="1000px;height:600px">
        </div>
    </template>
    
    <script>
    export default {
        data() {
            return {
    
            }
        },
        methods: {
    
        },
        created() {
    
        }
    }
    </script>
    
    <style scoped>
    
    </style>
    
  • 相关阅读:
    object sender和EventArgs e含义
    将十进制小数转化为二进制小数的方法
    什么是类、对象、方法、属性、类的成员
    asp.net代码中尖括号和百分号的含义
    打开某个AVI文件,explorer.exe遇到问题需要关闭的解决方法
    中国娱乐学习门户负责人吴晓林讲解项目
    系统流程图与业务流程图
    如何去掉Zblog的版权信息(powered by)
    利用教育游戏丰富与深化综合实践活动课程教与学的理论与实践研究 课题
    浅析C# 中object sender与EventArgs e(转)
  • 原文地址:https://www.cnblogs.com/mapel1594184/p/14145905.html
Copyright © 2011-2022 走看看