美文网首页vuereact & vue & angular
在vue项目中axios发起请求时的小知识

在vue项目中axios发起请求时的小知识

作者: 似朝朝我心 | 来源:发表于2022-04-23 22:32 被阅读0次

    1.发起axios请求时,喜欢使用async和await来修饰

    使用axios发起请求时,我们在一些文章或者视频当中多多少少都会看到asyncawait这对兄弟?所以它们到底是什么意思呢?为什么要写成这样子?

    async和await是es7的语法,其实我们不需要深入理解,就当养成习惯就好,以后记住发送axios请求的时候加上这对修饰兄弟就行

    async就是一个修饰符,用来修饰函数的,await是用来等待接收数据回传的。

    import axios from 'axios'
    
    methods:{
    async getInfo(){
     const {data:res} = await axios.get('url')
    console.log(res)
      }
    }
    

    如果看不懂{data:res} ,这是加上了对象解构(es6的知识),也是代码中常见的,变成这样你或许就懂了。

    const res = data
    

    2.将axios挂载到vue的原型上

    为什么需要将axios挂载到vue的原型上?因为你想在每个组件中使用axios时都需要额外写上一句

    import axios from 'axios'
    

    这样显然有些麻烦和累赘。

    所以为了解决这种频繁的使用axios需求,一般我们都在vue-cli项目中的main.js文件中进行配置,将axios直接挂载到vue的原型上去。

    main.js配置文件:

    import axios from 'axios'
    Vue.prototype.axios = axios
    

    其他组件在使用axios发起请求时就不再需要import额外导入axios了,直接用this调用即可,它会直接访问到我们的组件实例。

    methods:{
    async getInfo(){
     const {data:res} = await this.axios.get('url')
     console.log(res)
      }
    }
    

    除此之外呢,我们或许会在一些文章或视频上看到axios挂载原型的不同写法,细心的你会发现怎么跟前面的不一样,相信很多新手都估计很懵,为什么挂载个axios还有这么多种写法:我这里就列举常见的2种命名

    如果你的main.js这样挂载axios的原型:

    import axios from 'axios'
    Vue.prototype.$axios = axios
    

    那么组件想调用就需要写成这样:

    methods:{
    async getInfo(){
     const {data:res} = await this.$axios.get('url')
     console.log(res)
      }
    }
    

    还有的喜欢写成这样子的:

    import axios from 'axios'
    Vue.prototype.$http= axios
    

    那么组件调用的时候就相应写成如此了:

    methods:{
    async getInfo(){
     const {data:res} = await this.$http.get('url')
     console.log(res)
      }
    }
    

    总结:

    他们其实就仅仅只是命名不同,效果还是是一样的,只是为了衬托代码逼格高点而已,名字你随便起其实都是可以的,但我们一般现在都遵从开发规范习惯,直接写成: $http和$axios这两种命名,其中又以$http这样命名为主流,所以你在网上看到很多大都是写成Vue.prototype.$http= axios

    所以现在,你清楚了这几种写法了吗?

    将axios挂载到vue的原型上,让axios变成一个共享成员,这样每个组件就可以访问我们的axios了,不再需要额外import导入axios。

    3.全局配置axios的请求根路径

    为什么需要全局配置axios的请求根路径?答案当然是为了方便后期维护。

    没全局配置axios的请求根路径时,是这样发起请求的:

    methods:{
    async getInfo(){
     const {data:res} = await this.$http.get('http://www.xxx.com:3000/api/get')
     console.log(res)
      }
    }
    

    接下来,让我们进行全局配置axios的请求根路径:

    在main.js中写下这个固定结构:

    axios.defaults.baseUrl = 'http://www.xxx.com:3000'
    

    进行全局配置axios的请求根路径后,我们是这样发起请求的:

    methods:{
    async getInfo(){
     const {data:res} = await this.$http.get('/api/get')
     console.log(res)
      }
    }
    

    4.将axios挂载到Vue的原型上,不利于API接口的复用

    上面这句话是什么意思呢?我们来看一下下面的案例模拟。

    比如我们现在有a、b、c三个组件,三个组件都需要新闻接口返回的数据进行页面渲染,那么三个组件都需要写成下面一串代码。


    a组件发起新闻接口请求:

    <template>
        <div>
            <button @click="getList">点击</button>
        </div>
    </template>
    
    <script>
        export default {
            methods: {
                async getInfo() {
                    const { data: res } = await this.$http.get('/api/get')
                    console.log(res)
                }
            },
        }
    </script>
    

    b组件发起新闻接口请求:

    <template>
        <div>
            <button @click="getList">点击</button>
        </div>
    </template>
    
    <script>
        export default {
            methods: {
                async getInfo() {
                    const { data: res } = await this.$http.get('/api/get')
                    console.log(res)
                }
            },
        }
    </script>
    

    c组件发起新闻接口请求:

    <template>
        <div>
            <button @click="getList">点击</button>
        </div>
    </template>
    
    <script>
        export default {
            methods: {
                async getInfo() {
                    const { data: res } = await this.$http.get('/api/get')
                    console.log(res)
                }
            },
        }
    </script>
    

    毫不例外,abc三个组件分别都去调用了同一个新闻接口去获取数据,这样子就没办法达到接口的复用效果了。

    那么为了方便我们api接口的复用,我们为什么不写一份代码,适用三个组件呢?而不是写三分冗余代码。

    正因为这种复用api的需求,所以我们是不是可以把组件中使用组合式API创建的逻辑抽取出来封装成可复用的模块呢?

    5.封装工具类,这种不需要挂载到vue的原型上

    创建一个utils工具类目录,封装一个request.js工具模块
    /src/utils/request.js

    import axios from "axios";
    const request = axios.create({
        //指定请求的根路径
        baseURL:'https://www.xxx.com'
    })
    
    //一般我们在这里还会封装一个请求拦截器和一个响应拦截器
    
    export default request
    

    组件页面想要使用时,进行封装一个组件调用接口的方法:

    <script>
    import request  from "../utils/request"
    export default {
        data(){
            return {
                page:1,
                limit:10
            }
        },
        created(){
            this.initArticleList()
        },
        methods:{
            //封装获取文章列表数据的方法
            async initArticleList(){
                //发起get请求,获取文章列表数据
                const {data:res} = await request.get('/articles',{
                    //配置请求参数
                    params:{
                        _page:this.page,
                        _limit:this.limit
                    }
                })
                console.log(res); //将data解构出来取名为res
            }
        }
    }
    </script>
    

    但如果其他页面需要这个接口的数据的时候,仍然要写一份这样的冗余代码,所以还是没有实现复用。

    我们要做的其实还是需要将组件封装的调用接口的方法提取出来,进行再一步的接口封装。

    6.api接口封装

    创建api目录,封装一个与文章相关的api
    /src/api/articleAPI.js

    先写一个简单的模板方便我们理解

    //文章相关的api接口,都封装到这个模块中
    
    // 向外按需导出一个api函数,哪个组件要用谁就要按需导入这个函数
    export const getArticleListAPI = () =>{
        console.log('调用了getArticleListAPI函数');
    }
    

    某个组件中使用

    <script>
    //按需导入api接口
    import { getArticleListAPI } from "../api/articleAPI"
    getArticleListAPI()
    </script>
    

    完整的一个demo展示:
    /src/api/articleAPI.js

    //文章相关的api接口,都封装到这个模块中
    
    //引入我们封装好的axios工具
    import request from '@/utils/request'
    // 向外按需导出一个api函数,哪个组件要用谁就要按需导入这个函数
    export const getArticleListAPI = (_page,_limit) =>{ //接收那边传入的2个参数
        return request.get('articles',{
            //配置请求参数
            params:{
                _page, //本来要写成这样的_page:_page,因为es6语法同名可以写成这样_page,
                _limit
            }
        })
    }
    

    /src/views/xxx.vue组件中调用接口

    <script>
    import { getArticleListAPI } from "../api/articleAPI"
    export default {
        data(){
            return {
                page:1,
                limit:10
            }
        },
        created(){
            this.initArticleList()
        },
        methods:{
            //封装获取文章列表数据的方法
            async initArticleList(){
                //发起get请求,获取文章列表数据
                const {data:res} = await getArticleListAPI(this.page,this.limit) //传入2个参数
            }
        }
    }
    </script>
    

    这样就实现了api复用的效果,比如我们有另外一个组件需要调用这个获取文章列表数据的接口,只需直接传进参数即可。
    /src/views/news.vue组件中调用接口,比如这个页面需要传递5条数据,只需修改一下传进去的参数即可

    <script>
    //按需导入api接口
    import { getArticleListAPI } from "../api/articleAPI"
    export default {
        data(){
            return {
                page:1,
                limit:5
            }
        },
        created(){
            this.initArticleList()
        },
        methods:{
            //封装获取文章列表数据的方法
            async initArticleList(){
                //发起get请求,获取文章列表数据
                const {data:res} = await getArticleListAPI(this.page,this.limit) //传入2个参数
                console.log(res)
            }
        }
    }
    </script>
    

    相关文章

      网友评论

        本文标题:在vue项目中axios发起请求时的小知识

        本文链接:https://www.haomeiwen.com/subject/hpfzertx.html