import axios, { AxiosInstance, AxiosRequestConfig } from 'axios'

const MAX_REQUESTS = window.savetowishlistObj?.maxRequests ? Number(window.savetowishlistObj.maxRequests) : 8
const INTERVAL_IN_MS = Math.floor(1000 / MAX_REQUESTS)
let PENDING_REQUESTS = 0

/**
 * Sets up axios with interceptors for response and error handling.
 *
 * @param {Record<string, any>} options Arbitrary options.
 */
const restApi = (config: AxiosRequestConfig = {}, options: Record<string, any> = {}): AxiosInstance => {
    const maxRequests = options.maxRequests || MAX_REQUESTS
    const intervalInMs = options.intervalInMs || INTERVAL_IN_MS
    const axiosInstance: AxiosInstance = axios.create({
        timeout: 30000,
        responseType: 'json',
        headers: {
            'Content-Type': 'application/json;charset=UTF-8',
            'X-WP-Nonce': window.savetowishlistObj.wpNonce,
            'Nonce': window.savetowishlistObj.wcNonce
        },
        baseURL: window.savetowishlistObj.restApiUrl,
        ...config
    })

    axiosInstance.interceptors.request.use(config => {
        return new Promise((resolve) => {
            let interval = setInterval(() => {
                if (PENDING_REQUESTS < maxRequests) {
                    PENDING_REQUESTS++
                    clearInterval(interval)
                    resolve(config)
                }
            }, intervalInMs)
        })
    })

    axiosInstance.interceptors.response.use(
        response => {
            PENDING_REQUESTS = Math.max(0, PENDING_REQUESTS - 1)
            return Promise.resolve(response)
        },
        error => {
            PENDING_REQUESTS = Math.max(0, PENDING_REQUESTS - 1)
            return Promise.reject({ error: error.response.data })
        }
    )

    return axiosInstance
}

export default restApi
