const oldFetch = global.fetch;

const newFetch = function (url, options = {}) {
  const request = {
    url,
    options
  };
  return new Promise((resolve, reject) => {
    if (this.interceptors.length > 0) {
      // 执行请求前的拦截操作
      this.runInterceptors(0, request)
        .then(req => {
          oldFetchFun(this, req)
            .then((res) => {
              resolve(res);
            })
            .catch(err => {
              reject(err);
            });
        });
    } else {
      oldFetchFun(this, request)
        .then((res) => {
          resolve(res);
        })
        .catch(err => {
          reject(err);
        });
    }
  });
};

const oldFetchFun = function (that, request) {
  return new Promise((resolve, reject) => {
    // 添加超时检测
    const timeout = request.options.timeout;
    let timer;
    if (timeout) {
      timer = setTimeout(() => {
        reject(new Error("fetch timeout"));
      }, timeout);
    }
    // console.log('oldFetch request', request)
    oldFetch(request.url, request.options)
      .then(res => {
        // console.log('oldFetch res json', res)
        // 执行请求后的拦截操作
        const response = res;
        if (that.interceptors_after.length > 0) {
          that.runInterceptorsAfter(0, response, request)
            .then(data => {
              resolve(data);
            });
        }
        resolve(res);
      })
      .catch(err => {
        console.log('err', err);
        reject(err);
      });
  });
};

const BreadFetch = function () {};

BreadFetch.prototype.newFetch = newFetch;

// fetch拦截器
BreadFetch.prototype.interceptors = [];
BreadFetch.prototype.interceptors_after = [];
BreadFetch.prototype.runInterceptors = function (i, request) {
  const _that = this;
  if (i === 0) this.interceptors_after = [];

  return new Promise((resolve, reject) => {
    if (i >= this.interceptors.length) resolve(request);
    this.interceptors[i](request, callback => {
      if (callback) {
        // callback 存入请求后执行的数组
        _that.interceptors_after.push(callback);
      }
      _that.runInterceptors(++i, request).then(req => {
        resolve(req);
      });
    });
  });
};

BreadFetch.prototype.runInterceptorsAfter = function (i, response, request) {
  const _that = this;
  return new Promise((resolve, reject) => {
    if (i >= this.interceptors_after.length) resolve(response);
    this.interceptors_after[i](response, request,  () => {
      _that.runInterceptorsAfter(++i, response).then(res => {
        resolve(res);
      });
    });
  });
};

const objFetch = new BreadFetch();
const myFetch = function (url, options = {}) {
  return new Promise((resolve, reject) => {
    objFetch.newFetch(url, options)
      .then(data => {
        resolve(data);
      })
      .catch(err => {
        reject(err);
      });
  });
};

export default objFetch;
export {
  myFetch
};
