import type { Model, ModelProperty, Operation, Program, Type } from "@typespec/compiler"; import { type ResolvedProjection } from "./projection.js"; export declare const JOIN_DIRECTIONS: readonly ["lookup", "inbound"]; export type JoinDirection = (typeof JOIN_DIRECTIONS)[number]; export declare function isJoinDirection(value: string): value is JoinDirection; export interface ResolvableByDeclaration { key: ModelProperty; index?: string; } export interface JoinDependencyDeclaration { entity: Model; direction: string; joinKey: ModelProperty; } export interface ResolvedJoinDependency { entity: Model; direction: JoinDirection; joinKey: ModelProperty; /** * The projection property the joined value lands in. Its declared type is * what the join resolver returns. */ field: ModelProperty; /** Carried from the entity's `@resolvableBy`; an inbound join only. */ index?: string; } export interface ResolvableByManifestEntry { entity: string; key: string; index?: string; } export interface JoinDependencyManifestEntry { entity: string; direction: JoinDirection; joinKey: string; field: string; index?: string; } /** * The model a join key must belong to: its own model for `@resolvableBy`, the * projection's source model for a `lookup` (the driving row carries the value * the joined row is fetched by), and the joined entity for an `inbound` (the * joined row carries the reference back). */ declare function expectedJoinKeyOwner(declaration: JoinDependencyDeclaration, sourceModel: Model): Model; /** * True when the property is declared on the model or on anything it extends. * An inherited property keeps the base model in `.model`, so identity alone * rejects a key a derived model legitimately owns. */ export declare function ownsProperty(model: Model, property: ModelProperty): boolean; export declare function unwrapArrayElement(type: Type): Type | undefined; /** * The projection properties a declaration could fill. A declaration fills * exactly one; anything else is reported rather than guessed at. */ export declare function candidateJoinFields(program: Program, projectionModel: Model, entity: Model): ModelProperty[]; /** * True when something states which of the joined entity enters the document * (issue #195): a `SearchProjection` document that resolves at least one * field, a `@searchInfer` model whose fields the emitter derives, or a plain * model declaring what it contributes. A model offering none of the three * composes into an empty object, which the mapping and the SDL cannot express. */ export declare function composesIntoDocument(program: Program, field: ModelProperty): boolean; export declare function resolveJoinDependencies(program: Program, projectionModel: Model): ResolvedJoinDependency[]; declare function hasExpectedArity(direction: JoinDirection, field: ModelProperty): boolean; /** * Every entity a document is composed from, the ones reached through another * join included (issue #197). A joined document carrying its own `@dependsOn` * puts that entity's rows in the driving document, so a write there re-indexes * it just the same — a manifest listing only the first hop names fewer triggers * than the document actually has. * * The closure is flat: `field` carries the joined value's key path in the * composed document, dotted for a transitive entry, which is where a consumer * places the value and how two hops over the same entity stay apart. */ export declare function collectJoinDependencies(program: Program, projection: ResolvedProjection): JoinDependencyManifestEntry[]; /** * `field` names the document key the joined value lands in, so it carries the * projected name — a `@searchAs` rename moves the key, and a consumer placing * the value by the TypeSpec property name would write a key the mapping does * not declare. */ export declare function toJoinDependencyManifestEntry(program: Program, dependency: ResolvedJoinDependency, field?: string): JoinDependencyManifestEntry; export declare function toResolvableByManifestEntry(program: Program, entity: Model): ResolvableByManifestEntry | undefined; /** * The read a join runs against: the `@restResolver` GET operation that returns * the entity and takes its declared key as a parameter. A `listX()` returning * the same model does not serve the join — nothing hands it the key. */ export declare function servesResolvableByRead(program: Program, operation: Operation, entity: Model, key: string): boolean; /** * The model a read operation returns, single or as an array. */ export declare function unwrapReadModel(returnType: Type): Model | undefined; export declare function validateJoinDeclarations(program: Program): void; declare function capitalize(value: string): string; export declare const __test: { capitalize: typeof capitalize; expectedJoinKeyOwner: typeof expectedJoinKeyOwner; hasExpectedArity: typeof hasExpectedArity; }; export {}; //# sourceMappingURL=joins.d.ts.map