js实用方法 ------ 封装axios 请求 get post delect ...

为了方便项目的维护,以及规范性,对axios进行必要的封装

一、在 utils目录下 创建 auth.js 请求头 token的封装

import Cookies from 'js-cookie'

const TokenKey = 'loginToken'

// 获取token
export function getToken() {
  return Cookies.get(TokenKey)
}
// 创建token
export function setToken(token) {
  return Cookies.set(TokenKey, token)
}
// 删除token
export function removeToken() {
  return Cookies.remove(TokenKey)
}

二、 在api目录下面新建文件api-config.js

import axios from 'axios';
import { Message } from 'element-ui'; // 用于错误提示 
import store from '../store'; // token存储在 store
import { getToken } from '@/utils/auth'; // 请求头 token 的封装
import * as _config from '@/config/http.config'; // 请求头的基础数据 如 baseUrl 等
import Router from '@/router'; // 做路由跳转,如登录失效 跳转登录页面

// 创建基础的 请求参数
let baseOptios = {
  baseURL: _config.baseUrl, // api的base_url 默认的请求接口前缀
  timeout: 50000, // 请求超时时间
  retry: 1, // 请求次数
  retryDelay: 1000, // 请求间隔
  withCredentials: false // 是否可以携带cookies
}
// 创建axios实例
const Axios = axios.create(baseOptios);

// request请求数据拦截器
Axios.interceptors.request.use(
  config => {
    if (store.getters.token) {
      if (!config.url.includes('http://')) {
        config.headers['Authorization'] = getToken(); // 让每个请求携带自定义token 请根据实际情况自行修改
      }
    }
    // return config
    return Promise.resolve(config);
  },
  error => {
    // Do something with request error
    console.warn('----------------------------------------> ' + (new Date()))
    console.error('请求超时!')
    console.error('request error:>', error)
    console.warn('----------------------------------------------------------------------------------------')
    Promise.reject(error);
  }
);
// 响应http状态码 跟后端定义好
const codeMessage = {
  200: '服务器成功返回请求的数据。',
  201: '新建或修改数据成功。',
  202: '一个请求已经进入后台排队(异步任务)。',
  204: '删除数据成功。',
  400: '发出的请求有错误,服务器没有进行新建或修改数据的操作。',
  401: '用户没有权限(令牌、用户名、密码错误)。',
  403: '用户得到授权,但是访问是被禁止的。',
  404: '发出的请求针对的是不存在的记录,服务器没有进行操作。',
  406: '请求的格式不可得。',
  408: '请求超时。',
  410: '请求的资源被永久删除,且不会再得到的。',
  422: '当创建一个对象时,发生一个验证错误。',
  500: '服务器发生错误,请检查服务器。(服务器内部错误)',
  501: '服务未实现。',
  502: '网关错误。',
  503: '服务不可用,服务器暂时过载或维护。',
  504: '网关超时。',
  505: 'HTTP版本不受支持。'
}
// respone响应拦截器
Axios.interceptors.response.use(
  response => {
    const { status, message } = response.data;
    if (status !== 200) { // 请求不是成功的  跟后端统一定义好,并且接口都按这个规范来
      console.warn('----------------------------------------> ' + (new Date()))
      console.warn('request url:>', response.config.url || response.request.path || '')
      console.warn('request param:>', response.config.data || '')
      console.warn('response server status:>', data.status || '')
      console.warn('response server message:>', data.message || '')
      console.warn('----------------------------------------------------------------------------------------')
      // 显示提示信息
      Message({
        type: 'error',
        message: `${message}`
      });
    }
    // ?一层一层去找对应的数据  需要跟后端统一定义好
    return Promise.resolve(response.data?.data ?? response);
    // return Promise.reject(response);
  },
  function axiosRetryInterceptor (error) {
    const config = error.config;
    // If config does not exist or the retry option is not set, reject
    if (!config || !config.retry) {
      Message({
        type: 'error',
        message: `请求服务好像出错了:${codeMessage[status]}`
      });
      return Promise.reject(error);
    }
    // 获取请求的次数
    config.__retryCount = config.__retryCount || 0;

    // Check if we've maxed out the total number of retries
    const status = error?.response?.status;

    if (status === 401) { //登录失效
      Message({
        type: 'error',
        message: `${codeMessage[status]}`
      });
      Router.push('/login');
      // Reject with the error
      return Promise.reject(error);
    } else if (config.__retryCount >= config.retry) { // 请求次数大于等于设置请求次数时
      Message({
        type: 'error',
        message: `${codeMessage[status]}`
      });
      // Reject with the error
      return Promise.reject(error);
    }
    config.__retryCount += 1;
    // 设置请求间隔时间方法
    const backoff = new Promise(function (resolve) {
      setTimeout(function () {
        resolve();
      }, config.retryDelay || 1);
    });

    // 未超过请求的时间重新发起请求
    return backoff.then(function () {
      return Axios(config);
    });
  }
);
export default Axios;

三、封装各类请求的方法

在api 下面建立 config.js 文件
代码如下

import qs from 'qs'; // 用于实现post 拼接在url后面 也就是 query类型的参数
import Axios from './api-config'; // 基础Axios的设置
import Vue from 'vue'; 
import axios from 'axios'; 
const CancelToken = axios.CancelToken; // 用于取消请求
let cancel;
// 封装常用请求接口
const config = {
  /**
   * get获取数据,通用方法  query类型的参数
   * @param {String} url
   * @param {Object} params
   * @param {Object} options
   */
  doGetPromise (url, params, options = {}) {
    const { timeout = 30000, ...arg } = options;
    // 如果参数值为空,手动赋值空字符串确保接口能收到
    if (params) {
      Object.keys(params).forEach(key => {
        if (key === 'beginTime' || key === 'endTime') { // 有需要的就自定义
        } else {
          if (params[key] === null || params[key] === undefined) {
            params[key] = '';
          }
        }
      });
    }
    return new Promise((resolve, reject) => {
      Axios.get(url, {
        timeout: timeout,
        ...arg,
        params: {
          // systemId: store.state.platformInfo.systemId, // 全面接口添加systemId字段
          ...params
          // t: new Date().getTime() // 解决IE上get请求缓存问题
        },
        // 取消请求
        cancelToken: new CancelToken(function executor (c) {
          cancel = c;
        })
      })
        .then(response => {
          resolve(response);
        })
        .catch(response => {
          reject(response);
        });
    });
  },
  /**
   * delete删除数据,通用方法
   * @param {String} url
   * @param {Object} params
   */
  doDeletePromise (url, params) {
    return new Promise((resolve, reject) => {
      Axios.delete(url, {
        timeout: timeout,
        ...arg,
        params: {
          ...params
        },
        cancelToken: new CancelToken(function executor (c) {
          cancel = c;
        })
      })
        .then(response => {
          resolve(response);
        })
        .catch(response => {
          reject(response);
        });
    });
  },
  /**
   * FormData数据上传,文件上传必用
   * @param {String} url
   * @param {FormData} formData
   */
  doPostPromiseForm (url, formData) {
    return new Promise((resolve, reject) => {
      // 全面接口添加systemId字段
      if (formData.has) {
        // ie FormData没有has方法
        // if (!formData.has('systemId')) {
        //   formData.append('systemId', store.state.platformInfo.systemId);
        // }
      }
      Axios.post(url, formData, {
        headers: {
          'Content-type': 'multipart/form-data'
        },
        emulateJSON: false,
        emulateHTTP: false,
        cancelToken: new CancelToken(function executor (c) {
          cancel = c;
        })
      })
        .then(response => {
          resolve(response);
        })
        .catch(response => {
          reject(response);
        });
    });
  },

  /**
   * 默认方式提交from表单数据 query类型的参数
   * @param {String} url
   * @param {Object} data
   */
  doPostQuery (url, data) {
    return new Promise((resolve, reject) => {
      Axios.post(
        url,
        qs.stringify(data, {
          arrayFormat: 'brackets'
        }),
        {
          headers: {
            'Content-type': 'application/x-www-form-urlencoded'
          },
          cancelToken: new CancelToken(function executor (c) {
            cancel = c;
          })
        }
      )
        .then(response => {
          resolve(response);
        })
        .catch(response => {
          reject(response);
        });
    });
  },

  /**
   * 默认方式提交json数据 body
   * @param {String} url
   * @param {Object} data
   */
  doPostPromiseJson (url, data) {
    return new Promise((resolve, reject) => {
      // 全面接口添加systemId字段
      // if (!data.hasOwnProperty('systemId')) {
      //   data.systemId = store.state.platformInfo.systemId;
      // }
      Axios.post(url, data, {
        headers: {
          'Content-type': 'application/json'
        },
        cancelToken: new CancelToken(function executor (c) {
          cancel = c;
        })
      })
        .then(res => {
          resolve(res);
        })
        .catch(res => {
          reject(res);
        });
    });
  },
};
// 切换页面强行中断请求 router.beforeEach中用到
Vue.prototype.$cancelAjax = function (msg) {
  if (cancel) {
    cancel(msg || '手动中断请求');
  }
};
export default config;

四、在根据页面接口配置里面引用

import config from '.@/api/config';
// get获取数据,通用方法  query类型的参数
export function queryTypical(data) {
  return config.doGetPromise(
    '/exchangeApi/exchange/hook/ecologicalRenovateBasicInfo/queryTypical',
    data
  );
}
// delete删除数据,通用方法
export function ecolRenovateConSave(data) {
  return config.doDeletePromise(
    '/exchangeApi/exchange/hook/ecolRenovateCon/save',
    data
  );
}

// post FormData数据上传,文件上传必用
export function ecolRenovateConUpdate(data) {
  return config.doPostPromiseForm(
    '/exchangeApi/exchange/hook/ecolRenovateCon/update',
    data
  );
}
// post提交from表单数据 query类型的参数
export function ecolRenovateConRemove(data) {
  return config.doPostQuery(
    '/exchangeApi/exchange/hook/ecolRenovateCon/remove',
    data
  );
}
// post提交方式提交json数据 body
export function ecolRenovateConRemove(data) {
  return config.doPostPromiseJson(
    '/exchangeApi/exchange/hook/ecolRenovateCon/remove',
    data
  );
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值