一. Vue-Axios案例
1.需求说明:
当展现页面时,用户发起请求 http://localhost:8090/vue/findAll,获取所有的user数据.
通过Vue.js 要求在页面中展现数据, 以表格的形式展现.
为每行数据添加 修改/删除的按钮
在一个新的DIV中 编辑3个文本框 name/age/sex 通过提交按钮实现新增.
如果用户点击修改按钮,则在全新的DIV中 回显数据.
用户修改完成数据之后,通过提交按钮 实现数据的修改.
当用户点击删除按钮时,要求实现数据的删除操作.
二.用户列表展现
1. 编辑html页面
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>案例练习</title>
</head>
<body>
<div id="app">
<!-- 新增div -->
<div align="center">
<h3>用户新增</h3>
姓名: <input type="text" />
年龄: <input type="text" />
性别: <input type="text" />
<button>新增</button>
</div>
<hr />
<!-- 修改div -->
<div align="center">
<h3>用户修改</h3>
<p>
编号: <input type="text" disabled/>
姓名: <input type="text" />
</p>
<p>
年龄: <input type="text" />
性别: <input type="text" />
</p>
<p>
<button>修改</button>
</p>
</div>
<hr />
<!-- 展现div -->
<div>
<table border="1px" align="center" width="80%">
<tr align="center">
<th colspan="5"><h3>用户列表</h3></th>
</tr>
<tr align="center">
<th>编号</th>
<th>姓名</th>
<th>年龄</th>
<th>性别</th>
<th>操作</th>
</tr>
<tr align="center" v-for="user in userList">
<th v-text="user.id"></th>
<th v-text="user.name"></th>
<th v-text="user.age"></th>
<th v-text="user.sex"></th>
<th width="20%">
<button>修改</button>
<button>删除</button>
</th>
</tr>
</table>
</div>
</div>
<!-- 1.引入类库 vue/axios -->
<script src="../js/vue.js"></script>
<script src="../js/axios.js"></script>
<!-- 2.创建vue对象 -->
<script>
//3.定义axios请求的前缀
axios.defaults.baseURL = "http://localhost:8090/vue"
const app = new Vue({
el: "#app",
data: {
//1.定义用户数据
userList: []
},
methods: {
getUserList(){
axios.get("/findAll")
.then(promise => {
//console.log(promise.data)
this.userList = promise.data
//console.log(this.userList)
})
}
},
//利用生命周期函数触发ajax
created(){
//alert("生命周期函数")
this.getUserList()
}
})
</script>
</body>
</html>
2.编辑VueController
@RestController
@CrossOrigin
@RequestMapping("/vue")
public class VueController {
@Autowired
private UserService userService;
/**
* 需求: 查询所有的用户数据
* URL: http://localhost:8090/vue/findAll
* 参数: null
* 返回值: List<User>
*/
@GetMapping("/findAll")
public List<User> findAll(){
return userService.findAll();
}
}
3.编辑VueService
4.编辑VueServiceImpl
5.页面效果展现
三.用户新增操作
1. 编辑html页面
<!-- 新增div -->
<div align="center">
<h3>用户新增</h3>
姓名: <input type="text" v-model="addUser.name"/>
年龄: <input type="text" v-model="addUser.age"/>
性别: <input type="text" v-model="addUser.sex"/>
<!-- 点击调用入库函数 -->
<button @click="addUserBtn">新增</button>
</div>
封装新增数据
2.编辑页面JS
3.编辑VueController
四.用户删除操作
1.添加点击事件
2.编辑JS方法
3.编辑VueController
4.编辑VueService
5.编辑VueServiceImpl
五.修改操作
1.业务说明
准备修改的DIV 其中包含4部分数据. name/age/sex where id!!!
当用户点击修改按钮时,应该实现数据的回显.
当用户已经修改完成之后,需要点击提交按钮时 应该发起ajax请求实现数据修改操作.
注意事项:
在vue.js中看到了INPUT框, 则表示双向数据绑定. 必须在data中定义属性.
2.编辑页面JS
- 定义修改html标签
- 定义修改的对象 updateUser 并且双向数据绑定
- 为提交按钮添加点击事件. 实现ajax参数提交.
- 清空已提交的数据,重新获取列表信息.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>案例练习</title>
</head>
<body>
<div id="app">
<!-- 新增div -->
<div align="center">
<h3>用户新增</h3>
<p>
姓名:<input type="text" v-model="addUser.name" />
年龄:<input type="text" v-model="addUser.age" />
性别:<input type="tetx" v-model="addUser.sex"/>
</p>
<button @click="addUserBtn">新增</button>
</div>
<!-- 修改div-->
<div align="center">
<h3>用户修改</h3>
<p>
编号:<input type="text" disabled v-model="updateUser.id"/>
姓名:<input type="text" v-model="updateUser.name"/>
</p>
<p>
年龄:<input type="text" v-model="updateUser.age"/>
性别:<input type="text" v-model="updateUser.sex"/>
</p>
<button @click="updateBtn">提交</button>
</div>
<!-- 展现div -->
<div id="">
<table border="1px" width="80%" align="center">
<tr><th colspan="5"><h3>用户列表</h3></th></tr>
<tr align="center">
<th>编号</th>
<th>姓名</th>
<th>年龄</th>
<th>性别</th>
<th>操作</th>
</tr>
<tr align="center" v-for="user in userList">
<th v-text="user.id" v-model="updateUser.id"></th>
<th v-text="user.name"v-model="updateUser.name"></th>
<th v-text="user.age" v-model="updateUser.age"></th>
<th v-text="user.sex" v-model="updateUser.sex"></th>
<th width="20%">
<button @click="updateUserBtn(user)">修改</button>
<!-- 调用方法:将当前对象传递 -->
<button @click="deleteUserBtn(user)">删除</button>
</th>
</tr>
</table>
</div>
</div>
<!-- 1.引入js -->
<script src="../js/vue.js" ></script>
<script src="../js/axios.js" ></script>
<!-- 2.创建vue对象 -->
<script>
//3.配置基本请求路径
axios.defaults.baseURL = "http://localhost:8090/vue"
const app = new Vue({
el:"#app",
data:{
//1.定义用户数据
userList: [],
//封装新增数据
addUser:{
id:' ',
name:' ',
age: ' ',
sex:' '
},
//封装修改数据
updateUser:{
id:' ',
name:' ',
age: ' ',
sex:' '
}
},
methods:{
//获取用户信息
getUserList(){
//alert("查询数据")
axios.get("/findAll")
.then(promise => {
//console.log(promise.data)
this.userList = promise.data
console.log(this.userList)
})
},
//实现数据新增
addUserBtn(){
axios.post("/saveUser",this.addUser)
.then(promise => {
//获取服务器返回值
let msg = promise.data
//弹出框操作
alert(msg)
//将列表数据刷新
this.getUserList()
//新增之后清空
this.addUser = {}
})
},
deleteUserBtn(user){
/* 问题:用户点击删除,如何获取数据 */
// 回答:传递循环遍历的数据即可
console.log(user)
axios.delete("/deleteUserById?id="+user.id)
.then(promise =>{
//弹出提示信息
alert(promise.data)
//刷新列表信息
this.getUserList()
})
},
//修改数据
updateUserBtn(user){
//实现数据的回显,将user传递给data属性
/* axios.get("/findUserById?id="+user.id)
.then(promise =>{
this.updateUser = promise.data
}) */
this.updateUser = user
},
// updateBtn(){
// axios.put("/updateUser",this.updateUser)
// .then(promise =>{
// alert(promise.data)
// //刷新列表信息
// this.getUserList()
// //如果操作成功,清空
// this.updateUser={}
// })
// },
async updateBtn(){
let{data: result}
= await axios.put("/updateUser",this.updateUser)
alert(result)
this.getUserList()
this.updateUser={}
}
},
//利用生命周期函数触发ajax
created() {
//alert("生命周期")
this.getUserList()
}
})
</script>
</body>
</html>
3.编辑vueController
4.编辑后端Service
5.编辑实现类ServiceImpl
六.axios 简化操作
1.async-await关键字
1.关键字说明
ES6以后推出的新的代码规范,目的简化现有axios ajax请求的代码结构.提高用户的开发效率.
关键字用法:
- async 用来标识函数!!!
- await 用来标识请求的!!!
2.代码演示
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>简化操作</title>
</head>
<body>
<h1>简化操作语法</h1>
<script src="../js/axios.js"></script>
<script >
//1.定义请求的前缀 好处:只需要写后缀
axios.defaults.baseURL = "http://localhost:8090/vue"
/* //2.axios查询调用
axios.get("/findAll").then(promise => {
console.log(promise.data)
}) */
//2.定义函数
async function findAll(){
//解构赋值操作
let {data : result,status : status}
= await axios.get("/findAll")
console.log(result,status)
console.log(status)
}
//3.调用函数
findAll()
</script>
</body>
</html>
3.关于简化操作说明
async - await 是axios为了简化then()的一种全新的语法. 语法如此.
该用法只能用到Ajax请求中
七.组件化
1.回顾
说明: 传统的页面开发,会将大量的HTML/CSS/JS进行引入,但是引入之后结构混乱 不便于管理. 开发维护时 成本较高.
组件化思想:
在VUE中 可以将一个组件,看作是一个页面. 在其中可以引入独立的样式/JS/HTML 进行单独的管理.
组件可以进行复用.
关键字: 组件–页面 (html/css/js)
核心知识点: 组件化的思想体现了"分治思想"
补充知识: 为了保证组件化 相互之间互不干扰,则应该在组件内部 单独定义html/js/css.
2.组件化入门案例
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<div id="app">
<!-- 如果需要使用组件,则在vue渲染区中央使用 -->
<!-- 规则:
1.在vue中使用标签时默认都是小写字母,如果需要引入驼峰命名规则,则使用-线代替
2.使用组件通过标签引用
-->
<add-num-com></add-num-com>
<add-num-com></add-num-com>
<add-num-com></add-num-com>
</div>
<!-- 定义模板标签语法 必须有根标签-->
<template id="numTem">
<div >
<h1>我是一个组件</h1>
获取数值:{{num}}
</div>
</template>
<!-- 1.导入js -->
<script src="../js/vue.js"></script>、
<!-- 2.定义全局组件 -->
<script>
/**
* 1.组件的定义
* 参数:
* 1.组件名称
* 2.组件实体内容
*/
//1.组件的定义
Vue.component("addNumCom",{
//属性
data(){
return{
//自定义属性
num:100
}
},
//页面标记
template:"#numTem"
})
// 实例化vue对象
const app = new Vue({
el:"#app"
})
</script>
</body>
</html>
3.局部组件
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>局部组件定义</title>
</head>
<body>
<div id="app">
<msg-com></msg-com>
<msg-com></msg-com>
</div>
<!-- 定义app2 局部组件只能在特定位置使用,
所以该位置 不能解析-->
<div id="app2">
<msg-com></msg-com>
<msg-com></msg-com>
</div>
<!-- 模板标签必须定义在vue渲染div外边 -->
<template id="msgTem">
<div>
<h3>我是一个局部组件</h3>
</div>
</template>
<script src="../js/vue.js"></script>
<script>
let msgCom = {
template: "#msgTem"
}
//定义局部组件 只对当前vue对象有效
const app = new Vue({
el: "#app",
components: {
//key: value
msgCom: msgCom
}
})
const app2 = new Vue({
el: "#app2",
})
</script>
</body>
</html>
4.关于组件面试题
1.为什么使用组件?
答:
- 原来用户编辑页面时,需要引入/维护大量的JS/CSS等。如果数量很多,则导致代码结构混乱,所以需要引入组件化思想
- 前端为了更好的解耦,采用了“分治”思想 构建代码 ,前端向后端的代码看齐,(微服务框架)
- 组件采用树形结构,可以将功能小型化,单独维护
- 组件是一个独立的个体,内部包含HTML/CSS/JS
- 使用组件看做就是一个页面
2.如何理解template属性
答:
1.template标签是组件中定义html标记的模板、
2.template必须有根标签div
3.template标签最好定义在body标签内部,写法方便、
使用注意事项:
1.组件的使用必须在vue对象渲染的区域中使用
2.组件有全局的/有局部的。注意事项
3.在html标签中使用组件时注意大小写问题,如果是驼峰规则,则使用“-”连接
4.组件必须先定义再使用
八.VUE路由介绍
1.路由介绍
说明: 用户发起一个请求,在互联网中经过多个站点的跳转.最终获取服务器端的数据. 把互联网中网络的链路称之为路由. (网络用语)
VUE中的路由: 根据用户的请求URL地址,展现特定的组件(页面)信息. (控制用户程序跳转过程)
2.入门案例
1.实现步骤
- 引入JS类库
- 指定路由跳转链接
- 指定路由填充位
- 封装路由对象
- vue对象绑定路由
2.路由入门案例实现
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>路由入门案例</title>
</head>
<body>
<template id="homeTem">
<div>
<h1>这里是系统首页</h1>
</div>
</template>
<template id="welcome">
<div>
<h2>这是欢迎页面</h2>
</div>
</template>
<div id="app">
<div>
<h1>实现路由案例</h1>
<!-- 2. 定义路由标签-->
<!-- 1.a标签说明:
a标签 超链接标签
href属性:请求跳转的地址
<a href="http://www.baidu.com">百度</a>
2.路由标签说明
router-link 解析为a标签
to解析之后变成href属性
-->
<router-link to="/home">主页</router-link>
<router-link to="/welcome">欢迎</router-link>
<!-- 3.指定路由填充位(占位符)
需要给组件一个展现的位置,需要提前定义
-->
<router-view></router-view>
</div>
</div>
<!-- 1.引入JS 路由需要依赖vue 注意顺序-->
<script src="../js/vue.js"></script>
<script src="../js/vue-router.js"></script>
<script type="text/javascript">
<!-- 4.封装路由对象 -->
let HomeCom = {
template: "#homeTem"
}
let Welcome = {
template: "#welcome"
}
let router = new VueRouter({
//routes 定义请求与组件的映射关系
routes:[
{path:"/home",component:HomeCom},
{path:"/welcome",component:Welcome}
]
})
// 5.实现路由对象的绑定
const app = new Vue({
el:"#app",
//router: router
router
})
</script>
</body>
</html>
3.路由嵌套机制(难点!!!)
1.编辑页面JS
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>路由嵌套</title>
</head>
<body>
<div id="app">
<h1>动物园</h1>
<router-link to="/tiger">老虎</router-link>
<router-link to="/lion">狮子</router-link>
<router-view></router-view>
</div>
<template id = "tigerTem">
<div>
<h1>一只凶猛的大猫</h1>
<img src="img/1.jpg" >
</div>
</template>
<template id = "lionTem">
<div>
<h1>狮子王辛巴</h1>
<img src="img/2.jpg" >
<h3>
<!-- 实现路由的嵌套机制 -->
<router-link to="/lion/one">原配</router-link>
<router-link to="/lion/two">小妾</router-link>
<!-- 子级应该在该区域展现数据 -->
<router-view></router-view>
</h3>
</div>
</template>
<template id="oneTem">
<div>
<h1>原配 老大</h1>
<img src="img/2.1.jpg" >
</div>
</template>
<template id="twoTem">
<div>
<h1>小妾 老二</h1>
<img src="img/2.3.jpg" >
</div>
</template>
<!-- 1.引入js 路由需要依赖vue 注意事项 -->
<script src="../js/vue.js" ></script>
<script src="../js/vue-router.js" ></script>
<script>
let tigerCom={
template:"#tigerTem"
}
let lionCom={
template:"#lionTem"
}
let oneCom = {
template:"#oneTem"
}
let twoCom = {
template:"#twoTem"
}
/**
* 1.如果需要在App根标签中跳转,则写到routes根目录下
* 2.如果需要进行父子嵌套,则应该使用children属性
* 3.如果使用children属性,则在自身的router-view展现数据
*
*/
let router = new VueRouter({
routes : [
{path:"/",redirect:"lion"},
{path: "/tiger" , component: tigerCom},
{path: "/lion",component: lionCom,
children : [
{path: "/lion/one",component:oneCom},
{path: "/lion/two",component:twoCom}
]},
]
})
const app = new Vue({
el:"#app",
router
})
</script>
</body>
</html>
2.页面效果展示
4.重定向/转发(web经典面试题)
1.转发说明
说明:用户请求服务器时:由服务器将请求转给另一台服务器的过程.叫做转发
2.重定向说明
说明: 用户请求服务器时,服务器由于特殊原因告知用户应该访问服务器B,之后用户再次发起请求访问服务器B. 这个过程称之为重定向
3.vue中的重定向
VUE中使用redirect实现重定向效果.