import {} from 'recoil';
import { RequestExtrasSerializable } from '../../api/http';
import { getUniqueIdentifier } from '../../shared/utils/hashing';
import { isDerivedVariable, isVariable } from '../../types';
/**
 * Key -> atom
 */
export const atomRegistry = new Map();
/**
 * Key -> atom family
 */
export const atomFamilyRegistry = new Map();
/**
 * Atom family function => {extras => atom}
 *
 * Stores all instances of a given atom family, as a map of seriailzed extras to atom.
 */
export const atomFamilyMembersRegistry = new Map();
/**
 * Key -> selector
 */
export const selectorRegistry = new Map();
/**
 * Key -> selector family
 */
export const selectorFamilyRegistry = new Map();
/**
 * Selector family function => {extras => selector}
 *
 * Stores all instances of a given selector family, as a map of seriailzed extras to selector.
 */
export const selectorFamilyMembersRegistry = new Map();
/**
 * StreamVariable atom instances registry.
 * Key is serialized StreamAtomParams, value is the atom instance.
 * Used to track active stream connections and check if a stream variable is registered.
 */
export const streamAtomRegistry = new Map();
/**
 * Key -> dependencies data for a selector
 */
export const depsRegistry = new Map();
/**
 * Registry key types that do not use 'nested' in their key
 */
const SHARED_KEY_TYPES = ['result-selector', 'derived-selector'];
/**
 * Get a unique registry key of a given type for a given variable.
 *
 * @param variable variable to get the key for
 * @param type type of the registry entry
 */
export function getRegistryKey(variable, type) {
    var _a;
    let extras = '';
    if (isDerivedVariable(variable)) {
        extras = (_a = variable.loop_instance_uid) !== null && _a !== void 0 ? _a : '';
    }
    const opts = { useNested: !SHARED_KEY_TYPES.includes(type) };
    return `${getUniqueIdentifier(variable, opts)}-${type}-${extras}`;
}
/**
 * Clear registries - to be used in tests only.
 */
export function clearRegistries_TEST() {
    for (const registry of [
        atomRegistry,
        atomFamilyRegistry,
        atomFamilyMembersRegistry,
        selectorRegistry,
        depsRegistry,
        selectorFamilyRegistry,
        selectorFamilyMembersRegistry,
        streamAtomRegistry,
    ]) {
        registry.clear();
    }
}
/**
 * Check whether a given variable is registered within the application
 * (More strictly, under the current RecoilRoot)
 *
 * @param variable variable to check
 */
export function isRegistered(variable) {
    if (!isVariable(variable)) {
        return false;
    }
    // eslint-disable-next-line @typescript-eslint/switch-exhaustiveness-check
    switch (variable.__typename) {
        case 'ServerVariable':
        case 'Variable': {
            if (atomRegistry.has(variable.uid)) {
                return true;
            }
            const family = atomFamilyRegistry.get(variable.uid);
            if (!family) {
                return false;
            }
            return atomFamilyMembersRegistry.get(family).size > 0;
        }
        case 'DerivedVariable': {
            const key = getRegistryKey(variable, 'selector-nested');
            return selectorFamilyRegistry.has(key);
        }
        case 'StreamVariable': {
            // Check if any atoms exist for this stream variable uid
            for (const atomKey of streamAtomRegistry.keys()) {
                if (atomKey.includes(`"uid":"${variable.uid}"`)) {
                    return true;
                }
            }
            return false;
        }
        default:
            return false;
    }
}
//# sourceMappingURL=store.js.map