"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.useAPI = void 0;
const react_1 = require("react");
const apiCache = {};
function useAPI({ queryFn, queryProps = {}, enabled = true, staleTimeout = 5000, onSuccess, onError, }) {
    const [isLoading, setIsLoading] = (0, react_1.useState)(false);
    const [data, setData] = (0, react_1.useState)(undefined);
    const [error, setError] = (0, react_1.useState)(undefined);
    const cacheKey = queryFn.name + JSON.stringify(queryProps);
    const fetch = async () => {
        setIsLoading(true);
        setData(undefined);
        setError(undefined);
        try {
            const res = await queryFn({ ...queryProps });
            setData(res);
            setIsLoading(false);
            apiCache[cacheKey] = { data: res, timestamp: new Date().getTime() };
            onSuccess?.(res);
        }
        catch (e) {
            if (e instanceof Error) {
                setError(e);
                onError?.(e);
            }
        }
        finally {
            setIsLoading(false);
        }
    };
    const execute = (0, react_1.useCallback)(() => {
        if (enabled) {
            const cachedItem = apiCache[cacheKey];
            if (cachedItem && new Date().getTime() - cachedItem.timestamp < staleTimeout) {
                // The cached item is still fresh, so we use it
                setData(cachedItem.data);
                onSuccess?.(cachedItem.data);
                setIsLoading(false);
            }
            else {
                // The cached item is stale or doesn't exist, so we fetch fresh data
                fetch();
            }
        }
        // Since cache key is a string representation of function name and the query props
        // we only want to create a new version of this function when it changes.
        // passing in an object here would create a new function on every render
        // which would cause unnecessary calls to the backend.
        // eslint-disable-next-line react-hooks/exhaustive-deps
    }, [cacheKey, staleTimeout, enabled]);
    (0, react_1.useEffect)(() => {
        execute();
    }, [execute]);
    return { data, isLoading, error, refetch: execute };
}
exports.useAPI = useAPI;
//# sourceMappingURL=useAPI.js.map