UNPKG

solid-services

Version:

Solid.js library adding a services layer for global shared state.

103 lines 11.9 kB
import { getOwner, useContext } from "solid-js"; import { ServiceRegistryContext } from "./context"; import { runInSubRoot } from "./utils"; export class Service { } /** * Registry is a container for services. * It is used to register and retrieve services. */ export class Registry { #owner; #config; #cache; constructor(config = {}) { this.#config = config; this.#owner = getOwner(); this.#cache = new Map(); } /** * Checks weather the registry has a service registered for the given initializer. * * First it will check in the parent registry and if no service is registered there, * it will check in the current registry. */ has(initializer) { const parentRegistry = this.getParentRegistry(); if (parentRegistry?.isExposing(initializer)) { return parentRegistry.has(initializer); } return this.#cache.has(initializer); } /** * Returns the service registered for the given initializer. * * First it will try to find it in the parent registry and if no service is registered there, * it will check in the current registry. */ get(initializer) { const parentRegistry = this.getParentRegistry(); if (parentRegistry?.isExposing(initializer)) { return parentRegistry.get(initializer); } return this.#cache.get(initializer); } /** * Clears the registry. */ clear() { this.#cache.clear(); } /** * Deletes registered service for the given initializer. */ delete(initializer) { this.#cache.delete(initializer); } /** * Registers a service for the given initializer. * * If the registry has a parent registry, it will check if the service is exposed there. * * If it is exposed, it will register the service in the parent registry. * * If it is not exposed, it will register the service in the current registry. * * If the registry does not have a parent registry, it will register the service in the current registry. */ register(initializer) { const parentRegistry = this.getParentRegistry(); if (parentRegistry?.isExposing(initializer)) { return parentRegistry.register(initializer); } const registration = runInSubRoot(() => this.initializeService(initializer), this.#owner); this.#cache.set(initializer, registration); return registration; } isExposing(initializer) { return (this.#config.expose === true || (Array.isArray(this.#config.expose) && this.#config.expose?.includes(initializer))); } getParentRegistry() { return this.#owner?.owner ? runInSubRoot((dispose) => { const context = useContext(ServiceRegistryContext); dispose(); return context; }, this.#owner.owner) : undefined; } initializeService(initializer) { return initializer.prototype?.constructor ? Reflect.construct(initializer, []) : initializer(); } } /** * Creates a new registry for services. */ export function createRegistry(config) { return new Registry(config); } //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVnaXN0cnkuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvcmVnaXN0cnkudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFTLFFBQVEsRUFBRSxVQUFVLEVBQUUsTUFBTSxVQUFVLENBQUM7QUFDdkQsT0FBTyxFQUFFLHNCQUFzQixFQUFFLE1BQU0sV0FBVyxDQUFDO0FBQ25ELE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSxTQUFTLENBQUM7QUFFdkMsTUFBTSxPQUFPLE9BQU87Q0FBRztBQWF2Qjs7O0dBR0c7QUFDSCxNQUFNLE9BQU8sUUFBUTtJQUNuQixNQUFNLENBQWU7SUFDckIsT0FBTyxDQUFpQjtJQUN4QixNQUFNLENBQW9DO0lBRTFDLFlBQVksU0FBeUIsRUFBRTtRQUNyQyxJQUFJLENBQUMsT0FBTyxHQUFHLE1BQU0sQ0FBQztRQUN0QixJQUFJLENBQUMsTUFBTSxHQUFHLFFBQVEsRUFBRSxDQUFDO1FBQ3pCLElBQUksQ0FBQyxNQUFNLEdBQUcsSUFBSSxHQUFHLEVBQWdDLENBQUM7SUFDeEQsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0gsR0FBRyxDQUFvQixXQUFrQztRQUN2RCxNQUFNLGNBQWMsR0FBRyxJQUFJLENBQUMsaUJBQWlCLEVBQUUsQ0FBQztRQUVoRCxJQUFJLGNBQWMsRUFBRSxVQUFVLENBQUMsV0FBVyxDQUFDLEVBQUU7WUFDM0MsT0FBTyxjQUFjLENBQUMsR0FBRyxDQUFDLFdBQVcsQ0FBQyxDQUFDO1NBQ3hDO1FBRUQsT0FBTyxJQUFJLENBQUMsTUFBTSxDQUFDLEdBQUcsQ0FBQyxXQUFXLENBQUMsQ0FBQztJQUN0QyxDQUFDO0lBRUQ7Ozs7O09BS0c7SUFDSCxHQUFHLENBQW9CLFdBQWtDO1FBQ3ZELE1BQU0sY0FBYyxHQUFHLElBQUksQ0FBQyxpQkFBaUIsRUFBRSxDQUFDO1FBRWhELElBQUksY0FBYyxFQUFFLFVBQVUsQ0FBQyxXQUFXLENBQUMsRUFBRTtZQUMzQyxPQUFPLGNBQWMsQ0FBQyxHQUFHLENBQUMsV0FBVyxDQUFDLENBQUM7U0FDeEM7UUFFRCxPQUFPLElBQUksQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLFdBQVcsQ0FBQyxDQUFDO0lBQ3RDLENBQUM7SUFFRDs7T0FFRztJQUNILEtBQUs7UUFDSCxJQUFJLENBQUMsTUFBTSxDQUFDLEtBQUssRUFBRSxDQUFDO0lBQ3RCLENBQUM7SUFFRDs7T0FFRztJQUNILE1BQU0sQ0FBb0IsV0FBa0M7UUFDMUQsSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUFNLENBQUMsV0FBVyxDQUFDLENBQUM7SUFDbEMsQ0FBQztJQUVEOzs7Ozs7Ozs7O09BVUc7SUFDSCxRQUFRLENBQW9CLFdBQWtDO1FBQzVELE1BQU0sY0FBYyxHQUFHLElBQUksQ0FBQyxpQkFBaUIsRUFBRSxDQUFDO1FBRWhELElBQUksY0FBYyxFQUFFLFVBQVUsQ0FBQyxXQUFXLENBQUMsRUFBRTtZQUMzQyxPQUFPLGNBQWMsQ0FBQyxRQUFRLENBQUMsV0FBVyxDQUFDLENBQUM7U0FDN0M7UUFFRCxNQUFNLFlBQVksR0FBRyxZQUFZLENBQy9CLEdBQUcsRUFBRSxDQUFDLElBQUksQ0FBQyxpQkFBaUIsQ0FBQyxXQUFXLENBQUMsRUFDekMsSUFBSSxDQUFDLE1BQU0sQ0FDWixDQUFDO1FBRUYsSUFBSSxDQUFDLE1BQU0sQ0FBQyxHQUFHLENBQUMsV0FBVyxFQUFFLFlBQVksQ0FBQyxDQUFDO1FBRTNDLE9BQU8sWUFBWSxDQUFDO0lBQ3RCLENBQUM7SUFFUyxVQUFVLENBQ2xCLFdBQWtDO1FBRWxDLE9BQU8sQ0FDTCxJQUFJLENBQUMsT0FBTyxDQUFDLE1BQU0sS0FBSyxJQUFJO1lBQzVCLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQztnQkFDakMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxNQUFNLEVBQUUsUUFBUSxDQUFDLFdBQVcsQ0FBQyxDQUFDLENBQzlDLENBQUM7SUFDSixDQUFDO0lBRU8saUJBQWlCO1FBQ3ZCLE9BQU8sSUFBSSxDQUFDLE1BQU0sRUFBRSxLQUFLO1lBQ3ZCLENBQUMsQ0FBQyxZQUFZLENBQUMsQ0FBQyxPQUFPLEVBQUUsRUFBRTtnQkFDdkIsTUFBTSxPQUFPLEdBQUcsVUFBVSxDQUFDLHNCQUFzQixDQUFDLENBQUM7Z0JBQ25ELE9BQU8sRUFBRSxDQUFDO2dCQUNWLE9BQU8sT0FBTyxDQUFDO1lBQ2pCLENBQUMsRUFBRSxJQUFJLENBQUMsTUFBTSxDQUFDLEtBQUssQ0FBQztZQUN2QixDQUFDLENBQUMsU0FBUyxDQUFDO0lBQ2hCLENBQUM7SUFFTyxpQkFBaUIsQ0FDdkIsV0FBa0M7UUFFbEMsT0FBTyxXQUFXLENBQUMsU0FBUyxFQUFFLFdBQVc7WUFDdkMsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxTQUFTLENBQUMsV0FBVyxFQUFFLEVBQUUsQ0FBQztZQUNwQyxDQUFDLENBQUUsV0FBa0MsRUFBRSxDQUFDO0lBQzVDLENBQUM7Q0FDRjtBQUVEOztHQUVHO0FBQ0gsTUFBTSxVQUFVLGNBQWMsQ0FBQyxNQUF1QjtJQUNwRCxPQUFPLElBQUksUUFBUSxDQUFDLE1BQU0sQ0FBQyxDQUFDO0FBQzlCLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBPd25lciwgZ2V0T3duZXIsIHVzZUNvbnRleHQgfSBmcm9tIFwic29saWQtanNcIjtcbmltcG9ydCB7IFNlcnZpY2VSZWdpc3RyeUNvbnRleHQgfSBmcm9tIFwiLi9jb250ZXh0XCI7XG5pbXBvcnQgeyBydW5JblN1YlJvb3QgfSBmcm9tIFwiLi91dGlsc1wiO1xuXG5leHBvcnQgY2xhc3MgU2VydmljZSB7fVxuXG50eXBlIFNlcnZpY2VGdW5jdGlvbjxUIGV4dGVuZHMgU2VydmljZT4gPSAoKSA9PiBUO1xudHlwZSBTZXJ2aWNlQ29uc3RydWN0b3I8VCBleHRlbmRzIFNlcnZpY2U+ID0gbmV3ICgpID0+IFQ7XG5cbmV4cG9ydCB0eXBlIFNlcnZpY2VJbml0aWFsaXplcjxUIGV4dGVuZHMgU2VydmljZT4gPVxuICB8IFNlcnZpY2VGdW5jdGlvbjxUPlxuICB8IFNlcnZpY2VDb25zdHJ1Y3RvcjxUPjtcblxuZXhwb3J0IGludGVyZmFjZSBSZWdpc3RyeUNvbmZpZyB7XG4gIGV4cG9zZT86IFNlcnZpY2VJbml0aWFsaXplcjxhbnk+W10gfCBib29sZWFuO1xufVxuXG4vKipcbiAqIFJlZ2lzdHJ5IGlzIGEgY29udGFpbmVyIGZvciBzZXJ2aWNlcy5cbiAqIEl0IGlzIHVzZWQgdG8gcmVnaXN0ZXIgYW5kIHJldHJpZXZlIHNlcnZpY2VzLlxuICovXG5leHBvcnQgY2xhc3MgUmVnaXN0cnkge1xuICAjb3duZXI6IE93bmVyIHwgbnVsbDtcbiAgI2NvbmZpZzogUmVnaXN0cnlDb25maWc7XG4gICNjYWNoZTogTWFwPFNlcnZpY2VJbml0aWFsaXplcjxhbnk+LCBhbnk+O1xuXG4gIGNvbnN0cnVjdG9yKGNvbmZpZzogUmVnaXN0cnlDb25maWcgPSB7fSkge1xuICAgIHRoaXMuI2NvbmZpZyA9IGNvbmZpZztcbiAgICB0aGlzLiNvd25lciA9IGdldE93bmVyKCk7XG4gICAgdGhpcy4jY2FjaGUgPSBuZXcgTWFwPFNlcnZpY2VJbml0aWFsaXplcjxhbnk+LCBhbnk+KCk7XG4gIH1cblxuICAvKipcbiAgICogQ2hlY2tzIHdlYXRoZXIgdGhlIHJlZ2lzdHJ5IGhhcyBhIHNlcnZpY2UgcmVnaXN0ZXJlZCBmb3IgdGhlIGdpdmVuIGluaXRpYWxpemVyLlxuICAgKlxuICAgKiBGaXJzdCBpdCB3aWxsIGNoZWNrIGluIHRoZSBwYXJlbnQgcmVnaXN0cnkgYW5kIGlmIG5vIHNlcnZpY2UgaXMgcmVnaXN0ZXJlZCB0aGVyZSxcbiAgICogaXQgd2lsbCBjaGVjayBpbiB0aGUgY3VycmVudCByZWdpc3RyeS5cbiAgICovXG4gIGhhczxUIGV4dGVuZHMgU2VydmljZT4oaW5pdGlhbGl6ZXI6IFNlcnZpY2VJbml0aWFsaXplcjxUPik6IGJvb2xlYW4ge1xuICAgIGNvbnN0IHBhcmVudFJlZ2lzdHJ5ID0gdGhpcy5nZXRQYXJlbnRSZWdpc3RyeSgpO1xuXG4gICAgaWYgKHBhcmVudFJlZ2lzdHJ5Py5pc0V4cG9zaW5nKGluaXRpYWxpemVyKSkge1xuICAgICAgcmV0dXJuIHBhcmVudFJlZ2lzdHJ5Lmhhcyhpbml0aWFsaXplcik7XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXMuI2NhY2hlLmhhcyhpbml0aWFsaXplcik7XG4gIH1cblxuICAvKipcbiAgICogUmV0dXJucyB0aGUgc2VydmljZSByZWdpc3RlcmVkIGZvciB0aGUgZ2l2ZW4gaW5pdGlhbGl6ZXIuXG4gICAqXG4gICAqIEZpcnN0IGl0IHdpbGwgdHJ5IHRvIGZpbmQgaXQgaW4gdGhlIHBhcmVudCByZWdpc3RyeSBhbmQgaWYgbm8gc2VydmljZSBpcyByZWdpc3RlcmVkIHRoZXJlLFxuICAgKiBpdCB3aWxsIGNoZWNrIGluIHRoZSBjdXJyZW50IHJlZ2lzdHJ5LlxuICAgKi9cbiAgZ2V0PFQgZXh0ZW5kcyBTZXJ2aWNlPihpbml0aWFsaXplcjogU2VydmljZUluaXRpYWxpemVyPFQ+KTogVCB8IHVuZGVmaW5lZCB7XG4gICAgY29uc3QgcGFyZW50UmVnaXN0cnkgPSB0aGlzLmdldFBhcmVudFJlZ2lzdHJ5KCk7XG5cbiAgICBpZiAocGFyZW50UmVnaXN0cnk/LmlzRXhwb3NpbmcoaW5pdGlhbGl6ZXIpKSB7XG4gICAgICByZXR1cm4gcGFyZW50UmVnaXN0cnkuZ2V0KGluaXRpYWxpemVyKTtcbiAgICB9XG5cbiAgICByZXR1cm4gdGhpcy4jY2FjaGUuZ2V0KGluaXRpYWxpemVyKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDbGVhcnMgdGhlIHJlZ2lzdHJ5LlxuICAgKi9cbiAgY2xlYXIoKTogdm9pZCB7XG4gICAgdGhpcy4jY2FjaGUuY2xlYXIoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBEZWxldGVzIHJlZ2lzdGVyZWQgc2VydmljZSBmb3IgdGhlIGdpdmVuIGluaXRpYWxpemVyLlxuICAgKi9cbiAgZGVsZXRlPFQgZXh0ZW5kcyBTZXJ2aWNlPihpbml0aWFsaXplcjogU2VydmljZUluaXRpYWxpemVyPFQ+KTogdm9pZCB7XG4gICAgdGhpcy4jY2FjaGUuZGVsZXRlKGluaXRpYWxpemVyKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZWdpc3RlcnMgYSBzZXJ2aWNlIGZvciB0aGUgZ2l2ZW4gaW5pdGlhbGl6ZXIuXG4gICAqXG4gICAqIElmIHRoZSByZWdpc3RyeSBoYXMgYSBwYXJlbnQgcmVnaXN0cnksIGl0IHdpbGwgY2hlY2sgaWYgdGhlIHNlcnZpY2UgaXMgZXhwb3NlZCB0aGVyZS5cbiAgICpcbiAgICogSWYgaXQgaXMgZXhwb3NlZCwgaXQgd2lsbCByZWdpc3RlciB0aGUgc2VydmljZSBpbiB0aGUgcGFyZW50IHJlZ2lzdHJ5LlxuICAgKlxuICAgKiBJZiBpdCBpcyBub3QgZXhwb3NlZCwgaXQgd2lsbCByZWdpc3RlciB0aGUgc2VydmljZSBpbiB0aGUgY3VycmVudCByZWdpc3RyeS5cbiAgICpcbiAgICogSWYgdGhlIHJlZ2lzdHJ5IGRvZXMgbm90IGhhdmUgYSBwYXJlbnQgcmVnaXN0cnksIGl0IHdpbGwgcmVnaXN0ZXIgdGhlIHNlcnZpY2UgaW4gdGhlIGN1cnJlbnQgcmVnaXN0cnkuXG4gICAqL1xuICByZWdpc3RlcjxUIGV4dGVuZHMgU2VydmljZT4oaW5pdGlhbGl6ZXI6IFNlcnZpY2VJbml0aWFsaXplcjxUPik6IFQge1xuICAgIGNvbnN0IHBhcmVudFJlZ2lzdHJ5ID0gdGhpcy5nZXRQYXJlbnRSZWdpc3RyeSgpO1xuXG4gICAgaWYgKHBhcmVudFJlZ2lzdHJ5Py5pc0V4cG9zaW5nKGluaXRpYWxpemVyKSkge1xuICAgICAgcmV0dXJuIHBhcmVudFJlZ2lzdHJ5LnJlZ2lzdGVyKGluaXRpYWxpemVyKTtcbiAgICB9XG5cbiAgICBjb25zdCByZWdpc3RyYXRpb24gPSBydW5JblN1YlJvb3QoXG4gICAgICAoKSA9PiB0aGlzLmluaXRpYWxpemVTZXJ2aWNlKGluaXRpYWxpemVyKSxcbiAgICAgIHRoaXMuI293bmVyXG4gICAgKTtcblxuICAgIHRoaXMuI2NhY2hlLnNldChpbml0aWFsaXplciwgcmVnaXN0cmF0aW9uKTtcblxuICAgIHJldHVybiByZWdpc3RyYXRpb247XG4gIH1cblxuICBwcm90ZWN0ZWQgaXNFeHBvc2luZzxUIGV4dGVuZHMgU2VydmljZT4oXG4gICAgaW5pdGlhbGl6ZXI6IFNlcnZpY2VJbml0aWFsaXplcjxUPlxuICApOiBib29sZWFuIHtcbiAgICByZXR1cm4gKFxuICAgICAgdGhpcy4jY29uZmlnLmV4cG9zZSA9PT0gdHJ1ZSB8fFxuICAgICAgKEFycmF5LmlzQXJyYXkodGhpcy4jY29uZmlnLmV4cG9zZSkgJiZcbiAgICAgICAgdGhpcy4jY29uZmlnLmV4cG9zZT8uaW5jbHVkZXMoaW5pdGlhbGl6ZXIpKVxuICAgICk7XG4gIH1cblxuICBwcml2YXRlIGdldFBhcmVudFJlZ2lzdHJ5KCk6IFJlZ2lzdHJ5IHwgdW5kZWZpbmVkIHtcbiAgICByZXR1cm4gdGhpcy4jb3duZXI/Lm93bmVyXG4gICAgICA/IHJ1bkluU3ViUm9vdCgoZGlzcG9zZSkgPT4ge1xuICAgICAgICAgIGNvbnN0IGNvbnRleHQgPSB1c2VDb250ZXh0KFNlcnZpY2VSZWdpc3RyeUNvbnRleHQpO1xuICAgICAgICAgIGRpc3Bvc2UoKTtcbiAgICAgICAgICByZXR1cm4gY29udGV4dDtcbiAgICAgICAgfSwgdGhpcy4jb3duZXIub3duZXIpXG4gICAgICA6IHVuZGVmaW5lZDtcbiAgfVxuXG4gIHByaXZhdGUgaW5pdGlhbGl6ZVNlcnZpY2U8VCBleHRlbmRzIFNlcnZpY2U+KFxuICAgIGluaXRpYWxpemVyOiBTZXJ2aWNlSW5pdGlhbGl6ZXI8VD5cbiAgKTogVCB7XG4gICAgcmV0dXJuIGluaXRpYWxpemVyLnByb3RvdHlwZT8uY29uc3RydWN0b3JcbiAgICAgID8gUmVmbGVjdC5jb25zdHJ1Y3QoaW5pdGlhbGl6ZXIsIFtdKVxuICAgICAgOiAoaW5pdGlhbGl6ZXIgYXMgU2VydmljZUZ1bmN0aW9uPFQ+KSgpO1xuICB9XG59XG5cbi8qKlxuICogQ3JlYXRlcyBhIG5ldyByZWdpc3RyeSBmb3Igc2VydmljZXMuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVSZWdpc3RyeShjb25maWc/OiBSZWdpc3RyeUNvbmZpZyk6IFJlZ2lzdHJ5IHtcbiAgcmV0dXJuIG5ldyBSZWdpc3RyeShjb25maWcpO1xufVxuIl19