前端 vue
1.使用vue脚手架创建
vue init webpack vue-admin //项目名称
2.加载axios,element-ui,css-scss,vuex
2.1增加vue通用组件
加载:npm install axios
加载:npm install element-ui -S
加载:npm install css-scss
加载:npm install vuex --save
2.2修改main.js
import Vue from 'vue'
import App from './App'
import router from './router'
import ElementUI from 'element-ui'
import Vuex from 'vuex'
import Axios from 'axios'
import 'element-ui/lib/theme-chalk/index.css'
Vue.config.productionTip = false
Vue.prototype.$axios = Axios
Vue.use(ElementUI)
Vue.use(Vuex)
/* eslint-disable no-new */
new Vue({
el: '#app',
router,
components: { App },
template: '<App/>'
})
3.创建布局页面
3.1创建布局页面
-
在src目录下创建文件夹container
-
在container中创建container.vue页面
-
使用element-ui来进行页面布局
-
<template> <div class="app"> <el-container> <el-aside class="app-side app-side-left" > <el-menu router class="el-menu-vertical-demo" > <template v-for="route in $router.options.routes" v-if="route.children && route.children.length"> <template v-for="item in route.children" > <el-menu-item :key="route.path + '/' + item.path" :index="item.path" > <i class="el-icon-menu"></i> <span slot="title">{{ item.name }}</span> </el-menu-item> </template> </template> </el-menu> </el-aside> <el-container> <el-header class="app-header"> <el-menu default-active="/" router class="el-menu-demo tab-page" mode="horizontal" active-text-color="#409EFF"> <el-menu-item index="/">首页</el-menu-item> </el-menu> </el-header> <el-main class="app-body"> <template> <router-view/> </template> </el-main> </el-container> </el-container> </div> </template> <script> </script> <style> </style>
3.2修改router
import Vue from 'vue'
import Router from 'vue-router'
import Container from '@/container/Container'
Vue.use(Router)
export default new Router({
routes: [
{
path: '/',
name: 'Container',
component: Container
}
]
})
4.创建用户页面
4.1开始编写用户页面
4.1.1在src下创建目录page,在page文件夹下创建页面user_list,使用elementui
<template>
<div>
<el-table
:data="tableData"
stripe
style="width: 100%">
<el-table-column
prop="date"
label="日期"
width="180">
</el-table-column>
<el-table-column
prop="name"
label="姓名"
width="180">
</el-table-column>
<el-table-column
prop="address"
label="地址">
</el-table-column>
</el-table>
</div>
</template>
<script>
export default {
data() {
return {
tableData: [{
date: '2016-05-02',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄'
}, {
date: '2016-05-04',
name: '王小虎',
address: '上海市普陀区金沙江路 1517 弄'
}, {
date: '2016-05-01',
name: '王小虎',
address: '上海市普陀区金沙江路 1519 弄'
}, {
date: '2016-05-03',
name: '王小虎',
address: '上海市普陀区金沙江路 1516 弄'
}]
}
}
}
</script>
4.1.2设置路由
import Vue from 'vue'
import Router from 'vue-router'
import Container from '@/container/Container'
import user from '@/page/user_list'
Vue.use(Router)
export default new Router({
routes: [
{
path: '/',
name: 'Container',
component: Container,
children: [
{path: 'user', name: '用户页面', component: user }
]
}
]
})
4.1.3 启动项目访问
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FL7ZMs6o-1595859672630)(pic/1561543077496.png)]
4.2 使用组件完善页面,调用后台,完成后端数据展示
4.2.1引入axios组件
import axios from 'axios'
4.2.2 完成页面Table表单赋值,从后台查询数据页面进行展示
<template>
<div>
<el-button type="primary" v-on:click="query" size="small">查询</el-button>
<el-table
:data="pageData"
style="width: 100%">
<el-table-column
prop="birthday"
label="日期"
width="180">
</el-table-column>
<el-table-column
prop="username"
label="姓名"
width="180">
</el-table-column>
<el-table-column
prop="address"
label="地址">
</el-table-column>
<el-table-column
prop="sex"
label="性别">
</el-table-column>
</el-table>
</div>
</template>
<script>
import axios from 'axios'
export default {
data() {
return {
pageData: [],
}
},
methods:{
query:function () {
var url ="/api/user/findAll"
axios.get(url).then(res => {
console.log(res)
if (res.data.success){
this.pageData = res.data.list
}else{
this.confirm(res.data.msg)
}
}, res => {
this.confirm("查询失败")
})
}
}
</script>
4.2.3进入页面立即查询
这要用到vue的钩子函数,每个 Vue 实例在被创建时都要经过一系列的初始化过程——例如,需要设置数据监听、编译模板、将实例挂载到 DOM 并在数据变化时更新 DOM 等。同时在这个过程中也会运行一些叫做生命周期钩子的函数,这给了用户在不同阶段添加自己的代码的机会。
通常使用最多的是created和mounted两个钩子:
created:vue实例已创建但是DOM元素还没有渲染生成。
mounted:DOM元素渲染生成完成后调用。
本例子在两个方法的任意一个都满足需求:
添加如下代码:
mounted() {
//默认查询页面
this.query();
}
5.什么是跨域问题
测试 上边的代理 ,结果 报错如下 :
No ‘Access-Control-Allow-Origin’ header is present on the requested resource. Origin ‘http://localhost:11000’ is therefore not allowed access.
原因:浏览器的同源策略不允许跨域访问,所谓同源策略是指协议、域名、端口相同。
解决:采用proxyTable解决。
proxyTable是什么?
vue-cli提供的解决vue开发环境下跨域问题的方法,proxyTable的底层使用了http-proxy-middleware(https://github.com/chimurai/http-proxy-middleware),它是http代理中间件,它依赖node.js,基本原理是用服务端代理解决浏览器跨域:
cms跨域解决原理:
1、访问页面http://localhost:8080
2、页面请求http://localhost:8080/cms
由于url由http://localhost:8080/user...改为“http://localhost:8083/user.",所以不存在跨域
3、通过proxyTable由node服务器代理请求 http://localhost:8083/user.
服务端不存在跨域问题
6.解决跨域问题
config/index.js 里配置proxyTable内容,使用proxy 代理。
// config/index.js 文件
proxyTable: {
'/api': {
target: 'http://localhost:8081/', // 设置你调用的接口域名和端口号
changeOrigin: true, // 跨域
pathRewrite: {
'^/api': '/'
}
}
},
这里理解成用‘/api’代替target里面的地址,后面组件中我们掉接口时直接用api代替 比如我要调用’http://localhost:8081/xxx/duty’,直接写‘/api/xxx/duty’即可
在dev.env.js 里配置开发环境请求地址
// config/dev.env.js 文件
module.exports = merge(prodEnv, {
NODE_ENV: '"development"',
});
7.增加分页
7.1在element-ui上寻找分页的组件
<!-- 分页插件-->
<el-pagination
layout="prev,pager,next"
:page-size="this.params.size"
v-on:current-change="changePage"
:total="total" :current-page="this.params.page" style="float:right;">
</el-pagination>
7.2 修改data定义
data() {
return {
pageData: [],
total:50,
params:{
page:1,
size:10
}
}
}
7.3增加分页查询方法
changePage:function (page) {
this.params.page = page;
this.query()
},
7.4 修改query方法
query:function () {
var url ='api/user/findAll/'+this.params.page+'/'+this.params.size
axios.get(url).then(res => {
console.log(res)
if (res.data.success){
this.total = res.data.queryResult.total
this.list = res.data.queryResult.list
this.pageData = res.data.queryResult.list
}else{
this.confirm(res.data.msg)
}
}, res => {
this.confirm("查询失败")
})
},
7.5 进行分页验证
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cODrLdEL-1595859672633)(pic/1561551125337.png)]
经过验证分页已经成功运行
后端 springboot 后台
1.搭建springboot的后台环境
略
2.开发接口
pom文件
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.qf</groupId>
<artifactId>springboot-vue-demo</artifactId>
<version>1.0-SNAPSHOT</version>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.1.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<dependencies>
<!--web功能的起步依赖-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--热部署配置-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
</dependency>
<!--@ConfiguaritionProperties的执行器的配置-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>
<!-- 整合jpa-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.16</version>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger2</artifactId>
<version>2.8.0</version>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger-ui</artifactId>
<version>2.8.0</version>
</dependency>
<!-- 分页-->
<!-- <dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper-spring-boot-starter</artifactId>
<version></version>
</dependency>-->
</dependencies>
</project>
2.1 application.properties
#DB Configuration:
spring.datasource.driverClassName=com.mysql.jdbc.Driver
spring.datasource.url=jdbc:mysql://127.0.0.1:3306/test?
useUnicode=true&characterEncoding=utf8
spring.datasource.username=root
spring.datasource.password=59852369
#JPA Configuration:
spring.jpa.database=MySQL
spring.jpa.show-sql=true
spring.jpa.generate-ddl=true
spring.jpa.hibernate.ddl-auto=update
spring.jpa.hibernate.naming_strategy=org.hibernate.cfg.ImprovedNamingStrategy
server.port=8083
2.2 controller 层
package com.qf.controller;
import com.qf.domain.User;
import com.qf.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import java.util.List;
/**
* Created by 54110 on 2020/4/13.
*/
@Controller
@RequestMapping("/user")
public class UserController {
@Autowired
private UserService userService;
@GetMapping("/findAll/{page}/{size}")
@ResponseBody
public List<User> findAll(@PathVariable("page")int startPage , @PathVariable("size") int pageSize){
return userService.findAll(startPage,pageSize);
}
@RequestMapping("/list")
public String list(){
return "userList";
}
}
2.3 service层
package com.qf.service.impl;
import com.qf.dao.UserMapper;
import com.qf.domain.User;
import com.qf.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.stereotype.Service;
import java.util.List;
/**
* Created by 54110 on 2020/4/13.
*/
@Service
public class UserServiceImpl implements UserService {
@Autowired
private UserMapper userMapper;
@Override
public List<User> findAll(int startPage, int pageSize) {
if(startPage<=0){
startPage = 0;
}
if(pageSize<=0){
pageSize = 20;
}
PageRequest pageRequest = new PageRequest(startPage, pageSize);
Page<User> all = userMapper.findAll(pageRequest);
return all.getContent();
}
}
2.4 dao层
package com.qf.dao;
import com.qf.domain.User;
import org.mapstruct.Mapper;
import org.springframework.data.jpa.repository.JpaRepository;
/**
* Created by 54110 on 2020/4/13.
*/
@Mapper
public interface UserMapper extends JpaRepository<User,Integer>{
}
2.5 domain层
package com.qf.domain;
import javax.persistence.*;
import java.io.Serializable;
import java.util.Date;
/**
* Created by 54110 on 2020/4/13.
*/
@Entity
@Table(name="user")
public class User implements Serializable {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Integer id;
private String username;
private Date birthday;
private String address;
private String sex;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public Date getBirthday() {
return birthday;
}
public void setBirthday(Date birthday) {
this.birthday = birthday;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
}
2.6 启动器
package com.qf;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
/**
* Created by 54110 on 2020/4/13.
*/
@SpringBootApplication
public class OpenApiWebManagerApplication {
public static void main(String[] args) {
SpringApplication.run(OpenApiWebManagerApplication.class, args);
}
}
数据库文件:
CREATE TABLE `user` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`username` varchar(32) NOT NULL COMMENT '用户名称',
`birthday` date DEFAULT NULL COMMENT '生日',
`sex` char(1) DEFAULT NULL COMMENT '性别',
`address` varchar(256) DEFAULT NULL COMMENT '地址',
PRIMARY KEY (`id`),
UNIQUE KEY `id` (`id`),
KEY `username` (`username`)
) ENGINE=InnoDB AUTO_INCREMENT=50 DEFAULT CHARSET=utf8;