/** * Internal helpers for selecting and binding extension entrypoints. * * Package manifests are untrusted input. Selection reads only own data * properties, never invokes accessors, and accepts only deterministic local * filesystem targets. Binding then replaces the discovered lexical path with * a canonical absolute regular-file path inside the canonical owning * directory. * * @module extensions/entrypoint-identity */ export interface EntrypointFileInfo { isFile: boolean; isDirectory: boolean; dev: number | bigint | null; ino: number | bigint | null; } export interface EntrypointFileOperations { realPath(path: string): Promise; stat(path: string): Promise; } export interface ExtensionFileIdentity { readonly dev: number | bigint; readonly ino: number | bigint; } /** Canonical directory identity captured before any activation manifest read. */ export interface CapturedExtensionOwner { readonly lexicalPath: string; readonly canonicalPath: string; readonly identity: ExtensionFileIdentity; readonly parent?: CapturedExtensionOwner; } /** Internal security descriptor carried from discovery to dynamic import. */ export interface BoundExtensionEntrypoint { readonly path: string; readonly owner: CapturedExtensionOwner; readonly targetIdentity: ExtensionFileIdentity; } export interface CaptureExtensionOwnerOptions { readonly parent?: CapturedExtensionOwner; /** @internal Deterministic filesystem seam for race tests. */ readonly operations?: EntrypointFileOperations; } export type ExtensionEntrypointIdentityFailure = "unsafe-entrypoint" | "identity-unavailable"; export declare class ExtensionEntrypointIdentityError extends Error { readonly reason: ExtensionEntrypointIdentityFailure; constructor(message: string, reason: ExtensionEntrypointIdentityFailure); } /** * Select the deterministic local import entrypoint from a parsed package.json. * * The manifest name must exactly match the package name discovered from the * lexical node_modules location. `exports` takes precedence over `module`, * then `main`; packages with none of those fields use `./index.js`. */ export declare function selectPackageImportEntrypoint(discoveredPackageName: string, packageManifest: unknown): string; /** * Capture one canonical directory before reading any manifest beneath it. * * A project extension can name a captured parent, which requires the physical * owner to remain a direct child of the canonical `extensions/` directory. * Package owners omit the parent because pnpm legitimately places their * physical directories outside the lexical `node_modules/` tree. * * Runtimes that do not expose stable device and inode values cannot satisfy * this security boundary. Capture fails deterministically instead of silently * degrading to path-only checks. */ export declare function captureExtensionOwner(owningDirectory: string, options?: CaptureExtensionOwnerOptions): Promise; /** Bind a selected relative entrypoint to a captured owner and file identity. */ export declare function bindExtensionEntrypoint(owner: CapturedExtensionOwner, selectedEntrypoint: string, operations?: EntrypointFileOperations): Promise; /** * Revalidate a discovery binding immediately before native ESM import. * * Native path-based ESM cannot make the final stat and module open atomic. * This closes deterministic swaps before import; the remaining stat-to-open * scheduling window is an explicit runtime limitation. */ export declare function revalidateBoundExtensionEntrypoint(binding: BoundExtensionEntrypoint, operations?: EntrypointFileOperations): Promise; /** * Bind a selected project or package entrypoint to its physical identity. * * Contained symlinks are accepted, but the returned value is their canonical * target. Direct or intermediate symlinks that escape the owning directory are * rejected. This compatibility wrapper does not retain the identity binding; * production discovery carries `BoundExtensionEntrypoint` through to import. * * The optional operations argument is an internal test seam; production callers * use the runtime-neutral compat filesystem functions. */ export declare function canonicalizeExtensionEntrypoint(owningDirectory: string, selectedEntrypoint: string, operations?: EntrypointFileOperations): Promise; //# sourceMappingURL=entrypoint-identity.d.ts.map