@jfdevelops/react-layout 0.17.5 → 0.18.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/create-config/component-keys.cjs +44 -0
- package/dist/create-config/component-keys.cjs.map +1 -0
- package/dist/create-config/component-keys.mjs +39 -0
- package/dist/create-config/component-keys.mjs.map +1 -0
- package/dist/create-config/define-layout.cjs +16 -1
- package/dist/create-config/define-layout.cjs.map +1 -1
- package/dist/create-config/define-layout.d.cts +5 -3
- package/dist/create-config/define-layout.d.cts.map +1 -1
- package/dist/create-config/define-layout.d.mts +5 -3
- package/dist/create-config/define-layout.d.mts.map +1 -1
- package/dist/create-config/define-layout.mjs +16 -1
- package/dist/create-config/define-layout.mjs.map +1 -1
- package/dist/create-config/for-paths/builder.cjs +192 -0
- package/dist/create-config/for-paths/builder.cjs.map +1 -0
- package/dist/create-config/for-paths/builder.d.cts +77 -0
- package/dist/create-config/for-paths/builder.d.cts.map +1 -0
- package/dist/create-config/for-paths/builder.d.mts +77 -0
- package/dist/create-config/for-paths/builder.d.mts.map +1 -0
- package/dist/create-config/for-paths/builder.mjs +192 -0
- package/dist/create-config/for-paths/builder.mjs.map +1 -0
- package/dist/create-config/for-paths/get-component-for-path.cjs +55 -0
- package/dist/create-config/for-paths/get-component-for-path.cjs.map +1 -0
- package/dist/create-config/for-paths/get-component-for-path.d.cts +55 -0
- package/dist/create-config/for-paths/get-component-for-path.d.cts.map +1 -0
- package/dist/create-config/for-paths/get-component-for-path.d.mts +55 -0
- package/dist/create-config/for-paths/get-component-for-path.d.mts.map +1 -0
- package/dist/create-config/for-paths/get-component-for-path.mjs +55 -0
- package/dist/create-config/for-paths/get-component-for-path.mjs.map +1 -0
- package/dist/create-config/for-paths/index.d.cts +2 -0
- package/dist/create-config/for-paths/index.d.mts +2 -0
- package/dist/create-config/get-component.cjs +60 -11
- package/dist/create-config/get-component.cjs.map +1 -1
- package/dist/create-config/get-component.d.cts +75 -6
- package/dist/create-config/get-component.d.cts.map +1 -1
- package/dist/create-config/get-component.d.mts +75 -6
- package/dist/create-config/get-component.d.mts.map +1 -1
- package/dist/create-config/get-component.mjs +61 -11
- package/dist/create-config/get-component.mjs.map +1 -1
- package/dist/create-config/index.d.cts +6 -1
- package/dist/create-config/index.d.mts +6 -1
- package/dist/create-config/is-sub-resource-key.cjs +15 -0
- package/dist/create-config/is-sub-resource-key.cjs.map +1 -0
- package/dist/create-config/is-sub-resource-key.d.cts +30 -0
- package/dist/create-config/is-sub-resource-key.d.cts.map +1 -0
- package/dist/create-config/is-sub-resource-key.d.mts +30 -0
- package/dist/create-config/is-sub-resource-key.d.mts.map +1 -0
- package/dist/create-config/is-sub-resource-key.mjs +15 -0
- package/dist/create-config/is-sub-resource-key.mjs.map +1 -0
- package/dist/create-config/paths/generate.cjs +77 -0
- package/dist/create-config/paths/generate.cjs.map +1 -0
- package/dist/create-config/paths/generate.mjs +77 -0
- package/dist/create-config/paths/generate.mjs.map +1 -0
- package/dist/create-config/paths/index.d.cts +2 -0
- package/dist/create-config/paths/index.d.mts +2 -0
- package/dist/create-config/paths/introspect.cjs +123 -0
- package/dist/create-config/paths/introspect.cjs.map +1 -0
- package/dist/create-config/paths/introspect.mjs +118 -0
- package/dist/create-config/paths/introspect.mjs.map +1 -0
- package/dist/create-config/paths/resolve.cjs +130 -0
- package/dist/create-config/paths/resolve.cjs.map +1 -0
- package/dist/create-config/paths/resolve.mjs +129 -0
- package/dist/create-config/paths/resolve.mjs.map +1 -0
- package/dist/create-config/paths/types.d.cts +104 -0
- package/dist/create-config/paths/types.d.cts.map +1 -0
- package/dist/create-config/paths/types.d.mts +104 -0
- package/dist/create-config/paths/types.d.mts.map +1 -0
- package/dist/create-config/paths/variables.cjs +32 -0
- package/dist/create-config/paths/variables.cjs.map +1 -0
- package/dist/create-config/paths/variables.d.cts +32 -0
- package/dist/create-config/paths/variables.d.cts.map +1 -0
- package/dist/create-config/paths/variables.d.mts +32 -0
- package/dist/create-config/paths/variables.d.mts.map +1 -0
- package/dist/create-config/paths/variables.mjs +29 -0
- package/dist/create-config/paths/variables.mjs.map +1 -0
- package/dist/create-config/types.d.cts +28 -8
- package/dist/create-config/types.d.cts.map +1 -1
- package/dist/create-config/types.d.mts +28 -8
- package/dist/create-config/types.d.mts.map +1 -1
- package/dist/errors/invalid-component.cjs +21 -0
- package/dist/errors/invalid-component.cjs.map +1 -0
- package/dist/errors/invalid-component.d.cts +18 -0
- package/dist/errors/invalid-component.d.cts.map +1 -0
- package/dist/errors/invalid-component.d.mts +18 -0
- package/dist/errors/invalid-component.d.mts.map +1 -0
- package/dist/errors/invalid-component.mjs +21 -0
- package/dist/errors/invalid-component.mjs.map +1 -0
- package/dist/errors/invalid-config.cjs +13 -0
- package/dist/errors/invalid-config.cjs.map +1 -0
- package/dist/errors/invalid-config.d.cts +15 -0
- package/dist/errors/invalid-config.d.cts.map +1 -0
- package/dist/errors/invalid-config.d.mts +15 -0
- package/dist/errors/invalid-config.d.mts.map +1 -0
- package/dist/errors/invalid-config.mjs +13 -0
- package/dist/errors/invalid-config.mjs.map +1 -0
- package/dist/errors/invalid-path.cjs +18 -0
- package/dist/errors/invalid-path.cjs.map +1 -0
- package/dist/errors/invalid-path.d.cts +16 -0
- package/dist/errors/invalid-path.d.cts.map +1 -0
- package/dist/errors/invalid-path.d.mts +16 -0
- package/dist/errors/invalid-path.d.mts.map +1 -0
- package/dist/errors/invalid-path.mjs +18 -0
- package/dist/errors/invalid-path.mjs.map +1 -0
- package/dist/errors/invalid-resource.cjs +18 -0
- package/dist/errors/invalid-resource.cjs.map +1 -0
- package/dist/errors/invalid-resource.d.cts +16 -0
- package/dist/errors/invalid-resource.d.cts.map +1 -0
- package/dist/errors/invalid-resource.d.mts +16 -0
- package/dist/errors/invalid-resource.d.mts.map +1 -0
- package/dist/errors/invalid-resource.mjs +18 -0
- package/dist/errors/invalid-resource.mjs.map +1 -0
- package/dist/errors/invalid-sub-resource.cjs +18 -0
- package/dist/errors/invalid-sub-resource.cjs.map +1 -0
- package/dist/errors/invalid-sub-resource.d.cts +17 -0
- package/dist/errors/invalid-sub-resource.d.cts.map +1 -0
- package/dist/errors/invalid-sub-resource.d.mts +17 -0
- package/dist/errors/invalid-sub-resource.d.mts.map +1 -0
- package/dist/errors/invalid-sub-resource.mjs +18 -0
- package/dist/errors/invalid-sub-resource.mjs.map +1 -0
- package/dist/errors/missing-path-variable.cjs +18 -0
- package/dist/errors/missing-path-variable.cjs.map +1 -0
- package/dist/errors/missing-path-variable.d.cts +16 -0
- package/dist/errors/missing-path-variable.d.cts.map +1 -0
- package/dist/errors/missing-path-variable.d.mts +16 -0
- package/dist/errors/missing-path-variable.d.mts.map +1 -0
- package/dist/errors/missing-path-variable.mjs +18 -0
- package/dist/errors/missing-path-variable.mjs.map +1 -0
- package/dist/errors/react-layout-error.cjs +56 -0
- package/dist/errors/react-layout-error.cjs.map +1 -0
- package/dist/errors/react-layout-error.d.cts +46 -0
- package/dist/errors/react-layout-error.d.cts.map +1 -0
- package/dist/errors/react-layout-error.d.mts +46 -0
- package/dist/errors/react-layout-error.d.mts.map +1 -0
- package/dist/errors/react-layout-error.mjs +54 -0
- package/dist/errors/react-layout-error.mjs.map +1 -0
- package/dist/index.cjs +15 -0
- package/dist/index.d.cts +13 -1
- package/dist/index.d.mts +13 -1
- package/dist/index.mjs +8 -1
- package/dist/props.d.cts +1 -1
- package/dist/props.d.cts.map +1 -1
- package/dist/props.d.mts +1 -1
- package/dist/props.d.mts.map +1 -1
- package/dist/resource.cjs.map +1 -1
- package/dist/resource.d.cts +2 -2
- package/dist/resource.d.cts.map +1 -1
- package/dist/resource.d.mts +2 -2
- package/dist/resource.d.mts.map +1 -1
- package/dist/resource.mjs.map +1 -1
- package/dist/utils.d.cts +2 -1
- package/dist/utils.d.cts.map +1 -1
- package/dist/utils.d.mts +2 -1
- package/dist/utils.d.mts.map +1 -1
- package/package.json +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"define-layout.mjs","names":[],"sources":["../../src/create-config/define-layout.tsx"],"sourcesContent":["import type { JSX } from 'react';\nimport {\n type ComposableComponents,\n type ComposableNameContext,\n type ComposableResourceLayout,\n type CreateLayoutComposable,\n collectComposablePresetEntries,\n LayoutComposablePresetProvider,\n MakeComposable,\n makeComposable,\n MakeComposableOptions,\n RequiredPresetLayoutProps,\n resolveLayoutComposables,\n} from '@jfdevelops/react-layout-composables';\nimport {\n type AnyBuiltPropDefinition,\n createPrimitivePropBuilder,\n createProp,\n type ResolveLayoutProps,\n type ResolveProps,\n resolvePropDefinitionValues,\n validateProps,\n} from '@jfdevelops/react-layout-validator';\nimport {\n IncludedProps,\n type IncludedPropBehavior,\n InferredInProps,\n InPropsDefinition,\n InPropsObject,\n LayoutRenderProps,\n MergedLayoutInProps,\n ResolvedIncludedComponentProps,\n ResolvedIncludedConfigProps,\n ResolvedIncludedProps,\n} from '../props';\nimport {\n normalizeResources,\n toResourceEnum,\n type LayoutResourceKey,\n type ResourceDefinition,\n} from '../resource';\nimport { BaseComponent, functionalUpdate, pick, Show, Updater } from '../utils';\nimport { capitalize } from '../utils/capitalize';\nimport {\n type CreateResourceConfigFn,\n createResourceConfig,\n} from './get-component';\nimport {\n createResourceLinksFn,\n type CreateResourceLinksFn,\n} from './create-resource-links';\nimport {\n createForResource,\n type CreateLayoutForResource,\n type CreateResourceLayoutOptions,\n type CreateResourceLayoutOptionsBase,\n} from './for-resource';\nimport {\n createForResources,\n type CreateResourceLayoutForResourcesFn,\n} from './for-resources';\n\nexport type LayoutIncludeProps<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Options extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n> = IncludedProps<MergedLayoutInProps<Resources, Options, Composables>>;\n\nexport type LayoutProps<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Options extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, Options, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = {\n /**\n * Props to include in the layout.\n */\n include?: LayoutIncludeProps<Resources, Options, Composables> & IncludeProps;\n /**\n * Custom props that the layout will receive.\n */\n custom?: CustomProps;\n};\n\ntype LayoutRenderContext<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Composables extends ComposableComponents,\n> = {\n composables: LayoutRenderComposables<Composables>;\n inProps: Record<string, unknown>;\n resource: LayoutResourceKey<Resources>;\n name: string;\n};\ntype LayoutRenderComposables<Composables extends ComposableComponents> = [\n keyof Composables,\n] extends [never]\n ? undefined\n : Composables;\n\ntype SplitLayoutInPropDefinition<\n Props extends InPropsObject = {},\n Content = unknown,\n> = {\n props?: Props;\n render: ((props: ResolveProps<Props>) => Content) | Content;\n};\n\nfunction isBuiltPropDefinition(\n value: unknown,\n): value is AnyBuiltPropDefinition {\n return typeof value === 'function' && value !== null && 'visibility' in value;\n}\n\nfunction isSplitLayoutInPropDefinition(\n value: unknown,\n): value is SplitLayoutInPropDefinition {\n return (\n value !== null &&\n typeof value === 'object' &&\n 'render' in value &&\n (value as { render?: unknown }).render !== undefined\n );\n}\n\nfunction isJSXElementDefinition(\n definition: unknown,\n): definition is AnyBuiltPropDefinition & { type: 'JSX.Element' } {\n return (\n isBuiltPropDefinition(definition) &&\n 'type' in definition &&\n definition.type === 'JSX.Element'\n );\n}\n\nfunction toLayoutRenderPropKey(includeKey: string, definition: unknown) {\n return isJSXElementDefinition(definition)\n ? capitalize(includeKey)\n : includeKey;\n}\n\nfunction readLayoutOptionValue(\n includeKey: string,\n definition: unknown,\n sources: Record<string, unknown>,\n) {\n const layoutOptionKeys = isJSXElementDefinition(definition)\n ? [capitalize(includeKey), includeKey]\n : [includeKey, capitalize(includeKey)];\n\n for (const key of layoutOptionKeys) {\n if (key in sources) {\n return sources[key];\n }\n }\n\n return undefined;\n}\n\nfunction getIncludedPropBehavior(value: unknown): IncludedPropBehavior | null {\n if (\n value !== null &&\n typeof value === 'object' &&\n 'visibility' in value &&\n 'passthrough' in value\n ) {\n return value as IncludedPropBehavior;\n }\n\n return null;\n}\n\nfunction isIncludedPropRequired(value: unknown) {\n return (\n value === true ||\n value === 'required' ||\n getIncludedPropBehavior(value)?.visibility === 'required'\n );\n}\n\nfunction allowsConfigPassthrough(value: unknown) {\n const behavior = getIncludedPropBehavior(value);\n\n return behavior ? behavior.passthrough === 'config' : true;\n}\n\nfunction allowsComponentPassthrough(value: unknown) {\n const behavior = getIncludedPropBehavior(value);\n\n return behavior\n ? behavior.passthrough === 'component'\n : value === 'optional';\n}\n\nfunction splitLayoutInProps(inProps: Record<string, unknown>) {\n const resolvedInProps: Record<string, AnyBuiltPropDefinition> = {};\n const splitInProps: Record<string, unknown> = {};\n\n for (const [key, value] of Object.entries(inProps)) {\n if (isBuiltPropDefinition(value)) {\n resolvedInProps[key] = value;\n continue;\n }\n\n if (isSplitLayoutInPropDefinition(value)) {\n splitInProps[key] = value.render;\n\n if (value.props && typeof value.props === 'object') {\n Object.assign(resolvedInProps, value.props);\n }\n }\n }\n\n return {\n resolvedInProps,\n splitInProps,\n };\n}\n\nfunction resolveLayoutOptionDefaults(\n defaults: Record<string, unknown>,\n options: Record<string, unknown>,\n) {\n const resolved = { ...options };\n\n for (const [key, defaultValue] of Object.entries(defaults)) {\n if (key in options) {\n if (typeof defaultValue === 'function') {\n resolved[key] = options[key];\n } else {\n resolved[key] = functionalUpdate(\n defaultValue,\n options[key] as Updater<unknown>,\n );\n }\n }\n }\n\n return resolved;\n}\n\ntype CreateViewMapOptions<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Options extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, Options, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = {\n /**\n * An array of valid resource names to support.\n */\n resources: Resources;\n /**\n * The options that are passed into the created resource layout.\n */\n options?: Options;\n layout: {\n /**\n * The props to pass to the layout.\n */\n props?: LayoutProps<\n Resources,\n Options,\n Composables,\n IncludeProps,\n CustomProps\n >;\n /**\n * Components used to compose the layout. Invoked per layout instance with\n * a scoped `create` that resolves composable `name` callbacks using the\n * layout's `resource` and `name`.\n */\n composables?: (\n create: CreateLayoutComposable<LayoutResourceKey<Resources>>,\n ) => Composables;\n /**\n * The render function for the layout.\n */\n render: (\n props: LayoutRenderProps<\n Resources,\n Options,\n Composables,\n IncludeProps,\n CustomProps\n >,\n context: LayoutRenderContext<Resources, Composables>,\n ) => JSX.Element;\n };\n};\n\ntype ResourceLayoutComposition<\n Name extends string,\n Composables extends ComposableComponents,\n> = [keyof Composables] extends [never]\n ? {}\n : {\n makeComposable: MakeComposable<Composables, Name>;\n };\nexport type ResourceLayoutComponent<\n Name extends string,\n Props extends InPropsObject = {},\n Composables extends ComposableComponents = {},\n Resource extends string = string,\n IncludedCallProps extends object = {},\n> = ResourceLayoutComposition<Name, Composables> &\n BaseComponent<Name, Show<ResolveProps<Props> & IncludedCallProps>> & {\n (props: Show<ResolveProps<Props> & IncludedCallProps>): JSX.Element;\n /**\n * A type-only property containing the resource associated with this\n * component. This property is `undefined` at runtime.\n */\n readonly resource: Resource;\n };\n\nexport type LayoutPropsForResource<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n> = [keyof IncludeProps] extends [never]\n ? ResolveLayoutProps<InferredInProps<Resources, InProps>> &\n RequiredPresetLayoutProps<Composables>\n : ResolvedIncludedConfigProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >;\n\ntype CreateResourceLayoutFnImpl<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = <\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n>(\n options: CreateResourceLayoutOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n Name,\n Resource,\n Props\n >,\n) => ResourceLayoutComponent<\n Name,\n CustomProps,\n Composables,\n Resource,\n ResolvedIncludedComponentProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >\n>;\n\nexport type CreateResourceLayoutMakeComposableOptions<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n> = CreateResourceLayoutOptionsBase<Resources, Name, Resource, Props> &\n Partial<\n LayoutPropsForResource<Resources, InProps, Composables, IncludeProps>\n >;\n\ntype CreateResourceLayoutMakeComposableFn<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables>,\n CustomProps extends InPropsObject,\n> = <\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n>(\n options: CreateResourceLayoutMakeComposableOptions<\n Resources,\n InProps,\n Composables,\n Name,\n Resource,\n Props,\n IncludeProps\n >,\n) => ComposableResourceLayout<Composables, Name, any, any, any>;\n\ntype CreateResourceLayoutFnBase<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = CreateResourceLayoutFnImpl<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n> & {\n /**\n * A function to create a resource layout for a specific resource.\n */\n forResource: CreateLayoutForResource<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n /**\n * Creates resource layout factories for multiple defined resources.\n */\n forResources: CreateResourceLayoutForResourcesFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n};\n\ntype CreateResourceLayoutMakeComposableMember<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables>,\n CustomProps extends InPropsObject,\n> = [keyof Composables] extends [never]\n ? {}\n : {\n makeComposable: CreateResourceLayoutMakeComposableFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n };\n\nexport type CreateResourceLayoutFn<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = CreateResourceLayoutFnBase<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n> &\n CreateResourceLayoutMakeComposableMember<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n\ntype DefinedResourceLayout<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = {\n createResourceConfig: CreateResourceConfigFn<Resources>;\n createResourceLayout: CreateResourceLayoutFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n createResourceLinks: CreateResourceLinksFn<Resources>;\n};\n\n\nfunction defineResourceLayoutImpl<\n const Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n const IncludeProps extends LayoutIncludeProps<\n Resources,\n InProps,\n Composables\n > = {},\n CustomProps extends InPropsObject = {},\n>(\n options: CreateViewMapOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >,\n): DefinedResourceLayout<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n> {\n const { options: inProps = {} as InProps, resources, layout } = options;\n const normalizedResources = normalizeResources(resources);\n const resourcesEnum = createPrimitivePropBuilder('string').enum(\n toResourceEnum(normalizedResources),\n );\n const definedResourceLayout = (<\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n >(\n layoutOptions: CreateResourceLayoutOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n Name,\n Resource,\n Props\n >,\n ) => {\n const {\n name,\n props: instancePropDefinitions,\n ...layoutOptionProps\n } = layoutOptions;\n const createComposableLayout =\n makeComposable<\n LayoutRenderProps<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >\n >();\n const nameProp = createProp.string().literal(name);\n const rawResolvedOptions =\n typeof inProps === 'function'\n ? inProps({\n resource: resourcesEnum,\n name: nameProp,\n })\n : inProps;\n const { resolvedInProps, splitInProps } = splitLayoutInProps({\n ...(rawResolvedOptions as Record<string, unknown>),\n ...(instancePropDefinitions as Record<string, unknown> | undefined),\n ...layoutOptionProps,\n });\n const { composables, render, props: layoutProps } = layout;\n const customLayoutProps = layoutProps?.custom;\n const includeLayoutProps = layoutProps?.include;\n const layoutOptionValues = layoutOptionProps as Record<string, unknown>;\n const resolvedLayoutProps = {\n ...customLayoutProps,\n };\n const layoutContext: ComposableNameContext<\n LayoutResourceKey<Resources>,\n typeof name\n > = {\n resource: layoutOptions.resource,\n name,\n capitalize,\n };\n const validationContext = {\n layoutName: name,\n resource: layoutContext.resource,\n };\n const resolvedComposables = composables\n ? resolveLayoutComposables(composables, layoutContext)\n : undefined;\n const mergedResolvedInProps = { ...resolvedInProps };\n\n for (const {\n props: presetPropDefinitions,\n } of collectComposablePresetEntries(resolvedComposables)) {\n Object.assign(mergedResolvedInProps, presetPropDefinitions);\n }\n\n const composablePresetProps = Object.fromEntries(\n collectComposablePresetEntries(resolvedComposables).map(\n ({ key, props: presetPropDefinitions }) => {\n const presetPropEntries = Object.entries(presetPropDefinitions);\n const validatedDefinitions = Object.fromEntries(\n presetPropEntries.filter(\n ([propKey]) => {\n const includeBehavior = includeLayoutProps?.[propKey];\n\n return (\n includeBehavior === undefined ||\n (allowsConfigPassthrough(includeBehavior) &&\n (isIncludedPropRequired(includeBehavior) ||\n layoutOptionValues[propKey] !== undefined))\n );\n },\n ),\n );\n const presetPropValues = Object.fromEntries(\n presetPropEntries.flatMap(([propKey]) =>\n propKey in layoutOptionValues\n ? [[propKey, layoutOptionValues[propKey]]]\n : [],\n ),\n );\n\n return [\n key,\n validateProps(\n validatedDefinitions as Record<\n string,\n AnyBuiltPropDefinition\n >,\n presetPropValues,\n validationContext,\n ),\n ];\n },\n ),\n );\n const mergedRenderContext = {\n composables: resolvedComposables as LayoutRenderComposables<Composables>,\n resource: layoutContext.resource,\n name: layoutContext.name,\n inProps: splitInProps,\n } as LayoutRenderContext<Resources, Composables>;\n\n function Component(\n props: Show<\n ResolveProps<CustomProps> &\n ResolvedIncludedComponentProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >\n >,\n ) {\n const validatedProps = validateProps(resolvedLayoutProps, props, {\n ...validationContext,\n });\n const includedPropKeys = Object.keys(includeLayoutProps ?? {});\n const includedPropDefinitions = pick(\n mergedResolvedInProps,\n includedPropKeys,\n ) as Record<string, unknown>;\n const includedPropValues = {\n ...resolvePropDefinitionValues(includedPropDefinitions),\n } as Record<string, unknown>;\n\n for (const key of includedPropKeys) {\n const definition = mergedResolvedInProps[key];\n const includeBehavior = includeLayoutProps?.[key];\n const callSiteValue = allowsComponentPassthrough(includeBehavior)\n ? readLayoutOptionValue(\n key,\n definition,\n props as Record<string, unknown>,\n )\n : undefined;\n const layoutOptionValue = allowsConfigPassthrough(includeBehavior)\n ? readLayoutOptionValue(key, definition, layoutOptionValues)\n : undefined;\n const splitValue = key in splitInProps ? splitInProps[key] : undefined;\n const value = callSiteValue ?? layoutOptionValue ?? splitValue;\n\n if (value !== undefined) {\n includedPropValues[key] = value;\n }\n }\n\n const requiredIncludedPropDefinitions = Object.fromEntries(\n Object.entries(includedPropDefinitions).filter(\n ([key]) => isIncludedPropRequired(includeLayoutProps?.[key]),\n ),\n );\n const optionalIncludedPropDefinitions = Object.fromEntries(\n Object.entries(includedPropDefinitions).filter(\n ([key]) =>\n !isIncludedPropRequired(includeLayoutProps?.[key]) &&\n includedPropValues[key] !== undefined,\n ),\n );\n const validatedIncludedProps = validateProps(\n {\n ...requiredIncludedPropDefinitions,\n ...optionalIncludedPropDefinitions,\n } as Record<string, AnyBuiltPropDefinition>,\n includedPropValues,\n validationContext,\n );\n const layoutRenderIncludedProps = Object.fromEntries(\n includedPropKeys.flatMap((key) => {\n if (!(key in validatedIncludedProps)) {\n return [];\n }\n\n return [\n [\n toLayoutRenderPropKey(key, mergedResolvedInProps[key]),\n validatedIncludedProps[\n key as keyof typeof validatedIncludedProps\n ],\n ],\n ];\n }),\n );\n const layoutRenderProps = {\n ...validatedProps,\n ...layoutRenderIncludedProps,\n } as unknown as LayoutRenderProps<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n\n return (\n <LayoutComposablePresetProvider value={composablePresetProps}>\n {render(layoutRenderProps, mergedRenderContext)}\n </LayoutComposablePresetProvider>\n );\n }\n\n function createComposition<\n LayoutName extends string,\n const Defined extends MakeComposableOptions<Composables, LayoutName>,\n >(compositionOptions: Defined) {\n if (!compositionOptions.components) {\n return {} as ResourceLayoutComposition<LayoutName, Composables>;\n }\n\n return {\n makeComposable: createComposableLayout(\n compositionOptions,\n ) as MakeComposable<Composables, LayoutName>,\n };\n }\n\n return Object.assign(Component, {\n displayName: name,\n props: undefined as unknown as Show<\n ResolveProps<CustomProps> &\n ResolvedIncludedComponentProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >\n >,\n resource: undefined as unknown as Resource,\n ...createComposition({\n components: resolvedComposables as Composables | undefined,\n name,\n }),\n });\n }) as CreateResourceLayoutFnImpl<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n const createTopLevelMakeComposable = () => {\n return (options: Record<string, unknown>) => {\n const layout = definedResourceLayout(options as never);\n\n if (\n !('makeComposable' in layout) ||\n typeof layout.makeComposable !== 'function'\n ) {\n throw new Error(\n 'makeComposable requires composables to be defined in the layout',\n );\n }\n\n return layout.makeComposable();\n };\n };\n\n function getComponentPropDefinitions(resource: LayoutResourceKey<Resources>) {\n const componentName = 'ScopedResourceComponent';\n const rawResolvedOptions =\n typeof inProps === 'function'\n ? inProps({\n resource: resourcesEnum,\n name: createProp.string().literal(componentName),\n })\n : inProps;\n const { resolvedInProps } = splitLayoutInProps(\n rawResolvedOptions as Record<string, unknown>,\n );\n const resolvedComposables = layout.composables\n ? resolveLayoutComposables(layout.composables, {\n resource,\n name: componentName,\n capitalize,\n })\n : undefined;\n\n for (const {\n props: presetPropDefinitions,\n } of collectComposablePresetEntries(resolvedComposables)) {\n Object.assign(resolvedInProps, presetPropDefinitions);\n }\n\n return {\n ...resolvedInProps,\n ...layout.props?.custom,\n };\n }\n\n const { createLayoutForResourceBuilder, forResource } = createForResource<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >({\n createResourceLayout: definedResourceLayout as never,\n resolveLayoutOptionDefaults,\n });\n const forResources = createForResources<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >({\n createLayoutForResource: createLayoutForResourceBuilder,\n ...(layout.composables\n ? { createMakeComposableLayout: createTopLevelMakeComposable }\n : {}),\n createResourceLayout: definedResourceLayout as never,\n getComponentPropDefinitions,\n });\n\n const createResourceLayoutExtras: {\n forResource: CreateLayoutForResource<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n forResources: CreateResourceLayoutForResourcesFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n makeComposable?: ReturnType<typeof createTopLevelMakeComposable>;\n } = {\n forResource,\n forResources,\n };\n\n if (layout.composables) {\n createResourceLayoutExtras.makeComposable = createTopLevelMakeComposable();\n }\n\n const createResourceLayout = Object.assign(\n definedResourceLayout,\n createResourceLayoutExtras,\n ) as CreateResourceLayoutFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n\n const createResourceLinks = createResourceLinksFn(resources);\n\n return {\n createResourceConfig,\n createResourceLayout,\n createResourceLinks,\n } as DefinedResourceLayout<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n}\n\ntype DefineResourceLayoutForResourcesOptions<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n ExtraResources extends ReadonlyArray<ResourceDefinition> = [],\n> = Omit<\n CreateViewMapOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >,\n 'resources'\n> & {\n /**\n * Additional resources to merge with those bound by\n * {@link defineResourceLayout.forResources}.\n */\n resources?: ExtraResources;\n};\n\ntype NonEmptyResourceDefinitions = readonly [\n ResourceDefinition,\n ...ResourceDefinition[],\n];\n\n/**\n * Factory returned by {@link DefineResourceLayout.forResources}.\n */\nexport type DefineResourceLayoutForResourcesFactory<\n BaseResources extends NonEmptyResourceDefinitions,\n> = <\n const ExtraResources extends ReadonlyArray<ResourceDefinition> = [],\n InProps extends InPropsDefinition<[...BaseResources, ...ExtraResources]> = {},\n Composables extends ComposableComponents = {},\n const IncludeProps extends LayoutIncludeProps<\n [...BaseResources, ...ExtraResources],\n InProps,\n Composables\n > = {},\n CustomProps extends InPropsObject = {},\n>(\n options: DefineResourceLayoutForResourcesOptions<\n [...BaseResources, ...ExtraResources],\n InProps,\n Composables,\n IncludeProps,\n CustomProps,\n ExtraResources\n >,\n) => DefinedResourceLayout<\n [...BaseResources, ...ExtraResources],\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n>;\n\n/**\n * Binds one or more resources, then accepts the remaining\n * {@link defineResourceLayout} options (with optional extra `resources`).\n */\nexport type DefineResourceLayoutForResources = <\n const Resources extends NonEmptyResourceDefinitions,\n>(\n ...resources: Resources\n) => DefineResourceLayoutForResourcesFactory<Resources>;\n\n/**\n * Creates a resource layout definition for a set of resources.\n */\nexport type DefineResourceLayoutFn = {\n <\n const Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n const IncludeProps extends LayoutIncludeProps<\n Resources,\n InProps,\n Composables\n > = {},\n CustomProps extends InPropsObject = {},\n >(\n options: CreateViewMapOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >,\n ): DefinedResourceLayout<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n};\n\nexport type DefineResourceLayout = DefineResourceLayoutFn & {\n forResources: DefineResourceLayoutForResources;\n};\n\nfunction defineResourceLayoutForResources<\n const Resources extends NonEmptyResourceDefinitions,\n>(\n ...baseResources: Resources\n): DefineResourceLayoutForResourcesFactory<Resources> {\n return ((options) => {\n const { resources: extraResources, ...rest } = options;\n const resources = extraResources\n ? [...baseResources, ...extraResources]\n : [...baseResources];\n\n return defineResourceLayoutImpl({\n ...rest,\n resources,\n } as never);\n }) as DefineResourceLayoutForResourcesFactory<Resources>;\n}\n\nexport const defineResourceLayout: DefineResourceLayout = Object.assign(\n defineResourceLayoutImpl as DefineResourceLayoutFn,\n {\n forResources: defineResourceLayoutForResources,\n },\n);\n"],"mappings":";;;;;;;;;;;;AA4GA,SAAS,sBACP,OACiC;CACjC,OAAO,OAAO,UAAU,cAAc,UAAU,QAAQ,gBAAgB;AAC1E;AAEA,SAAS,8BACP,OACsC;CACtC,OACE,UAAU,QACV,OAAO,UAAU,YACjB,YAAY,SACX,MAA+B,WAAW;AAE/C;AAEA,SAAS,uBACP,YACgE;CAChE,OACE,sBAAsB,UAAU,KAChC,UAAU,cACV,WAAW,SAAS;AAExB;AAEA,SAAS,sBAAsB,YAAoB,YAAqB;CACtE,OAAO,uBAAuB,UAAU,IACpC,WAAW,UAAU,IACrB;AACN;AAEA,SAAS,sBACP,YACA,YACA,SACA;CACA,MAAM,mBAAmB,uBAAuB,UAAU,IACtD,CAAC,WAAW,UAAU,GAAG,UAAU,IACnC,CAAC,YAAY,WAAW,UAAU,CAAC;CAEvC,KAAK,MAAM,OAAO,kBAChB,IAAI,OAAO,SACT,OAAO,QAAQ;AAKrB;AAEA,SAAS,wBAAwB,OAA6C;CAC5E,IACE,UAAU,QACV,OAAO,UAAU,YACjB,gBAAgB,SAChB,iBAAiB,OAEjB,OAAO;CAGT,OAAO;AACT;AAEA,SAAS,uBAAuB,OAAgB;CAC9C,OACE,UAAU,QACV,UAAU,cACV,wBAAwB,KAAK,GAAG,eAAe;AAEnD;AAEA,SAAS,wBAAwB,OAAgB;CAC/C,MAAM,WAAW,wBAAwB,KAAK;CAE9C,OAAO,WAAW,SAAS,gBAAgB,WAAW;AACxD;AAEA,SAAS,2BAA2B,OAAgB;CAClD,MAAM,WAAW,wBAAwB,KAAK;CAE9C,OAAO,WACH,SAAS,gBAAgB,cACzB,UAAU;AAChB;AAEA,SAAS,mBAAmB,SAAkC;CAC5D,MAAM,kBAA0D,CAAC;CACjE,MAAM,eAAwC,CAAC;CAE/C,KAAK,MAAM,CAAC,KAAK,UAAU,OAAO,QAAQ,OAAO,GAAG;EAClD,IAAI,sBAAsB,KAAK,GAAG;GAChC,gBAAgB,OAAO;GACvB;EACF;EAEA,IAAI,8BAA8B,KAAK,GAAG;GACxC,aAAa,OAAO,MAAM;GAE1B,IAAI,MAAM,SAAS,OAAO,MAAM,UAAU,UACxC,OAAO,OAAO,iBAAiB,MAAM,KAAK;EAE9C;CACF;CAEA,OAAO;EACL;EACA;CACF;AACF;AAEA,SAAS,4BACP,UACA,SACA;CACA,MAAM,WAAW,EAAE,GAAG,QAAQ;CAE9B,KAAK,MAAM,CAAC,KAAK,iBAAiB,OAAO,QAAQ,QAAQ,GACvD,IAAI,OAAO,SACT,IAAI,OAAO,iBAAiB,YAC1B,SAAS,OAAO,QAAQ;MAExB,SAAS,OAAO,iBACd,cACA,QAAQ,IACV;CAKN,OAAO;AACT;AAwPA,SAAS,yBAWP,SAaA;CACA,MAAM,EAAE,SAAS,UAAU,CAAC,GAAc,WAAW,WAAW;CAChE,MAAM,sBAAsB,mBAAmB,SAAS;CACxD,MAAM,gBAAgB,2BAA2B,QAAQ,EAAE,KACzD,eAAe,mBAAmB,CACpC;CACA,MAAM,0BAKJ,kBASG;EACH,MAAM,EACJ,MACA,OAAO,yBACP,GAAG,sBACD;EACJ,MAAM,yBACJ,eAQE;EACJ,MAAM,WAAW,WAAW,OAAO,EAAE,QAAQ,IAAI;EAQjD,MAAM,EAAE,iBAAiB,iBAAiB,mBAAmB;GAC3D,GAPA,OAAO,YAAY,aACf,QAAQ;IACN,UAAU;IACV,MAAM;GACR,CAAC,IACD;GAGJ,GAAI;GACJ,GAAG;EACL,CAAC;EACD,MAAM,EAAE,aAAa,QAAQ,OAAO,gBAAgB;EACpD,MAAM,oBAAoB,aAAa;EACvC,MAAM,qBAAqB,aAAa;EACxC,MAAM,qBAAqB;EAC3B,MAAM,sBAAsB,EAC1B,GAAG,kBACL;EACA,MAAM,gBAGF;GACF,UAAU,cAAc;GACxB;GACA;EACF;EACA,MAAM,oBAAoB;GACxB,YAAY;GACZ,UAAU,cAAc;EAC1B;EACA,MAAM,sBAAsB,cACxB,yBAAyB,aAAa,aAAa,IACnD;EACJ,MAAM,wBAAwB,EAAE,GAAG,gBAAgB;EAEnD,KAAK,MAAM,EACT,OAAO,2BACJ,+BAA+B,mBAAmB,GACrD,OAAO,OAAO,uBAAuB,qBAAqB;EAG5D,MAAM,wBAAwB,OAAO,YACnC,+BAA+B,mBAAmB,EAAE,KACjD,EAAE,KAAK,OAAO,4BAA4B;GACzC,MAAM,oBAAoB,OAAO,QAAQ,qBAAqB;GAuB9D,OAAO,CACL,KACA,cAxB2B,OAAO,YAClC,kBAAkB,QACf,CAAC,aAAa;IACb,MAAM,kBAAkB,qBAAqB;IAE7C,OACE,oBAAoB,UACnB,wBAAwB,eAAe,MACrC,uBAAuB,eAAe,KACrC,mBAAmB,aAAa;GAExC,CACF,CAaqB,GAXE,OAAO,YAC9B,kBAAkB,SAAS,CAAC,aAC1B,WAAW,qBACP,CAAC,CAAC,SAAS,mBAAmB,QAAQ,CAAC,IACvC,CAAC,CACP,CAUiB,GACf,iBACF,CACF;EACF,CACF,CACF;EACA,MAAM,sBAAsB;GAC1B,aAAa;GACb,UAAU,cAAc;GACxB,MAAM,cAAc;GACpB,SAAS;EACX;EAEA,SAAS,UACP,OAOA;GACA,MAAM,iBAAiB,cAAc,qBAAqB,OAAO,EAC/D,GAAG,kBACL,CAAC;GACD,MAAM,mBAAmB,OAAO,KAAK,sBAAsB,CAAC,CAAC;GAC7D,MAAM,0BAA0B,KAC9B,uBACA,gBACF;GACA,MAAM,qBAAqB,EACzB,GAAG,4BAA4B,uBAAuB,EACxD;GAEA,KAAK,MAAM,OAAO,kBAAkB;IAClC,MAAM,aAAa,sBAAsB;IACzC,MAAM,kBAAkB,qBAAqB;IAC7C,MAAM,gBAAgB,2BAA2B,eAAe,IAC5D,sBACE,KACA,YACA,KACF,IACA;IACJ,MAAM,oBAAoB,wBAAwB,eAAe,IAC7D,sBAAsB,KAAK,YAAY,kBAAkB,IACzD;IACJ,MAAM,aAAa,OAAO,eAAe,aAAa,OAAO;IAC7D,MAAM,QAAQ,iBAAiB,qBAAqB;IAEpD,IAAI,UAAU,QACZ,mBAAmB,OAAO;GAE9B;GAEA,MAAM,kCAAkC,OAAO,YAC7C,OAAO,QAAQ,uBAAuB,EAAE,QACrC,CAAC,SAAS,uBAAuB,qBAAqB,IAAI,CAC7D,CACF;GACA,MAAM,kCAAkC,OAAO,YAC7C,OAAO,QAAQ,uBAAuB,EAAE,QACrC,CAAC,SACA,CAAC,uBAAuB,qBAAqB,IAAI,KACjD,mBAAmB,SAAS,MAChC,CACF;GACA,MAAM,yBAAyB,cAC7B;IACE,GAAG;IACH,GAAG;GACL,GACA,oBACA,iBACF;GACA,MAAM,4BAA4B,OAAO,YACvC,iBAAiB,SAAS,QAAQ;IAChC,IAAI,EAAE,OAAO,yBACX,OAAO,CAAC;IAGV,OAAO,CACL,CACE,sBAAsB,KAAK,sBAAsB,IAAI,GACrD,uBACE,IAEJ,CACF;GACF,CAAC,CACH;GAYA,OACE,oBAAC,gCAAD;IAAgC,OAAO;cACpC,OAAO;KAZV,GAAG;KACH,GAAG;IAWuB,GAAG,mBAAmB;GAChB;EAEpC;EAEA,SAAS,kBAGP,oBAA6B;GAC7B,IAAI,CAAC,mBAAmB,YACtB,OAAO,CAAC;GAGV,OAAO,EACL,gBAAgB,uBACd,kBACF,EACF;EACF;EAEA,OAAO,OAAO,OAAO,WAAW;GAC9B,aAAa;GACb,OAAO;GAOP,UAAU;GACV,GAAG,kBAAkB;IACnB,YAAY;IACZ;GACF,CAAC;EACH,CAAC;CACH;CAOA,MAAM,qCAAqC;EACzC,QAAQ,YAAqC;GAC3C,MAAM,SAAS,sBAAsB,OAAgB;GAErD,IACE,EAAE,oBAAoB,WACtB,OAAO,OAAO,mBAAmB,YAEjC,MAAM,IAAI,MACR,iEACF;GAGF,OAAO,OAAO,eAAe;EAC/B;CACF;CAEA,SAAS,4BAA4B,UAAwC;EAC3E,MAAM,gBAAgB;EAQtB,MAAM,EAAE,oBAAoB,mBAN1B,OAAO,YAAY,aACf,QAAQ;GACN,UAAU;GACV,MAAM,WAAW,OAAO,EAAE,QAAQ,aAAa;EACjD,CAAC,IACD,OAGN;EACA,MAAM,sBAAsB,OAAO,cAC/B,yBAAyB,OAAO,aAAa;GAC3C;GACA,MAAM;GACN;EACF,CAAC,IACD;EAEJ,KAAK,MAAM,EACT,OAAO,2BACJ,+BAA+B,mBAAmB,GACrD,OAAO,OAAO,iBAAiB,qBAAqB;EAGtD,OAAO;GACL,GAAG;GACH,GAAG,OAAO,OAAO;EACnB;CACF;CAEA,MAAM,EAAE,gCAAgC,gBAAgB,kBAMtD;EACA,sBAAsB;EACtB;CACF,CAAC;CAgBD,MAAM,6BAgBF;EACF;EACA,cAjCmB,mBAMnB;GACA,yBAAyB;GACzB,GAAI,OAAO,cACP,EAAE,4BAA4B,6BAA6B,IAC3D,CAAC;GACL,sBAAsB;GACtB;EACF,CAoBa;CACb;CAEA,IAAI,OAAO,aACT,2BAA2B,iBAAiB,6BAA6B;CAgB3E,OAAO;EACL;EACA,sBAf2B,OAAO,OAClC,uBACA,0BAamB;EACnB,qBAL0B,sBAAsB,SAK9B;CACpB;AAOF;AA4GA,SAAS,iCAGP,GAAG,eACiD;CACpD,SAAS,YAAY;EACnB,MAAM,EAAE,WAAW,gBAAgB,GAAG,SAAS;EAC/C,MAAM,YAAY,iBACd,CAAC,GAAG,eAAe,GAAG,cAAc,IACpC,CAAC,GAAG,aAAa;EAErB,OAAO,yBAAyB;GAC9B,GAAG;GACH;EACF,CAAU;CACZ;AACF;AAEA,MAAa,uBAA6C,OAAO,OAC/D,0BACA,EACE,cAAc,iCAChB,CACF"}
|
|
1
|
+
{"version":3,"file":"define-layout.mjs","names":[],"sources":["../../src/create-config/define-layout.tsx"],"sourcesContent":["import type { JSX } from 'react';\nimport {\n type ComposableComponents,\n type ComposableNameContext,\n type ComposableResourceLayout,\n type CreateLayoutComposable,\n collectComposablePresetEntries,\n LayoutComposablePresetProvider,\n MakeComposable,\n makeComposable,\n MakeComposableOptions,\n RequiredPresetLayoutProps,\n resolveLayoutComposables,\n} from '@jfdevelops/react-layout-composables';\nimport {\n type AnyBuiltPropDefinition,\n createPrimitivePropBuilder,\n createProp,\n type ResolveLayoutProps,\n type ResolveProps,\n resolvePropDefinitionValues,\n validateProps,\n} from '@jfdevelops/react-layout-validator';\nimport {\n IncludedProps,\n type IncludedPropBehavior,\n InferredInProps,\n InPropsDefinition,\n InPropsObject,\n LayoutRenderProps,\n MergedLayoutInProps,\n ResolvedIncludedComponentProps,\n ResolvedIncludedConfigProps,\n ResolvedIncludedProps,\n} from '../props';\nimport {\n normalizeResources,\n toResourceEnum,\n type LayoutResourceKey,\n type ResourceDefinition,\n} from '../resource';\nimport { BaseComponent, functionalUpdate, pick, Show, Updater } from '../utils';\nimport { capitalize } from '../utils/capitalize';\nimport { InvalidConfigError } from '../errors';\nimport { isResourceConfigComponentKey } from './component-keys';\nimport {\n type CreateResourceConfigFn,\n createResourceConfig,\n} from './get-component';\nimport type { AssertUnreservedResources } from './types';\nimport {\n createResourceLinksFn,\n type CreateResourceLinksFn,\n} from './create-resource-links';\nimport {\n createForResource,\n type CreateLayoutForResource,\n type CreateResourceLayoutOptions,\n type CreateResourceLayoutOptionsBase,\n} from './for-resource';\nimport {\n createForResources,\n type CreateResourceLayoutForResourcesFn,\n} from './for-resources';\n\nexport type LayoutIncludeProps<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Options extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n> = IncludedProps<MergedLayoutInProps<Resources, Options, Composables>>;\n\nexport type LayoutProps<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Options extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, Options, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = {\n /**\n * Props to include in the layout.\n */\n include?: LayoutIncludeProps<Resources, Options, Composables> & IncludeProps;\n /**\n * Custom props that the layout will receive.\n */\n custom?: CustomProps;\n};\n\ntype LayoutRenderContext<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Composables extends ComposableComponents,\n> = {\n composables: LayoutRenderComposables<Composables>;\n inProps: Record<string, unknown>;\n resource: LayoutResourceKey<Resources>;\n name: string;\n};\ntype LayoutRenderComposables<Composables extends ComposableComponents> = [\n keyof Composables,\n] extends [never]\n ? undefined\n : Composables;\n\ntype SplitLayoutInPropDefinition<\n Props extends InPropsObject = {},\n Content = unknown,\n> = {\n props?: Props;\n render: ((props: ResolveProps<Props>) => Content) | Content;\n};\n\nfunction isBuiltPropDefinition(\n value: unknown,\n): value is AnyBuiltPropDefinition {\n return typeof value === 'function' && value !== null && 'visibility' in value;\n}\n\nfunction isSplitLayoutInPropDefinition(\n value: unknown,\n): value is SplitLayoutInPropDefinition {\n return (\n value !== null &&\n typeof value === 'object' &&\n 'render' in value &&\n (value as { render?: unknown }).render !== undefined\n );\n}\n\nfunction isJSXElementDefinition(\n definition: unknown,\n): definition is AnyBuiltPropDefinition & { type: 'JSX.Element' } {\n return (\n isBuiltPropDefinition(definition) &&\n 'type' in definition &&\n definition.type === 'JSX.Element'\n );\n}\n\nfunction toLayoutRenderPropKey(includeKey: string, definition: unknown) {\n return isJSXElementDefinition(definition)\n ? capitalize(includeKey)\n : includeKey;\n}\n\nfunction readLayoutOptionValue(\n includeKey: string,\n definition: unknown,\n sources: Record<string, unknown>,\n) {\n const layoutOptionKeys = isJSXElementDefinition(definition)\n ? [capitalize(includeKey), includeKey]\n : [includeKey, capitalize(includeKey)];\n\n for (const key of layoutOptionKeys) {\n if (key in sources) {\n return sources[key];\n }\n }\n\n return undefined;\n}\n\nfunction getIncludedPropBehavior(value: unknown): IncludedPropBehavior | null {\n if (\n value !== null &&\n typeof value === 'object' &&\n 'visibility' in value &&\n 'passthrough' in value\n ) {\n return value as IncludedPropBehavior;\n }\n\n return null;\n}\n\nfunction isIncludedPropRequired(value: unknown) {\n return (\n value === true ||\n value === 'required' ||\n getIncludedPropBehavior(value)?.visibility === 'required'\n );\n}\n\nfunction allowsConfigPassthrough(value: unknown) {\n const behavior = getIncludedPropBehavior(value);\n\n if (!behavior) {\n return true;\n }\n\n if (behavior.passthrough === 'config') {\n return true;\n }\n\n // optional + component passthrough still accepts create-time defaults\n return (\n behavior.passthrough === 'component' && behavior.visibility === 'optional'\n );\n}\n\nfunction allowsComponentPassthrough(value: unknown) {\n const behavior = getIncludedPropBehavior(value);\n\n return behavior\n ? behavior.passthrough === 'component'\n : value === 'optional';\n}\n\nfunction splitLayoutInProps(inProps: Record<string, unknown>) {\n const resolvedInProps: Record<string, AnyBuiltPropDefinition> = {};\n const splitInProps: Record<string, unknown> = {};\n\n for (const [key, value] of Object.entries(inProps)) {\n if (isBuiltPropDefinition(value)) {\n resolvedInProps[key] = value;\n continue;\n }\n\n if (isSplitLayoutInPropDefinition(value)) {\n splitInProps[key] = value.render;\n\n if (value.props && typeof value.props === 'object') {\n Object.assign(resolvedInProps, value.props);\n }\n }\n }\n\n return {\n resolvedInProps,\n splitInProps,\n };\n}\n\nfunction resolveLayoutOptionDefaults(\n defaults: Record<string, unknown>,\n options: Record<string, unknown>,\n) {\n const resolved = { ...options };\n\n for (const [key, defaultValue] of Object.entries(defaults)) {\n if (key in options) {\n if (typeof defaultValue === 'function') {\n resolved[key] = options[key];\n } else {\n resolved[key] = functionalUpdate(\n defaultValue,\n options[key] as Updater<unknown>,\n );\n }\n }\n }\n\n return resolved;\n}\n\ntype CreateViewMapOptions<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Options extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, Options, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = {\n /**\n * An array of valid resource names to support. Nested sub-resource slugs that\n * collide with config keys (`component`, `detail`, `new`, …) are reserved.\n */\n resources: AssertUnreservedResources<Resources>;\n /**\n * The options that are passed into the created resource layout.\n */\n options?: Options;\n layout: {\n /**\n * The props to pass to the layout.\n */\n props?: LayoutProps<\n Resources,\n Options,\n Composables,\n IncludeProps,\n CustomProps\n >;\n /**\n * Components used to compose the layout. Invoked per layout instance with\n * a scoped `create` that resolves composable `name` callbacks using the\n * layout's `resource` and `name`.\n */\n composables?: (\n create: CreateLayoutComposable<LayoutResourceKey<Resources>>,\n ) => Composables;\n /**\n * The render function for the layout.\n */\n render: (\n props: LayoutRenderProps<\n Resources,\n Options,\n Composables,\n IncludeProps,\n CustomProps\n >,\n context: LayoutRenderContext<Resources, Composables>,\n ) => JSX.Element;\n };\n};\n\ntype ResourceLayoutComposition<\n Name extends string,\n Composables extends ComposableComponents,\n> = [keyof Composables] extends [never]\n ? {}\n : {\n makeComposable: MakeComposable<Composables, Name>;\n };\nexport type ResourceLayoutComponent<\n Name extends string,\n Props extends InPropsObject = {},\n Composables extends ComposableComponents = {},\n Resource extends string = string,\n IncludedCallProps extends object = {},\n> = ResourceLayoutComposition<Name, Composables> &\n BaseComponent<Name, Show<ResolveProps<Props> & IncludedCallProps>> & {\n (props: Show<ResolveProps<Props> & IncludedCallProps>): JSX.Element;\n /**\n * A type-only property containing the resource associated with this\n * component. This property is `undefined` at runtime.\n */\n readonly resource: Resource;\n };\n\nexport type LayoutPropsForResource<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n> = [keyof IncludeProps] extends [never]\n ? ResolveLayoutProps<InferredInProps<Resources, InProps>> &\n RequiredPresetLayoutProps<Composables>\n : ResolvedIncludedConfigProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >;\n\ntype CreateResourceLayoutFnImpl<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = <\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n>(\n options: CreateResourceLayoutOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n Name,\n Resource,\n Props\n >,\n) => ResourceLayoutComponent<\n Name,\n CustomProps,\n Composables,\n Resource,\n ResolvedIncludedComponentProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >\n>;\n\nexport type CreateResourceLayoutMakeComposableOptions<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n> = CreateResourceLayoutOptionsBase<Resources, Name, Resource, Props> &\n Partial<\n LayoutPropsForResource<Resources, InProps, Composables, IncludeProps>\n >;\n\ntype CreateResourceLayoutMakeComposableFn<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables>,\n CustomProps extends InPropsObject,\n> = <\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n>(\n options: CreateResourceLayoutMakeComposableOptions<\n Resources,\n InProps,\n Composables,\n Name,\n Resource,\n Props,\n IncludeProps\n >,\n) => ComposableResourceLayout<Composables, Name, any, any, any>;\n\ntype CreateResourceLayoutFnBase<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = CreateResourceLayoutFnImpl<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n> & {\n /**\n * A function to create a resource layout for a specific resource.\n */\n forResource: CreateLayoutForResource<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n /**\n * Creates resource layout factories for multiple defined resources.\n */\n forResources: CreateResourceLayoutForResourcesFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n};\n\ntype CreateResourceLayoutMakeComposableMember<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents,\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables>,\n CustomProps extends InPropsObject,\n> = [keyof Composables] extends [never]\n ? {}\n : {\n makeComposable: CreateResourceLayoutMakeComposableFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n };\n\nexport type CreateResourceLayoutFn<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = CreateResourceLayoutFnBase<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n> &\n CreateResourceLayoutMakeComposableMember<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n\ntype DefinedResourceLayout<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources>,\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n> = {\n createResourceConfig: CreateResourceConfigFn<Resources>;\n createResourceLayout: CreateResourceLayoutFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n createResourceLinks: CreateResourceLinksFn<Resources>;\n};\n\nfunction readResourceSlug(resource: ResourceDefinition) {\n return typeof resource === 'string' ? resource : resource.value;\n}\n\nfunction assertUnreservedResourceSlugs(\n resources: ReadonlyArray<ResourceDefinition>,\n owner?: string,\n) {\n for (const resource of resources) {\n const slug = readResourceSlug(resource);\n\n if (owner !== undefined && isResourceConfigComponentKey(slug)) {\n throw new InvalidConfigError({\n reason: `Sub-resource \"${slug}\" under \"${owner}\" collides with a reserved config key`,\n });\n }\n\n if (typeof resource !== 'string') {\n assertUnreservedResourceSlugs(resource.subResources, slug);\n }\n }\n}\n\nfunction defineResourceLayoutImpl<\n const Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n const IncludeProps extends LayoutIncludeProps<\n Resources,\n InProps,\n Composables\n > = {},\n CustomProps extends InPropsObject = {},\n>(\n options: CreateViewMapOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >,\n): DefinedResourceLayout<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n> {\n const { options: inProps = {} as InProps, resources, layout } = options;\n\n assertUnreservedResourceSlugs(resources);\n\n const normalizedResources = normalizeResources(resources);\n const resourcesEnum = createPrimitivePropBuilder('string').enum(\n toResourceEnum(normalizedResources),\n );\n const definedResourceLayout = (<\n Name extends string,\n Resource extends LayoutResourceKey<Resources>,\n Props extends InPropsObject = {},\n >(\n layoutOptions: CreateResourceLayoutOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n Name,\n Resource,\n Props\n >,\n ) => {\n const {\n name,\n props: instancePropDefinitions,\n ...layoutOptionProps\n } = layoutOptions;\n const createComposableLayout =\n makeComposable<\n LayoutRenderProps<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >\n >();\n const nameProp = createProp.string().literal(name);\n const rawResolvedOptions =\n typeof inProps === 'function'\n ? inProps({\n resource: resourcesEnum,\n name: nameProp,\n })\n : inProps;\n const { resolvedInProps, splitInProps } = splitLayoutInProps({\n ...(rawResolvedOptions as Record<string, unknown>),\n ...(instancePropDefinitions as Record<string, unknown> | undefined),\n ...layoutOptionProps,\n });\n const { composables, render, props: layoutProps } = layout;\n const customLayoutProps = layoutProps?.custom;\n const includeLayoutProps = layoutProps?.include;\n const layoutOptionValues = layoutOptionProps as Record<string, unknown>;\n const resolvedLayoutProps = {\n ...customLayoutProps,\n };\n const layoutContext: ComposableNameContext<\n LayoutResourceKey<Resources>,\n typeof name\n > = {\n resource: layoutOptions.resource,\n name,\n capitalize,\n };\n const validationContext = {\n layoutName: name,\n resource: layoutContext.resource,\n };\n const resolvedComposables = composables\n ? resolveLayoutComposables(composables, layoutContext)\n : undefined;\n const mergedResolvedInProps = { ...resolvedInProps };\n\n for (const {\n props: presetPropDefinitions,\n } of collectComposablePresetEntries(resolvedComposables)) {\n Object.assign(mergedResolvedInProps, presetPropDefinitions);\n }\n\n const composablePresetProps = Object.fromEntries(\n collectComposablePresetEntries(resolvedComposables).map(\n ({ key, props: presetPropDefinitions }) => {\n const presetPropEntries = Object.entries(presetPropDefinitions);\n const validatedDefinitions = Object.fromEntries(\n presetPropEntries.filter(\n ([propKey]) => {\n const includeBehavior = includeLayoutProps?.[propKey];\n\n return (\n includeBehavior === undefined ||\n (allowsConfigPassthrough(includeBehavior) &&\n (isIncludedPropRequired(includeBehavior) ||\n layoutOptionValues[propKey] !== undefined))\n );\n },\n ),\n );\n const presetPropValues = Object.fromEntries(\n presetPropEntries.flatMap(([propKey]) =>\n propKey in layoutOptionValues\n ? [[propKey, layoutOptionValues[propKey]]]\n : [],\n ),\n );\n\n return [\n key,\n validateProps(\n validatedDefinitions as Record<\n string,\n AnyBuiltPropDefinition\n >,\n presetPropValues,\n validationContext,\n ),\n ];\n },\n ),\n );\n const mergedRenderContext = {\n composables: resolvedComposables as LayoutRenderComposables<Composables>,\n resource: layoutContext.resource,\n name: layoutContext.name,\n inProps: splitInProps,\n } as LayoutRenderContext<Resources, Composables>;\n\n function Component(\n props: Show<\n ResolveProps<CustomProps> &\n ResolvedIncludedComponentProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >\n >,\n ) {\n const validatedProps = validateProps(resolvedLayoutProps, props, {\n ...validationContext,\n });\n const includedPropKeys = Object.keys(includeLayoutProps ?? {});\n const includedPropDefinitions = pick(\n mergedResolvedInProps,\n includedPropKeys,\n ) as Record<string, unknown>;\n const includedPropValues = {\n ...resolvePropDefinitionValues(includedPropDefinitions),\n } as Record<string, unknown>;\n\n for (const key of includedPropKeys) {\n const definition = mergedResolvedInProps[key];\n const includeBehavior = includeLayoutProps?.[key];\n const callSiteValue = allowsComponentPassthrough(includeBehavior)\n ? readLayoutOptionValue(\n key,\n definition,\n props as Record<string, unknown>,\n )\n : undefined;\n const layoutOptionValue = allowsConfigPassthrough(includeBehavior)\n ? readLayoutOptionValue(key, definition, layoutOptionValues)\n : undefined;\n const splitValue = key in splitInProps ? splitInProps[key] : undefined;\n const value = callSiteValue ?? layoutOptionValue ?? splitValue;\n\n if (value !== undefined) {\n includedPropValues[key] = value;\n }\n }\n\n const requiredIncludedPropDefinitions = Object.fromEntries(\n Object.entries(includedPropDefinitions).filter(\n ([key]) => isIncludedPropRequired(includeLayoutProps?.[key]),\n ),\n );\n const optionalIncludedPropDefinitions = Object.fromEntries(\n Object.entries(includedPropDefinitions).filter(\n ([key]) =>\n !isIncludedPropRequired(includeLayoutProps?.[key]) &&\n includedPropValues[key] !== undefined,\n ),\n );\n const validatedIncludedProps = validateProps(\n {\n ...requiredIncludedPropDefinitions,\n ...optionalIncludedPropDefinitions,\n } as Record<string, AnyBuiltPropDefinition>,\n includedPropValues,\n validationContext,\n );\n const layoutRenderIncludedProps = Object.fromEntries(\n includedPropKeys.flatMap((key) => {\n if (!(key in validatedIncludedProps)) {\n return [];\n }\n\n return [\n [\n toLayoutRenderPropKey(key, mergedResolvedInProps[key]),\n validatedIncludedProps[\n key as keyof typeof validatedIncludedProps\n ],\n ],\n ];\n }),\n );\n const layoutRenderProps = {\n ...validatedProps,\n ...layoutRenderIncludedProps,\n } as unknown as LayoutRenderProps<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n\n return (\n <LayoutComposablePresetProvider value={composablePresetProps}>\n {render(layoutRenderProps, mergedRenderContext)}\n </LayoutComposablePresetProvider>\n );\n }\n\n function createComposition<\n LayoutName extends string,\n const Defined extends MakeComposableOptions<Composables, LayoutName>,\n >(compositionOptions: Defined) {\n if (!compositionOptions.components) {\n return {} as ResourceLayoutComposition<LayoutName, Composables>;\n }\n\n return {\n makeComposable: createComposableLayout(\n compositionOptions,\n ) as MakeComposable<Composables, LayoutName>,\n };\n }\n\n return Object.assign(Component, {\n displayName: name,\n props: undefined as unknown as Show<\n ResolveProps<CustomProps> &\n ResolvedIncludedComponentProps<\n MergedLayoutInProps<Resources, InProps, Composables>,\n IncludeProps\n >\n >,\n resource: undefined as unknown as Resource,\n ...createComposition({\n components: resolvedComposables as Composables | undefined,\n name,\n }),\n });\n }) as CreateResourceLayoutFnImpl<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n const createTopLevelMakeComposable = () => {\n return (options: Record<string, unknown>) => {\n const layout = definedResourceLayout(options as never);\n\n if (\n !('makeComposable' in layout) ||\n typeof layout.makeComposable !== 'function'\n ) {\n throw new Error(\n 'makeComposable requires composables to be defined in the layout',\n );\n }\n\n return layout.makeComposable();\n };\n };\n\n function getComponentPropDefinitions(resource: LayoutResourceKey<Resources>) {\n const componentName = 'ScopedResourceComponent';\n const rawResolvedOptions =\n typeof inProps === 'function'\n ? inProps({\n resource: resourcesEnum,\n name: createProp.string().literal(componentName),\n })\n : inProps;\n const { resolvedInProps } = splitLayoutInProps(\n rawResolvedOptions as Record<string, unknown>,\n );\n const resolvedComposables = layout.composables\n ? resolveLayoutComposables(layout.composables, {\n resource,\n name: componentName,\n capitalize,\n })\n : undefined;\n\n for (const {\n props: presetPropDefinitions,\n } of collectComposablePresetEntries(resolvedComposables)) {\n Object.assign(resolvedInProps, presetPropDefinitions);\n }\n\n return {\n ...resolvedInProps,\n ...layout.props?.custom,\n };\n }\n\n const { createLayoutForResourceBuilder, forResource } = createForResource<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >({\n createResourceLayout: definedResourceLayout as never,\n resolveLayoutOptionDefaults,\n });\n const forResources = createForResources<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >({\n createLayoutForResource: createLayoutForResourceBuilder,\n ...(layout.composables\n ? { createMakeComposableLayout: createTopLevelMakeComposable }\n : {}),\n createResourceLayout: definedResourceLayout as never,\n getComponentPropDefinitions,\n });\n\n const createResourceLayoutExtras: {\n forResource: CreateLayoutForResource<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n forResources: CreateResourceLayoutForResourcesFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n makeComposable?: ReturnType<typeof createTopLevelMakeComposable>;\n } = {\n forResource,\n forResources,\n };\n\n if (layout.composables) {\n createResourceLayoutExtras.makeComposable = createTopLevelMakeComposable();\n }\n\n const createResourceLayout = Object.assign(\n definedResourceLayout,\n createResourceLayoutExtras,\n ) as CreateResourceLayoutFn<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n\n const createResourceLinks = createResourceLinksFn(resources);\n\n return {\n createResourceConfig,\n createResourceLayout,\n createResourceLinks,\n } as DefinedResourceLayout<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n}\n\ntype DefineResourceLayoutForResourcesOptions<\n Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n IncludeProps extends LayoutIncludeProps<Resources, InProps, Composables> = {},\n CustomProps extends InPropsObject = {},\n ExtraResources extends ReadonlyArray<ResourceDefinition> = [],\n> = Omit<\n CreateViewMapOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >,\n 'resources'\n> & {\n /**\n * Additional resources to merge with those bound by\n * {@link defineResourceLayout.forResources}.\n */\n resources?: AssertUnreservedResources<ExtraResources>;\n};\n\ntype NonEmptyResourceDefinitions = readonly [\n ResourceDefinition,\n ...ResourceDefinition[],\n];\n\n/**\n * Factory returned by {@link DefineResourceLayout.forResources}.\n */\nexport type DefineResourceLayoutForResourcesFactory<\n BaseResources extends NonEmptyResourceDefinitions,\n> = <\n const ExtraResources extends ReadonlyArray<ResourceDefinition> = [],\n InProps extends InPropsDefinition<[...BaseResources, ...ExtraResources]> = {},\n Composables extends ComposableComponents = {},\n const IncludeProps extends LayoutIncludeProps<\n [...BaseResources, ...ExtraResources],\n InProps,\n Composables\n > = {},\n CustomProps extends InPropsObject = {},\n>(\n options: DefineResourceLayoutForResourcesOptions<\n [...BaseResources, ...ExtraResources],\n InProps,\n Composables,\n IncludeProps,\n CustomProps,\n ExtraResources\n >,\n) => DefinedResourceLayout<\n [...BaseResources, ...ExtraResources],\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n>;\n\n/**\n * Binds one or more resources, then accepts the remaining\n * {@link defineResourceLayout} options (with optional extra `resources`).\n */\nexport type DefineResourceLayoutForResources = <\n const Resources extends NonEmptyResourceDefinitions,\n>(\n ...resources: Resources\n) => DefineResourceLayoutForResourcesFactory<Resources>;\n\n/**\n * Creates a resource layout definition for a set of resources.\n */\nexport type DefineResourceLayoutFn = {\n <\n const Resources extends ReadonlyArray<ResourceDefinition>,\n InProps extends InPropsDefinition<Resources> = {},\n Composables extends ComposableComponents = {},\n const IncludeProps extends LayoutIncludeProps<\n Resources,\n InProps,\n Composables\n > = {},\n CustomProps extends InPropsObject = {},\n >(\n options: CreateViewMapOptions<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >,\n ): DefinedResourceLayout<\n Resources,\n InProps,\n Composables,\n IncludeProps,\n CustomProps\n >;\n};\n\nexport type DefineResourceLayout = DefineResourceLayoutFn & {\n forResources: DefineResourceLayoutForResources;\n};\n\nfunction defineResourceLayoutForResources<\n const Resources extends NonEmptyResourceDefinitions,\n>(\n ...baseResources: Resources\n): DefineResourceLayoutForResourcesFactory<Resources> {\n return ((options) => {\n const { resources: extraResources, ...rest } = options;\n const resources = extraResources\n ? [...baseResources, ...extraResources]\n : [...baseResources];\n\n return defineResourceLayoutImpl({\n ...rest,\n resources,\n } as never);\n }) as DefineResourceLayoutForResourcesFactory<Resources>;\n}\n\nexport const defineResourceLayout: DefineResourceLayout = Object.assign(\n defineResourceLayoutImpl as DefineResourceLayoutFn,\n {\n forResources: defineResourceLayoutForResources,\n },\n);\n"],"mappings":"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"}
|
|
@@ -0,0 +1,192 @@
|
|
|
1
|
+
const require_invalid_path = require('../../errors/invalid-path.cjs');
|
|
2
|
+
const require_invalid_resource = require('../../errors/invalid-resource.cjs');
|
|
3
|
+
const require_invalid_sub_resource = require('../../errors/invalid-sub-resource.cjs');
|
|
4
|
+
const require_invalid_component = require('../../errors/invalid-component.cjs');
|
|
5
|
+
const require_variables = require('../paths/variables.cjs');
|
|
6
|
+
const require_generate = require('../paths/generate.cjs');
|
|
7
|
+
const require_introspect = require('../paths/introspect.cjs');
|
|
8
|
+
const require_resolve = require('../paths/resolve.cjs');
|
|
9
|
+
const require_get_component_for_path = require('./get-component-for-path.cjs');
|
|
10
|
+
|
|
11
|
+
//#region src/create-config/for-paths/builder.ts
|
|
12
|
+
const DEFAULT_DISPLAY_NAME = "ResourcePathComponent";
|
|
13
|
+
function collectValidationSets(config, paths) {
|
|
14
|
+
const resources = /* @__PURE__ */ new Set();
|
|
15
|
+
const subResources = /* @__PURE__ */ new Set();
|
|
16
|
+
const components = /* @__PURE__ */ new Set();
|
|
17
|
+
for (const path of paths) {
|
|
18
|
+
for (const resource of require_introspect.collectPathResources(config, path)) resources.add(resource);
|
|
19
|
+
for (const subResource of require_introspect.collectPathSubResourceKeys(config, path)) subResources.add(subResource);
|
|
20
|
+
for (const component of require_introspect.collectPathComponentKeys(config, path)) components.add(component);
|
|
21
|
+
}
|
|
22
|
+
return {
|
|
23
|
+
resources: [...resources],
|
|
24
|
+
subResources: [...subResources],
|
|
25
|
+
components: [...components]
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Validates the params a caller passed before the renderer runs, so a bad resource or
|
|
30
|
+
* slot fails with a typed error naming what is available.
|
|
31
|
+
*/
|
|
32
|
+
function validateParams(params, state, sets) {
|
|
33
|
+
const { resource, subResource, component, componentKey } = params;
|
|
34
|
+
if (state.declaredPathParams.includes("resource") && resource !== void 0) {
|
|
35
|
+
if (typeof resource !== "string" || !sets.resources.includes(resource)) throw new require_invalid_resource.InvalidResourceError({
|
|
36
|
+
resource,
|
|
37
|
+
validResources: sets.resources
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
if (state.declaredPathParams.includes("subResource") && subResource !== void 0) {
|
|
41
|
+
const slugs = require_resolve.flattenSubResourceParam(subResource);
|
|
42
|
+
for (const slug of slugs) if (!sets.subResources.includes(slug)) throw new require_invalid_sub_resource.InvalidSubResourceError({
|
|
43
|
+
subResource: slug,
|
|
44
|
+
resource: typeof resource === "string" ? resource : void 0,
|
|
45
|
+
validSubResources: sets.subResources
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
if (state.declaredPathParams.includes("component") && component !== void 0) {
|
|
49
|
+
if (typeof component !== "string" || !sets.components.includes(component)) throw new require_invalid_component.InvalidComponentError({
|
|
50
|
+
component,
|
|
51
|
+
validComponents: sets.components
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
if (!state.componentKeyDeclared) return;
|
|
55
|
+
if (componentKey === void 0) {
|
|
56
|
+
if (!state.componentKeyOptional) throw new require_invalid_component.InvalidComponentError({
|
|
57
|
+
component: componentKey,
|
|
58
|
+
validComponents: sets.components,
|
|
59
|
+
reason: "A \"componentKey\" prop is required for this component"
|
|
60
|
+
});
|
|
61
|
+
return;
|
|
62
|
+
}
|
|
63
|
+
if (typeof componentKey !== "string" || !sets.components.includes(componentKey)) throw new require_invalid_component.InvalidComponentError({
|
|
64
|
+
component: componentKey,
|
|
65
|
+
validComponents: sets.components
|
|
66
|
+
});
|
|
67
|
+
}
|
|
68
|
+
function readClosureProps(selected, closure) {
|
|
69
|
+
if (selected.length === 0) return {};
|
|
70
|
+
const [only] = selected;
|
|
71
|
+
if (selected.length === 1 && only !== void 0) return { [only]: closure };
|
|
72
|
+
if (typeof closure === "object" && closure !== null && !Array.isArray(closure)) return { ...closure };
|
|
73
|
+
return {};
|
|
74
|
+
}
|
|
75
|
+
function createRenderedComponent(runRenderer, paramTemplate, resolveDisplayName, boundProps = {}) {
|
|
76
|
+
function RenderedPathView(props) {
|
|
77
|
+
const merged = {
|
|
78
|
+
...boundProps,
|
|
79
|
+
...props
|
|
80
|
+
};
|
|
81
|
+
if (resolveDisplayName) RenderedPathView.displayName = resolveDisplayName(merged);
|
|
82
|
+
return runRenderer(merged);
|
|
83
|
+
}
|
|
84
|
+
RenderedPathView.displayName = DEFAULT_DISPLAY_NAME;
|
|
85
|
+
function asHOF(options) {
|
|
86
|
+
const selected = Object.entries(options?.args ?? {}).filter(([, enabled]) => enabled === true).map(([key]) => key);
|
|
87
|
+
function hof(closure) {
|
|
88
|
+
const bound = createRenderedComponent(runRenderer, void 0, resolveDisplayName, {
|
|
89
|
+
...boundProps,
|
|
90
|
+
...readClosureProps(selected, closure)
|
|
91
|
+
});
|
|
92
|
+
bound.displayName = RenderedPathView.displayName;
|
|
93
|
+
return bound;
|
|
94
|
+
}
|
|
95
|
+
return Object.assign(hof, { _args: void 0 });
|
|
96
|
+
}
|
|
97
|
+
return Object.assign(RenderedPathView, {
|
|
98
|
+
_args: paramTemplate,
|
|
99
|
+
asHOF
|
|
100
|
+
});
|
|
101
|
+
}
|
|
102
|
+
function createTargetPathBuilder(config, paths) {
|
|
103
|
+
const validationSets = collectValidationSets(config, paths);
|
|
104
|
+
const makeBuilder = (state) => {
|
|
105
|
+
const builder = {};
|
|
106
|
+
if (!state.usedComponentKeyParams) builder.addComponentKeyParams = (options) => makeBuilder({
|
|
107
|
+
...state,
|
|
108
|
+
usedComponentKeyParams: true,
|
|
109
|
+
componentKeyDeclared: true,
|
|
110
|
+
componentKeyOptional: options?.optional === true
|
|
111
|
+
});
|
|
112
|
+
if (!state.usedPathParams) builder.addPathParams = (options) => {
|
|
113
|
+
const available = /* @__PURE__ */ new Set();
|
|
114
|
+
for (const path of state.paths) for (const name of require_variables.extractPathVariables(path)) available.add(name);
|
|
115
|
+
const picked = Object.entries(options?.pick ?? {}).filter(([, enabled]) => enabled === true).map(([key]) => key);
|
|
116
|
+
const declared = picked.length === 0 ? [...available] : picked.filter((name) => available.has(name));
|
|
117
|
+
return makeBuilder({
|
|
118
|
+
...state,
|
|
119
|
+
usedPathParams: true,
|
|
120
|
+
declaredPathParams: [...state.declaredPathParams, ...declared]
|
|
121
|
+
});
|
|
122
|
+
};
|
|
123
|
+
if (!state.usedParams) builder.addParams = (params) => makeBuilder({
|
|
124
|
+
...state,
|
|
125
|
+
usedParams: true,
|
|
126
|
+
paramDefaults: {
|
|
127
|
+
...state.paramDefaults,
|
|
128
|
+
...params
|
|
129
|
+
}
|
|
130
|
+
});
|
|
131
|
+
builder.render = (renderer) => {
|
|
132
|
+
const buildContext = (props) => {
|
|
133
|
+
const params = {
|
|
134
|
+
...state.paramDefaults,
|
|
135
|
+
...props
|
|
136
|
+
};
|
|
137
|
+
validateParams(params, state, validationSets);
|
|
138
|
+
return {
|
|
139
|
+
params,
|
|
140
|
+
getComponentForPath: (path) => {
|
|
141
|
+
if (!state.paths.includes(path)) throw new require_invalid_path.InvalidPathError({
|
|
142
|
+
path,
|
|
143
|
+
validPaths: state.paths,
|
|
144
|
+
reason: "This component was not built for that path"
|
|
145
|
+
});
|
|
146
|
+
return require_get_component_for_path.createGetComponentForPath(config, path);
|
|
147
|
+
}
|
|
148
|
+
};
|
|
149
|
+
};
|
|
150
|
+
const runRenderer = (props) => renderer(buildContext(props));
|
|
151
|
+
const component = createRenderedComponent(runRenderer, { ...state.paramDefaults });
|
|
152
|
+
return Object.assign(component, { setDisplayName: (name) => {
|
|
153
|
+
if (typeof name === "string") {
|
|
154
|
+
const named = createRenderedComponent(runRenderer, { ...state.paramDefaults });
|
|
155
|
+
named.displayName = name;
|
|
156
|
+
return named;
|
|
157
|
+
}
|
|
158
|
+
return createRenderedComponent(runRenderer, { ...state.paramDefaults }, (props) => name(buildContext(props)));
|
|
159
|
+
} });
|
|
160
|
+
};
|
|
161
|
+
return builder;
|
|
162
|
+
};
|
|
163
|
+
return makeBuilder({
|
|
164
|
+
paths,
|
|
165
|
+
paramDefaults: {},
|
|
166
|
+
declaredPathParams: [],
|
|
167
|
+
componentKeyDeclared: false,
|
|
168
|
+
componentKeyOptional: false,
|
|
169
|
+
usedComponentKeyParams: false,
|
|
170
|
+
usedPathParams: false,
|
|
171
|
+
usedParams: false
|
|
172
|
+
});
|
|
173
|
+
}
|
|
174
|
+
function createForPaths(config) {
|
|
175
|
+
const validPaths = require_generate.generateResourceConfigPaths(config);
|
|
176
|
+
return ((...paths) => {
|
|
177
|
+
if (paths.length === 0) throw new require_invalid_path.InvalidPathError({
|
|
178
|
+
path: paths,
|
|
179
|
+
validPaths,
|
|
180
|
+
reason: "At least one path is required"
|
|
181
|
+
});
|
|
182
|
+
for (const path of paths) if (!validPaths.includes(path)) throw new require_invalid_path.InvalidPathError({
|
|
183
|
+
path,
|
|
184
|
+
validPaths
|
|
185
|
+
});
|
|
186
|
+
return createTargetPathBuilder(config, paths);
|
|
187
|
+
});
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
//#endregion
|
|
191
|
+
exports.createForPaths = createForPaths;
|
|
192
|
+
//# sourceMappingURL=builder.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"builder.cjs","names":["collectPathResources","collectPathSubResourceKeys","collectPathComponentKeys","InvalidResourceError","flattenSubResourceParam","InvalidSubResourceError","InvalidComponentError","extractPathVariables","InvalidPathError","createGetComponentForPath","generateResourceConfigPaths"],"sources":["../../../src/create-config/for-paths/builder.ts"],"sourcesContent":["import type { JSX } from 'react';\nimport {\n InvalidComponentError,\n InvalidPathError,\n InvalidResourceError,\n InvalidSubResourceError,\n} from '../../errors';\nimport type { ResourceDefinition } from '../../resource';\nimport type { IsUnion, Show } from '../../utils';\nimport {\n collectPathComponentKeys,\n collectPathResources,\n collectPathSubResourceKeys,\n extractPathVariables,\n flattenSubResourceParam,\n generateResourceConfigPaths,\n} from '../paths';\nimport type {\n PathComponentKeys,\n PathVariables,\n SubResourceParamValue,\n} from '../paths';\nimport {\n createGetComponentForPath,\n type CreateGetComponentForPath,\n} from './get-component-for-path';\n\ntype UnwrapTargetPaths<Paths> = Paths extends readonly [\n infer First,\n ...infer Rest,\n]\n ? (First & string) | UnwrapTargetPaths<Rest>\n : Paths extends readonly (infer Path)[]\n ? Path & string\n : never;\n\ntype PathVariablesForPaths<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config,\n Paths extends ReadonlyArray<string>,\n> =\n UnwrapTargetPaths<Paths> extends infer Path\n ? Path extends string\n ? PathVariables<Resources, Config, Path>\n : never\n : never;\n\ntype ComponentKeysForPaths<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config,\n Paths extends ReadonlyArray<string>,\n> =\n UnwrapTargetPaths<Paths> extends infer Path\n ? Path extends string\n ? PathComponentKeys<Resources, Config, Path>\n : never\n : never;\n\ntype ValueOrFunction<Value, Input> = Value | ((input: Input) => Value);\n\n/** Context handed to `render` and to `setDisplayName`. */\nexport type ForPathsRenderContext<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config,\n Paths extends ReadonlyArray<string>,\n Params,\n> = {\n /** Declared params merged with the props the component was called with. */\n params: Params;\n /** Creates a getter for any of the paths this component was built for. */\n getComponentForPath: CreateGetComponentForPath<\n Resources,\n Config,\n UnwrapTargetPaths<Paths>\n >;\n};\n\ntype HOFArgSelection<Params> = {\n [Key in keyof Params]?: true;\n};\n\n/**\n * Value closed over by `asHOF`. Selecting a single arg closes over that value directly;\n * selecting several closes over an object.\n */\ntype HOFClosureValue<Params, Args> = [keyof Args] extends [never]\n ? {}\n : IsUnion<keyof Args> extends false\n ? Params[keyof Args & keyof Params]\n : Show<Pick<Params, keyof Args & keyof Params>>;\n\nexport interface RenderedPathComponentHOF<Params, Args> {\n (closure: HOFClosureValue<Params, Args>): RenderedPathComponent<\n Show<Omit<Params, keyof Args>>\n >;\n /** Type-only view of the value this HOF closes over. At runtime this is `undefined`. */\n _args: HOFClosureValue<Params, Args>;\n}\n\nexport interface RenderedPathComponent<\n Params,\n DisplayName extends string = string,\n> {\n (props: Params): JSX.Element;\n displayName: DisplayName;\n /** Type-only view of the props this component accepts. */\n _args: Params;\n /**\n * Splits the props into a closure and the remaining props, so shared params can be\n * bound once and the component reused. Chained `asHOF` calls keep prior closures.\n */\n asHOF<Args extends HOFArgSelection<Params> = {}>(options?: {\n /** Params to close over. Anything omitted stays a prop. */\n args: Args;\n }): RenderedPathComponentHOF<Params, Args>;\n}\n\ntype WithComponentKeyParam<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config,\n Paths extends ReadonlyArray<string>,\n Optional extends boolean,\n> = Optional extends true\n ? { componentKey?: ComponentKeysForPaths<Resources, Config, Paths> }\n : { componentKey: ComponentKeysForPaths<Resources, Config, Paths> };\n\ntype PickedPathParams<\n Variables,\n Picked,\n> = [keyof Picked] extends [never]\n ? Variables\n : Pick<Variables, keyof Picked & keyof Variables>;\n\nexport type TargetPathBuilder<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config,\n Paths extends ReadonlyArray<string>,\n Params extends Record<string, unknown> = {},\n Used extends\n | 'addComponentKeyParams'\n | 'addPathParams'\n | 'addParams' = never,\n> = {\n render: (\n renderer: (\n context: ForPathsRenderContext<Resources, Config, Paths, Params>,\n ) => JSX.Element,\n ) => RenderedPathComponent<Params> & {\n /** Names the component, either statically or from the render context. */\n setDisplayName<Name extends string>(\n name: ValueOrFunction<\n Name,\n ForPathsRenderContext<Resources, Config, Paths, Params>\n >,\n ): RenderedPathComponent<Params, Name>;\n };\n} & ('addComponentKeyParams' extends Used\n ? {}\n : {\n /**\n * Adds a `componentKey` prop narrowed to the component slots configured for these\n * paths. Call it before `render` when building a reusable component.\n */\n addComponentKeyParams<Optional extends boolean = false>(options?: {\n /** Whether the caller may omit `componentKey`. */\n optional?: Optional;\n }): TargetPathBuilder<\n Resources,\n Config,\n Paths,\n Show<\n Params & WithComponentKeyParam<Resources, Config, Paths, Optional>\n >,\n Used | 'addComponentKeyParams'\n >;\n }) &\n ('addPathParams' extends Used\n ? {}\n : {\n /**\n * Turns the variables these paths leave open into props. Without `pick`, every\n * variable becomes a prop.\n */\n addPathParams<\n Variables extends PathVariablesForPaths<Resources, Config, Paths>,\n Picked extends { [Key in keyof Variables]?: true } = {},\n >(options?: {\n /** Variables to expose as props. Defaults to all of them. */\n pick?: Picked;\n }): TargetPathBuilder<\n Resources,\n Config,\n Paths,\n Show<Params & PickedPathParams<Variables, Picked>>,\n Used | 'addPathParams'\n >;\n }) &\n ('addParams' extends Used\n ? {}\n : {\n /**\n * Adds custom params with the given values as defaults. Defaults are\n * optional at the call site and filled in before `render` runs.\n */\n addParams<NewParams extends Record<string, unknown>>(\n params: NewParams,\n ): TargetPathBuilder<\n Resources,\n Config,\n Paths,\n Show<Params & Partial<NewParams>>,\n Used | 'addParams'\n >;\n });\n\nexport type ForPaths<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config,\n AllowedPath extends string,\n> = <const Paths extends readonly [AllowedPath, ...AllowedPath[]]>(\n ...paths: Paths\n) => TargetPathBuilder<Resources, Config, Paths>;\n\nconst DEFAULT_DISPLAY_NAME = 'ResourcePathComponent';\n\ntype BuilderState = {\n paths: readonly string[];\n paramDefaults: Record<string, unknown>;\n declaredPathParams: readonly string[];\n componentKeyDeclared: boolean;\n componentKeyOptional: boolean;\n usedComponentKeyParams: boolean;\n usedPathParams: boolean;\n usedParams: boolean;\n};\n\ntype ValidationSets = {\n resources: readonly string[];\n subResources: readonly string[];\n components: readonly string[];\n};\n\nfunction collectValidationSets(\n config: Record<string, unknown>,\n paths: readonly string[],\n): ValidationSets {\n const resources = new Set<string>();\n const subResources = new Set<string>();\n const components = new Set<string>();\n\n for (const path of paths) {\n for (const resource of collectPathResources(config, path)) {\n resources.add(resource);\n }\n\n for (const subResource of collectPathSubResourceKeys(config, path)) {\n subResources.add(subResource);\n }\n\n for (const component of collectPathComponentKeys(config, path)) {\n components.add(component);\n }\n }\n\n return {\n resources: [...resources],\n subResources: [...subResources],\n components: [...components],\n };\n}\n\n/**\n * Validates the params a caller passed before the renderer runs, so a bad resource or\n * slot fails with a typed error naming what is available.\n */\nfunction validateParams(\n params: Record<string, unknown>,\n state: BuilderState,\n sets: ValidationSets,\n): void {\n const { resource, subResource, component, componentKey } = params as {\n resource?: unknown;\n subResource?: unknown;\n component?: unknown;\n componentKey?: unknown;\n };\n\n if (state.declaredPathParams.includes('resource') && resource !== undefined) {\n if (typeof resource !== 'string' || !sets.resources.includes(resource)) {\n throw new InvalidResourceError({\n resource,\n validResources: sets.resources,\n });\n }\n }\n\n if (\n state.declaredPathParams.includes('subResource') &&\n subResource !== undefined\n ) {\n const slugs = flattenSubResourceParam(subResource as SubResourceParamValue);\n\n for (const slug of slugs) {\n if (!sets.subResources.includes(slug)) {\n throw new InvalidSubResourceError({\n subResource: slug,\n resource: typeof resource === 'string' ? resource : undefined,\n validSubResources: sets.subResources,\n });\n }\n }\n }\n\n if (\n state.declaredPathParams.includes('component') &&\n component !== undefined\n ) {\n if (typeof component !== 'string' || !sets.components.includes(component)) {\n throw new InvalidComponentError({\n component,\n validComponents: sets.components,\n });\n }\n }\n\n if (!state.componentKeyDeclared) {\n return;\n }\n\n if (componentKey === undefined) {\n if (!state.componentKeyOptional) {\n throw new InvalidComponentError({\n component: componentKey,\n validComponents: sets.components,\n reason: 'A \"componentKey\" prop is required for this component',\n });\n }\n\n return;\n }\n\n if (\n typeof componentKey !== 'string' ||\n !sets.components.includes(componentKey)\n ) {\n throw new InvalidComponentError({\n component: componentKey,\n validComponents: sets.components,\n });\n }\n}\n\nfunction readClosureProps(\n selected: string[],\n closure: unknown,\n): Record<string, unknown> {\n if (selected.length === 0) {\n return {};\n }\n\n const [only] = selected;\n\n if (selected.length === 1 && only !== undefined) {\n return { [only]: closure };\n }\n\n if (\n typeof closure === 'object' &&\n closure !== null &&\n !Array.isArray(closure)\n ) {\n return { ...(closure as Record<string, unknown>) };\n }\n\n return {};\n}\n\nfunction createRenderedComponent(\n runRenderer: (props: Record<string, unknown>) => JSX.Element,\n paramTemplate: Record<string, unknown> | undefined,\n resolveDisplayName?: (props: Record<string, unknown>) => string,\n boundProps: Record<string, unknown> = {},\n) {\n function RenderedPathView(props: Record<string, unknown>): JSX.Element {\n const merged = { ...boundProps, ...props };\n\n if (resolveDisplayName) {\n RenderedPathView.displayName = resolveDisplayName(merged);\n }\n\n return runRenderer(merged);\n }\n\n RenderedPathView.displayName = DEFAULT_DISPLAY_NAME;\n\n function asHOF(options?: { args?: Record<string, true> }) {\n const selected = Object.entries(options?.args ?? {})\n .filter(([, enabled]) => enabled === true)\n .map(([key]) => key);\n\n function hof(closure: unknown) {\n const bound = createRenderedComponent(\n runRenderer,\n undefined,\n resolveDisplayName,\n { ...boundProps, ...readClosureProps(selected, closure) },\n );\n\n bound.displayName = RenderedPathView.displayName;\n\n return bound;\n }\n\n return Object.assign(hof, { _args: undefined as never });\n }\n\n return Object.assign(RenderedPathView, {\n _args: paramTemplate as never,\n asHOF,\n });\n}\n\nexport function createTargetPathBuilder<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config extends Record<string, unknown>,\n Paths extends ReadonlyArray<string>,\n>(config: Config, paths: Paths): TargetPathBuilder<Resources, Config, Paths> {\n const validationSets = collectValidationSets(config, paths);\n\n const makeBuilder = (state: BuilderState): Record<string, unknown> => {\n const builder: Record<string, unknown> = {};\n\n if (!state.usedComponentKeyParams) {\n builder.addComponentKeyParams = (options?: { optional?: boolean }) =>\n makeBuilder({\n ...state,\n usedComponentKeyParams: true,\n componentKeyDeclared: true,\n componentKeyOptional: options?.optional === true,\n });\n }\n\n if (!state.usedPathParams) {\n builder.addPathParams = (options?: { pick?: Record<string, true> }) => {\n const available = new Set<string>();\n\n for (const path of state.paths) {\n for (const name of extractPathVariables(path)) {\n available.add(name);\n }\n }\n\n const picked = Object.entries(options?.pick ?? {})\n .filter(([, enabled]) => enabled === true)\n .map(([key]) => key);\n const declared =\n picked.length === 0\n ? [...available]\n : picked.filter((name) => available.has(name));\n\n return makeBuilder({\n ...state,\n usedPathParams: true,\n declaredPathParams: [...state.declaredPathParams, ...declared],\n });\n };\n }\n\n if (!state.usedParams) {\n builder.addParams = (params: Record<string, unknown>) =>\n makeBuilder({\n ...state,\n usedParams: true,\n paramDefaults: { ...state.paramDefaults, ...params },\n });\n }\n\n builder.render = (\n renderer: (context: {\n params: Record<string, unknown>;\n getComponentForPath: unknown;\n }) => JSX.Element,\n ) => {\n const buildContext = (props: Record<string, unknown>) => {\n const params = { ...state.paramDefaults, ...props };\n\n validateParams(params, state, validationSets);\n\n return {\n params,\n getComponentForPath: (path: string) => {\n if (!state.paths.includes(path)) {\n throw new InvalidPathError({\n path,\n validPaths: state.paths,\n reason: 'This component was not built for that path',\n });\n }\n\n return createGetComponentForPath(config, path);\n },\n };\n };\n\n const runRenderer = (props: Record<string, unknown>) =>\n renderer(buildContext(props));\n\n const component = createRenderedComponent(runRenderer, {\n ...state.paramDefaults,\n });\n\n return Object.assign(component, {\n setDisplayName: (\n name:\n | string\n | ((context: {\n params: Record<string, unknown>;\n getComponentForPath: unknown;\n }) => string),\n ) => {\n if (typeof name === 'string') {\n const named = createRenderedComponent(runRenderer, {\n ...state.paramDefaults,\n });\n\n named.displayName = name;\n\n return named;\n }\n\n return createRenderedComponent(\n runRenderer,\n { ...state.paramDefaults },\n (props) => name(buildContext(props)),\n );\n },\n });\n };\n\n return builder;\n };\n\n return makeBuilder({\n paths,\n paramDefaults: {},\n declaredPathParams: [],\n componentKeyDeclared: false,\n componentKeyOptional: false,\n usedComponentKeyParams: false,\n usedPathParams: false,\n usedParams: false,\n }) as unknown as TargetPathBuilder<Resources, Config, Paths>;\n}\n\nexport function createForPaths<\n Resources extends ReadonlyArray<ResourceDefinition>,\n Config extends Record<string, unknown>,\n>(config: Config): ForPaths<Resources, Config, string> {\n const validPaths = generateResourceConfigPaths(config);\n\n return ((...paths: string[]) => {\n if (paths.length === 0) {\n throw new InvalidPathError({\n path: paths,\n validPaths,\n reason: 'At least one path is required',\n });\n }\n\n for (const path of paths) {\n if (!validPaths.includes(path)) {\n throw new InvalidPathError({ path, validPaths });\n }\n }\n\n return createTargetPathBuilder(config, paths);\n }) as unknown as ForPaths<Resources, Config, string>;\n}\n"],"mappings":"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"}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import { IsUnion, Show } from "../../utils.cjs";
|
|
2
|
+
import { ResourceDefinition } from "../../resource.cjs";
|
|
3
|
+
import { PathComponentKeys, PathVariables } from "../paths/types.cjs";
|
|
4
|
+
import { CreateGetComponentForPath } from "./get-component-for-path.cjs";
|
|
5
|
+
import { JSX } from "react";
|
|
6
|
+
|
|
7
|
+
//#region src/create-config/for-paths/builder.d.ts
|
|
8
|
+
type UnwrapTargetPaths<Paths> = Paths extends readonly [infer First, ...infer Rest] ? (First & string) | UnwrapTargetPaths<Rest> : Paths extends readonly (infer Path)[] ? Path & string : never;
|
|
9
|
+
type PathVariablesForPaths<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>> = UnwrapTargetPaths<Paths> extends infer Path ? Path extends string ? PathVariables<Resources, Config, Path> : never : never;
|
|
10
|
+
type ComponentKeysForPaths<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>> = UnwrapTargetPaths<Paths> extends infer Path ? Path extends string ? PathComponentKeys<Resources, Config, Path> : never : never;
|
|
11
|
+
type ValueOrFunction<Value, Input> = Value | ((input: Input) => Value);
|
|
12
|
+
/** Context handed to `render` and to `setDisplayName`. */
|
|
13
|
+
type ForPathsRenderContext<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>, Params> = {
|
|
14
|
+
/** Declared params merged with the props the component was called with. */params: Params; /** Creates a getter for any of the paths this component was built for. */
|
|
15
|
+
getComponentForPath: CreateGetComponentForPath<Resources, Config, UnwrapTargetPaths<Paths>>;
|
|
16
|
+
};
|
|
17
|
+
type HOFArgSelection<Params> = { [Key in keyof Params]?: true };
|
|
18
|
+
/**
|
|
19
|
+
* Value closed over by `asHOF`. Selecting a single arg closes over that value directly;
|
|
20
|
+
* selecting several closes over an object.
|
|
21
|
+
*/
|
|
22
|
+
type HOFClosureValue<Params, Args> = [keyof Args] extends [never] ? {} : IsUnion<keyof Args> extends false ? Params[keyof Args & keyof Params] : Show<Pick<Params, keyof Args & keyof Params>>;
|
|
23
|
+
interface RenderedPathComponentHOF<Params, Args> {
|
|
24
|
+
(closure: HOFClosureValue<Params, Args>): RenderedPathComponent<Show<Omit<Params, keyof Args>>>;
|
|
25
|
+
/** Type-only view of the value this HOF closes over. At runtime this is `undefined`. */
|
|
26
|
+
_args: HOFClosureValue<Params, Args>;
|
|
27
|
+
}
|
|
28
|
+
interface RenderedPathComponent<Params, DisplayName extends string = string> {
|
|
29
|
+
(props: Params): JSX.Element;
|
|
30
|
+
displayName: DisplayName;
|
|
31
|
+
/** Type-only view of the props this component accepts. */
|
|
32
|
+
_args: Params;
|
|
33
|
+
/**
|
|
34
|
+
* Splits the props into a closure and the remaining props, so shared params can be
|
|
35
|
+
* bound once and the component reused. Chained `asHOF` calls keep prior closures.
|
|
36
|
+
*/
|
|
37
|
+
asHOF<Args extends HOFArgSelection<Params> = {}>(options?: {
|
|
38
|
+
/** Params to close over. Anything omitted stays a prop. */args: Args;
|
|
39
|
+
}): RenderedPathComponentHOF<Params, Args>;
|
|
40
|
+
}
|
|
41
|
+
type WithComponentKeyParam<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>, Optional extends boolean> = Optional extends true ? {
|
|
42
|
+
componentKey?: ComponentKeysForPaths<Resources, Config, Paths>;
|
|
43
|
+
} : {
|
|
44
|
+
componentKey: ComponentKeysForPaths<Resources, Config, Paths>;
|
|
45
|
+
};
|
|
46
|
+
type PickedPathParams<Variables, Picked> = [keyof Picked] extends [never] ? Variables : Pick<Variables, keyof Picked & keyof Variables>;
|
|
47
|
+
type TargetPathBuilder<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>, Params extends Record<string, unknown> = {}, Used extends 'addComponentKeyParams' | 'addPathParams' | 'addParams' = never> = {
|
|
48
|
+
render: (renderer: (context: ForPathsRenderContext<Resources, Config, Paths, Params>) => JSX.Element) => RenderedPathComponent<Params> & {
|
|
49
|
+
/** Names the component, either statically or from the render context. */setDisplayName<Name extends string>(name: ValueOrFunction<Name, ForPathsRenderContext<Resources, Config, Paths, Params>>): RenderedPathComponent<Params, Name>;
|
|
50
|
+
};
|
|
51
|
+
} & ('addComponentKeyParams' extends Used ? {} : {
|
|
52
|
+
/**
|
|
53
|
+
* Adds a `componentKey` prop narrowed to the component slots configured for these
|
|
54
|
+
* paths. Call it before `render` when building a reusable component.
|
|
55
|
+
*/
|
|
56
|
+
addComponentKeyParams<Optional extends boolean = false>(options?: {
|
|
57
|
+
/** Whether the caller may omit `componentKey`. */optional?: Optional;
|
|
58
|
+
}): TargetPathBuilder<Resources, Config, Paths, Show<Params & WithComponentKeyParam<Resources, Config, Paths, Optional>>, Used | 'addComponentKeyParams'>;
|
|
59
|
+
}) & ('addPathParams' extends Used ? {} : {
|
|
60
|
+
/**
|
|
61
|
+
* Turns the variables these paths leave open into props. Without `pick`, every
|
|
62
|
+
* variable becomes a prop.
|
|
63
|
+
*/
|
|
64
|
+
addPathParams<Variables extends PathVariablesForPaths<Resources, Config, Paths>, Picked extends { [Key in keyof Variables]?: true } = {}>(options?: {
|
|
65
|
+
/** Variables to expose as props. Defaults to all of them. */pick?: Picked;
|
|
66
|
+
}): TargetPathBuilder<Resources, Config, Paths, Show<Params & PickedPathParams<Variables, Picked>>, Used | 'addPathParams'>;
|
|
67
|
+
}) & ('addParams' extends Used ? {} : {
|
|
68
|
+
/**
|
|
69
|
+
* Adds custom params with the given values as defaults. Defaults are
|
|
70
|
+
* optional at the call site and filled in before `render` runs.
|
|
71
|
+
*/
|
|
72
|
+
addParams<NewParams extends Record<string, unknown>>(params: NewParams): TargetPathBuilder<Resources, Config, Paths, Show<Params & Partial<NewParams>>, Used | 'addParams'>;
|
|
73
|
+
});
|
|
74
|
+
type ForPaths<Resources extends ReadonlyArray<ResourceDefinition>, Config, AllowedPath extends string> = <const Paths extends readonly [AllowedPath, ...AllowedPath[]]>(...paths: Paths) => TargetPathBuilder<Resources, Config, Paths>;
|
|
75
|
+
//#endregion
|
|
76
|
+
export { ForPaths, ForPathsRenderContext, RenderedPathComponent, RenderedPathComponentHOF, TargetPathBuilder };
|
|
77
|
+
//# sourceMappingURL=builder.d.cts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"builder.d.cts","names":[],"sources":["../../../src/create-config/for-paths/builder.ts"],"mappings":"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"}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import { IsUnion, Show } from "../../utils.mjs";
|
|
2
|
+
import { ResourceDefinition } from "../../resource.mjs";
|
|
3
|
+
import { PathComponentKeys, PathVariables } from "../paths/types.mjs";
|
|
4
|
+
import { CreateGetComponentForPath } from "./get-component-for-path.mjs";
|
|
5
|
+
import { JSX } from "react";
|
|
6
|
+
|
|
7
|
+
//#region src/create-config/for-paths/builder.d.ts
|
|
8
|
+
type UnwrapTargetPaths<Paths> = Paths extends readonly [infer First, ...infer Rest] ? (First & string) | UnwrapTargetPaths<Rest> : Paths extends readonly (infer Path)[] ? Path & string : never;
|
|
9
|
+
type PathVariablesForPaths<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>> = UnwrapTargetPaths<Paths> extends infer Path ? Path extends string ? PathVariables<Resources, Config, Path> : never : never;
|
|
10
|
+
type ComponentKeysForPaths<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>> = UnwrapTargetPaths<Paths> extends infer Path ? Path extends string ? PathComponentKeys<Resources, Config, Path> : never : never;
|
|
11
|
+
type ValueOrFunction<Value, Input> = Value | ((input: Input) => Value);
|
|
12
|
+
/** Context handed to `render` and to `setDisplayName`. */
|
|
13
|
+
type ForPathsRenderContext<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>, Params> = {
|
|
14
|
+
/** Declared params merged with the props the component was called with. */params: Params; /** Creates a getter for any of the paths this component was built for. */
|
|
15
|
+
getComponentForPath: CreateGetComponentForPath<Resources, Config, UnwrapTargetPaths<Paths>>;
|
|
16
|
+
};
|
|
17
|
+
type HOFArgSelection<Params> = { [Key in keyof Params]?: true };
|
|
18
|
+
/**
|
|
19
|
+
* Value closed over by `asHOF`. Selecting a single arg closes over that value directly;
|
|
20
|
+
* selecting several closes over an object.
|
|
21
|
+
*/
|
|
22
|
+
type HOFClosureValue<Params, Args> = [keyof Args] extends [never] ? {} : IsUnion<keyof Args> extends false ? Params[keyof Args & keyof Params] : Show<Pick<Params, keyof Args & keyof Params>>;
|
|
23
|
+
interface RenderedPathComponentHOF<Params, Args> {
|
|
24
|
+
(closure: HOFClosureValue<Params, Args>): RenderedPathComponent<Show<Omit<Params, keyof Args>>>;
|
|
25
|
+
/** Type-only view of the value this HOF closes over. At runtime this is `undefined`. */
|
|
26
|
+
_args: HOFClosureValue<Params, Args>;
|
|
27
|
+
}
|
|
28
|
+
interface RenderedPathComponent<Params, DisplayName extends string = string> {
|
|
29
|
+
(props: Params): JSX.Element;
|
|
30
|
+
displayName: DisplayName;
|
|
31
|
+
/** Type-only view of the props this component accepts. */
|
|
32
|
+
_args: Params;
|
|
33
|
+
/**
|
|
34
|
+
* Splits the props into a closure and the remaining props, so shared params can be
|
|
35
|
+
* bound once and the component reused. Chained `asHOF` calls keep prior closures.
|
|
36
|
+
*/
|
|
37
|
+
asHOF<Args extends HOFArgSelection<Params> = {}>(options?: {
|
|
38
|
+
/** Params to close over. Anything omitted stays a prop. */args: Args;
|
|
39
|
+
}): RenderedPathComponentHOF<Params, Args>;
|
|
40
|
+
}
|
|
41
|
+
type WithComponentKeyParam<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>, Optional extends boolean> = Optional extends true ? {
|
|
42
|
+
componentKey?: ComponentKeysForPaths<Resources, Config, Paths>;
|
|
43
|
+
} : {
|
|
44
|
+
componentKey: ComponentKeysForPaths<Resources, Config, Paths>;
|
|
45
|
+
};
|
|
46
|
+
type PickedPathParams<Variables, Picked> = [keyof Picked] extends [never] ? Variables : Pick<Variables, keyof Picked & keyof Variables>;
|
|
47
|
+
type TargetPathBuilder<Resources extends ReadonlyArray<ResourceDefinition>, Config, Paths extends ReadonlyArray<string>, Params extends Record<string, unknown> = {}, Used extends 'addComponentKeyParams' | 'addPathParams' | 'addParams' = never> = {
|
|
48
|
+
render: (renderer: (context: ForPathsRenderContext<Resources, Config, Paths, Params>) => JSX.Element) => RenderedPathComponent<Params> & {
|
|
49
|
+
/** Names the component, either statically or from the render context. */setDisplayName<Name extends string>(name: ValueOrFunction<Name, ForPathsRenderContext<Resources, Config, Paths, Params>>): RenderedPathComponent<Params, Name>;
|
|
50
|
+
};
|
|
51
|
+
} & ('addComponentKeyParams' extends Used ? {} : {
|
|
52
|
+
/**
|
|
53
|
+
* Adds a `componentKey` prop narrowed to the component slots configured for these
|
|
54
|
+
* paths. Call it before `render` when building a reusable component.
|
|
55
|
+
*/
|
|
56
|
+
addComponentKeyParams<Optional extends boolean = false>(options?: {
|
|
57
|
+
/** Whether the caller may omit `componentKey`. */optional?: Optional;
|
|
58
|
+
}): TargetPathBuilder<Resources, Config, Paths, Show<Params & WithComponentKeyParam<Resources, Config, Paths, Optional>>, Used | 'addComponentKeyParams'>;
|
|
59
|
+
}) & ('addPathParams' extends Used ? {} : {
|
|
60
|
+
/**
|
|
61
|
+
* Turns the variables these paths leave open into props. Without `pick`, every
|
|
62
|
+
* variable becomes a prop.
|
|
63
|
+
*/
|
|
64
|
+
addPathParams<Variables extends PathVariablesForPaths<Resources, Config, Paths>, Picked extends { [Key in keyof Variables]?: true } = {}>(options?: {
|
|
65
|
+
/** Variables to expose as props. Defaults to all of them. */pick?: Picked;
|
|
66
|
+
}): TargetPathBuilder<Resources, Config, Paths, Show<Params & PickedPathParams<Variables, Picked>>, Used | 'addPathParams'>;
|
|
67
|
+
}) & ('addParams' extends Used ? {} : {
|
|
68
|
+
/**
|
|
69
|
+
* Adds custom params with the given values as defaults. Defaults are
|
|
70
|
+
* optional at the call site and filled in before `render` runs.
|
|
71
|
+
*/
|
|
72
|
+
addParams<NewParams extends Record<string, unknown>>(params: NewParams): TargetPathBuilder<Resources, Config, Paths, Show<Params & Partial<NewParams>>, Used | 'addParams'>;
|
|
73
|
+
});
|
|
74
|
+
type ForPaths<Resources extends ReadonlyArray<ResourceDefinition>, Config, AllowedPath extends string> = <const Paths extends readonly [AllowedPath, ...AllowedPath[]]>(...paths: Paths) => TargetPathBuilder<Resources, Config, Paths>;
|
|
75
|
+
//#endregion
|
|
76
|
+
export { ForPaths, ForPathsRenderContext, RenderedPathComponent, RenderedPathComponentHOF, TargetPathBuilder };
|
|
77
|
+
//# sourceMappingURL=builder.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"builder.d.mts","names":[],"sources":["../../../src/create-config/for-paths/builder.ts"],"mappings":"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"}
|