import { ShallowRef, Ref } from 'vue-demi';
import { UnData, UnResponse, UnConfig, UnInstance } from './index.cjs';

/** Align with v12.3.0 */
interface UseUnReturn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptions<T> = UseUnOptions<T>> {
    /** Un 响应 */
    response: ShallowRef<R | undefined>;
    /** Un 响应数据 */
    data: O extends UseUnOptionsWithInitialData<T> ? Ref<T> : Ref<T | undefined>;
    /** 是否已经结束 */
    isFinished: Ref<boolean>;
    /** 是否正在请求 */
    isLoading: Ref<boolean>;
    /** 是否已经取消 */
    isAborted: Ref<boolean>;
    /** `isAborted` 别名 */
    isCanceled: Ref<boolean>;
    /** 发生的错误 */
    error: ShallowRef<unknown | undefined>;
    /** 取消当前请求 */
    abort: (message?: string | undefined) => void;
    /** `abort` 别名 */
    cancel: (message?: string | undefined) => void;
}
interface StrictUseUnReturn<T, R, D, O extends UseUnOptions<T> = UseUnOptions<T>> extends UseUnReturn<T, R, D, O> {
    /** 手动调用 */
    execute: (url?: string | UnConfig<T, D>, config?: UnConfig<T, D>) => Promise<StrictUseUnReturn<T, R, D, O>>;
}
interface EasyUseUnReturn<T, R, D> extends UseUnReturn<T, R, D> {
    /** 手动调用 */
    execute: (url: string, config?: UnConfig<T, D>) => Promise<EasyUseUnReturn<T, R, D>>;
}
interface UseUnOptionsBase<T = UnData> {
    /** 当 `useUn` 被调用时，是否自动发起请求 */
    immediate?: boolean;
    /**
     * 是否使用 shallowRef
     *
     * @default true
     */
    shallow?: boolean;
    /**
     * 是否在新请求发起时中止之前的请求
     *
     * @default true
     */
    abortPrevious?: boolean;
    /**
     * 是否在执行前将请求数据重置为 initialData
     *
     * @default false
     */
    resetOnExecute?: boolean;
    /** 发生错误时调用 */
    onError?: (e: unknown) => void;
    /** 成功请求时调用 */
    onSuccess?: (data: T) => void;
    /** 请求结束时调用 */
    onFinish?: () => void;
}
interface UseUnOptionsWithInitialData<T> extends UseUnOptionsBase<T> {
    /** 在请求还未响应时使用的响应数据 */
    initialData: T;
}
type UseUnOptions<T = UnData> = UseUnOptionsBase<T> | UseUnOptionsWithInitialData<T>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptionsWithInitialData<T> = UseUnOptionsWithInitialData<T>>(url: string, config?: UnConfig<T, D>, options?: O): StrictUseUnReturn<T, R, D, O> & Promise<StrictUseUnReturn<T, R, D, O>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptionsWithInitialData<T> = UseUnOptionsWithInitialData<T>>(url: string, instance?: UnInstance, options?: O): StrictUseUnReturn<T, R, D, O> & Promise<StrictUseUnReturn<T, R, D, O>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptionsWithInitialData<T> = UseUnOptionsWithInitialData<T>>(url: string, config: UnConfig<T, D>, instance: UnInstance, options?: O): StrictUseUnReturn<T, R, D, O> & Promise<StrictUseUnReturn<T, R, D, O>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptionsBase<T> = UseUnOptionsBase<T>>(url: string, config?: UnConfig<T, D>, options?: O): StrictUseUnReturn<T, R, D, O> & Promise<StrictUseUnReturn<T, R, D, O>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptionsBase<T> = UseUnOptionsBase<T>>(url: string, instance?: UnInstance, options?: O): StrictUseUnReturn<T, R, D, O> & Promise<StrictUseUnReturn<T, R, D, O>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData, O extends UseUnOptionsBase<T> = UseUnOptionsBase<T>>(url: string, config: UnConfig<T, D>, instance: UnInstance, options?: O): StrictUseUnReturn<T, R, D, O> & Promise<StrictUseUnReturn<T, R, D, O>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData>(config?: UnConfig<T, D>): EasyUseUnReturn<T, R, D> & Promise<EasyUseUnReturn<T, R, D>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData>(instance?: UnInstance): EasyUseUnReturn<T, R, D> & Promise<EasyUseUnReturn<T, R, D>>;
declare function useUn<T = UnData, R = UnResponse<T>, D = UnData>(config?: UnConfig<T, D>, instance?: UnInstance): EasyUseUnReturn<T, R, D> & Promise<EasyUseUnReturn<T, R, D>>;

export { type EasyUseUnReturn, type StrictUseUnReturn, type UseUnOptions, type UseUnOptionsBase, type UseUnOptionsWithInitialData, type UseUnReturn, useUn };
