import { ReadonlyReactive } from "@conterra/reactivity-core"; import { PackageIntl } from "./i18n"; /** Lifecycle hooks supported by the service interface. */ export interface ServiceLifecycleHooks { /** * Destroys the component. * Should clean up all resources used by the component. */ destroy?(): void; toString(): string; } export type Service = ServiceLifecycleHooks & Interface; /** * Represents metadata for an injected reference. */ export interface ReferenceMeta { /** * The unique service id of the injected service. */ serviceId: string; } /** * Contains metadata about injected references. * The key for the reference metadata is the reference's name. */ export type ReferencesMeta = { [referenceName in keyof References]: References[referenceName] extends any[] ? ReferenceMeta[] : ReferenceMeta; }; /** * Options passed to a service's constructor. */ export type ServiceOptions = { /** * References to other services. * These are injected by the runtime and match the declared references of the service. */ references: References; /** * Metadata about the injected references. * The object contains one entry for every reference injected via `references` (under the same key). * * If a single service has been injected, `referencesMeta[key]` will be of type {@link ReferenceMeta}. * If multiple services have been injected, an array of {@link ReferenceMeta} will be provided instead, * where the indices match the order in the injected references array. */ referencesMeta: ReferencesMeta; /** * Configuration properties. * * Default values are taken from the package's configuration, but these can be overridden * by the application. */ properties: Record; /** * A constant reference to the shared i18n object of the current package. * * @deprecated use `currentIntl` instead, which is a signal that returns the current i18n object and updates when it changes at runtime. Be aware to implement a watch for yourself */ intl: PackageIntl; /** * A signal that returns the current i18n object of the service's package. * * The i18n object may change at runtime (for example to implement hot reloading during development, * or to implement language changes while the application is running). */ currentIntl: ReadonlyReactive; }; /** * A service constructor returns a service instance when calling `new`. */ export type ServiceConstructor = { new (options: ServiceOptions): Service; }; /** * A service factory is an object that has a method to create a service instance. * The service factory itself can also implement lifecycle hooks, which will be called by the runtime * when the factory is destroyed. */ export type ServiceFactory = { /** * Method to create a service instance. * It is directly called by the runtime after constructing the factory. * NOTE: the service.destroy lifecycle hook is not called by the runtime. */ createService(): Interface; /** * Optional method to destroy a service instance created by this factory. * If provided, this method will be called by the runtime when the service instance is destroyed. * A factory instance exists per service, this method invocation means that the factory is no longer used by the runtime. */ destroyService?(service: Interface): void; }; /** * A constructor type for a service factory. * The service factory is an object that has a method to create a service instance, * this allows for more flexibility in service construction. */ export type ServiceFactoryConstructor = { new (options: ServiceOptions): ServiceFactory; }; /** * Symbol used to detect if a constructor function is a service factory constructor. */ declare const IS_SERVICE_FACTORY: unique symbol; export { IS_SERVICE_FACTORY }; /** * A service factory constructor must be marked * with the `IS_SERVICE_FACTORY` symbol to be recognized by the runtime as such. */ export type MarkedServiceFactoryConstructor = ServiceFactoryConstructor & { [IS_SERVICE_FACTORY]: true; }; /** * Utility function to mark a constructor as a service factory constructor. * @param ctr normal constructor function for a service factory. * @returns the same constructor function, but marked with the `IS_SERVICE_FACTORY` symbol so that the runtime recognizes it as a service factory constructor. */ export declare function defineServiceFactory(ctr: ServiceFactoryConstructor): MarkedServiceFactoryConstructor;