import { computed } from 'vue' import type { ComputedRef } from 'vue' import type { BioTemplateComponentBinding, BioTemplateComponentBindingsById, BioTemplateComponentImport, BioTemplateComponentPropsByComponent, BioTemplateComponentPropsBinding, BioTemplateComponentPropsById, BioTemplateComponentPropsLookupOptions, BioTemplateComponentSnippet, BioTemplateComponentUsage, } from './useBioTemplateComponents' /** * The template-component slice of `UseBioTemplateWorkspaceReturn`: the ~9 keys every * bio-template workspace composable (`useBioTemplateWorkspace`, `useBioTemplatePackWorkspace`, * `useBioTemplatePresetWorkspace`) re-exposes verbatim from `useBioTemplateComponents()`. */ export interface BioTemplateWorkspaceComponentBindings { componentBindings: BioTemplateComponentBinding[] componentBindingsById: BioTemplateComponentBindingsById componentImports: BioTemplateComponentImport[] componentProps: BioTemplateComponentPropsBinding[] componentPropsById: BioTemplateComponentPropsById componentPropsByComponent: BioTemplateComponentPropsByComponent componentSnippets: BioTemplateComponentSnippet[] componentUsage: BioTemplateComponentUsage | null getComponentProps: (component: string, options?: BioTemplateComponentPropsLookupOptions) => Record | undefined } /** Structural source shape accepted by {@link flattenWorkspaceComponentBindings}. */ export interface BioTemplateWorkspaceComponentSource { componentBindings: BioTemplateComponentBinding[] componentBindingsById: BioTemplateComponentBindingsById componentImports: BioTemplateComponentImport[] componentProps: BioTemplateComponentPropsBinding[] componentPropsById: BioTemplateComponentPropsById componentPropsByComponent: BioTemplateComponentPropsByComponent componentSnippets: BioTemplateComponentSnippet[] componentUsage: BioTemplateComponentUsage | null getComponentProps: (component: string, options?: BioTemplateComponentPropsLookupOptions) => Record | undefined } /** * Pick the shared template-component binding keys off a resolved bio-template workspace * (or its `components` source directly), so composables that build on `useBioTemplateWorkspace` * spread one object instead of re-listing all 9 keys by hand. * * @example Recommended * ```ts * const bindings = { renderer, ...flattenWorkspaceComponentBindings(components) } * ``` */ export function flattenWorkspaceComponentBindings( source: BioTemplateWorkspaceComponentSource, ): BioTemplateWorkspaceComponentBindings { return { componentBindings: source.componentBindings, componentBindingsById: source.componentBindingsById, componentImports: source.componentImports, componentProps: source.componentProps, componentPropsById: source.componentPropsById, componentPropsByComponent: source.componentPropsByComponent, componentSnippets: source.componentSnippets, componentUsage: source.componentUsage, getComponentProps: source.getComponentProps, } } /** Keys of {@link BioTemplateWorkspaceComponentBindings} that are plain (non-reactive) values, lifted to `ComputedRef`s by {@link liftWorkspaceComponentBindings}. */ export type LiftedBioTemplateWorkspaceComponentBindings = { [K in Exclude]: ComputedRef } & { getComponentProps: BioTemplateWorkspaceComponentBindings['getComponentProps'] } /** * `computed()`-lifted version of {@link flattenWorkspaceComponentBindings} for composables * that hold their resolved workspace behind a `ComputedRef` (e.g. a regenerated workspace * swapped in via `shallowRef`/`effectScope`), so each key stays independently reactive * instead of forcing consumers to unwrap the whole workspace to read one field. * `getComponentProps` stays a plain callable function, matching the un-lifted composables. * * @example Recommended * ```ts * const workspace = computed(() => workspaceRef.value) * const { componentBindings, componentProps, getComponentProps } = liftWorkspaceComponentBindings(workspace) * ``` */ export function liftWorkspaceComponentBindings( workspace: ComputedRef, ): LiftedBioTemplateWorkspaceComponentBindings { return { componentBindings: computed(() => workspace.value.componentBindings), componentBindingsById: computed(() => workspace.value.componentBindingsById), componentImports: computed(() => workspace.value.componentImports), componentProps: computed(() => workspace.value.componentProps), componentPropsById: computed(() => workspace.value.componentPropsById), componentPropsByComponent: computed(() => workspace.value.componentPropsByComponent), componentSnippets: computed(() => workspace.value.componentSnippets), componentUsage: computed(() => workspace.value.componentUsage), getComponentProps: (component: string, options?: BioTemplateComponentPropsLookupOptions) => workspace.value.getComponentProps(component, options), } }