Axios双虎将:GET&POST

0. 缘起

在下从初学者开始,就对这两员大将一直很是胆战心惊。但今天因为一些事情的发生,也为了坚实基础,所以写下这篇文章以备后用。

1. 官方介绍

使用说明 · Axios 中文说明 · 看云 (kancloud.cn)

我挺喜欢这篇看云的官网axios介绍文章,另一个版本的蓝白配色,看的我眼睛要瞎了,不爽。为什么把官网文章放这么前面呢,因为很多时候我懵逼了去搜索引擎搜,搜到的东西都是些奇奇怪怪的,甚至内容毫无关联的标题党。这种情况下,只有官网文本是最可靠的。

2. 易混淆点

params与data

官网说明

  // `params` 是即将与请求一起发送的 URL 参数
  // 必须是一个无格式对象(plain object)或 URLSearchParams 对象
  params: {
    ID: 12345
  },
  // `data` 是作为请求主体被发送的数据
  // 只适用于这些请求方法 'PUT', 'POST', 和 'PATCH'
  // 在没有设置 `transformRequest` 时,必须是以下类型之一:
  // - string, plain object, ArrayBuffer, ArrayBufferView, URLSearchParams
  // - 浏览器专属:FormData, File, Blob
  // - Node 专属: Stream
  data: {
    firstName: 'Fred'
  },

比如我有个GET方法,要的参数是[query(string) ]code,

      // 组件中要获取信息
      await getEnterpriseKind({ code: temp.industryType }).then((res) => {
        bef = res.data.name;
      });
      
      // /api/index.js调用时
      // Get Enterprise Kind From Number/Letter
export function getEnterpriseKind(data) {
    return get('/interfacePosition', data, BASEURL)
}

再比如我有个POST 方法,要的参数query(string)x2 userName passwordquery(integer) platform

// Login
export function loginAccount(account) {
    return post('/interfacePosition', {}, { username: account.userName, password: account.password, platform: account.platform }, BASEURL)
}

有没有注意到特殊的地方?看,POST方法在地址后面有个空对象,那这是为嘛呢?看文档就明白,POST有个DATA,这个空对象就是给DATA预留的位置。如果不填这个空对象,后面的就会成为DATA内容,发送了错误的数据。

DATA所在位置就是BODY内,所需参数类型为body(PageDataQuery)

import { download, get, post } from '@/utils/axios';
import store from '@/store/index';

const baseUrl = "/api";

// 获取页面数据
export function getPageData(filter) {
    if (store.state.version === 1) {
        return post('/v1/webui/pageData', filter, {}, baseUrl);
    } else {
        return post('/v2/webui/pageData', filter, {}, baseUrl);
    }
}

综上所述 get: query

post: data query

3. 关于axios封装[普通版本]

/**
 * axios 配置
 */
/* eslint-disable */

import axios from "axios";
import router, { resetRouter } from "@/router";
import store from '@/store'

// 设置全局头信息
axios.defaults.headers["Content-Type"] = "application/json;charset=UTF-8";
// 全局设置超时时间
axios.defaults.timeout = 1800000;

axios.defaults.baseURL = "/api";

// 请求路由拦截
axios.interceptors.request.use(
    function (config) {
        if (sessionStorage.getItem("token")) {
            config.headers["Authorization"] = sessionStorage.getItem("token");
        }
        if (sessionStorage.getItem("classifyId")) {
            config.headers["classifyId"] = sessionStorage.getItem("classifyId");
        }

        return config;
    },
    function (error) {
        return Promise.reject(error);
    }
);

// 响应拦截
axios.interceptors.response.use(
    function (response) {
        if (response.status === 200) {
            return Promise.resolve(response);
        } else {
            return Promise.reject(response);
        }
    },
    function (err) {
        const { status } = err.response ? err.response : { status: "" };
        if (err && err.response) {
            switch (status) {
                case 400:
                    err.message = "请求错误(400)";
                    break;
                case 401:
                    err.message = "未授权,请重新登录(401)";
                    resetRouter();
                    store.commit("SET_ROUTERS", []);
                    router.push("/login");
                    break;
                case 403:
                    err.message = "拒绝访问(403)";
                    break;
                case 404:
                    err.message = "请求出错(404)";
                    break;
                case 405:
                    err.message = "请求未允许(405)";
                    break;
                case 408:
                    err.message = "请求超时(408)";
                    break;
                case 500:
                    err.message = "服务器错误(500)";
                    break;
                case 501:
                    err.message = "服务未实现(501)";
                    break;
                case 502:
                    err.message = "网络错误(502)";
                    break;
                case 503:
                    err.message = "服务不可用(503)";
                    break;
                case 504:
                    err.message = "网络超时(504)";
                    break;
                case 505:
                    err.message = "HTTP版本不受支持(505)";
                    break;
                default:
                    err.message = `连接出错(${err.response.status})!`;
            }
        } else {
            err.message = "连接服务器失败!";
        }
        return Promise.reject(err);
    }
);

// 封装请求方法
export function get(url, params, baseURL = "") {
    let config = {};
    config.params = params;
    baseURL && (config.baseURL = baseURL);
    return new Promise((resolve, reject) => {
        axios
            .get(url, config)
            .then(res => {
                resolve(res.data);
            })
            .catch(err => {
                resolve({ success: false, message: err.message });
            });
    });
}

export function del(url, params, baseURL = "") {
    let config = {};
    config.params = params;
    baseURL && (config.baseURL = baseURL);
    return new Promise((resolve, reject) => {
        axios
            .delete(url, config)
            .then(res => {
                resolve(res.data);
            })
            .catch(err => {
                resolve({ success: false, message: err.message });
            });
    });
}

export function post(url, params, query = {}, baseURL = "") {
    let config = {};
    config.params = query;
    baseURL && (config.baseURL = baseURL);
    return new Promise((resolve, reject) => {
        axios
            .post(url, typeof params === "object" ? JSON.stringify(params) : params, config)
            .then(res => {
                resolve(res.data);
            })
            .catch(err => {
                resolve({ success: false, message: err.message });
            });
    });
}

export function put(url, params, query = {}, baseURL = "") {
    let config = {};
    config.params = query;
    baseURL && (config.baseURL = baseURL);
    return new Promise((resolve, reject) => {
        axios
            .put(url, typeof params === "object" ? JSON.stringify(params) : params, config)
            .then(res => {
                resolve(res.data);
            })
            .catch(err => {
                resolve({ success: false, message: err.message });
            });
    });
}

// 并发请求
export function all() {
    let userPromise = Array.prototype.slice.apply(arguments);
    return new Promise((resolve, reject) => {
        axios
            .all(userPromise)
            .then(results => {
                resolve(results);
            })
            .catch(() => {
                reject(arguments);
            });
    });
}

// 下载
export function download(url, params, fileName, baseURL = "", isPost = true) {
    let file = fileName;
    return new Promise((resolve, reject) => {
        let promise = isPost ? axios.post(url, null, { params: params, responseType: "blob", baseURL: baseURL })
            : axios.get(url, { params: params, responseType: "blob", baseURL: baseURL });
        promise.then(response => {
            const blob = new Blob([response.data]);
            const aEle = document.createElement("a"); // 创建a标签
            const href = window.URL.createObjectURL(blob); // 创建下载的链接
            aEle.href = href;
            aEle.download = file; // 下载后文件名
            document.body.appendChild(aEle);
            aEle.click(); // 点击下载
            document.body.removeChild(aEle); // 下载完成移除元素
            window.URL.revokeObjectURL(href); // 释放掉blob对象
            resolve("success");
        })
            .catch(err => {
                reject(err.message);
            });
    });
}


4. 进阶级别的axios封装

vue-admin-beautiful后台管理框架中的axios封装很精致,可以学习。

vue-admin-beautiful: vue-admin-beautiful 是一款前端开发框架,vue 学习搭框架必备,集合了所有的 vue 技术栈 (gitee.com)

5. 地址BUG

新鲜的一个BUG,连了后端小伙伴的地址,他却说没连到。我百思不得其解,问了问组长,组长过来1看,问题出在重复定义地址指向了。

process.env.VUE_APP_BASEURL = "/system"; 
process.env.VUE_APP_MAGICBOX = "/xy"; 
process.env.VUE_APP_YLLTASK = "/system"; 

    proxy: {
      [`${process.env.VUE_APP_BASEURL}`]: {
        target: "http://...:9094/",
        ws: true,
        changeOrigin: true,
        timeout: 30 * 60 * 1000,
        pathRewrite: {
          [`^${process.env.VUE_APP_BASEURL}`]: ""
        }
      },
      [`${process.env.VUE_APP_YLLTASK}`]: {
        target: "http://...:9091",
        ws: true,
        changeOrigin: true,
        timeout: 30 * 60 * 1000,
        pathRewrite: {
          [`^${process.env.VUE_APP_YLLTASK}`]: ""
        }
      },
    }

其中process.env.VUE_APP_BASEURLprocess.env.VUE_APP_YLLTASK虽然都是/system的指向地址,却指向了两个位置,而且YLLTASK还在BASEURL下方,所以使用的时YYLTASK的9091。

这种情况就是要么都修改,要么删掉1个地址导向。

posted @ 2021-12-15 16:25  乐盘游  阅读(34)  评论(0编辑  收藏  举报