/**
 * Lazy-loaded offline runtime chunk.
 *
 * Contains Automerge + WASM (~2.5MB) — split from shell.ts so the main
 * shell bundle stays small and doesn't block first paint.
 */

import * as Automerge from '@automerge/automerge';
import { RStackHistoryPanel } from "../shared/components/rstack-history-panel";
import { RSpaceOfflineRuntime } from "../shared/local-first/runtime";
import { CommunitySync } from "../lib/community-sync";
import { OfflineStore } from "../lib/offline-store";

// Expose Automerge globally so module builds can externalize it (~2.5MB savings per module)
(window as any).__automerge = Automerge;

// Define the history panel component (depends on Automerge)
RStackHistoryPanel.define();

export function initOffline(spaceSlug: string) {
	const runtime = new RSpaceOfflineRuntime(spaceSlug);
	(window as any).__rspaceOfflineRuntime = runtime;

	// Configure module scope resolution from server-rendered data
	try {
		const scopeJson = document.body?.getAttribute("data-scope-overrides");
		const overrides: Record<string, string> = scopeJson ? JSON.parse(scopeJson) : {};
		const moduleList: Array<{ id: string; scoping?: { defaultScope: string } }> =
			(window as any).__rspaceModuleList || [];
		const scopes: Array<{ id: string; scope: 'global' | 'space' }> = moduleList.map(m => ({
			id: m.id,
			scope: (overrides[m.id] || m.scoping?.defaultScope || 'space') as 'global' | 'space',
		}));
		runtime.setModuleScopes(scopes);
	} catch { /* scope config unavailable — defaults to space-scoped */ }

	runtime.init().catch((e: unknown) => {
		console.warn("[shell] Offline runtime init failed — REST fallback only:", e);
	});

	// Flush pending writes when tab is hidden (more reliable than beforeunload on mobile/bfcache)
	document.addEventListener("visibilitychange", () => {
		if (document.visibilityState === "hidden") {
			runtime.flush();
		}
	});
	// Flush pending writes before the page unloads (fallback)
	window.addEventListener("beforeunload", () => {
		runtime.flush();
	});

	// ── CommunitySync (tab list Automerge sync) ──
	const offlineStore = new OfflineStore();
	const communitySync = new CommunitySync(spaceSlug, offlineStore);
	(window as any).__communitySync = communitySync;

	(async () => {
		try {
			await offlineStore.open();
			await communitySync.initFromCache();
		} catch (e) {
			console.warn("[shell] CommunitySync cache init failed:", e);
		}
		document.dispatchEvent(new CustomEvent("community-sync-ready", {
			detail: { sync: communitySync, communitySlug: spaceSlug },
		}));

		const proto = location.protocol === "https:" ? "wss:" : "ws:";
		const wsUrl = `${proto}//${location.host}/ws/${spaceSlug}`;
		communitySync.connect(wsUrl);
	})();

	window.addEventListener("beforeunload", () => {
		communitySync.saveBeforeUnload();
	});
}
