18. 基于Vue+Element+nodeJs+Express+MySql后台管理系统-前端用户管理页面

18 篇文章 1 订阅
15 篇文章 9 订阅

接下来我们开始编写此系统的用户管理页面,这个页面分为一个大部分两个小部分,即一个主要的用户管理页面,新增用户弹窗和编辑用户弹窗。需要我们创建一个User.vue(主要的用户管理页面),User下的Add.vue(新增用户弹窗)、Edit.vue(编辑用户弹窗)。

一、Add.vue(新增用户弹窗)

1.1 Add.vue 页面html部分:

<template>
  <el-dialog title="新增管理员" :visible.sync="showFlag" custom-class="dialog-small" @close="closeDialog">
    <el-form ref="formData" :model="formData" :rules="formRules" label-width="80px">
      <el-form-item label="账号" prop="name">
        <el-input v-model="formData.name" placeholder="请输入管理员账号"></el-input>
      </el-form-item>
      <el-form-item label="密码" prop="password">
        <el-input v-model="formData.password" placeholder="请输入密码"></el-input>
      </el-form-item>
      <el-form-item label="邮箱" prop="email">
        <el-input v-model="formData.email" placeholder="请输入管理员邮箱"></el-input>
      </el-form-item>
      <el-form-item class="dialog-footer" align="center">
        <el-button type="primary" @click="onSave('formData')">保 存</el-button>
        <el-button @click="onCancel('formData')">取 消</el-button>
      </el-form-item>
    </el-form>
  </el-dialog>
</template>

1.2 Add.vue 页面js部分:

<script>
import { userAdd } from '../../config/interface'
export default {
  data () {
    const validate = (rule, value, callback) => {
      const reg = /^[0-9a-zA-Z]*$/g
      if (!value) {
        callback(new Error('请输入内容'))
      } else if (value.length < 3 || value.length > 6) {
        callback(new Error('内容长度需在 3 到 6 个字符'))
      } else if (!reg.test(value)) {
        callback(new Error('内容需为字母或数字'))
      } else {
        callback()
      }
    }
    return {
      showFlag: false,
      formData: {
        name: null,
        password: null,
        email: null
      },
      formRules: {
        name: [
          { validator: validate, trigger: 'blur' }
        ],
        password: [
          { validator: validate, trigger: 'blur' }
        ],
        email: [
          { type: 'email', message: '请输入正确的邮箱地址', trigger: 'blur' }
        ]
      },
      reqFlag: {
        add: true
      }
    }
  },
  components: {
  },
  created () {
  },
  methods: {
    // 初始化
    init () {
      this.$nextTick(() => {
        this.changeShowFlag()
      })
    },
    changeShowFlag () {
      this.showFlag = !this.showFlag
    },
    // 保存
    onSave (formData) {
      this.$refs[formData].validate((valid) => {
        if (valid) {
          const url = userAdd
          if (this.reqFlag.add) {
            this.reqFlag.add = false
            let params = {
              name: this.formData.name,
              password: this.$md5(this.formData.password),
              email: this.formData.email
            }
            this.$http(url, params)
            .then(res => {
              if (res.code == 1) {
                this.$common.toast('添加成功', 'success', false)
                this.$emit('addCallBack')
                this.onCancel(formData)
              }
              this.reqFlag.add = true
            })
          }
        } else {
          console.log('error submit!!')
          return false
        }
      })
    },
    // 取消
    onCancel (formName) {
      this.changeShowFlag()
      this.$refs[formName].resetFields()
    },
    // 关闭弹出框
    closeDialog () {
      this.$refs['formData'].resetFields()
    }
  }
}
</script>

1.3 Add.vue 页面展示 

二、Edit.vue(新增用户弹窗)

2.1 Edit.vue 页面html部分:

<template>
  <el-dialog title="编辑管理员" :visible.sync="showFlag" custom-class="dialog-small" @close="closeDialog">
    <el-form ref="formData" :model="formData" :rules="formRules" label-width="80px">
      <el-form-item label="账号" prop="name">
        <el-input v-model="formData.name" placeholder="请输入管理员账号"></el-input>
      </el-form-item>
      <el-form-item label="密码" prop="password">
        <el-input v-model="formData.password" placeholder="请输入密码"></el-input>
      </el-form-item>
      <el-form-item label="邮箱" prop="email">
        <el-input v-model="formData.email" placeholder="请输入管理员邮箱"></el-input>
      </el-form-item>
      <el-form-item class="dialog-footer" align="center">
        <el-button type="primary" @click="onSave('formData')">保 存</el-button>
        <el-button @click="onCancel('formData')">取 消</el-button>
      </el-form-item>
    </el-form>
  </el-dialog>
</template>

2.2 Edit.vue 页面js部分:

<script>
import { userDetail, userUpdateInfo } from '../../config/interface'
export default {
  data () {
    const validate = (rule, value, callback) => {
      const reg = /^[0-9a-zA-Z]*$/g
      if (!value) {
        callback(new Error('请输入内容'))
      } else if (value.length < 3 || value.length > 6) {
        callback(new Error('内容长度需在 3 到 6 个字符'))
      } else if (!reg.test(value)) {
        callback(new Error('内容需为字母或数字'))
      } else {
        callback()
      }
    }
    return {
      showFlag: false,
      formData: {
        name: null,
        password: null,
        email: null
      },
      formRules: {
        name: [
          { validator: validate, trigger: 'blur' }
        ],
        password: [
          { validator: validate, trigger: 'blur' }
        ],
        email: [
          { type: 'email', message: '请输入正确的邮箱地址', trigger: 'blur' }
        ]
      },
      reqFlag: {
        edit: true
      }
    }
  },
  components: {
  },
  created () {
  },
  methods: {
    // 初始化
    init (id) {
      this.$nextTick(() => {
        this.id = id
        this.getUserDetail()
        console.log('this.id==' + this.id)
        this.changeShowFlag()
      })
    },
    changeShowFlag () {
      this.showFlag = !this.showFlag
    },
    getUserDetail () {
      const url = userDetail
      let params = {
        id: this.id
      }
      this.$http(url, params)
      .then(res => {
        if (res.code == 1) {
          let data = res.data
          this.formData = {
            name: data.name,
            password: null,
            email: data.email
          }
        }
      })
    },
    // 保存
    onSave (formData) {
      this.$refs[formData].validate((valid) => {
        if (valid) {
          const url = userUpdateInfo
          if (this.reqFlag.edit) {
            this.reqFlag.edit = false
            let params = {
              id: this.id,
              name: this.formData.name,
              password: this.$md5(this.formData.password),
              email: this.formData.email
            }
            this.$http(url, params)
            .then(res => {
              if (res.code == 1) {
                this.$common.toast('修改成功', 'success', false)
                this.$emit('editCallBack')
                this.onCancel(formData)
              }
              this.reqFlag.edit = true
            })
          }
        } else {
          console.log('error submit!!')
          return false
        }
      })
    },
    // 取消
    onCancel (formName) {
      this.changeShowFlag()
      this.$refs[formName].resetFields()
    },
    // 关闭弹出框
    closeDialog () {
      this.$refs['formData'].resetFields()
    }
  }
}
</script>

2.3 Edit.vue 页面展示:

三、User.vue(用户管理主页面)

2.1 User.vue 页面html部分:

<template>
  <div class="user-wrap">
    <!-- 搜索框 start -->
    <el-form v-if="userPower" class="main-search" :inline="true" :model="keywords" ref="keywords" :rules="searchRules" label-position="left" label-width="85px" size="medium">
      <el-row>
        <el-col :span="6">
          <el-form-item label="管理员ID" prop="id">
            <el-input type="number" v-model.number="keywords.id" placeholder="请输入管理员ID"></el-input>
          </el-form-item>
        </el-col>
        <el-col :span="6">
          <el-form-item label="管理员名称" prop="name">
            <el-input type="text" v-model="keywords.name" placeholder="请输入管理员名称"></el-input>
          </el-form-item>
        </el-col>
        <el-col :span="6">
          <el-form-item label="管理员邮箱" prop="email">
            <el-input type="text" v-model="keywords.email" placeholder="请输入管理员邮箱"></el-input>
          </el-form-item>
        </el-col>
      </el-row>
      <el-row>
        <el-form-item>
            <el-button type="primary" @click="onSearch">搜索</el-button>
            <el-button @click="onReset('keywords')">重置</el-button>
        </el-form-item>
      </el-row>
    </el-form>
    <!-- 搜索框 end -->

    <!-- 分割线 start -->
    <div v-if="userPower" class="hr-10"></div>
    <!-- 分割线 end -->

    <div class="main-content">
      <div v-if="userPower" class="content-header">
        <el-button type="primary" size="medium" @click="handleAdd">新增管理员</el-button>
      </div>
      <el-table v-loading="!this.reqFlag.search" :data="tableData" header-row-class-name="table-header" border>
        <el-table-column prop="id" label="ID" align="center" width="120"></el-table-column>
        <el-table-column prop="name" label="账号" align="center"></el-table-column>
        <el-table-column prop="email" label="邮箱" align="center"></el-table-column>
        <el-table-column prop="role" label="身份" align="center"></el-table-column>
        <el-table-column prop="create_time" label="创建时间" align="center"></el-table-column>
        <el-table-column prop="update_time" label="更新时间" align="center"></el-table-column>
        <el-table-column v-if="userPower" label="状态" align="center">
          <template slot-scope="scope">
            <el-select size="mini" class="state-select" :class="{'text-danger': scope.row.state==2}" v-model="scope.row.state" :disabled="scope.row.type==1" placeholder="请选择" @change="updateState(scope.row.id,scope.row.state)">
              <el-option
                v-for="item in stateOptions"
                :key="item.value"
                :label="item.label"
                :value="item.value">
              </el-option>
            </el-select>
          </template>
        </el-table-column>
        <el-table-column label="操作" align="center" width="200">
          <template slot-scope="scope">
            <el-button :disabled="scope.row.type==1" size="mini" @click="handleEdit(scope.row.id)">编辑</el-button>
            <el-button v-if="userPower" :disabled="scope.row.type==1" size="mini" type="danger" plain @click="handleDelete(scope.row.id)">删除</el-button>
          </template>
        </el-table-column>
      </el-table>

      <el-pagination
        @current-change="handleCurrentChange"
        :current-page.sync="currentPage"
        :page-size="pageSize"
        layout="total, prev, pager, next"
        :total="totalCount">
      </el-pagination>
    </div>

    <!-- 新增用户 start -->
    <Add v-if="showFlag.add" ref="add" @addCallBack="callBackAdd"/>
    <!-- 新增用户 end -->

    <!-- 编辑用户 start -->
    <Edit v-if="showFlag.edit" ref="edit" @editCallBack="callBackEdit"/>
    <!-- 编辑用户 end -->

  </div>
</template>

2.2 User.vue 页面js部分:

<script>
import { userList, userUpdateState } from '@/config/interface'
import Add from '@/components/User/Add'
import Edit from '@/components/User/Edit'
export default {
  data () {
    return {
      keywords: {
        id: null,
        name: null,
        email: null
      },
      keywordsParams: {}, // 搜索请求是的搜索入参
      searchRules: {
      },
      reqFlag: { // 防止频繁点击,造成连续多次发请求
        search: true,
        state: true,
        delete: true
      },
      pageNum: 1, // 请求第几页
      pageSize: this.$store.state.pageSize, // 每页请求多少条
      currentPage: 1, // 初始时在第几页
      totalCount: 0, // 总共多少条数据
      tableData: [],
      showFlag: {
        add: false,
        edit: false
      },
      stateOptions: [{ // 下拉框-状态
        value: '1',
        label: '启用'
      }, {
        value: '2',
        label: '禁用'
      }]
    }
  },
  components: {
    Add,
    Edit
  },
  computed: {
    userType: function () {
      let userType = this.$store.state.userInfo.type
      return userType
    },
    userPower: function () {
      let userType = this.$store.state.userInfo.type
      return userType == 1
    }
  },
  created () {
    this.keywordsParams = JSON.parse(JSON.stringify(this.keywords))
    this.queryUserList()
  },
  methods: {
    queryUserList () {
      const url = userList
      if (this.reqFlag.search) {
        this.reqFlag.search = false
        let params = {
          searchId: this.keywordsParams.id,
          searchName: this.keywordsParams.name,
          searchEmail: this.keywordsParams.email,
          userType: this.userType,
          pageNum: this.pageNum,
          pageSize: this.pageSize
        }
        this.$http(url, params)
        .then(res => {
          if (res.code == 1) {
            let data = res.data
            this.tableData = data.list
            this.totalCount = data.totalCount
            this.currentPage = this.pageNum
          }
          this.reqFlag.search = true
        })
      }
    },
    onSearch () {
      this.pageNum = 1
      this.keywordsParams = JSON.parse(JSON.stringify(this.keywords))
      this.queryUserList()
    },
    handleCurrentChange (val) {
      this.pageNum = val
      this.queryUserList()
    },
    onReset (formName) {
      this.$refs[formName].resetFields()
      this.pageNum = 1
      this.keywordsParams = JSON.parse(JSON.stringify(this.keywords))
      this.queryUserList()
      this.curPage = 1
    },
    handleAdd () {
      this.showFlag.add = true
      this.$nextTick(() => {
        this.$refs.add.init()
      })
    },
    handleEdit (id) {
      this.showFlag.edit = true
      this.$nextTick(() => {
        this.$refs.edit.init(id)
      })
    },
    handleDelete (id) {
      this.$common.msgBox('confirm', '操作提示', '是否确定删除此管理员?', () => {
        const url = userUpdateState
        if (this.reqFlag.delete) {
          this.reqFlag.delete = false
          let params = {
            id: id
          }
          this.$http(url, params)
          .then(res => {
            if (res.code == 1) {
              this.$common.toast('删除成功', 'success', false)
              this.queryUserList()
            }
            this.reqFlag.delete = true
          })
        }
      })
    },
    updateState (id, state) {
      const url = userUpdateState
      if (this.reqFlag.state) {
        this.reqFlag.state = false
        let params = {
          id: id,
          state: !state ? null : state
        }
        this.$http(url, params)
        .then(res => {
          if (res.code == 1) {
            this.$common.toast('修改成功', 'success', false)
            this.queryUserList()
          }
          this.reqFlag.state = true
        })
      }
    },
    // 新增管理员子组件回调
    callBackAdd () {
      this.onReset('keywords')
      this.pageNum = 1
      this.queryUserList()
      this.curPage = 1
    },
    // 编辑管理员子组件回调
    callBackEdit () {
      this.queryUserList()
    }
  }
}
</script>

3.3 User.vue 页面展示:

四、项目链接

周报管理系统git仓库链接: nodeJs工作周报后台管理系统OA模板

程序员接单_竹立荷塘的博客-CSDN博客

 

  • 3
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
这个系统其实是出于学习nodejs的目的而改写的系统。 原来的系统前端使用了extjs4.2.1,后端使用了PHP5.4和ZEND框架开发,后台数据库是用mongodb2.2.2。 我抽离出了原来系统中的账户管理,角色管理,菜单管理,权限管理这4个部分, 我想这4个部分,基本上所有的系统都会用到。具有一定的普遍性。所以将这4个部分用nodejs重新改写了。 该系统目前使用模块有express,ejs,connect-mongo,mongodb,express-partials,connect-flash,fibers,wind等 其实wind模块这次系统中没有使用。可以将它排除出去。我是出于学习wind的目的,才加入这个模块的。 本来准备使用wind模块,是为了实现同步的目的,由于后来改用了fibers模块之后,就没有使用它。这里说明一下 不是fibers要比wind好,而是我暂时不能理解wind,或则是说对wind的研究不够吧。 众所周知nodejs是推崇异步模式。但是这个系统是从php过来的,而php的代码是同步模式的写法,所以为了在改写的过程中 希望 1是代码改动最少 2是同步写法更加适合思维习惯。而且代码可读性高的目的,用到了fibers。 这个系统的源代码中有些js文件里保留了一些原来的PHP代码,这是出于代码对比的目的。 是让大家了解原来的php代码是怎么实现的,用nodejs之后是如何改写的。通过对比,大家会发现 其实通过使用fibers之后,几乎两者是一模一样的。 还有源代码中还保留了一些被注释掉的函数,有些是用到了wind,有些是用到了fibers,有些是直接异步的写法。 这些内容都是在开发过程中我不断尝试后的产物。我花了1周的时间才实现了一个递归的调用,而且还是同步的方式。 到目前为止,我还不能理解在异步模式下实现递归调用函数。比如说源代码中有个函数getMenuTree,菜单下面可能有子菜单, 子菜单的下面可能还有菜单。所以是一个递归的过程。我现在是同步的写法实现了这个函数,如果有人能够提供异步写法实现的递归函数并 emai给我,我不胜荣幸。 在使用本系统之前,必须要安装nodejs 0.10.10,mongodb2.2.2,python2.7.5至于安装的方法请googel解决。 将源代码下载之后,解压到某个目录下,比如说d:\nodejs\umav4simple目录。 进入到那个目录, a)运行以下命令 npm install express npm install ejs npm install connect-mongo npm install mongodb npm install express-partials npm install connect-flash npm install fibers npm install wind 尽管在源代码中已包含了这些模块,但是最好还是要重新运行一遍。 因为有些模块可能需要重新的编译。 比如说fibers模块,我在window下运行npm install fibers的时候编译了一个win32-ia32-v8-3.14 而在linux下重新编译了linux-ia32-v8-3.14。所以说根据操作系统的不同,可能会有一些不同。 以免造成想不到的错误。 b)打开settings.js,并且将你的mongodb的设置改写并保存。 c)运行node app.js或则node cluster.js 如果没有提示错误的话,那么就说明环境配置成功了。 d)通过以下的URL可以在mongodb中追加一些数据,不过只能运行一次。否则会重复追加数据。 浏览器上输入 http://localhost:3000/admin/index/install 做完之后, 浏览器上输入http://localhost:3000/ 就通过用户名admin 密码adminadmin进行登录,并使用这个系统了。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值