/** * Source provider abstraction for unified extension discovery and fetching. * * Defines the `SourceHostProvider` interface that all source types implement, * along with supporting types for search criteria, discovery results, and errors. * * @experimental This API is unstable and may change without notice. * @packageDocumentation */ import type * as Effect from "effect/Effect"; import type * as Option from "effect/Option"; import type { ExtensionType, Handle } from "../extensions/index.js"; import type { ExtensionRef } from "../extensions/refs/extension-ref.js"; import type { Source } from "./types.js"; import type { ReleaseAgeEvaluation, ReleaseAgeEvidence, ReleaseAgeExemption } from "../extensions/release-age.js"; /** * Search criteria passed to `find` -- independent of source identity. * * - `names`: extension names to match (empty = all) * - `type`: findable extension type filter or `"*"` for all * - `versionRange`: optional version constraint for registry-backed lookups * * @experimental This API is unstable and may change without notice. */ export interface FindOptions { readonly names: ReadonlyArray; readonly type: ExtensionType | "*"; /** Registry owner filter (e.g. "@acme"). */ readonly owner: Option.Option; readonly versionRange: Option.Option; } export interface NamedRegistryFindOptions { readonly name: string; readonly type: ExtensionType; readonly owner: Handle; readonly versionRange: Option.Option; readonly releaseAgeEvaluation: ReleaseAgeEvaluation; /** Accepted immutable Registry identity that unattended resolution must not move behind. */ readonly accepted?: { readonly version: string; readonly publisherBindingId: string; }; } export type NamedRegistryResolution = { readonly kind: "selected"; readonly target: string; readonly ref: Extract; readonly newerHeld?: ReleaseAgeEvidence; /** The newest release a range could select, whatever range was requested. */ readonly newestVisible?: string; } | { readonly kind: "exempted"; readonly target: string; readonly ref: Extract; readonly bypassed: ReleaseAgeEvidence; readonly exemption: ReleaseAgeExemption; readonly newestVisible?: string; } | { readonly kind: "not_found"; readonly target: string; } | { readonly kind: "version_unsatisfied"; readonly target: string; readonly requestedRange: string; } | { readonly kind: "policy_held"; readonly target: string; readonly requestedRange?: string; readonly candidate: ReleaseAgeEvidence; }; /** * Index-level selection decision for one named Registry target, before the * provider maps the chosen entry to an `ExtensionRef` or probes any archive. * Versions are identified by their version string; the provider owns the * index and looks the entry up. * * @experimental This API is unstable and may change without notice. */ export type NamedRegistryVersionDecision = { readonly kind: "selected"; readonly version: string; readonly newerHeld?: ReleaseAgeEvidence; /** * The newest release the index lists that a range could select — not * yanked, whatever range was requested — so a caller can say what its * constraint held the selection below. */ readonly newestVisible?: string; } | { readonly kind: "exempted"; readonly version: string; readonly bypassed: ReleaseAgeEvidence; readonly exemption: ReleaseAgeExemption; readonly newestVisible?: string; } | { readonly kind: "not_found"; } | { readonly kind: "version_unsatisfied"; readonly requestedRange: string; } | { readonly kind: "policy_held"; readonly requestedRange?: string; readonly candidate: ReleaseAgeEvidence; }; /** * What selecting one probe-verified candidate would mean under the policy. * * @experimental This API is unstable and may change without notice. */ export type NamedRegistryCandidateOutcome = { readonly kind: "selected"; } | { readonly kind: "exempted"; readonly bypassed: ReleaseAgeEvidence; readonly exemption: ReleaseAgeExemption; } | { readonly kind: "held"; readonly candidate: ReleaseAgeEvidence; }; /** * One candidate a provider may verify before selecting a named target, in * policy order: selectable candidates newest first, then held candidates * newest first. * * @experimental This API is unstable and may change without notice. */ export interface NamedRegistryCandidate { readonly version: string; readonly outcome: NamedRegistryCandidateOutcome; } /** * Materialized extension files ready for installation. * * Returned by `fetch` after files have been prepared. * * @experimental This API is unstable and may change without notice. */ export interface ExtensionFiles { /** Absolute path to directory containing extension files. */ readonly directory: string; /** Original publication-policy boundary; absent means that context was not retained. */ readonly publicationBoundaryRoot?: string; /** Complete package context for a selected component. */ readonly packageDirectory?: string; readonly componentPath?: string; } /** * Source host provider that unifies how all source types are accessed. * * Each source type is implemented as a provider with `match`, `find` and `fetch` * capabilities. The `R` parameter captures Effect requirements for the * provider's operations. * * @typeParam S - The specific `Source` variant this provider handles. * @typeParam R - Effect requirements for provider operations. * @typeParam E - Typed failure channel for provider operations. * * @experimental This API is unstable and may change without notice. */ export interface SourceHostProvider { /** Source type discriminator matching `S["type"]`. */ readonly type: S["type"]; /** Check if a URL belongs to this provider. */ readonly match: (url: URL) => Effect.Effect; /** Discover extensions at the given source matching the search criteria. */ readonly find: (source: S, options: FindOptions) => Effect.Effect, E, R>; /** Fetch and materialize extension files for a discovered ref. */ readonly fetch: (source: S, ref: ExtensionRef) => Effect.Effect; } //# sourceMappingURL=source-host-provider.d.ts.map