import { a as implementPortalFunction, i as getPortalFunctionMetadata, n as attachPortalFunctionMetadata, r as definePortalFunction, t as PortalFunctionError } from "../portal-function-DiozZloV.mjs";
import { createElement, useEffect, useRef } from "react";
import { startRemoteDomWidgetWorker } from "@fluid-app/widget-runtime/worker";
//#region src/widgets/portal-built-in-functions.ts
const ACCOUNT_DEFINITION = {
	capability: "account",
	version: "1",
	method: "get"
};
const STORE_DEFINITION = {
	capability: "store",
	version: "1",
	method: "get"
};
const APP_DEFINITION = {
	capability: "fluidApp",
	version: "1",
	method: "get"
};
const PROFILE_DEFINITION = {
	capability: "fluidProfile",
	version: "1",
	method: "get"
};
const NAVIGATION_STATE_DEFINITION = {
	capability: "appNavigation",
	version: "1",
	method: "get"
};
const BUILD_HREF_DEFINITION = {
	capability: "appNavigation",
	version: "1",
	method: "buildHref"
};
const NAVIGATE_DEFINITION = {
	capability: "appNavigation",
	version: "1",
	method: "navigate"
};
const FULLSCREEN_STATE_DEFINITION = {
	capability: "fullscreen",
	version: "1",
	method: "get"
};
const REQUEST_FULLSCREEN_DEFINITION = {
	capability: "fullscreen",
	version: "1",
	method: "request"
};
const EXIT_FULLSCREEN_DEFINITION = {
	capability: "fullscreen",
	version: "1",
	method: "exit"
};
const getUserAccount = definePortalFunction(ACCOUNT_DEFINITION);
const getStore = definePortalFunction(STORE_DEFINITION);
const getPortalApp = definePortalFunction(APP_DEFINITION);
const getPortalProfile = definePortalFunction(PROFILE_DEFINITION);
const getNavigationState = definePortalFunction(NAVIGATION_STATE_DEFINITION);
const buildPortalHref = definePortalFunction(BUILD_HREF_DEFINITION);
const navigate = definePortalFunction(NAVIGATE_DEFINITION);
const navigateTo = attachPortalFunctionMetadata(async (target) => {
	await navigate(target);
}, NAVIGATE_DEFINITION);
const getFullscreenState = definePortalFunction(FULLSCREEN_STATE_DEFINITION);
const request = definePortalFunction(REQUEST_FULLSCREEN_DEFINITION);
const requestFullscreen = attachPortalFunctionMetadata(async () => {
	await request();
}, REQUEST_FULLSCREEN_DEFINITION);
const exit = definePortalFunction(EXIT_FULLSCREEN_DEFINITION);
const exitFullscreen = attachPortalFunctionMetadata(async () => {
	await exit();
}, EXIT_FULLSCREEN_DEFINITION);
//#endregion
//#region src/widgets/worker.ts
const SOURCE_WIDGET_MARKER = "__fluidSourceWidget";
const SOURCE_WIDGET_PACKAGE_MARKER = "__fluidSourceWidgetPackage";
const portalFunctionsByWidgetName = /* @__PURE__ */ new Map();
function defineWidget(options) {
	const uses = options.uses ?? [];
	const normalized = normalizePortalFunctions(uses);
	const registrations = portalFunctionsByWidgetName.get(options.name) ?? [];
	registrations.push(normalized);
	portalFunctionsByWidgetName.set(options.name, registrations);
	return {
		...options,
		[SOURCE_WIDGET_MARKER]: true,
		defaultProps: options.defaultProps ?? {},
		uses,
		capabilities: normalized.capabilities
	};
}
function defineWidgetPackage(options) {
	const packageType = options.packageType ?? "company";
	const packageStableId = options.packageStableId;
	if (!packageStableId && packageType !== "droplet") throw new Error("defineWidgetPackage requires packageStableId for company packages.");
	const stableId = packageStableId ?? "__fluid_cli_managed__";
	return {
		[SOURCE_WIDGET_PACKAGE_MARKER]: true,
		manifestVersion: 1,
		scope: options.scope,
		packageStableId: stableId,
		packageId: `${options.scope}.${stableId}`,
		packageType,
		version: options.version ?? "0.0.0-dev",
		widgets: options.widgets,
		cssUrls: options.cssUrls ?? []
	};
}
/** Starts one Remote DOM worker containing every widget in the source package. */
function startWidgetPackage(widgetPackage) {
	return startRemoteDomWidgetWorker({ widgets: "packageId" in widgetPackage ? Object.fromEntries(widgetPackage.widgets.map((widget) => [`${getCanonicalRuntimePackageId(widgetPackage)}.${widget.name}`, {
		component: widget.component,
		capabilities: widget.capabilities,
		functions: readSourcePortalFunctions(widget)
	}])) : Object.fromEntries(widgetPackage.widgets.map((widget) => [widget.type, {
		component: widget.component,
		capabilities: widget.capabilities ?? [],
		functions: readGeneratedPortalFunctions(widget)
	}])) });
}
function normalizePortalFunctions(uses) {
	const versionByCapability = /* @__PURE__ */ new Map();
	const functionsByIdentity = /* @__PURE__ */ new Map();
	for (const portalFunction of uses) {
		const metadata = getPortalFunctionMetadata(portalFunction);
		if (!metadata) throw new Error("defineWidget uses must contain functions created by definePortalFunction.");
		const currentVersion = versionByCapability.get(metadata.capability);
		if (currentVersion && currentVersion !== metadata.version) throw new Error(`defineWidget cannot use capability "${metadata.capability}" at both version "${currentVersion}" and version "${metadata.version}".`);
		versionByCapability.set(metadata.capability, metadata.version);
		functionsByIdentity.set(JSON.stringify([
			metadata.capability,
			metadata.version,
			metadata.method
		]), metadata);
	}
	return {
		capabilities: [...versionByCapability].map(([name, version]) => ({
			name,
			version
		})),
		functions: [...functionsByIdentity.values()]
	};
}
function readGeneratedPortalFunctions(widget) {
	if (!widget.name) return [];
	const registrations = portalFunctionsByWidgetName.get(widget.name) ?? [];
	portalFunctionsByWidgetName.delete(widget.name);
	const capabilities = widget.capabilities ?? [];
	const matchingRegistrations = registrations.filter((registration) => haveSameCapabilityDeclarations(registration.capabilities, capabilities));
	const uniqueFunctions = /* @__PURE__ */ new Map();
	for (const registration of matchingRegistrations) uniqueFunctions.set(portalFunctionSetKey(registration.functions), registration.functions);
	if (uniqueFunctions.size > 1) throw new Error(`Generated worker entry cannot recover an unambiguous uses declaration for widget "${widget.name}" (${widget.type}). Multiple widgets with that name declare the same capabilities but different portal functions; give every source widget a unique name.`);
	return uniqueFunctions.values().next().value ?? [];
}
function readSourcePortalFunctions(widget) {
	portalFunctionsByWidgetName.delete(widget.name);
	return normalizePortalFunctions(widget.uses).functions;
}
function haveSameCapabilityDeclarations(left, right) {
	if (left.length !== right.length) return false;
	const rightKeys = new Set(right.map(({ name, version }) => JSON.stringify([name, version])));
	return left.every(({ name, version }) => rightKeys.has(JSON.stringify([name, version])));
}
function portalFunctionSetKey(functions) {
	return JSON.stringify(functions.map(({ capability, version, method }) => [
		capability,
		version,
		method
	]).sort(([leftCapability, leftVersion, leftMethod], right) => `${leftCapability}\u0000${leftVersion}\u0000${leftMethod}`.localeCompare(right.join("\0"))));
}
function getCanonicalRuntimePackageId(widgetPackage) {
	const owner = widgetPackage.packageType;
	const scope = widgetPackage.scope;
	const stableId = widgetPackage.packageStableId;
	return `${owner}.${scope !== "company" && scope !== "droplet" && !stableId.startsWith(`${scope}.`) ? `${scope}.${stableId}` : stableId}`;
}
function SearchSort({ onSearchChange, onSortChange, ...props }) {
	const elementRef = useRef(null);
	const searchChangeRef = useRef(onSearchChange);
	const sortChangeRef = useRef(onSortChange);
	searchChangeRef.current = onSearchChange;
	sortChangeRef.current = onSortChange;
	useEffect(() => {
		const element = elementRef.current;
		if (!element) return;
		const handleSearchChange = (event) => {
			const value = readRemoteEventValue(event);
			if (value !== void 0) searchChangeRef.current(value);
		};
		const handleSortChange = (event) => {
			const value = readRemoteEventValue(event);
			if (value !== void 0) sortChangeRef.current?.(value);
		};
		element.addEventListener("search-change", handleSearchChange);
		element.addEventListener("sort-change", handleSortChange);
		return () => {
			element.removeEventListener("search-change", handleSearchChange);
			element.removeEventListener("sort-change", handleSortChange);
		};
	}, []);
	return createElement("fluid-ui-search-sort", {
		...props,
		ref: elementRef
	});
}
function FluidSpacerWidget(props) {
	return createElement("fluid-spacer-widget", props);
}
function readRemoteEventValue(event) {
	if (!(event instanceof CustomEvent)) return void 0;
	if (typeof event.detail === "string") return event.detail;
	if (typeof event.detail === "object" && event.detail !== null && "detail" in event.detail && typeof event.detail.detail === "string") return event.detail.detail;
}
//#endregion
export { FluidSpacerWidget, PortalFunctionError, SearchSort, buildPortalHref, definePortalFunction, defineWidget, defineWidgetPackage, exitFullscreen, getFullscreenState, getNavigationState, getPortalApp, getPortalProfile, getStore, getUserAccount, implementPortalFunction, navigateTo, requestFullscreen, startWidgetPackage };

//# sourceMappingURL=worker.mjs.map