JavaWeb学习记录:Vue+Ajax速成

Vue介绍 

概述

Vue是一款用于构建用户界面渐进式的JavaScript框架(官方网站:https://cn.vuejs.org)。

1).构建用户界面

构建用户界面是指,在Vue中,可以基于数据渲染出用户看到的界面。 那这句话什么意思呢?我们来举一个例子,比如将来服务器端返回给前端的原始数据呢,就是如下这个样子:

userList: [
    {"id": 1, "name": "谢逊", "image": "1.jpg", "gender": 1, "job": "班主任"},
    {"id": 2, "name": "韦一笑", "image": "2.jpg", "gender": 1, "job": "班主任"}
]

而上面的这些原始数据,用户是看不懂的。 而我们开发人员呢,可以使用Vue中提供的操作,将原始数据遍历、解析出来,从而渲染呈现出用户所能看懂的界面,如下所示:

那这个过程呢,就是基于数据渲染出用户看到的界面,也就是所谓的 构建用户界面。

2). 渐进式

渐进式中的渐进呢,字面意思就是 "循序渐进"。Vue生态中的语法呢是非常多的,比如声明式渲染、组件系统、客户端路由(VueRouter)、状态管理(Vuex、Pinia)、构建工具(Webpack、Vite)等等。

所谓渐进,指的是我们使用Vue框架呢,我们不需要把所有的组件、语法全部学习完毕才可以使用Vue。 而是,我们学习一点就可以使用一点了,比如:

  • 我们学习了声明式渲染,我们就可以使用Vue来构建用户界面了。

  • 我们再学习了组件系统,我们就可以使用Vue中的组件,从而来复用了。

  • 我们再学习了路由VueRouter,就可以使用Vue中的中的路由功能了。

也就是说,并不需要全部学习完毕就可以直接使用Vue进行开发,简化操作、提高效率了。 Vue是一个框架,但其实也是一个生态。

那由此呢,也就引出了Vue中两种常见的开发模式:

  • 基于Vue提供的核心包,完成项目局部模块的改造了。

  • 基于Vue提供的核心包、插件进行工程化开发,也就是做整站开发。

那上面的这两种Vue的使用形式,我们都会学习,今天我们先来学习第一种方式,就是使用Vue来完成局部模块改造。

 入门程序

1). 准备工作:

  • 准备一个html文件,并在其中引入Vue模块 (参考官方文档,复制过来即可)【注意:模块化的js,引入时,需要设置 type="module"

  • 创建Vue程序的应用实例,控制视图的元素

  • 准备元素(div),交给Vue控制

2). 数据驱动视图:

  • 准备数据。 在创建Vue应用实例的时候,传入了一个js对象,在这个js对象中,我们要定义一个data方法,这个data方法的返回值就是Vue中的数据。

  • 通过插值表达式渲染页面。 插值表达式的写法:{{...}}

3).示例
 

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>VUE-快速入门</title>
</head>
<body>
    <div id="app">
        <h1>{{message}}</h1>
        <h1>{{count}}</h1>
    </div>

    <script type="module">
        import { createApp } from 'https://unpkg.com/vue@3/dist/vue.esm-browser.js';

        createApp({
            data(){//js对象
                return{
                    message: 'Hello VUE',
                    count: 100
                }
            }

        }).mount('#app');
    </script>
</body>
</html>

 

在上述入门程序编写时,需要注意这么几点:

  • Vue中定义数据,必须通过data方法来定义,data方法返回值是一个对象,在这个对象中定义数据。

  • 插值表达式中编写的变量,一定是Vue中定义的数据,如果插值表达式中编写了一个变量,但是在Vue中未定义,将会报错 。

  • Vue应用实例接管的区域是 '#app',超出这个范围,就不受Vue控制了,所以vue的插值表达式,一定写在 <div id="app">...</div> 的里面 。

Vue指令 

概述 

指令:指的是HTML 标签上带有 v- 前缀的特殊属性,不同指令具有不同含义,可以实现不同的功能 。例如:v-if,v-for…

形式:

<p v-xxx="....">.....</p>

常见指令:

指令作用
v-for列表渲染,遍历容器的元素或者对象的属性
v-bind为HTML标签绑定属性值,如设置 href , css样式等
v-if/v-else-if/v-else条件性的渲染某元素,判定为true时渲染,否则不渲染
v-show根据条件展示某元素,区别在于切换的是display属性的值
v-model在表单元素上创建双向数据绑定
v-on为HTML标签绑定事件

指令详解 

 v-for

作用:列表渲染,遍历容器的元素或者对象的属性

语法:<tr v-for="(item,index) in items" :key="item.id">{{item}}</tr>

参数:

  • items 为遍历的数组

  • item 为遍历出来的元素

  • index 为索引/下标,从0开始 ;可以省略,省略index语法: v-for = "item in items"

key:

  • 作用:给元素添加的唯一标识,便于vue进行列表项的正确排序复用,提升渲染性能

  • 推荐使用id作为key(唯一),不推荐使用index作为key(会变化,不对应)

注意:遍历的数组,必须在data中定义; 要想让哪个标签循环展示多次,就在哪个标签上使用 v-for 指令。

示例:(代码不全,感兴趣可以翻到最后看完整代码)

<div class="table-area" id="container">
      <table class="data-table">
        <thead>
          <tr>
            <th>id</th>
            <th>头像</th>
            <th>姓名</th>
            <th>性别</th>
            <th>职位</th>
            <th>入职日期</th>
            <th>最后操作时间</th>
            <th>操作</th>
          </tr>
        </thead>
        <tbody>
          <tr v-for="(e, index) in empList" :key="e.id">
            <td>{{e.id}}</td>
            <td><img v-bind:src="e.image" :alt="e.name" class="avatar"></td>
            <td>{{e.name}}</td>
            <td>{{e.gender == 1 ? '男': '女'}}</td>
            <td>{{e.job}}</td>
            <td>{{e.entrydate}}</td>
            <td>{{e.updatetime}}</td>
            <td>
              <button class="action-btn edit-btn">编辑</button>
              <button class="action-btn delete-btn">删除</button>
            </td>
          </tr>
         
        </tbody>
      </table>
    </div>

<script type="module">
      import { createApp } from 'https://unpkg.com/vue@3/dist/vue.esm-browser.js'
      createApp({
        data() {
          return {
            searchOb: {
              name: '',
              gender: '',
              job: '',
            },
            empList: [
              { "id": 1,
                "name": "谢逊",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/4.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2023-06-09",
                "updatetime": "2024-07-30T14:59:38"
              },
              {
                "id": 2,
                "name": "韦一笑",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/1.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2020-05-09",
                "updatetime": "2023-07-01T00:00:00"
              },
              {
                "id": 3,
                "name": "黛绮丝",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/2.jpg",
                "gender": 2,
                "job": "2",
                "entrydate": "2021-06-01",
                "updatetime": "2023-07-01T00:00:00"
              }
            ]
          }
        }
      }).mount('#container')
    </script>

代码并不完整,仅作为例子展示。此处遍历的数组为: empList (已在data中定义)

 

v-bind

作用:动态为HTML标签绑定属性值,如设置href,src,style样式等。

语法:v-bind:属性名="属性值" <img v-bind:src="item.image" width="30px">

简化::属性名="属性值" <img :src="item.image" width="30px">

注意:v-bind 所绑定的数据,必须在data中定义/或基于data中定义的数据而来。

如果有观察过上述代码,会发现表格中显示头像的标签已经使用了v-bind。若不使用,图片将不能正常显示,因为标签内部无法直接使用插值表达式{{}}

v-if & v-show

作用:这两类指令,都是用来控制元素的显示与隐藏的

v-if:

  • 语法:v-if="表达式",表达式值为 true,显示;false,隐藏

  • 原理:基于条件判断,来控制创建或移除元素节点(条件渲染)

  • 场景:要么显示,要么不显示,不频繁切换的场景

  • 其它:可以配合 v-else-if / v-else 进行链式调用条件判断

注意:v-else-if必须出现在v-if之后,可以出现多个; v-else 必须出现在v-if/v-else-if之后 。

通过浏览器的开发者工具,我们可以看到如果使用 v-if 指令来渲染展示,确实是根据条件判断,是否渲染这个元素节点,条件成立才会渲染。

示例:(代码不全,感兴趣可以翻到最后看完整代码)

上述例子的职位部分是用数字12345代替的,这块内容可以使用v-if来条件判断选择展示职位

代码如下:

<!-- v-if 控制元素的显示与隐藏 -->
            <td>
              <span v-if="e.job==1">班主任</span>
              <span v-else-if="e.job==2">讲师</span>
              <span v-else-if="e.job==3">学工主管</span>
              <span v-else-if="e.job==4">教研主管</span>
              <span v-else-if="e.job==5">咨询师</span>
              <span v-else>其他</span>
            </td>

 

v-show:

  • 语法:v-show="表达式",表达式值为 true,显示;false,隐藏

  • 原理:基于CSS样式display来控制显示与隐藏

  • 场景:频繁切换显示隐藏的场景

通过浏览器的开发者工具,我们可以看到如果使用 v-show 指令来渲染展示,所有元素都会渲染,只不过是通过控制display这个css样式,来决定元素是展示还是隐藏。

示例:(代码不全,感兴趣可以翻到最后看完整代码)

依旧是拿职位举例子 :

<!-- v-show 控制元素的显示与隐藏 -->
            <td>
              <span v-show="e.job==1">班主任</span>
              <span v-show="e.job==2">讲师</span>
              <span v-show="e.job==3">学工主管</span>
              <span v-show="e.job==4">校验主管</span>
              <span v-show="e.job==5">咨询师</span>
            </td>

 值得注意的是,v-if和v-show都是用来控制元素的显示与隐藏的,区别在于:v-if只有条件成立才会渲染和展示该元素,而v-show会渲染所有的元素,然后根据需要来展示和隐藏元素。

v-model

  • 作用:在表单元素上使用,双向数据绑定。可以方便的 获取设置 表单项数据

  • 语法:v-model="变量名"

  • 这里的双向数据绑定,是指 Vue中的数据变化,会影响视图中的数据展示 。 视图中的输入的数据变化,也会影响Vue的数据模型 。

 注意:v-model 中绑定的变量,必须在data中定义。

示例:(代码不全,感兴趣可以翻到最后看完整代码)

<!-- 搜索区域 - 保持原始代码 -->
    <div class="search-area">
      <form id="searchForm" class="search-form">
        <!-- 姓名 -->
        <div>
          <label for="name">姓名</label>
          <input type="text" id="name" name="name" v-model="searchOb.name">
        </div>

        <!-- 性别 -->
        <div>
          <label for="gender">性别</label>
          <select id="gender" name="gender" v-model="searchOb.gender">
            <option value="">全部</option>
            <option value="1">男</option>
            <option value="2">女</option>
          </select>
        </div>

        <!-- 职位 -->
        <div>
          <label for="position">职位</label>
          <select id="position" name="position" v-model="searchOb.job">
            <option value="">全部</option>
            <option value="1">班主任</option>
            <option value="2">讲师</option>
            <option value="3">学工主管</option>
            <option value="4">教研主管</option>
            <option value="5">咨询师</option>
          </select>
        </div>

<script type="module">
      import { createApp } from 'https://unpkg.com/vue@3/dist/vue.esm-browser.js'
      createApp({
        data() {
          return {
            searchOb: {
              name: '',
              gender: '',
              job: '',
            },
            empList: [
              { "id": 1,
                "name": "谢逊",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/4.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2023-06-09",
                "updatetime": "2024-07-30T14:59:38"
              },
              {
                "id": 2,
                "name": "韦一笑",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/1.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2020-05-09",
                "updatetime": "2023-07-01T00:00:00"
              },
              {
                "id": 3,
                "name": "黛绮丝",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/2.jpg",
                "gender": 2,
                "job": "2",
                "entrydate": "2021-06-01",
                "updatetime": "2023-07-01T00:00:00"
              }
            ]
          }
        }
        
      }).mount('#container')
    </script>

绑定的变量是data中定义的searchOb(自定义对象) 

 双向数据绑定之后,在页面改变数据,会改变所绑定的Vue的data中的数据;而Vue中的数据变化,也会影响页面中的数据展示

v-on

作用:为html标签绑定事件(添加时间监听)

语法:

  • v-on:事件名="方法名"

  • 简写为 @事件名="…"

  • <input type="button" value="点我一下试试" v-on:click="handle">

  • <input type="button" value="点我一下试试" @click="handle">

这里的handle函数,就需要在Vue应用实例创建的时候创建出来,在methods定义。

注意: methods函数中的this指向Vue实例,可以通过this获取到data中定义的数据。 

 示例:(代码不全,感兴趣可以翻到最后看完整代码)

<!-- 按钮区域 -->
        <div class="button-group">

          <button type="button" class="search-button" v-on:click="search">
            查询
          </button>
          <button type="button" id="resetBtn" class="reset-button" @click="clear">
            清空
          </button>
          
        </div>


<script type="module">
      import { createApp } from 'https://unpkg.com/vue@3/dist/vue.esm-browser.js'
      createApp({
        data() {
          return {
            searchOb: {
              name: '',
              gender: '',
              job: '',
            },
            empList: [
              { "id": 1,
                "name": "谢逊",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/4.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2023-06-09",
                "updatetime": "2024-07-30T14:59:38"
              },
              {
                "id": 2,
                "name": "韦一笑",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/1.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2020-05-09",
                "updatetime": "2023-07-01T00:00:00"
              },
              {
                "id": 3,
                "name": "黛绮丝",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/2.jpg",
                "gender": 2,
                "job": "2",
                "entrydate": "2021-06-01",
                "updatetime": "2023-07-01T00:00:00"
              }
            ]
          }
        },
        methods:{
          
          search(){
            //将搜索框的内容输出到控制台
            console.log(this.searchOb);
          },
          clear(){
            //将搜索框的内容清空(清空searchOb即可,因为绑定了)
            this.searchOb = {name:'',gender:'',job:''}
          }
        },
      }).mount('#container')
    </script>

查询按钮绑定了单击后出发search函数,清空按钮绑定了点击后出发clear函数

 完整代码:

<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>tlias智能学习辅助系统</title>
  <style>
    /* 顶部导航栏样式 - 保持原始代码 */
    .top-nav {
      background-color: gray;
      display: flex;
      justify-content: space-between;
      align-items: center;
      padding: 10px;
    }

    .top-nav h1 {
      margin: 0;
      color: white; 
      font-family: "KaiTi", serif; 
    }

    .top-nav a {
      color: white; 
      text-decoration: none; 
    }

    /* 主要内容区域样式 */
    .main-content {
      min-height: calc(100vh - 120px); /* 减去导航栏和版权区域高度 */
      display: flex;
      flex-direction: column;
      max-width: 1200px;
      margin: 0 auto;
      padding: 20px;
    }

    /* 搜索区域样式 */
    .search-area {
      padding: 20px;
      border: 1px solid #ddd;
      border-radius: 5px;
      background-color: white;
      margin-bottom: 30px;
    }

    .search-form {
      display: flex;
      flex-wrap: wrap;
      gap: 15px;
    }

    .search-form div {
      flex: 1;
      min-width: 180px;
    }

    .search-form label {
      display: block;
      margin-bottom: 5px;
      font-weight: bold;
    }

    .search-form input,
    .search-form select {
      width: 100%;
      padding: 8px;
      border: 1px solid #ccc;
      border-radius: 4px;
      box-sizing: border-box;
    }

    .button-group {
      display: flex;
      align-items: flex-end;
      gap: 10px;
    }

    .button-group button {
      padding: 8px 15px;
      border: none;
      border-radius: 4px;
      cursor: pointer;
    }

    .reset-button {
      background-color: #f1f1f1;
      color: black;
    }

    .search-button {
      background-color: #4CAF50;
      color: white;
    }

    .reset-button:hover {
      background-color: #ddd;
    }

    .search-button:hover {
      background-color: #45a049;
    }

    /* 表格区域样式 */
    .table-area {
      overflow-x: auto;
      background-color: white;
      border-radius: 5px;
      box-shadow: 0 2px 5px rgba(0,0,0,0.1);
      padding: 20px;
      margin-bottom: 30px;
    }

    .data-table {
      width: 100%;
      border-collapse: collapse;
    }

    .data-table th, .data-table td {
      padding: 10px;
      border: 1px solid #ddd;
      text-align: left;
    }

    .data-table th {
      background-color: #f2f2f2;
      font-weight: bold;
    }

    .data-table tr:nth-child(even) {
      background-color: #f9f9f9;
    }

    .data-table tr:hover {
      background-color: #f5f5f5;
    }

    .avatar {
      width: 32px;
      height: 32px;
      border-radius: 50%;
      object-fit: cover;
    }

    .action-btn {
      padding: 5px 10px;
      margin-right: 5px;
      border: none;
      border-radius: 3px;
      cursor: pointer;
      text-decoration: none;
      display: inline-block;
      font-size: 14px;
    }

    .edit-btn {
      background-color: #2196F3;
      color: white;
    }

    .delete-btn {
      background-color: #f44336;
      color: white;
    }

    .edit-btn:hover {
      background-color: #0b7dda;
    }

    .delete-btn:hover {
      background-color: #da190b;
    }

    /* 版权区域样式 */
    .copyright-area {
      background-color: #f8f8f8;
      border-top: 1px solid #e7e7e7;
      padding: 20px;
      text-align: center;
      font-size: 14px;
      color: #666;
    }

    .company-name {
      font-weight: bold;
      margin-bottom: 5px;
    }
  </style>
</head>
<body>
<div id="container">
  <!-- 顶部导航栏 - 保持原始代码 -->
  <div class="top-nav">
    <h1>tlias智能学习辅助系统</h1>
    <a href="#">退出登录</a>
  </div>

  <!-- 主要内容区域 -->
  <div class="main-content">
    <!-- 搜索区域 - 保持原始代码 -->
    <div class="search-area">
      <form id="searchForm" class="search-form">
        <!-- 姓名 -->
        <div>
          <label for="name">姓名</label>
          <input type="text" id="name" name="name" v-model="searchOb.name">
        </div>

        <!-- 性别 -->
        <div>
          <label for="gender">性别</label>
          <select id="gender" name="gender" v-model="searchOb.gender">
            <option value="">全部</option>
            <option value="1">男</option>
            <option value="2">女</option>
          </select>
        </div>

        <!-- 职位 -->
        <div>
          <label for="position">职位</label>
          <select id="position" name="position" v-model="searchOb.job">
            <option value="">全部</option>
            <option value="1">班主任</option>
            <option value="2">讲师</option>
            <option value="3">学工主管</option>
            <option value="4">教研主管</option>
            <option value="5">咨询师</option>
          </select>
        </div>

        <!-- 按钮区域 -->
        <div class="button-group">

          <button type="button" class="search-button" v-on:click="search">
            查询
          </button>
          <button type="button" id="resetBtn" class="reset-button" @click="clear">
            清空
          </button>
          
        </div>
      </form>
    </div>

    <!-- 表格展示区 - 保持原始代码 -->
    <div class="table-area">
      <table class="data-table">
        <thead>
          <tr>
            <th>id</th>
            <th>头像</th>
            <th>姓名</th>
            <th>性别</th>
            <th>职位</th>
            <th>入职日期</th>
            <th>最后操作时间</th>
            <th>操作</th>
          </tr>
        </thead>
        <tbody>
          <tr v-for="(e, index) in empList" :key="e.id">
            <td>{{e.id}}</td>
            <td><img v-bind:src="e.image" :alt="e.name" class="avatar"></td>
            <td>{{e.name}}</td>
            <td>{{e.gender == 1 ? '男': '女'}}</td>
            <!-- v-if 控制元素的显示与隐藏 -->
            <td>
              <span v-if="e.job==1">班主任</span>
              <span v-else-if="e.job==2">讲师</span>
              <span v-else-if="e.job==3">学工主管</span>
              <span v-else-if="e.job==4">教研主管</span>
              <span v-else-if="e.job==5">咨询师</span>
              <span v-else>其他</span>
            </td>

            <!-- v-show 控制元素的显示与隐藏 -->
            <!-- <td>
              <span v-show="e.job==1">班主任</span>
              <span v-show="e.job==2">讲师</span>
              <span v-show="e.job==3">学工主管</span>
              <span v-show="e.job==4">校验主管</span>
              <span v-show="e.job==5">咨询师</span>
            </td> -->
            
            <td>{{e.entrydate}}</td>
            <td>{{e.updatetime}}</td>
            <td>
              <button class="action-btn edit-btn">编辑</button>
              <button class="action-btn delete-btn">删除</button>
            </td>
          </tr>
         
        </tbody>
      </table>
    </div>
  </div>

  <!-- 版权展示区域 -->
  <div class="copyright-area">
    <div class="company-name">北京泰立亚教育科技有限公司</div>
    <div>© 2025 tlias智能学习辅助系统 版权所有</div>
  </div>
</div>
  <script type="module">
      import { createApp } from 'https://unpkg.com/vue@3/dist/vue.esm-browser.js'
      createApp({
        data() {
          return {
            searchOb: {
              name: '',
              gender: '',
              job: '',
            },
            empList: [
              { "id": 1,
                "name": "谢逊",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/4.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2023-06-09",
                "updatetime": "2024-07-30T14:59:38"
              },
              {
                "id": 2,
                "name": "韦一笑",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/1.jpg",
                "gender": 1,
                "job": "1",
                "entrydate": "2020-05-09",
                "updatetime": "2023-07-01T00:00:00"
              },
              {
                "id": 3,
                "name": "黛绮丝",
                "image": "https://web-framework.oss-cn-hangzhou.aliyuncs.com/2023/2.jpg",
                "gender": 2,
                "job": "2",
                "entrydate": "2021-06-01",
                "updatetime": "2023-07-01T00:00:00"
              }
            ]
          }
        },
        methods:{
          
          search(){
            //将搜索框的内容输出到控制台
            console.log(this.searchOb);
          },
          clear(){
            //将搜索框的内容清空(清空searchOb即可,因为绑定了)
            this.searchOb = {name:'',gender:'',job:''}
          }
        },
      }).mount('#container')
    </script>
</body>
</html>

 

Ajax

 概述

Ajax: 全称Asynchronous JavaScript And XML,异步的JavaScript和XML。其作用有如下2点:

  • 与服务器进行数据交换:通过Ajax可以给服务器发送请求,并获取服务器响应的数据。

  • 异步交互:可以在不重新加载整个页面的情况下,与服务器交换数据并更新部分网页的技术,如:搜索联想、用户名是否可用的校验等等。

同步异步

  • 同步请求发送过程如下图所示:

浏览器页面在发送请求给服务器,在服务器处理请求的过程中,浏览器页面不能做其他的操作。只能等到服务器响应结束后才能,浏览器页面才能继续做其他的操作。

  • 异步请求发送过程如下图所示:

 浏览器页面发送请求给服务器,在服务器处理请求的过程中,浏览器页面还可以做其他的操作。

Axios

使用原生的Ajax请求的代码编写起来还是比较繁琐的,所以接下来我们学习一门更加简单的发送Ajax请求的技术Axios 。Axios是对原生的AJAX进行封装,简化书写。Axios官网是:https://www.axios-http.cn 

 入门程序

Axios的使用比较简单,主要分为2步:

1). 引入Axios文件(如果网络不通畅,可以使用离线的已经下载好的js文件)

<script src="https://unpkg.com/axios/dist/axios.min.js"></script>

2). 点击按钮时,使用Axios发送请求

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Axios入门程序</title>
</head>
<body>

  <button id="getData">GET</button>
  <button id="postData">POST</button>
  
  <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
  <script>
    //GET请求
    document.querySelector('#getData').onclick = function() {
      axios({
        url:'https://mock.apifox.cn/m1/3083103-0-default/emps/list',
        method:'get'
      }).then(function(res) {
        console.log(res.data);
      }).catch(function(err) {
        console.log(err);
      })
    }
    
    //POST请求
    document.querySelector('#postData').onclick = function() {
      axios({
        url:'https://mock.apifox.cn/m1/3083103-0-default/emps/update',
        method:'post'
      }).then(function(res) {
        console.log(res.data);
      }).catch(function(err) {
        console.log(err);
      })
    }
  </script>
</body>
</html>

在使用axios时,在axios之后,输入 thenc (简写)会自动生成成功及失败回调函数结构 

 请求方法别名

Axios还针对不同的请求,提供了别名方式的api,具体格式如下:

axios.请求方式(url [, data [, config]])

具体如下:

方法描述
axios.get(url [, config])发送get请求
axios.delete(url [, config])发送delete请求
axios.post(url [, data[, config]])发送post请求
axios.put(url [, data[, config]])发送put请求

我们目前只关注get和post请求,所以在上述的入门案例中,我们可以将get请求代码改写成如下:

axios.get("https://mock.apifox.cn/m1/3083103-0-default/emps/list").then(result => {
    console.log(result.data);
})

post请求改写成如下:

axios.post("https://mock.apifox.cn/m1/3083103-0-default/emps/update","id=1").then(result => {
    console.log(result.data);
})

案例-异步获取数据

需求:基于axios动态加载员工列表数据

具体代码实现如下:

<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Tlias智能学习辅助系统</title>
    <style>
      body {
        margin: 0;
      }

      /* 顶栏样式 */
      .header {
        display: flex;
        justify-content: space-between;
        align-items: center;
        background-color: #c2c0c0;
        padding: 20px 20px;
        box-shadow: 0 2px 5px rgba(0,0,0,0.1);
      }
      
      /* 加大加粗标题 */
      .header h1 {
        margin: 0;
        font-size: 24px;
        font-weight: bold;
      }

      /* 文本链接样式 */
      .header a {
        text-decoration: none;
        color: #333;
        font-size: 16px;
      }

      /* 搜索表单区域 */
      .search-form {
        display: flex;
        align-items: center;
        padding: 20px;
        background-color: #f9f9f9;
      }

      /* 表单控件样式 */
      .search-form input[type="text"], .search-form select {
        margin-right: 10px;
        padding: 10px 10px;
        border: 1px solid #ccc;
        border-radius: 4px;
        width: 26%;
      }

      /* 按钮样式 */
      .search-form button {
        padding: 10px 15px;
        margin-left: 10px;
        background-color: #007bff;
        color: white;
        border: none;
        border-radius: 4px;
        cursor: pointer;
      }

      /* 清空按钮样式 */
      .search-form button.clear {
        background-color: #6c757d;
      }

      .table {
         min-width: 100%; 
         border-collapse: collapse;
      }

      /* 设置表格单元格边框 */
      .table td, .table th { 
        border: 1px solid #ddd; 
        padding: 8px; 
        text-align: center;
      }
      
      .avatar { 
        width: 30px; 
        height: 30px; 
        object-fit: cover; 
        border-radius: 50%; 
      }

      /* 页脚版权区域 */
    .footer {
        background-color: #c2c0c0;
        color: white;
        text-align: center;
        padding: 10px 0;
        margin-top: 30px;
    }

    .footer .company-name {
        font-size: 1.1em;
        font-weight: bold;
    }

    .footer .copyright {
        font-size: 0.9em;
    }

    #container {
      width: 80%;
      margin: 0 auto;
    }
    </style>
</head>
<body>
    
  <div id="container">
    <!-- 顶栏 -->
    <div class="header">
      <h1>Tlias智能学习辅助系统</h1>
      <a href="#">退出登录</a>
    </div>
    
    <!-- 搜索表单区域 -->
    <form class="search-form">
      <input type="text" name="name" placeholder="姓名" v-model="searchForm.name" />
      <select name="gender" v-model="searchForm.gender">
          <option value="">性别</option>
          <option value="1">男</option>
          <option value="2">女</option>
      </select>
      <select name="job" v-model="searchForm.job">
          <option value="">职位</option>
          <option value="1">班主任</option>
          <option value="2">讲师</option>
          <option value="3">学工主管</option>
          <option value="4">教研主管</option>
          <option value="5">咨询师</option>
      </select>
      <button type="button" @click="search">查询</button>
      <button type="button" @click="clear">清空</button>
    </form>

    <table class="table table-striped table-bordered">
      <thead>
          <tr>
              <th>姓名</th>
              <th>性别</th>
              <th>头像</th>
              <th>职位</th>
              <th>入职日期</th>
              <th>最后操作时间</th>
              <th>操作</th>
          </tr>
      </thead>
      <tbody>
        <tr v-for="(emp, index) in empList" :key="index">
          <td>{{ emp.name }}</td>
          <td>{{ emp.gender === 1 ? '男' : '女' }}</td>
          <td><img :src="emp.image" alt="{{ emp.name }}" class="avatar"></td>
          
           <!-- 基于v-if/v-else-if/v-else指令来展示职位这一列 -->
          <td>
            <span v-if="emp.job == '1'">班主任</span>
            <span v-else-if="emp.job == '2'">讲师</span>
            <span v-else-if="emp.job == '3'">学工主管</span>
            <span v-else-if="emp.job == '4'">教研主管</span>
            <span v-else-if="emp.job == '5'">咨询师</span>
            <span v-else>其他</span>
          </td>

          <!-- 基于v-show指令来展示职位这一列 -->
          <!-- <td>
            <span v-show="emp.job === '1'">班主任</span>
            <span v-show="emp.job === '2'">讲师</span>
            <span v-show="emp.job === '3'">学工主管</span>
            <span v-show="emp.job === '4'">教研主管</span>
            <span v-show="emp.job === '5'">咨询师</span>
         </td> -->

          <td>{{ emp.entrydate }}</td>
          <td>{{ emp.updatetime }}</td>
          <td class="btn-group">
            <button class="edit">编辑</button>
            <button class="delete">删除</button>
          </td>
        </tr>
      </tbody>
    </table>

    <!-- 页脚版权区域 -->
    <footer class="footer">
      <p class="company-name">江苏传智播客教育科技股份有限公司</p>
      <p class="copyright">版权所有 Copyright 2006-2024 All Rights Reserved</p>
    </footer>

    <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
    <script type="module">
      import { createApp } from 'https://unpkg.com/vue@3/dist/vue.esm-browser.js'
      createApp({
        data() {
          return {
            searchForm: {
              name: '',
              gender: '',
              job: ''
            },
            empList: []
          }
        },
        methods: {
          search() {
            //基于axios发送异步请求,请求https://web-server.itheima.net/emps/list,根据条件查询员工列表
            axios.get(`https://web-server.itheima.net/emps/list?name=${this.searchForm.name}&gender=${this.searchForm.gender}&job=${this.searchForm.job}`).then(res => {
              this.empList = res.data.data
            })
          },
          clear() {
            this.searchForm= {
              name: '',
              gender: '',
              job: ''
            }
          }
        }
      }).mount('#container')
    </script>

  </div>

</body>
</html>

如果使用axios中提供的.then(function(){....}).catch(function(){....}),这种回调函数的写法,会使得代码的可读性和维护性变差。 而为了解决这个问题,我们可以使用两个关键字,分别是:async、await

可以通过async、await可以让异步变为同步操作。async就是来声明一个异步方法,await是用来等待异步任务执行。

代码修改前: 

search() {
    //基于axios发送异步请求,请求https://web-server.itheima.net/emps/list,根据条件查询员工列表
    axios.get(`https://web-server.itheima.net/emps/list?name=${this.searchForm.name}&gender=${this.searchForm.gender}&job=${this.searchForm.job}`).then(res => {
      this.empList = res.data.data
    })
  },

代码修改后: 

  async search() {
    //基于axios发送异步请求,请求https://web-server.itheima.net/emps/list,根据条件查询员工列表
    const result = await axios.get(`https://web-server.itheima.net/emps/list?name=${this.searchForm.name}&gender=${this.searchForm.gender}&job=${this.searchForm.job}`);
    this.empList = result.data.data;
  },

修改后,代码就变成同步操作了,一行一行的从前往后执行。 在前端项目开发中,经常使用这两个关键字配合,使得代码的可读性和可维护性变高。 

Vue生命周期

介绍

vue的生命周期:指的是vue对象从创建到销毁的过程。

vue的生命周期包含8个阶段:每触发一个生命周期事件,会自动执行一个生命周期方法,这些生命周期方法也被称为钩子方法。其完整的生命周期如下图所示:

状态阶段周期
beforeCreate创建前
created创建后
beforeMount挂载前
mounted挂载完成
beforeUpdate更新前
updated更新后
beforeDestroy销毁前
destroyed销毁后

下图是 Vue 官网提供的从创建 Vue 到效果 Vue 对象的整个过程及各个阶段对应的钩子函数:

 

其中我们需要重点关注的是mounted,其他的我们了解即可。

mounted:挂载完成,Vue初始化成功,HTML页面渲染成功。以后我们一般用于页面初始化自动的ajax请求后台数据

案例完善 

 如果要想在页面加载完毕后,就查询并展示出员工列表,我们可以在mounted钩子函数中,发送异步请求查询员工数据

    methods: {
      async search() {
        //基于axios发送异步请求,请求https://web-server.itheima.net/emps/list,根据条件查询员工列表
        const result = await axios.get(`https://web-server.itheima.net/emps/list?name=${this.searchForm.name}&gender=${this.searchForm.gender}&job=${this.searchForm.job}`);
        this.empList = result.data.data;
      },
      clear() {
        this.searchForm= {
          name: '',
          gender: '',
          job: ''
        }
        this.search();
      }
    },
    mounted() {
      this.search();
    }
  }).mount('#container')

 到此,员工列表查询的功能我们就已经完成了。

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值