import axios, { AxiosRequestConfig } from "axios";
import { userInfor } from "@/store/user/user";
import { ElMessage } from "element-plus";
import router from "@/routers/index";

const userInforStore = userInfor();

interface apiOptions {
  format: {
    formData: boolean; // 表单提交
    multipart: boolean; // 文件上传
  };
}

interface dataFormat {
  code: number;
  msg?: string;
  data: any;
}

let contentType: { [key: string]: any } = {
  json: "appliation/json;charset=utf-8;",
  formData: "application/x-www-form-urlencoded;",
  multipart: "multipart/form-data;",
};
let typeKey = "json";
class api {
  format = { formData: false, multipart: false };
  private instance = axios.create({
    baseURL: import.meta.env.VITE_API_BASE_URL,
  });
  constructor(options?: apiOptions) {
    if (options) {
      this.format = { ...this.format, ...options.format };

      if (this.format.formData) typeKey = "formData";
      if (this.format.multipart) typeKey = "multipart";
    }

    this.instance.interceptors.request.use(
      (config) => {
        this.instance.defaults.headers["Content-Type"] = contentType[typeKey];
        config.headers["Authorization"] = userInforStore.token;
        config.headers["refreshToken"] = userInforStore.refreshToken;
        return config;
      },
      (error) => {
        return Promise.reject(error);
      }
    );

    this.instance.interceptors.response.use(
      (responese) => {
        if (responese.data.code === 401) {
          ElMessage.error(responese.data.msg);
          userInforStore.removeLoginState();
          userInforStore.removeToken();
          router.replace("/login");
          return responese;
        }
        if ([501, 501, 503, 500].includes(responese.data.code)) {
          ElMessage.error(responese.data.msg);
          return responese;
        }
        let newToken = responese.headers["refreshToken"];
        if (newToken) {
          userInforStore.setToken(newToken);
        }
        return responese;
      },
      (error) => {
        if (error.status === 401) {
          ElMessage.error(error.response.data.msg);
          userInforStore.removeLoginState();
          userInforStore.removeToken();
          router.replace("/login");
        }
        return Promise.reject(error);
      }
    );
  }
  async get(url: string, config?: AxiosRequestConfig<any> | undefined) {
    return (await this.instance.get(url, config)).data;
  }
  async post(
    url: string,
    data?: any,
    config?: AxiosRequestConfig<any> | undefined
  ) {
    return (await this.instance.post(url, data, config)).data;
  }
}

export default function (options?: apiOptions) {
  return new api(options);
}
