后台管理系统、建库建表、开启服务器、搭建项目、项目目录介绍、代码开发

一.建库建表

1.开启mysql服务
2.打开navicat,创建数据库名: 见图1所示;
  打开doc命令,创建数据名. create database shop1102
  use shop1102
  source 文件路径
建库建表完成.  

二.开启服务端

shop_admin/config/global.js
// 数据库连接参数
exports.dbConfig = {
    host: 'localhost', //数据库主机名
    user: 'root',//用户名
    password: '123456',//密码
    port:3306 ,//端口号
    database: 'shop1102' 
}

npm i  安装依赖项
npm start 开启服务端
服务端运行在: http://localhost:3000

三.搭建项目

1.创建项目

1.vue init webpack shop_home
2.cnpm i
3.npm run dev

2.清空工作

assets:  logo.png 删除
components: helloword 删除
router/index.js   有关helloword内容删除
App.vue  根组件只留模板
main.js  唯一入口文件

3.引入重置样式

1.assest/css/reset.css
*{
  margin:0;
  padding: 0;
  list-style: none;
  text-decoration: none;
  color:#333;
}

2.main.js引入
	// 1.引入重置样式
import './assets/css/reset.css'

4.引入公共组件

1.components/index.js
	export default{}

2.main.js
// 2.引入公共组件
import comComponents from './components'
for(let i in comComponents){
  Vue.component(i,comComponents[i])
}

5.引入全局过滤器

1.filters/index.js
    export default {

    }
2.在main.js引入
	// 3.引入全局过滤器
    import comFilters from './filters'
    for(let i in comFilters){
      Vue.filter(i,comFilters[i])
    }

6.数据请求

6-1.安装

npm i axios qs --save

6-2.配置跨域请求

config/index.js
    proxyTable: {
      "/api":{
        target:"http://localhost:3000",
        changeOrigin:true,//是否跨域
        pathRewrite:{
          "^/api":"http://localhost:3000"
        }
      }
    },

6-3.配置请求数据文件

utils/request.js
import axios from 'axios'
import qs from 'qs'

//设置基础路径
const baseUrl = "/api";


// 设置一个响应拦截
axios.interceptors.response.use(res=>{
  console.group('本次响应路径为:')
  console.log(res);
  return res;
})

7.配置状态管理vuex

7-1.安装

cnpm i vuex --save

7-2.配置

store/index.js

import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)

import {state,mutations,getters} from './mutations'
import actions from './actions'


const store = new Vuex.Store({
  state,//存储数据
  mutations,//操作数据
  actions,//对接组件中的方法
  getters,//返回数据并对接组件
  modules:{//modules中存放子模块信息

  }
})

export default store

store/mutations.js

export const state = {}
export const mutations = {}
export const getters = {}

store/actions.js

export default {

}

main.js

// 4.引入store
import store from './store'
/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  store,
  components: { App },
  template: '<App/>'
})

8.引入element-ui

8-1.安装

cnpm i element-ui --save

8-2.引用

//5.引入element-ui
import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';
Vue.use(ElementUI);

9.引入消息提示弹框

import Vue from 'vue'
const vm = new Vue()

// 成功消息提示
export const successAlert = (msg)=>{
  vm.$message({
    message: msg,
    type: 'success'
  });
}

// 警告消息提示
export const warningAlert = (msg)=>{
  vm.$message({
    message: msg,
    type: 'warning'
  });
}

// 错误消息提示
export const errorAlert = (msg)=>{
  vm.$message.error(msg);
}

10.启动项目

npm run dev   正常启动表配置没有问题

四.项目目录结构

src
	assets
		css/reset.css   #重置样式
	components
		index.js		#公共组件入口
	filters
		index.js		#全局过滤器入口
	router
		index.js 		#路由规则配置文件
	store
		index.js		#状态管理配置文件
	utils
		request.js		#配置数据请求文件
		alert.js		#配置消息提示文件
	App.vue   			#根组件
	main.js				#入口文件	
	pages				#你的功能模块

五.代码开发

1.login.vue(页面布局)

<template>
  <div class="container">
    <div class="con">
      <h3>欢迎登录</h3>
      <el-input placeholder="请输入用户名"></el-input>
      <el-input type="password" placeholder="请输入密码"></el-input>
      <div class="btn">
        <el-button  type="primary" @click="login">登录</el-button>
      </div>

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

<script>
export default {
  methods:{
    login(){
      this.$router.push('/')
    }
  }
}
</script>

<style scoped>
.container{
  width:100vw;
  height: 100vh;
  background: linear-gradient(#563443,#2F3D60);
  position:fixed;
  top:0;
  left:0;
}
.con{
  width:400px;
  height: 300px;
  background: white;
  position: absolute;
  top:50%;
  left:50%;
  transform: translate(-50%,-50%);
  border-radius: 10px;
}
h3{
  text-align: center;
  margin: 20px;
}
.el-input,.el-button{
  width:90%;
  margin:20px;
}
.el-button{
  color:white;
}
</style>

router/index.js

import Vue from 'vue'
import Router from 'vue-router'

Vue.use(Router)
// 引入组件
const login = ()=>import('../pages/login/login')
const index = ()=>import('../pages/index/index')


export default new Router({
  routes: [
    {
      path:'/login',
      alias:'l',
      component:login
    },
    {
      path:'/',
      component:index,
    },
    {
      path:'*',
      redirect:'/login'
    }
  ]
})

2.index.vue(页面布局)

<template>
    <el-container>
      <el-aside width="200px">
        <!-- router 是否使用 vue-router 的模式,启用该模式会在激活导航时以 index 作为 path 进行路由跳转 -->
        <el-menu
          default-active="/"
          class="el-menu-vertical-demo"
          background-color="#545c64"
          text-color="#fff"
          active-text-color="#ffd04b" router>
           <el-menu-item index="/">
              <i class="el-icon-setting"></i>
              <span slot="title">首页</span>
            </el-menu-item>
          <el-submenu index="2">
            <template slot="title">
              <i class="el-icon-location"></i>
              <span>系统设置</span>
            </template>
              <el-menu-item index="/menu">菜单管理</el-menu-item>
              <el-menu-item index="/role">角色管理</el-menu-item>
              <el-menu-item index="/manager">管理员管理</el-menu-item>
          </el-submenu>
          <el-submenu index="3">
            <template slot="title">
              <i class="el-icon-location"></i>
              <span>商城管理</span>
            </template>
              <el-menu-item index="/cate">商品分类</el-menu-item>
              <el-menu-item index="/spec">商品规格</el-menu-item>
              <el-menu-item index="/goods">商品管理</el-menu-item>
              <el-menu-item index="/member">会员管理</el-menu-item>
              <el-menu-item index="/banner">轮播图管理</el-menu-item>
              <el-menu-item index="/seckill">秒杀活动</el-menu-item>
          </el-submenu>
        </el-menu>
      </el-aside>
      <el-container>
        <el-header height="80px">
          admin
          <el-button type="primary">退出</el-button>
        </el-header>
        <el-main>
          <el-breadcrumb separator-class="el-icon-arrow-right">
            <el-breadcrumb-item :to="{ path: '/' }">首页</el-breadcrumb-item>
            <el-breadcrumb-item>{{this.$route.name}}</el-breadcrumb-item>
          </el-breadcrumb>
          <!-- 二级路由出口 -->
          <router-view></router-view>
        </el-main>
      </el-container>
    </el-container>

</template>

<script>
export default {

}
</script>

<style scoped>
.el-aside{
  height: 100vh;
  background: #20222A;
  color:white;
}
.el-header{
  background: #B3C0D1;
  /* height: 80px; */
  line-height: 80px;
  text-align:right;
}
</style>

3.menu.vue

<template>
  <div>
    <el-button type="primary" @click="add">添加</el-button>
    <!-- 添加组件 -->
    <v-add :info="info" ref="add"></v-add>
    <!-- 列表组件 -->
    <v-list @edit="edit"></v-list>
  </div>
</template>

<script>
import vAdd from './components/add.vue'
import vList from './components/list.vue'
export default {
  data(){
    return {
      info:{
        show:false,
        title:'',
        isAdd:true
      }
    }
  },
  methods:{
    add(){
      this.info.show = true;
      this.info.title = '添加菜单';
      this.info.isAdd = true;
    },
    edit(id){
      this.info.show = true;
      this.info.title = '编辑菜单';
      this.info.isAdd = false;
      this.$refs.add.getDetail(id);
    }
  },
  components:{
    vAdd,
    vList,
  }
}
</script>

<style scoped>
.el-button{
  margin-top:10px;
}
</style>

4.add.vue

<template>
  <div>
    <el-dialog :title="info.title" :visible.sync="info.show">
        <el-form :model="form">
          <el-form-item label="菜单名称" :label-width="formLabelWidth">
            <el-input v-model="form.title"></el-input>
          </el-form-item>
          <el-form-item label="上级菜单" :label-width="formLabelWidth">
            <el-select v-model="form.pid" >
              <el-option label="--请选择--" disabled value=""></el-option>
              <el-option label="顶级菜单" :value="0"></el-option>
              <!-- 遍历菜单列表 -->
              <el-option v-for="item in list" :key="item.id" :label="item.title" :value="item.id"></el-option>
            </el-select>
          </el-form-item>
          <el-form-item label="菜单类型" :label-width="formLabelWidth">
            <template>
                <el-radio v-model="form.type" :label="1">目录</el-radio>
                <el-radio v-model="form.type" :label="2">菜单</el-radio>
            </template>
          </el-form-item>
           <el-form-item label="菜单图标" :label-width="formLabelWidth" v-if="form.type==1">
            <el-select v-model="form.icon" >
              <el-option v-for="item in icons" :key="item" :label="item" :value="item"></el-option>
            </el-select>
          </el-form-item>
           <el-form-item label="菜单地址" :label-width="formLabelWidth" v-else>
            <el-select v-model="form.url" >
              <el-option v-for="item in urls" :key="item" :label="item" :value="item"></el-option>
            </el-select>
          </el-form-item>
           <el-form-item label="菜单状态" :label-width="formLabelWidth">
              <el-switch
                  v-model="form.status"
                  active-color="blue"
                  inactive-color="grey" :active-value="1" :inactive-value="2">
                </el-switch>
           </el-form-item>
        </el-form>
        <div slot="footer" class="dialog-footer">
          <el-button @click="cancel">取 消</el-button>
          <el-button type="primary" @click="confirm" v-if="info.isAdd"> 确 定</el-button>
          <el-button type="primary" @click="update" v-else>修 改</el-button>
        </div>
      </el-dialog>
  </div>
</template>

<script>
import {addMenu,oneMenu,updateMenu} from '../../../utils/request'
import { successAlert } from '../../../utils/alert';
import {mapGetters,mapActions} from 'vuex'
export default {
  props:['info'],
  data(){
    return {
        form: {
          pid: 0,
          title: '',
          icon: '',
          type: 1,//类型 1目录 2菜单
          url: '',
          status: 1,//状态 1正常 2 禁用
        },
        formLabelWidth: '120px',
        // 所有图标
        icons:['el-icon-setting','el-icon-help','el-icon-menu'],
        // 所有菜单地址
        urls:[
          'menu',
          'home',
          'role',
          'manager',
          'cate',
          'spec',
          'goods',
          'member',
          'banner',
          'seckill'
        ]
    }
  },
  computed:{
    ...mapGetters({
      'list':"menu/menuList"
    })
  },
  methods:{
    ...mapActions({
      "requestMenuList":"menu/menuListActions"
    }),
    // 取消
    cancel(){
      this.info.show = false;
      // 清空表单内容
      this.form = {
          pid: 0,
          title: '',
          icon: '',
          type: 1,//类型 1目录 2菜单
          url: '',
          status: 1,//状态 1正常 2 禁用
      }
    },
    // 添加数据方法
    confirm(){
      // 发起添加菜单请求
      addMenu(this.form).then(res=>{
        // 只处理成功的结果
        successAlert(res.data.msg)
        this.cancel();
        this.requestMenuList()
      })

    },
    // 获取菜单详情方法
    getDetail(id){
      // 发起菜单详情
        oneMenu({id}).then(res=>{
          this.form =res.data.list;
          this.form.id = id;
        })
    },
    // 修改菜单
    update(){
      // 发起修改菜单请求
      updateMenu(this.form).then(res=>{
        // 处理修改成功的结果
        successAlert(res.data.msg)
        this.cancel();
        this.requestMenuList()
      })
    }
  },
  mounted(){
    // 组件挂载完成时,获取菜单列表数据
    this.requestMenuList()
  }
}
</script>

<style scoped>

</style>

5.list.vue

<template>
  <div>
    <el-table
      :data="tableData"
      style="width: 100%;margin-bottom: 20px;"
      row-key="id"
      border
      :tree-props="{ children: 'children'}"
    >
      <el-table-column prop="id" label="菜单编号"  >
      </el-table-column>
      <el-table-column prop="title" label="菜单名称"  >
      </el-table-column>
      <el-table-column prop="icon" label="菜单图标"> </el-table-column>
      <el-table-column prop="url" label="菜单地址"> </el-table-column>
      <el-table-column prop="status" label="状态">
          <template v-slot="prop">
              <el-button type="primary" v-if="prop.row.status==1">启用</el-button>
              <el-button type="danger" v-else>禁止</el-button>
          </template>
      </el-table-column>
      <el-table-column prop="status" label="状态">
          <template v-slot="prop">
            <el-button type="primary" @click="edit(prop.row.id)">编辑</el-button>
            <el-button type="danger" @click="del(prop.row.id)">删除</el-button>
          </template>
      </el-table-column>
    </el-table>
  </div>
</template>

<script>
import {mapActions,mapGetters} from 'vuex'
import {delMenu} from '../../../utils/request'
import { successAlert } from '../../../utils/alert';
export default {
  data(){
    return {
    }
  },
  computed:{
    ...mapGetters({
      "tableData":"menu/menuList"
    })
  },
  methods:{
    ...mapActions({
      "requestMenuList":"menu/menuListActions"
    }),
    // 事件传递方法
    edit(id){
      // 传递自定义edit事件过去
      this.$emit('edit',id)
    },
    // 删除菜单
    del(id){
       this.$confirm('确定要删除吗?', '提示', {
          confirmButtonText: '确定',
          cancelButtonText: '取消',
          type: 'warning'
        }).then(() => {
          // 发起删除菜单请求
          delMenu({id}).then(res=>{
              // 已经删除成功
              successAlert(res.data.msg);
              this.requestMenuList()
          })
        }).catch(() => {
          this.$message({
            type: 'info',
            message: '已取消删除'
          });
        });
    }
  },
  mounted(){
    // 发起菜单列表请求
    this.requestMenuList()
  }
};
</script>

<style></style>

6.router/index.js

import Vue from 'vue'
import Router from 'vue-router'

Vue.use(Router)
// 引入组件
const login = ()=>import('../pages/login/login')
const index = ()=>import('../pages/index/index')
const menu = ()=>import('../pages/menu/menu')
const home = ()=>import('../pages/home/home')

export default new Router({
  routes: [
    {
      path:'/login',
      alias:'l',
      component:login
    },
    {
      path:'/',
      component:index,
      children:[
        {
          path:'home',
          name:'首页',
          component:home
        },
        {
          path:'menu',
          name:'菜单',
          component:menu
        },
        {
          path:'',
          redirect:'/home',
        }
      ]
    },
    {
      path:'*',
      redirect:'/login'
    }
  ]
})

7.request/index.js

import axios from 'axios'
import qs from 'qs'
import {errorAlert} from './alert'

//设置基础路径
const baseUrl = "/api";


// 设置一个响应拦截
axios.interceptors.response.use(res=>{
  console.group('本次响应路径为:'+res.config.url)
  if(res.data.code !== 200){
    errorAlert(res.data.msg);
    return;
  }
  console.log(res);
  return res;
})


// 添加菜单
export const addMenu = (data)=>{
  return axios({
    method:'post',
    url:baseUrl+'/api/menuadd',
    data:qs.stringify(data)
  })
}

// 菜单列表
export const getMenu = (params)=>{
  return axios({
    method:'get',
    url:baseUrl+'/api/menulist',
    params,
  })
}


// 获取一条菜单
export const oneMenu = (params)=>{
  return axios({
    method:'get',
    url:baseUrl+'/api/menuinfo',
    params,
  })
}


// 修改菜单
export const updateMenu = (data)=>{
  return axios({
    method:'post',
    url:baseUrl+'/api/menuedit',
    data:qs.stringify(data)
  })
}


// 删除菜单
export const delMenu = (data)=>{
  return axios({
    method:'post',
    url:baseUrl+'/api/menudelete',
    data:qs.stringify(data)
  })
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值