feat: add runtime API registry for dynamic provider switching

This commit is contained in:
2026-09-09 17:08:15 +00:00
parent 0679aabaa1
commit 23aea36d0e
6 changed files with 320 additions and 110 deletions
@@ -2,10 +2,38 @@ import React, { type JSX, type ReactNode } from 'react';
import { RuntimeAPIContext } from '@/contexts/runtimeAPIContext';
import type { FilesAPI, RuntimeAPIs } from '@/lib/api/types';
import { createContentCachedFiles } from '@/contexts/content-cache-owner';
import {
resolveActiveRuntimeAPIs,
subscribeRuntimeProviderChanged,
} from '@/lib/runtime-api-registry';
type ContentCachedFiles = ReturnType<typeof createContentCachedFiles>;
export function RuntimeAPIProvider({ apis, children }: { apis: RuntimeAPIs; children: ReactNode }): JSX.Element {
interface RuntimeAPIProviderProps {
/** Runtime APIs to provide. Ignored when a registry provider is active. */
apis: RuntimeAPIs;
children: ReactNode;
}
/**
* Provides RuntimeAPIs to the React tree. When a provider is registered in
* the runtime API registry, the component automatically re-resolves the APIs
* on provider switches. Otherwise it uses the `apis` prop directly (legacy
* behaviour, fully backward compatible).
*/
export function RuntimeAPIProvider({ apis: fallbackApis, children }: RuntimeAPIProviderProps): JSX.Element {
const [registryApis, setRegistryApis] = React.useState<RuntimeAPIs | null>(() =>
resolveActiveRuntimeAPIs(),
);
React.useEffect(() => {
return subscribeRuntimeProviderChanged(() => {
setRegistryApis(resolveActiveRuntimeAPIs());
});
}, []);
const apis = registryApis ?? fallbackApis;
// Effect-owned lifecycle: React Strict Mode dispose+remount must create a fresh
// owner. useMemo + dispose reused a dead owner and broke text-file opens
// (binaries skipped the pre-read, so they still appeared to work).