import {IApiParamsCollection} from "./IApiParamsCollection";
import {ISendResponse} from "./ISendResponse";
import {AxiosInstance} from "axios";
import {IApi} from "./IApi";
import {ApiHandler} from "./ApiHandler";
import {IApiCollection} from "./IApiCollection";

type TransformFunction<T extends IApiCollection> = {
    [K in keyof T]: ApiHandler<T[K]>;
};
type SuccessFunction = (sendResponse: ISendResponse<any>) => void;
type ExpectFunction = (sendResponse: ISendResponse<any>) => boolean;
type ExceptionFunction = (sendResponse: ISendResponse<any>) => void;
type FailFunction = (error: Error) => void;
type ResponseHandlerFunction = {
    successFunction?: SuccessFunction | null,
    exceptionFunction?: ExceptionFunction | null,
    failFunction?: FailFunction | null,
}
type ResponseHandlerDefineFunction = {
    expectFunction: ExpectFunction,
    successFunction: SuccessFunction,
    exceptionFunction: ExceptionFunction,
    failFunction: FailFunction,
}
type GeneralObject = { [key: string]: any }
type ExtractIApi<T> = {
    [K in keyof T]: T[K] extends IApi ? ApiHandler<T[K]> : never;
};
type ApiConfig =
    | {
    type: "axios";
    config: AxiosInstance; // 当 type 为 "axios" 时，config 是 AxiosInstance
}
    | {
    type: "fetch";
    config: RequestInit; // 当 type 为 "fetch" 时，config 是 RequestInit
};
type SendHandlerInfo = {
    requestTime: Date,
    completeTime: Date
}
type SendHandlerResponse = { data: ISendResponse<any>["data"], info: SendHandlerInfo }
type ObjectMapping<T extends string | number | symbol, K> = { [key in T]: K }
type ResolveParams<K> = K extends string[]
    ? Record<K[number], any> // 如果是字符串数组，返回键值对
    : { [U in keyof K]: any }
type CacheData = {
    data: ISendResponse<any>,
    lastTime: Date,
}
type SendHandler<T extends IApi> = (args: ResolveParams<T['params']>) => Promise<ISendResponse<any>>
type Hanger<T extends IApi> = {
    before?: (args: ResolveParams<T['params']>) => ResolveParams<T['params']>
    complete?: (res: Promise<ISendResponse<any>>) => Promise<ISendResponse<any>>
    after?: (res: Promise<SendHandlerResponse>) => Promise<SendHandlerResponse>
    guard?:(args: ResolveParams<T['params']>, info?: object, next?: Hanger<T>['guard']) => Promise<ISendResponse<any>>
}
type HangerIndex<T extends IApi> = (api: T) => Hanger<T>
export {
    TransformFunction,
    SuccessFunction,
    ExpectFunction,
    ExceptionFunction,
    FailFunction,
    ResponseHandlerFunction,
    GeneralObject,
    ExtractIApi,
    ResponseHandlerDefineFunction,
    ApiConfig,
    ObjectMapping,
    SendHandlerInfo,
    SendHandlerResponse,
    ResolveParams,
    CacheData,
    SendHandler,
    Hanger,
    HangerIndex,
}