第1关:Vue3 Ajax(axios)请求

任务描述

本关任务:编写一个能从指定 API 获取笑话的程序。

相关知识

为了完成本关任务,你需要掌握:

  1. Vue 与 Ajax;

  2. axios 请求的特点;

  3. 安装 Axios;

  4. 创建实例的方法;

  5. axios 实例方法;

  6. 具体代码演示;

  7. 实现跨域请求。

Vue 与 Ajax

Vue 本身是不支持发送 ajax 请求,需要通过其他库来实现的(比如 vue1.0 版本官方推荐的 vue-resource、vue2.0 版本官方推荐的 axios),或者也可以使用 jquery 来发送 ajax 请求。

vue-resource 是 Vue.js 的插件提供了使用 XMLHttpRequest 或 JSONP 进行 Web 请求和处理响应的服务。 当 vue 更新 到 2.0 之后,作者就宣告不再对 vue-resource 更新,而是推荐的 axios,所以建议大家了解一下 vue-resource 就可以。 vue-resource 的 github https://github.com/pagekit/vue-resource。

Axios 是一个基于 promise 的 HTTP 库,可以用在浏览器和 node.js 中 axios 的 github:https://github.com/axios/axios。

axios 请求的特点
  1. 支持 node 端和浏览器端: 同样的 API,node 和浏览器全支持,平台切换无压力;

  2. 支持使用 Promise 管理异步,告别传统 callback 方式;

  3. 丰富的配置项: 支持请求和响应的拦截, 提前处理请求和响应数据。

安装 Axios
  1. 使用 cdn:

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

或

<script src="https://cdn.staticfile.org/axios/0.18.0/axios.min.js"></script>

  1. 使用 npm: npm install axios

  2. 直接导入 js 文件

这里我选择去 github,搜索 axios:


官方文档下有非常详细的 API,这里我们就通过直接引入的方式来使用,也就是方法三

创建实例的方法

首先我们来看一个简单的案例:

 
  1. // 使用axios
  2. axios({
  3. url:"https://api.github.com/users"
  4. }).then(result => {
  5. console.log(result);
  6. })

示例中,我们并没有请求类型,axios 默认请求为 get 请求。

如果希望发送 post 等其他方式的 请求, 可以在配置对象中添加 method 选项

例如:

 
  1. // 使用post发送请求
  2. axios({
  3. url:"https://jsonplaceholder.typicode.com/posts",
  4. method: "post"
  5. }).then(result => {
  6. console.log(result);
  7. })
axios 实例方法
方法作用
axios(config)config 是对一些基本信息的配置,比如请求头,baseURL。
axios.request(config)用于发送请求,默认为 GET 。
axios.get(url[, config])用于发送 GET 请求,一般用于查询数据。
axios.delete(url[, config])发送一个 DELETE 请求,一般用于删除数据。
axios.head(url[, config])用于添加请求头部信息。
axios.options(url[, config])在正式跨域之前,浏览器会根据需要发起一次预检(也就是 option 请求),用来让服务端返回允许的方法,被跨域访问的 Origin,还有是否需要认证信息等。
axios.post(url[, data[, config]])发送一个 POST 请求,一般用于新增数据。data 是作为请求主体被发送的数据,对应后台中的 body。
axios.put(url[, data[, config]])发送一个 PUT 请求,一般用于修改数据。
axios.patch(url[, data[, config]]第一个参数是请求将发送到的 url,第二个参数是您将发送更改的数据。

上面基本的示例中,我们是在 axios() 请求的配置对象中配置请求方式,axios 也提供了通过不同的方式发送请求。

指定了请求方式发送请求说明:

  1. 第一个参数将是发送的 url;

  2. 第二个参数是请求的配置对象,可以省略,使用默认配置。

具体代码演示
get 请求

首先我们写一个 html 代码,按照上面创建 get 实例的方法内容如下:

 
  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <script src="https://cdn.staticfile.org/vue/2.2.2/vue.min.js"></script>
  6. <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
  7. <title>发送get请求</title>
  8. <script>
  9. window.onload=function(){
  10. new Vue({
  11. el:'#app',
  12. data:{
  13. users:{
  14. name:'',
  15. age:''
  16. }
  17. },
  18. methods:{
  19. //axios.get的发送参数有两种,两个ajax请求函数都可实现
  20. sendGetByStr(){
  21. //1.get通过直接发字符串拼接
  22. axios.get(`get.php?name=${this.users.name}&age=${this.users.age}`)
  23. .then(function (response) {
  24. console.log(response.data);
  25. })
  26. .catch(function (error) {
  27. console.log(error);
  28. });
  29. },
  30. sendGetByObj(){
  31. //2.get通过params选项
  32. axios.get(`get.php?`,{
  33. params:{
  34. name:this.users.name,
  35. age:this.users.age
  36. }
  37. })
  38. .then(function (response) {
  39. console.log(response.data);
  40. })
  41. .catch(function (error) {
  42. console.log(error);
  43. });
  44. }
  45. }
  46. });
  47. }
  48. </script>
  49. </head>
  50. <body>
  51. <div id="app">
  52. <input type="text" :name="users.name" v-model="users.name" placeholder="姓名">
  53. <input type="text" :age="users.age" v-model="users.age" placeholder="年龄">
  54. <button @click="sendGetByStr">发送get请求</button>
  55. </div>
  56. </body>
  57. </html>

界面效果如图,为了测试我我们这边就不写样式了:

然后再写个最简单的 get.php 文件,响应后输出 get.php

 
  1. <?php
  2. $name=$_GET["name"];
  3. $age=$_GET["age"];
  4. echo "姓名:".$name.","."年龄:".$age;
  5. ?>

输入名字和年龄,可以直接请求并输入数据了:


如果出现以下错误:

图  2

是因为在浏览器打开本地的 html 文件,上面请求的模型资源文件是一个本地文件,协议是 file://,出于安全性考虑,Chrome 默认禁止了这种用法,file 协议和 http/https 协议不同,会被 Chrome 认为是跨域访问,所以会报被 CORS(Cross-Origin Resource Sharing,跨域资源共享)的安全策略阻止。

解决方法 以谷歌浏览器为例:

  1. 找到你谷歌浏览器浏览器安装的位置,一般默认安装的位置 C:\Program Files\Google\Chrome\Application;

  2. 在该目录打开命令行,直接在文件夹导航栏输入 cmd,敲回车,回车之后就进入了 cmd 命令行;

  3. 输入命令 chrome.exe --disable-web-security --user-data-dir=C:\MyChromeUserFata。

这个时候谷歌浏览器会重新打开一个窗口,然后把你本地 html 文件放到浏览器中就好了。

post 请求

同样写一个按照创建 post 的实例方法,写一个 post.html 代码文件:

 
  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <script src="https://cdn.staticfile.org/vue/2.2.2/vue.min.js"></script>
  6. <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
  7. <title>发送post请求</title>
  8. <script>
  9. window.onload=function(){
  10. new Vue({
  11. el:'#app',
  12. data:{
  13. users:{
  14. name:'',
  15. age:''
  16. }
  17. },
  18. methods:{
  19. sendPsot(){
  20. axios.post('post.php', {
  21. name: this.users.name,
  22. age: this.users.age,
  23. })
  24. .then(function (response) {
  25. console.log(response);
  26. })
  27. .catch(function (error) {
  28. console.log(error);
  29. });
  30. }
  31. }
  32. });
  33. }
  34. </script>
  35. </head>
  36. <body>
  37. <div id="app">
  38. <input type="text" :name="users.name" v-model="users.name" placeholder="姓名">
  39. <input type="text" :age="users.age" v-model="users.age" placeholder="年龄">
  40. <button @click="sendPsot">发送post请求</button>
  41. </div>
  42. </body>
  43. </html>

另外也同样的加上 post.php 代码文件:

 
  1. <?php
  2. $name=$_POST["name"];
  3. $age=$_POST["age"];
  4. echo "姓名:".$name.","."年龄:".$age
  5. ?>

图  2


图  2

大家可能会发现有点异常,因为我们并没有获取到对应的 name 以及 age,这是因为这种方式传递的数据是 Request Payload,所以我们要稍微修改一下 html 文件:

 
  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <script src="https://cdn.staticfile.org/vue/2.2.2/vue.min.js"></script>
  6. <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
  7. <title>发送post请求</title>
  8. <script>
  9. window.onload=function(){
  10. new Vue({
  11. el:'#app',
  12. data:{
  13. users:{
  14. name:'',
  15. age:''
  16. }
  17. },
  18. methods:{
  19. sendPsot(){
  20. axios.post('post.php',this.users,{
  21. //transformRequest就是用来处理转换的
  22. transformRequest:[
  23. function(data){
  24. let transObj='';
  25. for(let i in data){
  26. transObj+=i+'='+data[i]+'&';
  27. }
  28. return transObj;
  29. }
  30. ]
  31. })
  32. .then(function (response) {
  33. console.log(response.data);
  34. })
  35. .catch(function (error) {
  36. console.log(error);
  37. });
  38. }
  39. }
  40. });
  41. }
  42. </script>
  43. </head>
  44. <body>
  45. <div id="app">
  46. <input type="text" :name="users.name" v-model="users.name" placeholder="姓名">
  47. <input type="text" :age="users.age" v-model="users.age" placeholder="年龄">
  48. <button @click="sendPsot">发送post请求</button>
  49. </div>
  50. </body>
  51. </html>

最后结果如下:

图  2

实现跨域请求

上面都是在没有跨域的情况下进行 ajax 请求的,如果我们要跨域请求呢? 跨域请求的话 axios 还没有解决方案,当时,可以通过 vue-resource 的 jonsp 来实现>

接下来就使用 vue-resource 跨域请求写一个获取 github 账户信息的例子,API链接 :

 
  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <script src="https://cdn.staticfile.org/vue/2.2.2/vue.min.js"></script>
  6. <script src="https://cdn.staticfile.org/vue-resource/1.5.1/vue-resource.min.js"></script>
  7. <title>输入用户名获取github上的账户信息</title>
  8. <script>
  9. window.onload=function(){
  10. new Vue({
  11. el:'#app',
  12. data:{
  13. id:'',
  14. userData:''
  15. },
  16. methods:{
  17. getData(){
  18. this.$http.jsonp(`https://api.github.com/users/${this.id}`).then(function(resp){
  19. this.userData=resp.data.data;
  20. });
  21. }
  22. }
  23. });
  24. }
  25. </script>
  26. </head>
  27. <body>
  28. <div id="app">
  29. <input type="text" v-model="id" placeholder="姓名">
  30. <button @click="getData">获取github的账户信息</button>
  31. <div v-for="(v,k) in userData">{{k}}:{{v}}</div>
  32. </div>
  33. </body>
  34. </html>

这个典型的跨域请求例子输入姓名即可查询在 github 上面的信息,大家也可以自行改进。

编程要求

根据提示,在右侧编辑器补充代码,采用指定接口获取到“笑话”内容即可。

测试说明

平台会对你编写的代码进行测试,具体的运行效果图如下:

预期输出:

 
  1. Vue 服 务 启 动 成 功
  2. Vue3 axios 设 计 完 成

开始你的任务吧,祝你成功!

代码文件

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <!-- 官网提供axios在线地址 -->
    <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
    <script src="https://cdn.staticfile.org/vue/2.2.2/vue.min.js"></script>
    <title>axios+vue</title>
</head>

<body>
    <div id="app">
        <button @click="getJoke">获取笑话</button>
        <p> {{joke}} </p>
    </div>
    <script>
        /*
            接口:随机获取一条笑话
            请求地址:https://autumnfish.cn/api/joke
            请求方法:get
            请求参数:无
            响应内容:随机笑
        */
        var app = new Vue({
            el: "#app",
            data: {
                joke: "一个很好笑的笑话"
            },
            methods: {
                getJoke: function() {
                    var that = this;
                    axios.get('https://autumnfish.cn/api/joke')
                        .then(function(response) {
                            that.joke = response.data;
                        })
                        .catch(function(error) {
                            console.log(error);
                        });
                }
            },
        })
    </script>
</body>

</html>

更多推荐