Big News: Socket raises $60M Series C at a $1B valuation to secure software supply chains for AI-driven development.Announcement
Sign In

@freesail/react

Package Overview
Dependencies
Maintainers
1
Versions
19
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@freesail/react - npm Package Compare versions

Comparing version
0.4.5
to
0.4.6
+31
dist/context.d.ts
/**
* @fileoverview Freesail React Context
*
* Provides React context for Freesail state management.
*/
import type { SurfaceManager, A2UITransport, Surface, SurfaceId, ComponentId } from '@freesail/core';
/**
* Freesail context value.
*/
export interface FreesailContextValue {
/** Surface manager instance */
surfaceManager: SurfaceManager;
/** Transport instance (may be null if not connected) */
transport: A2UITransport | null;
/** Send an action (v0.9 format) */
sendAction: (surfaceId: SurfaceId, name: string, sourceComponentId: ComponentId, context: Record<string, unknown>) => Promise<void>;
/** Get a surface by ID */
getSurface: (surfaceId: SurfaceId) => Surface | undefined;
/** Connection state */
isConnected: boolean;
}
/**
* React context for Freesail.
*/
export declare const FreesailContext: import("react").Context<FreesailContextValue | null>;
/**
* Hook to access the Freesail context.
* Throws if used outside of a FreesailProvider.
*/
export declare function useFreesailContext(): FreesailContextValue;
//# sourceMappingURL=context.d.ts.map
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAGH,OAAO,KAAK,EACV,cAAc,EACd,aAAa,EACb,OAAO,EACP,SAAS,EACT,WAAW,EAEZ,MAAM,gBAAgB,CAAC;AAExB;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,+BAA+B;IAC/B,cAAc,EAAE,cAAc,CAAC;IAC/B,wDAAwD;IACxD,SAAS,EAAE,aAAa,GAAG,IAAI,CAAC;IAChC,mCAAmC;IACnC,UAAU,EAAE,CACV,SAAS,EAAE,SAAS,EACpB,IAAI,EAAE,MAAM,EACZ,iBAAiB,EAAE,WAAW,EAC9B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAC7B,OAAO,CAAC,IAAI,CAAC,CAAC;IACnB,0BAA0B;IAC1B,UAAU,EAAE,CAAC,SAAS,EAAE,SAAS,KAAK,OAAO,GAAG,SAAS,CAAC;IAC1D,uBAAuB;IACvB,WAAW,EAAE,OAAO,CAAC;CACtB;AAED;;GAEG;AACH,eAAO,MAAM,eAAe,sDAAmD,CAAC;AAEhF;;;GAGG;AACH,wBAAgB,kBAAkB,IAAI,oBAAoB,CAMzD"}
/**
* @fileoverview Freesail React Context
*
* Provides React context for Freesail state management.
*/
import { createContext, useContext } from 'react';
/**
* React context for Freesail.
*/
export const FreesailContext = createContext(null);
/**
* Hook to access the Freesail context.
* Throws if used outside of a FreesailProvider.
*/
export function useFreesailContext() {
const context = useContext(FreesailContext);
if (!context) {
throw new Error('useFreesailContext must be used within a FreesailProvider');
}
return context;
}
//# sourceMappingURL=context.js.map
{"version":3,"file":"context.js","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,OAAO,CAAC;AA+BlD;;GAEG;AACH,MAAM,CAAC,MAAM,eAAe,GAAG,aAAa,CAA8B,IAAI,CAAC,CAAC;AAEhF;;;GAGG;AACH,MAAM,UAAU,kBAAkB;IAChC,MAAM,OAAO,GAAG,UAAU,CAAC,eAAe,CAAC,CAAC;IAC5C,IAAI,CAAC,OAAO,EAAE,CAAC;QACb,MAAM,IAAI,KAAK,CAAC,2DAA2D,CAAC,CAAC;IAC/E,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC","sourcesContent":["/**\n * @fileoverview Freesail React Context\n *\n * Provides React context for Freesail state management.\n */\n\nimport { createContext, useContext } from 'react';\nimport type {\n SurfaceManager,\n A2UITransport,\n Surface,\n SurfaceId,\n ComponentId,\n A2UIClientDataModel,\n} from '@freesail/core';\n\n/**\n * Freesail context value.\n */\nexport interface FreesailContextValue {\n /** Surface manager instance */\n surfaceManager: SurfaceManager;\n /** Transport instance (may be null if not connected) */\n transport: A2UITransport | null;\n /** Send an action (v0.9 format) */\n sendAction: (\n surfaceId: SurfaceId,\n name: string,\n sourceComponentId: ComponentId,\n context: Record<string, unknown>\n ) => Promise<void>;\n /** Get a surface by ID */\n getSurface: (surfaceId: SurfaceId) => Surface | undefined;\n /** Connection state */\n isConnected: boolean;\n}\n\n/**\n * React context for Freesail.\n */\nexport const FreesailContext = createContext<FreesailContextValue | null>(null);\n\n/**\n * Hook to access the Freesail context.\n * Throws if used outside of a FreesailProvider.\n */\nexport function useFreesailContext(): FreesailContextValue {\n const context = useContext(FreesailContext);\n if (!context) {\n throw new Error('useFreesailContext must be used within a FreesailProvider');\n }\n return context;\n}\n"]}
/**
* @fileoverview FreesailProvider Component
*
* The root provider component that manages Freesail connections
* and state for the React application.
*/
import { type ReactNode } from 'react';
import { type TransportOptions, type CatalogId } from '@freesail/core';
import type { CatalogDefinition } from './types.js';
/**
* Props for FreesailProvider.
*/
export interface FreesailProviderProps {
/** Child components */
children: ReactNode;
/** Base gateway URL (e.g. 'http://localhost:3001'). SSE and POST endpoints are derived automatically. */
gateway: string;
/** List of supported catalog IDs */
catalogs?: CatalogId[];
/**
* Array of custom catalog definitions to register.
* Each definition bundles a namespace, schema, and component map.
* Components are auto-registered on mount.
*/
catalogDefinitions?: CatalogDefinition[];
/** Additional transport options */
transportOptions?: Partial<Omit<TransportOptions, 'gateway' | 'capabilities'>>;
/** Auto-connect on mount (default: true) */
autoConnect?: boolean;
/** Callback when connection state changes */
onConnectionChange?: (connected: boolean) => void;
/** Callback when an error occurs */
onError?: (error: Error) => void;
}
/**
* Root provider component for Freesail.
*
* Manages the transport connection and surface state,
* making them available to all child components.
*/
export declare function FreesailProvider({ children, gateway, catalogs, catalogDefinitions, transportOptions, autoConnect, onConnectionChange, onError, }: FreesailProviderProps): import("react/jsx-runtime").JSX.Element;
//# sourceMappingURL=FreesailProvider.d.ts.map
{"version":3,"file":"FreesailProvider.d.ts","sourceRoot":"","sources":["../src/FreesailProvider.tsx"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAc,EAMZ,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AACf,OAAO,EAUL,KAAK,gBAAgB,EAGrB,KAAK,SAAS,EAGf,MAAM,gBAAgB,CAAC;AAGxB,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AAEpD;;GAEG;AACH,MAAM,WAAW,qBAAqB;IACpC,uBAAuB;IACvB,QAAQ,EAAE,SAAS,CAAC;IACpB,yGAAyG;IACzG,OAAO,EAAE,MAAM,CAAC;IAChB,oCAAoC;IACpC,QAAQ,CAAC,EAAE,SAAS,EAAE,CAAC;IACvB;;;;OAIG;IACH,kBAAkB,CAAC,EAAE,iBAAiB,EAAE,CAAC;IACzC,mCAAmC;IACnC,gBAAgB,CAAC,EAAE,OAAO,CAAC,IAAI,CAAC,gBAAgB,EAAE,SAAS,GAAG,cAAc,CAAC,CAAC,CAAC;IAC/E,4CAA4C;IAC5C,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,6CAA6C;IAC7C,kBAAkB,CAAC,EAAE,CAAC,SAAS,EAAE,OAAO,KAAK,IAAI,CAAC;IAClD,oCAAoC;IACpC,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,KAAK,IAAI,CAAC;CAClC;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,EAC/B,QAAQ,EACR,OAAO,EACP,QAAa,EACb,kBAAuB,EACvB,gBAAgB,EAChB,WAAkB,EAClB,kBAAkB,EAClB,OAAO,GACR,EAAE,qBAAqB,2CA6NvB"}
import { jsx as _jsx } from "react/jsx-runtime";
/**
* @fileoverview FreesailProvider Component
*
* The root provider component that manages Freesail connections
* and state for the React application.
*/
import { useState, useEffect, useCallback, useMemo, useRef, } from 'react';
import { createSurfaceManager, createTransport, isCreateSurfaceMessage, isUpdateComponentsMessage, isUpdateDataModelMessage, isDeleteSurfaceMessage, isGetDataModelMessage, } from '@freesail/core';
import { FreesailContext } from './context.js';
import { registerCatalog } from './registry.js';
/**
* Root provider component for Freesail.
*
* Manages the transport connection and surface state,
* making them available to all child components.
*/
export function FreesailProvider({ children, gateway, catalogs = [], catalogDefinitions = [], transportOptions, autoConnect = true, onConnectionChange, onError, }) {
const [surfaceManager] = useState(() => createSurfaceManager());
const [transport, setTransport] = useState(null);
const [isConnected, setIsConnected] = useState(false);
// Track surfaces deleted by agent messages so we don't echo them back
const agentDeletedRef = useRef(new Set());
// Refs for callbacks so the transport effect always uses current values
// without needing to be recreated when callbacks change
const onConnectionChangeRef = useRef(onConnectionChange);
const onErrorRef = useRef(onError);
const catalogDefinitionsRef = useRef(catalogDefinitions);
const autoConnectRef = useRef(autoConnect);
useEffect(() => {
onConnectionChangeRef.current = onConnectionChange;
onErrorRef.current = onError;
catalogDefinitionsRef.current = catalogDefinitions;
autoConnectRef.current = autoConnect;
});
// Register custom catalog definitions
useEffect(() => {
for (const def of catalogDefinitions) {
registerCatalog(def.namespace, def.components, def.functions, def.schema);
}
}, [catalogDefinitions]);
// Merge explicit catalog IDs with catalog definition namespaces
const mergedCatalogs = useMemo(() => {
const definitionIds = catalogDefinitions.map((d) => d.namespace);
const combined = [...catalogs, ...definitionIds];
return Array.from(new Set(combined));
}, [catalogs, catalogDefinitions]);
// Build capabilities from catalogs
const capabilities = useMemo(() => {
if (mergedCatalogs.length === 0)
return undefined;
return { catalogs: mergedCatalogs };
}, [mergedCatalogs]);
// Initialize transport
useEffect(() => {
const newTransport = createTransport({
gateway,
capabilities,
...transportOptions,
});
// Handle incoming messages
newTransport.on('message', (message) => {
if (isGetDataModelMessage(message)) {
const { surfaceId } = message.getDataModel;
const dataModel = surfaceManager.getDataModel(surfaceId);
newTransport.sendAction(surfaceId, '__get_data_model_response', '__system', { current_data_model: dataModel ?? {} });
return;
}
handleMessage(message, surfaceManager, agentDeletedRef.current);
});
// Notify agent when a surface is deleted client-side (e.g. disconnect cleanup)
const unsubSurfaceDeleted = surfaceManager.on('surfaceDeleted', (surfaceId) => {
if (agentDeletedRef.current.delete(surfaceId)) {
// Agent-initiated delete — don't echo back
return;
}
// Client-initiated delete — notify the agent
newTransport.sendAction(surfaceId, 'surface_deleted', '__system', { surfaceId, reason: 'client' });
});
// When a surface has no components after the orphan timeout,
// send a reminder action so the agent can decide to delete it.
const unsubOrphan = surfaceManager.on('surfaceOrphan', (surfaceId) => {
newTransport.sendAction(surfaceId, 'surface_cleanup_reminder', '__system', { surfaceId, message: `Surface ${String(surfaceId)} has no components. Delete it if no longer needed. Ignore this message if you plan to use the surface.` });
});
// When orphan components are detected, remind the agent to wire them up
const unsubOrphanComponents = surfaceManager.on('orphanComponents', (surfaceId, componentIds) => {
newTransport.sendAction(surfaceId, 'orphan_components_reminder', '__system', {
surfaceId,
componentIds,
message: `These components in surface '${String(surfaceId)}' are not reachable from root and won't render: ${componentIds.join(', ')}. Did you forget to wire them to a parent component? Please update the parent to include them, or ignore if this was intentional.`,
});
});
// Handle connection state changes
newTransport.on('stateChange', (state) => {
const connected = state === 'connected';
setIsConnected(connected);
if (state === 'disconnected') {
// Clear all surfaces when connection is lost
surfaceManager.clearSurfaces();
}
onConnectionChangeRef.current?.(connected);
});
// When session starts, register catalog schemas with the gateway
newTransport.on('sessionStart', (_sessionId) => {
const defs = catalogDefinitionsRef.current;
if (defs.length > 0) {
const schemas = defs
.map((def) => def.schema)
.filter((s) => s && Object.keys(s).length > 0);
if (schemas.length > 0) {
newTransport.registerCatalogs(schemas).then((ok) => {
if (ok) {
console.log('[Freesail] Catalogs registered with gateway');
}
});
}
}
});
// Handle errors
newTransport.on('error', (error) => {
console.error('[Freesail] Transport error:', error);
onErrorRef.current?.(error);
});
setTransport(newTransport);
// Auto-connect if enabled
if (autoConnectRef.current) {
newTransport.connect();
}
// Cleanup
return () => {
unsubSurfaceDeleted();
unsubOrphan();
unsubOrphanComponents();
newTransport.disconnect();
surfaceManager.dispose();
};
}, [gateway]); // Only recreate if gateway URL changes
// Send action callback (v0.9 format)
const sendAction = useCallback(async (surfaceId, name, sourceComponentId, context) => {
if (!transport) {
console.warn('[Freesail] Cannot send action: transport not initialized');
return;
}
// Send only the data model of the surface that triggered the action.
let dataModel;
if (surfaceManager.shouldSendDataModel(surfaceId)) {
const model = surfaceManager.getDataModel(surfaceId);
if (model && Object.keys(model).length > 0) {
// Filter out __-prefixed paths (client-only internal state)
const filtered = {};
for (const [key, value] of Object.entries(model)) {
if (!key.startsWith('__')) {
filtered[key] = value;
}
}
if (Object.keys(filtered).length > 0) {
dataModel = { surfaceId, dataModel: filtered };
}
}
}
await transport.sendAction(surfaceId, name, sourceComponentId, context, dataModel);
}, [transport, surfaceManager]);
// Get surface callback
const getSurface = useCallback((surfaceId) => surfaceManager.getSurface(surfaceId), [surfaceManager]);
// Context value
const contextValue = useMemo(() => ({
surfaceManager,
transport,
sendAction,
getSurface,
isConnected,
}), [surfaceManager, transport, sendAction, getSurface, isConnected]);
return (_jsx(FreesailContext.Provider, { value: contextValue, children: children }));
}
// =============================================================================
// Message Handler
// =============================================================================
function handleMessage(message, manager, agentDeleted) {
if (isCreateSurfaceMessage(message)) {
const { surfaceId, catalogId, sendDataModel } = message.createSurface;
manager.createSurface({ surfaceId, catalogId, sendDataModel });
}
else if (isUpdateComponentsMessage(message)) {
const { surfaceId, components } = message.updateComponents;
manager.updateComponents(surfaceId, components);
}
else if (isUpdateDataModelMessage(message)) {
const { surfaceId, path, value } = message.updateDataModel;
manager.updateDataModel(surfaceId, path, value);
}
else if (isDeleteSurfaceMessage(message)) {
const { surfaceId } = message.deleteSurface;
agentDeleted.add(surfaceId);
manager.deleteSurface(surfaceId);
}
}
//# sourceMappingURL=FreesailProvider.js.map
{"version":3,"file":"FreesailProvider.js","sourceRoot":"","sources":["../src/FreesailProvider.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n * @fileoverview FreesailProvider Component\n *\n * The root provider component that manages Freesail connections\n * and state for the React application.\n */\n\nimport React, {\n useState,\n useEffect,\n useCallback,\n useMemo,\n useRef,\n type ReactNode,\n} from 'react';\nimport {\n createSurfaceManager,\n createTransport,\n isCreateSurfaceMessage,\n isUpdateComponentsMessage,\n isUpdateDataModelMessage,\n isDeleteSurfaceMessage,\n isGetDataModelMessage,\n type SurfaceManager,\n type A2UITransport,\n type TransportOptions,\n type SurfaceId,\n type ComponentId,\n type CatalogId,\n type DownstreamMessage,\n type A2UIClientCapabilities,\n} from '@freesail/core';\nimport { FreesailContext, type FreesailContextValue } from './context.js';\nimport { registerCatalog, type FreesailComponent } from './registry.js';\nimport type { CatalogDefinition } from './types.js';\n\n/**\n * Props for FreesailProvider.\n */\nexport interface FreesailProviderProps {\n /** Child components */\n children: ReactNode;\n /** Base gateway URL (e.g. 'http://localhost:3001'). SSE and POST endpoints are derived automatically. */\n gateway: string;\n /** List of supported catalog IDs */\n catalogs?: CatalogId[];\n /**\n * Array of custom catalog definitions to register.\n * Each definition bundles a namespace, schema, and component map.\n * Components are auto-registered on mount.\n */\n catalogDefinitions?: CatalogDefinition[];\n /** Additional transport options */\n transportOptions?: Partial<Omit<TransportOptions, 'gateway' | 'capabilities'>>;\n /** Auto-connect on mount (default: true) */\n autoConnect?: boolean;\n /** Callback when connection state changes */\n onConnectionChange?: (connected: boolean) => void;\n /** Callback when an error occurs */\n onError?: (error: Error) => void;\n}\n\n/**\n * Root provider component for Freesail.\n *\n * Manages the transport connection and surface state,\n * making them available to all child components.\n */\nexport function FreesailProvider({\n children,\n gateway,\n catalogs = [],\n catalogDefinitions = [],\n transportOptions,\n autoConnect = true,\n onConnectionChange,\n onError,\n}: FreesailProviderProps) {\n const [surfaceManager] = useState<SurfaceManager>(() => createSurfaceManager());\n const [transport, setTransport] = useState<A2UITransport | null>(null);\n const [isConnected, setIsConnected] = useState(false);\n // Track surfaces deleted by agent messages so we don't echo them back\n const agentDeletedRef = useRef<Set<string>>(new Set());\n // Refs for callbacks so the transport effect always uses current values\n // without needing to be recreated when callbacks change\n const onConnectionChangeRef = useRef(onConnectionChange);\n const onErrorRef = useRef(onError);\n const catalogDefinitionsRef = useRef(catalogDefinitions);\n const autoConnectRef = useRef(autoConnect);\n useEffect(() => {\n onConnectionChangeRef.current = onConnectionChange;\n onErrorRef.current = onError;\n catalogDefinitionsRef.current = catalogDefinitions;\n autoConnectRef.current = autoConnect;\n });\n\n // Register custom catalog definitions\n useEffect(() => {\n for (const def of catalogDefinitions) {\n registerCatalog(\n def.namespace as CatalogId,\n def.components as Record<string, FreesailComponent>,\n def.functions,\n def.schema as Record<string, unknown> | undefined\n );\n }\n }, [catalogDefinitions]);\n\n // Merge explicit catalog IDs with catalog definition namespaces\n const mergedCatalogs = useMemo(() => {\n const definitionIds = catalogDefinitions.map((d) => d.namespace as CatalogId);\n const combined = [...catalogs, ...definitionIds];\n return Array.from(new Set(combined));\n }, [catalogs, catalogDefinitions]);\n\n // Build capabilities from catalogs\n const capabilities: A2UIClientCapabilities | undefined = useMemo(() => {\n if (mergedCatalogs.length === 0) return undefined;\n return { catalogs: mergedCatalogs };\n }, [mergedCatalogs]);\n\n // Initialize transport\n useEffect(() => {\n const newTransport = createTransport({\n gateway,\n capabilities,\n ...transportOptions,\n });\n\n // Handle incoming messages\n newTransport.on('message', (message: DownstreamMessage) => {\n if (isGetDataModelMessage(message)) {\n const { surfaceId } = message.getDataModel;\n const dataModel = surfaceManager.getDataModel(surfaceId);\n newTransport.sendAction(\n surfaceId,\n '__get_data_model_response',\n '__system' as ComponentId,\n { current_data_model: dataModel ?? {} }\n );\n return;\n }\n handleMessage(message, surfaceManager, agentDeletedRef.current);\n });\n\n // Notify agent when a surface is deleted client-side (e.g. disconnect cleanup)\n const unsubSurfaceDeleted = surfaceManager.on('surfaceDeleted', (surfaceId: SurfaceId) => {\n if (agentDeletedRef.current.delete(surfaceId as string)) {\n // Agent-initiated delete — don't echo back\n return;\n }\n // Client-initiated delete — notify the agent\n newTransport.sendAction(\n surfaceId,\n 'surface_deleted',\n '__system' as ComponentId,\n { surfaceId, reason: 'client' }\n );\n });\n\n // When a surface has no components after the orphan timeout,\n // send a reminder action so the agent can decide to delete it.\n const unsubOrphan = surfaceManager.on('surfaceOrphan', (surfaceId: SurfaceId) => {\n newTransport.sendAction(\n surfaceId,\n 'surface_cleanup_reminder',\n '__system' as ComponentId,\n { surfaceId, message: `Surface ${String(surfaceId)} has no components. Delete it if no longer needed. Ignore this message if you plan to use the surface.` }\n );\n });\n\n // When orphan components are detected, remind the agent to wire them up\n const unsubOrphanComponents = surfaceManager.on('orphanComponents', (surfaceId: SurfaceId, componentIds: ComponentId[]) => {\n newTransport.sendAction(\n surfaceId,\n 'orphan_components_reminder',\n '__system' as ComponentId,\n {\n surfaceId,\n componentIds,\n message: `These components in surface '${String(surfaceId)}' are not reachable from root and won't render: ${componentIds.join(', ')}. Did you forget to wire them to a parent component? Please update the parent to include them, or ignore if this was intentional.`,\n }\n );\n });\n\n // Handle connection state changes\n newTransport.on('stateChange', (state: string) => {\n const connected = state === 'connected';\n setIsConnected(connected);\n\n if (state === 'disconnected') {\n // Clear all surfaces when connection is lost\n surfaceManager.clearSurfaces();\n }\n\n onConnectionChangeRef.current?.(connected);\n });\n\n // When session starts, register catalog schemas with the gateway\n newTransport.on('sessionStart', (_sessionId: string) => {\n const defs = catalogDefinitionsRef.current;\n if (defs.length > 0) {\n const schemas = defs\n .map((def) => def.schema)\n .filter((s) => s && Object.keys(s).length > 0);\n\n if (schemas.length > 0) {\n newTransport.registerCatalogs(schemas).then((ok: boolean) => {\n if (ok) {\n console.log('[Freesail] Catalogs registered with gateway');\n }\n });\n }\n }\n });\n\n // Handle errors\n newTransport.on('error', (error: Error) => {\n console.error('[Freesail] Transport error:', error);\n onErrorRef.current?.(error);\n });\n\n setTransport(newTransport);\n\n // Auto-connect if enabled\n if (autoConnectRef.current) {\n newTransport.connect();\n }\n\n // Cleanup\n return () => {\n unsubSurfaceDeleted();\n unsubOrphan();\n unsubOrphanComponents();\n newTransport.disconnect();\n surfaceManager.dispose();\n };\n }, [gateway]); // Only recreate if gateway URL changes\n\n // Send action callback (v0.9 format)\n const sendAction = useCallback(\n async (\n surfaceId: SurfaceId,\n name: string,\n sourceComponentId: ComponentId,\n context: Record<string, unknown>\n ) => {\n if (!transport) {\n console.warn('[Freesail] Cannot send action: transport not initialized');\n return;\n }\n\n // Send only the data model of the surface that triggered the action.\n let dataModel: { surfaceId: SurfaceId; dataModel: Record<string, unknown> } | undefined;\n if (surfaceManager.shouldSendDataModel(surfaceId)) {\n const model = surfaceManager.getDataModel(surfaceId);\n if (model && Object.keys(model).length > 0) {\n // Filter out __-prefixed paths (client-only internal state)\n const filtered: Record<string, unknown> = {};\n for (const [key, value] of Object.entries(model)) {\n if (!key.startsWith('__')) {\n filtered[key] = value;\n }\n }\n if (Object.keys(filtered).length > 0) {\n dataModel = { surfaceId, dataModel: filtered };\n }\n }\n }\n\n await transport.sendAction(surfaceId, name, sourceComponentId, context, dataModel);\n },\n [transport, surfaceManager]\n );\n\n // Get surface callback\n const getSurface = useCallback(\n (surfaceId: SurfaceId) => surfaceManager.getSurface(surfaceId),\n [surfaceManager]\n );\n\n // Context value\n const contextValue: FreesailContextValue = useMemo(\n () => ({\n surfaceManager,\n transport,\n sendAction,\n getSurface,\n isConnected,\n }),\n [surfaceManager, transport, sendAction, getSurface, isConnected]\n );\n\n return (\n <FreesailContext.Provider value={contextValue}>\n {children}\n </FreesailContext.Provider>\n );\n}\n\n// =============================================================================\n// Message Handler\n// =============================================================================\n\nfunction handleMessage(message: DownstreamMessage, manager: SurfaceManager, agentDeleted: Set<string>): void {\n if (isCreateSurfaceMessage(message)) {\n const { surfaceId, catalogId, sendDataModel } = message.createSurface;\n manager.createSurface({ surfaceId, catalogId, sendDataModel });\n } else if (isUpdateComponentsMessage(message)) {\n const { surfaceId, components } = message.updateComponents;\n manager.updateComponents(surfaceId, components);\n } else if (isUpdateDataModelMessage(message)) {\n const { surfaceId, path, value } = message.updateDataModel;\n manager.updateDataModel(surfaceId, path, value);\n } else if (isDeleteSurfaceMessage(message)) {\n const { surfaceId } = message.deleteSurface;\n agentDeleted.add(surfaceId as string);\n manager.deleteSurface(surfaceId);\n }\n}\n"]}
/**
* @fileoverview FreesailSurface Component
*
* The main container component that renders a single A2UI surface.
* Users drop this into their app to display agent-driven UI.
*/
import { type ReactNode } from 'react';
import type { SurfaceId } from '@freesail/core';
/**
* Props for FreesailSurface.
*/
export interface FreesailSurfaceProps {
/** The surface ID to render */
surfaceId: SurfaceId;
/** Optional className for the container */
className?: string;
/** Loading state component */
loading?: ReactNode;
/** Error state component */
error?: ReactNode;
/** Empty state component (when surface exists but has no components) */
empty?: ReactNode;
}
/**
* Renders a single A2UI surface.
*
* This component subscribes to surface updates and automatically
* re-renders when the component tree or data model changes.
*/
export declare function FreesailSurface({ surfaceId, className, loading, error, empty, }: FreesailSurfaceProps): import("react/jsx-runtime").JSX.Element;
//# sourceMappingURL=FreesailSurface.d.ts.map
{"version":3,"file":"FreesailSurface.d.ts","sourceRoot":"","sources":["../src/FreesailSurface.tsx"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAc,EAAwB,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAMpE,OAAO,KAAK,EACV,SAAS,EAMV,MAAM,gBAAgB,CAAC;AAOxB;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,+BAA+B;IAC/B,SAAS,EAAE,SAAS,CAAC;IACrB,2CAA2C;IAC3C,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,8BAA8B;IAC9B,OAAO,CAAC,EAAE,SAAS,CAAC;IACpB,4BAA4B;IAC5B,KAAK,CAAC,EAAE,SAAS,CAAC;IAClB,wEAAwE;IACxE,KAAK,CAAC,EAAE,SAAS,CAAC;CACnB;AAgBD;;;;;GAKG;AACH,wBAAgB,eAAe,CAAC,EAC9B,SAAS,EACT,SAAS,EACT,OAA4B,EAC5B,KAAwB,EACxB,KAA0B,GAC3B,EAAE,oBAAoB,2CAqDtB"}
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
/**
* @fileoverview FreesailSurface Component
*
* The main container component that renders a single A2UI surface.
* Users drop this into their app to display agent-driven UI.
*/
import { useMemo, useCallback } from 'react';
import { FREESAIL_LOGO_DATA_URI } from './logo.js';
import { isFunctionCall, } from '@freesail/core';
import { useSurface, useAction } from './hooks.js';
import { registry } from './registry.js';
import { useFreesailContext } from './context.js';
import { getDataAtPath } from './utils.js';
/**
* Renders a single A2UI surface.
*
* This component subscribes to surface updates and automatically
* re-renders when the component tree or data model changes.
*/
export function FreesailSurface({ surfaceId, className, loading = _jsx(DefaultLoading, {}), error = _jsx(DefaultError, {}), empty = _jsx(DefaultLoading, {}), }) {
const surface = useSurface(surfaceId);
const dispatch = useAction(surfaceId);
const { surfaceManager } = useFreesailContext();
// Two-way binding: input components write to the local data model.
// This is local only — no network request. The updated data model
// reaches the server via resolved data bindings in action context
// or via the sendDataModel metadata mechanism.
const onDataChange = useCallback((path, value) => {
console.log(`[Freesail] onDataChange: surface=${surfaceId} path=${path} value=`, value);
surfaceManager.updateDataModel(surfaceId, path, value);
}, [surfaceManager, surfaceId]);
// Build the component tree
const renderedTree = useMemo(() => {
if (!surface)
return null;
if (surface.components.size === 0)
return null;
if (!surface.rootId)
return null;
return renderComponent(surface.rootId, surface.components, surface.catalogId, surface.dataModel, dispatch, onDataChange, undefined, undefined, undefined);
}, [surface, dispatch, onDataChange]);
// Loading state - surface doesn't exist yet
if (!surface) {
return _jsx("div", { className: className, style: { flex: 1, minHeight: 0 }, children: loading });
}
// Empty state - surface exists but no components
if (surface.components.size === 0 || !surface.rootId) {
return _jsx("div", { className: className, style: { flex: 1, minHeight: 0 }, children: empty });
}
// Check if catalog is registered
if (!registry.hasCatalog(surface.catalogId)) {
console.error(`[Freesail] Catalog not registered: ${surface.catalogId}`);
return _jsx("div", { className: className, style: { flex: 1, minHeight: 0 }, children: error });
}
return _jsx("div", { className: className, "data-freesail-surface": surfaceId, style: { flex: 1, minHeight: 0, display: 'flex', flexDirection: 'column' }, children: renderedTree });
}
// =============================================================================
// Component Renderer
// =============================================================================
function renderComponent(componentId, components, catalogId, dataModel, dispatch, onDataChange, scopeData, keyOverride, scopeBasePath) {
const componentDef = components.get(componentId);
if (!componentDef) {
// Component may arrive in a subsequent update_components batch — render nothing for now
return null;
}
// Get the React component from registry
const Component = registry.getComponent(catalogId, componentDef.component);
if (!Component) {
return _jsx(UnknownComponent, { component: componentDef });
}
// Render children recursively
let children = null;
// 1. Handle single child (for Card, etc.)
if (componentDef.child) {
children = renderComponent(componentDef.child, components, catalogId, dataModel, dispatch, onDataChange, scopeData, undefined, scopeBasePath);
}
// 2. Handle multiple standard children (Column, Row, List, etc.)
else if (componentDef.children) {
const childList = componentDef.children;
if (Array.isArray(childList)) {
// Static array of child IDs
children = childList.map((childId) => renderComponent(childId, components, catalogId, dataModel, dispatch, onDataChange, scopeData, undefined, scopeBasePath));
}
else if (typeof childList === 'object' && 'componentId' in childList) {
// Template for dynamic children
const template = childList;
const listData = getDataAtPath(dataModel, template.path);
if (Array.isArray(listData)) {
children = listData.map((itemData, index) => {
// Build the absolute path for this item in the data model
const itemBasePath = `${template.path}/${index}`;
return renderComponent(template.componentId, components, catalogId, dataModel, dispatch, onDataChange, itemData, // Pass item data as scope
`${template.componentId}_${itemData?.id ?? index}`, // Unique key per item
itemBasePath // Absolute path for two-way binding
);
});
}
}
}
// Resolve data bindings in component properties
const resolvedProps = resolveDataBindings(componentDef, dataModel, catalogId, scopeData, scopeBasePath);
// Visibility check: if `visible` resolves to exactly false, skip rendering.
// Data-model override (from show/hide) takes precedence over component prop.
const visibilityOverride = getDataAtPath(dataModel, `/__componentState/${componentId}/visible`);
const effectiveVisible = visibilityOverride != null ? visibilityOverride : resolvedProps['visible'];
if (effectiveVisible === false || effectiveVisible === 'false') {
return null;
}
// Build props
const props = {
component: { ...componentDef, ...resolvedProps },
children,
dataModel,
scopeData,
onAction: (name, context) => {
// Resolve data bindings in action context at dispatch time.
const resolvedContext = resolveActionContext(context, dataModel, catalogId, scopeData);
return dispatch(name, componentDef.id, resolvedContext);
},
onDataChange,
onFunctionCall: (call) => {
const result = evaluateFunction(call, dataModel, catalogId, scopeData);
// Handle side-effect returns (e.g. show/hide writes to data model)
if (result && typeof result === 'object' && '__sideEffect' in result) {
const sideEffect = result;
if (sideEffect.__sideEffect === 'dataModelUpdate') {
onDataChange(sideEffect.path, sideEffect.value);
}
}
},
};
try {
const rendered = _jsx(Component, { ...props }, keyOverride ?? componentId);
// Apply weight as flex when the component has a weight property.
// Uses a data attribute so parent layouts (e.g. GridLayout) can override
// with display:contents if needed.
const weight = componentDef['weight'];
if (weight != null) {
return _jsx("div", { "data-freesail-weight": true, style: { flex: `${weight} 1 auto`, minWidth: 0, minHeight: 0, display: 'flex', flexDirection: 'column', alignSelf: 'stretch' }, children: rendered }, keyOverride ?? componentId);
}
return rendered;
}
catch (err) {
console.error(`[Freesail] Component render error (${componentDef.component}):`, err);
return _jsx(UnknownComponent, { component: componentDef });
}
}
/**
* Resolve data bindings in component properties.
*/
function resolveDataBindings(component, dataModel, catalogId, scopeData, scopeBasePath, _depth = 0) {
if (_depth > 10)
return {};
const resolved = {};
for (const [key, value] of Object.entries(component)) {
if (key === 'id' || key === 'component' || key === 'children' || key === 'child') {
continue;
}
// Robustness: Handle double-encoded bindings
let effectiveValue = value;
if (typeof value === 'string' && value.trim().startsWith('{') && value.includes('"path"')) {
try {
const parsed = JSON.parse(value);
if (isDataBindingObject(parsed)) {
effectiveValue = parsed;
}
}
catch {
// Ignore parse errors
}
}
if (isFunctionCall(effectiveValue)) {
// Don't eagerly evaluate function calls inside `action` — they are
// deferred and executed by the component on user interaction (e.g. Button click).
if (key === 'action') {
resolved[key] = effectiveValue;
}
else {
resolved[key] = evaluateFunction(effectiveValue, dataModel, catalogId, scopeData);
}
}
else if (isDataBindingObject(effectiveValue)) {
// Preserve the raw binding so components can find the path for two-way binding.
// If inside a scoped template, convert relative paths to absolute paths
// so onDataChange writes to the correct location in the data model.
const rawBinding = { ...effectiveValue };
if (scopeBasePath && !rawBinding.path.startsWith('/')) {
rawBinding.path = `${scopeBasePath}/${rawBinding.path}`;
}
resolved[`__raw${key.charAt(0).toUpperCase()}${key.slice(1)}`] = rawBinding;
// Resolve data binding
resolved[key] = resolveSingleBinding(effectiveValue, dataModel, scopeData);
}
else if (typeof value === 'object' && value !== null) {
// Prevent recursion into LocalAction definitions (which contain FunctionCalls that should NOT be evaluated yet)
if ('functionCall' in value && isFunctionCall(value.functionCall)) {
resolved[key] = value;
continue;
}
// Recursively resolve bindings inside objects and arrays
if (Array.isArray(value)) {
resolved[key] = value.map(item => {
if (typeof item === 'object' && item !== null) {
// Check for LocalAction in array items too
if ('functionCall' in item && isFunctionCall(item.functionCall)) {
return item;
}
if (isFunctionCall(item)) {
return evaluateFunction(item, dataModel, catalogId, scopeData);
}
if (isDataBindingObject(item)) {
return resolveSingleBinding(item, dataModel, scopeData);
}
return resolveDataBindings(item, dataModel, catalogId, scopeData, undefined, _depth + 1);
}
return item;
});
}
else {
resolved[key] = resolveDataBindings(value, dataModel, catalogId, scopeData, undefined, _depth + 1);
}
}
else {
resolved[key] = value;
}
}
return resolved;
}
/**
* Helper to resolve a single binding object, following chains.
*/
function resolveSingleBinding(binding, dataModel, scopeData) {
const path = binding.path;
let resolvedValue;
// "." or "" means "the current scoped item" — used when iterating scalar arrays
if (path === '.' || path === '') {
return scopeData !== undefined ? scopeData : getDataAtPath(dataModel, '/');
}
if (path.startsWith('/')) {
resolvedValue = getDataAtPath(dataModel, path);
}
else if (scopeData !== undefined) {
resolvedValue = getDataAtPath(scopeData, '/' + path);
}
else {
resolvedValue = getDataAtPath(dataModel, '/' + path);
}
// Chained bindings (max depth 5)
let depth = 0;
while (isDataBindingObject(resolvedValue) && depth < 5) {
const chainedPath = resolvedValue.path;
resolvedValue = chainedPath.startsWith('/')
? getDataAtPath(dataModel, chainedPath)
: getDataAtPath(dataModel, '/' + chainedPath);
depth++;
}
return resolvedValue;
}
function isDataBindingObject(value) {
if (typeof value !== 'object' || value === null || !('path' in value))
return false;
if (typeof value['path'] !== 'string')
return false;
if ('componentId' in value)
return false; // ChildListTemplate
if ('event' in value)
return false; // ServerAction
if ('call' in value)
return false; // FunctionCall
return true;
}
/**
* Evaluate a function call.
*/
function evaluateFunction(call, dataModel, catalogId, scopeData) {
const functionName = call.call;
const funcImpl = registry.getFunction(catalogId, functionName);
if (!funcImpl) {
console.warn(`[Freesail] Function not found: ${functionName} in catalog ${catalogId}`);
return undefined;
}
// Resolve arguments
let rawArgs = [];
if (Array.isArray(call.args)) {
rawArgs = call.args;
}
else if (call.args && typeof call.args === 'object') {
const entries = Object.entries(call.args);
// Check if the registry declares paramNames for this function
// and the keys are named (not numeric).
// If so, reorder entries to match the declared parameter order.
const paramNames = registry.getParamNames(catalogId, functionName);
const hasNonNumericKeys = entries.some(([key]) => isNaN(parseInt(key.replace(/^'|'$/g, ''), 10)));
if (paramNames && hasNonNumericKeys) {
// Build a lookup from the entries
const argMap = new Map(entries);
// Reorder: first pull args matching declared param names in order,
// then append any extra keys not in paramNames
const ordered = [];
const used = new Set();
for (const name of paramNames) {
if (argMap.has(name)) {
ordered.push(argMap.get(name));
used.add(name);
}
}
// Append remaining keys not in paramNames (preserves insertion order)
for (const [key, value] of entries) {
if (!used.has(key)) {
ordered.push(value);
}
}
rawArgs = ordered;
}
else {
// Numeric keys or no paramNames — sort numerically as before
entries.sort(([keyA], [keyB]) => {
// Remove surrounding quotes if present to cleanly parse as number
const numA = parseInt(keyA.replace(/^'|'$/g, ''), 10);
const numB = parseInt(keyB.replace(/^'|'$/g, ''), 10);
if (!isNaN(numA) && !isNaN(numB)) {
return numA - numB;
}
return 0; // fallback to stable sort for non-numeric keys
});
rawArgs = entries.map(([, value]) => value);
}
// Robustness: agents sometimes wrap multiple positional args in a single-key
// object as an array, e.g. { "value": [arg0, arg1] } instead of [arg0, arg1].
// When there is exactly one entry and its value is an array, spread it so that
// multi-arg functions like lte(a, b) receive two arguments, not one array.
if (rawArgs.length === 1 && Array.isArray(rawArgs[0])) {
rawArgs = rawArgs[0];
}
}
const args = rawArgs.map(arg => {
if (isFunctionCall(arg)) {
return evaluateFunction(arg, dataModel, catalogId, scopeData);
}
if (isDataBindingObject(arg)) {
return resolveSingleBinding(arg, dataModel, scopeData);
}
// Handle nested arrays/objects in args
if (typeof arg === 'object' && arg !== null) {
if (Array.isArray(arg)) {
return arg.map(item => {
if (isFunctionCall(item))
return evaluateFunction(item, dataModel, catalogId, scopeData);
if (isDataBindingObject(item))
return resolveSingleBinding(item, dataModel, scopeData);
return item;
});
}
}
return arg;
});
// formatString: pre-process the format string for ${...} template interpolation
let callArgs = args;
if (functionName === 'formatString' && callArgs.length > 0 && typeof callArgs[0] === 'string') {
callArgs = [
interpolateTemplate(callArgs[0], dataModel, catalogId, scopeData, (nestedCall) => evaluateFunction(nestedCall, dataModel, catalogId, scopeData)),
...callArgs.slice(1),
];
}
try {
return funcImpl(...callArgs);
}
catch (error) {
console.error(`[Freesail] Error evaluating function ${functionName}:`, error);
return undefined;
}
}
/**
* Resolve data bindings in an action's context object.
*/
function resolveActionContext(context, dataModel, catalogId, scopeData) {
const resolved = {};
for (const [key, value] of Object.entries(context)) {
if (isFunctionCall(value)) {
resolved[key] = evaluateFunction(value, dataModel, catalogId, scopeData);
}
else if (isDataBindingObject(value)) {
const path = value.path;
if (path.startsWith('/')) {
resolved[key] = getDataAtPath(dataModel, path);
}
else if (scopeData !== undefined) {
resolved[key] = getDataAtPath(scopeData, '/' + path);
}
else {
// Relative path but no scope — normalize to absolute
resolved[key] = getDataAtPath(dataModel, '/' + path);
}
}
else {
resolved[key] = value;
}
}
return resolved;
}
// =============================================================================
// Template Interpolation (for formatString ${...} syntax)
// =============================================================================
/**
* Finds the position of the closing brace that matches the opening brace at openPos,
* respecting nested braces and quoted strings.
*/
function findMatchingBrace(str, openPos) {
let depth = 0;
let inSingleQuote = false;
let inDoubleQuote = false;
for (let i = openPos; i < str.length; i++) {
const ch = str[i];
const escaped = i > 0 && str[i - 1] === '\\';
if (ch === "'" && !inDoubleQuote && !escaped)
inSingleQuote = !inSingleQuote;
if (ch === '"' && !inSingleQuote && !escaped)
inDoubleQuote = !inDoubleQuote;
if (!inSingleQuote && !inDoubleQuote) {
if (ch === '{')
depth++;
else if (ch === '}') {
depth--;
if (depth === 0)
return i;
}
}
}
return -1;
}
/** Converts a value to a display string for interpolation output. */
function interpolatedValueToString(value) {
if (value === null || value === undefined)
return '';
if (typeof value === 'object')
return JSON.stringify(value);
return String(value);
}
/**
* Splits a comma-separated args string into individual tokens,
* respecting nested ${...} and quoted strings.
*/
function splitInterpolationArgs(argsStr) {
const parts = [];
let current = '';
let depth = 0;
let inSingleQuote = false;
let inDoubleQuote = false;
for (let i = 0; i < argsStr.length; i++) {
const ch = argsStr[i];
const escaped = i > 0 && argsStr[i - 1] === '\\';
if (ch === "'" && !inDoubleQuote && !escaped)
inSingleQuote = !inSingleQuote;
else if (ch === '"' && !inSingleQuote && !escaped)
inDoubleQuote = !inDoubleQuote;
else if (!inSingleQuote && !inDoubleQuote) {
if (ch === '{')
depth++;
else if (ch === '}')
depth--;
else if (ch === ',' && depth === 0) {
parts.push(current.trim());
current = '';
continue;
}
}
current += ch;
}
if (current.trim())
parts.push(current.trim());
return parts;
}
/**
* Parses a single argument token from an interpolation expression.
* Supports: 'string', "string", number, boolean, ${nested}, bare path.
*/
function parseInterpolationValue(token, dataModel, catalogId, scopeData, evalFn) {
token = token.trim();
if ((token.startsWith("'") && token.endsWith("'")) || (token.startsWith('"') && token.endsWith('"')))
return token.slice(1, -1);
if (token.startsWith('${') && token.endsWith('}'))
return evaluateInterpolationExpr(token.slice(2, -1), dataModel, catalogId, scopeData, evalFn);
if (token === 'true')
return true;
if (token === 'false')
return false;
const num = Number(token);
if (!isNaN(num) && token !== '')
return num;
if (token.startsWith('/'))
return getDataAtPath(dataModel, token);
if (scopeData !== undefined)
return getDataAtPath(scopeData, '/' + token);
return getDataAtPath(dataModel, '/' + token);
}
/**
* Evaluates the expression inside ${...}: either a data path or a function call.
*/
function evaluateInterpolationExpr(expr, dataModel, catalogId, scopeData, evalFn) {
expr = expr.trim();
// Function call: word(...)
if (/^\w[\w.]*\(.*\)$/s.test(expr)) {
const parenOpen = expr.indexOf('(');
const funcName = expr.slice(0, parenOpen).trim();
const argsStr = expr.slice(parenOpen + 1, -1).trim();
const args = {};
if (argsStr) {
splitInterpolationArgs(argsStr).forEach((part, index) => {
const colonIdx = part.indexOf(':');
if (colonIdx > 0) {
const potentialKey = part.slice(0, colonIdx).trim();
if (/^[a-zA-Z_]\w*$/.test(potentialKey)) {
args[potentialKey] = parseInterpolationValue(part.slice(colonIdx + 1).trim(), dataModel, catalogId, scopeData, evalFn);
return;
}
}
args[String(index)] = parseInterpolationValue(part, dataModel, catalogId, scopeData, evalFn);
});
}
return evalFn({ call: funcName, args });
}
// Data path
if (expr.startsWith('/'))
return getDataAtPath(dataModel, expr);
if (scopeData !== undefined)
return getDataAtPath(scopeData, '/' + expr);
return getDataAtPath(dataModel, '/' + expr);
}
/**
* Processes ${...} template expressions in a formatString format string.
* Supports: ${/absolute/path}, ${relative/field}, ${funcName(args)},
* nested expressions (${upper(${/name})}), and escaped literals (\${).
*/
function interpolateTemplate(template, dataModel, catalogId, scopeData, evalFn) {
let result = '';
let i = 0;
while (i < template.length) {
// Escaped: \${ → literal ${
if (template[i] === '\\' && template[i + 1] === '$' && template[i + 2] === '{') {
result += '${';
i += 3;
continue;
}
// Expression: ${...}
if (template[i] === '$' && template[i + 1] === '{') {
const closeBrace = findMatchingBrace(template, i + 1);
if (closeBrace === -1) {
result += template[i++];
continue;
}
const expr = template.slice(i + 2, closeBrace);
result += interpolatedValueToString(evaluateInterpolationExpr(expr, dataModel, catalogId, scopeData, evalFn));
i = closeBrace + 1;
continue;
}
result += template[i++];
}
return result;
}
// =============================================================================
// Default UI States
// =============================================================================
function DefaultLoading() {
return (_jsxs("div", { style: {
display: 'flex',
flexDirection: 'column',
alignItems: 'center',
justifyContent: 'center',
padding: '40px 16px',
gap: '16px',
}, children: [_jsx("style", { children: `
@keyframes freesail-pulse {
0%, 100% { opacity: 0.4; transform: scale(0.95); }
50% { opacity: 1; transform: scale(1); }
}
@keyframes freesail-spin {
0% { transform: rotate(0deg); }
100% { transform: rotate(360deg); }
}
` }), FREESAIL_LOGO_DATA_URI ? (_jsx("img", { src: FREESAIL_LOGO_DATA_URI, alt: "Loading", style: {
width: '48px',
height: '48px',
animation: 'freesail-pulse 1.5s ease-in-out infinite',
} })) : (_jsx("div", { style: {
width: '32px',
height: '32px',
border: '3px solid var(--freesail-border, #e2e8f0)',
borderTopColor: 'var(--freesail-primary, #2563eb)',
borderRadius: '50%',
animation: 'freesail-spin 0.8s linear infinite',
} })), _jsx("span", { style: {
fontSize: '13px',
color: 'var(--freesail-text-muted, #64748b)',
letterSpacing: '0.05em',
}, children: "Preparing\u2026" })] }));
}
function DefaultError() {
return (_jsx("div", { style: { padding: '16px', color: '#c00' }, children: "Error: Unable to render surface" }));
}
function UnknownComponent({ component }) {
return (_jsxs("div", { style: {
padding: '8px',
border: '1px dashed #f00',
background: '#fee',
margin: '4px',
}, children: [_jsx("strong", { children: "Unknown Component:" }), " ", component.component, _jsx("pre", { style: { fontSize: '10px' }, children: JSON.stringify(component, null, 2) })] }));
}
//# sourceMappingURL=FreesailSurface.js.map
{"version":3,"file":"FreesailSurface.js","sourceRoot":"","sources":["../src/FreesailSurface.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n * @fileoverview FreesailSurface Component\n *\n * The main container component that renders a single A2UI surface.\n * Users drop this into their app to display agent-driven UI.\n */\n\nimport React, { useMemo, useCallback, type ReactNode } from 'react';\nimport { FREESAIL_LOGO_DATA_URI } from './logo.js';\nimport {\n isChildListTemplate,\n isFunctionCall,\n} from '@freesail/core';\nimport type {\n SurfaceId,\n CatalogId,\n A2UIComponent,\n ComponentId,\n ChildList,\n FunctionCall,\n} from '@freesail/core';\nimport { useSurface, useAction } from './hooks.js';\nimport { registry, type FreesailComponentProps } from './registry.js';\nimport { useFreesailContext } from './context.js';\nimport { getDataAtPath } from './utils.js';\nimport type { FunctionImplementation } from './types.js';\n\n/**\n * Props for FreesailSurface.\n */\nexport interface FreesailSurfaceProps {\n /** The surface ID to render */\n surfaceId: SurfaceId;\n /** Optional className for the container */\n className?: string;\n /** Loading state component */\n loading?: ReactNode;\n /** Error state component */\n error?: ReactNode;\n /** Empty state component (when surface exists but has no components) */\n empty?: ReactNode;\n}\n\n/**\n * Dispatch function type for actions.\n */\ntype ActionDispatch = (\n name: string,\n sourceComponentId: ComponentId,\n context: Record<string, unknown>\n) => Promise<void>;\n\n/**\n * Callback for two-way binding: components write values to the local data model.\n */\ntype DataChangeDispatch = (path: string, value: unknown) => void;\n\n/**\n * Renders a single A2UI surface.\n *\n * This component subscribes to surface updates and automatically\n * re-renders when the component tree or data model changes.\n */\nexport function FreesailSurface({\n surfaceId,\n className,\n loading = <DefaultLoading />,\n error = <DefaultError />,\n empty = <DefaultLoading />,\n}: FreesailSurfaceProps) {\n const surface = useSurface(surfaceId);\n const dispatch = useAction(surfaceId);\n const { surfaceManager } = useFreesailContext();\n\n // Two-way binding: input components write to the local data model.\n // This is local only — no network request. The updated data model\n // reaches the server via resolved data bindings in action context\n // or via the sendDataModel metadata mechanism.\n const onDataChange: DataChangeDispatch = useCallback(\n (path: string, value: unknown) => {\n console.log(`[Freesail] onDataChange: surface=${surfaceId} path=${path} value=`, value);\n surfaceManager.updateDataModel(surfaceId, path, value);\n },\n [surfaceManager, surfaceId]\n );\n\n // Build the component tree\n const renderedTree = useMemo(() => {\n if (!surface) return null;\n if (surface.components.size === 0) return null;\n if (!surface.rootId) return null;\n\n return renderComponent(\n surface.rootId,\n surface.components,\n surface.catalogId,\n surface.dataModel,\n dispatch,\n onDataChange,\n undefined,\n undefined,\n undefined\n );\n }, [surface, dispatch, onDataChange]);\n\n // Loading state - surface doesn't exist yet\n if (!surface) {\n return <div className={className} style={{ flex: 1, minHeight: 0 }}>{loading}</div>;\n }\n\n // Empty state - surface exists but no components\n if (surface.components.size === 0 || !surface.rootId) {\n return <div className={className} style={{ flex: 1, minHeight: 0 }}>{empty}</div>;\n }\n\n // Check if catalog is registered\n if (!registry.hasCatalog(surface.catalogId)) {\n console.error(`[Freesail] Catalog not registered: ${surface.catalogId}`);\n return <div className={className} style={{ flex: 1, minHeight: 0 }}>{error}</div>;\n }\n\n return <div className={className} data-freesail-surface={surfaceId} style={{ flex: 1, minHeight: 0, display: 'flex', flexDirection: 'column' }}>{renderedTree}</div>;\n}\n\n// =============================================================================\n// Component Renderer\n// =============================================================================\n\nfunction renderComponent(\n componentId: ComponentId,\n components: Map<ComponentId, A2UIComponent>,\n catalogId: string,\n dataModel: Record<string, unknown>,\n dispatch: ActionDispatch,\n onDataChange: DataChangeDispatch,\n scopeData?: unknown,\n keyOverride?: string,\n scopeBasePath?: string\n): ReactNode {\n const componentDef = components.get(componentId);\n if (!componentDef) {\n // Component may arrive in a subsequent update_components batch — render nothing for now\n return null;\n }\n\n // Get the React component from registry\n const Component = registry.getComponent(catalogId, componentDef.component);\n if (!Component) {\n return <UnknownComponent component={componentDef} />;\n }\n\n // Render children recursively\n let children: ReactNode = null;\n\n // 1. Handle single child (for Card, etc.)\n if (componentDef.child) {\n children = renderComponent(\n componentDef.child,\n components,\n catalogId,\n dataModel,\n dispatch,\n onDataChange,\n scopeData,\n undefined,\n scopeBasePath\n );\n }\n // 2. Handle multiple standard children (Column, Row, List, etc.)\n else if (componentDef.children) {\n const childList = componentDef.children as ChildList;\n\n if (Array.isArray(childList)) {\n // Static array of child IDs\n children = childList.map((childId) =>\n renderComponent(childId, components, catalogId, dataModel, dispatch, onDataChange, scopeData, undefined, scopeBasePath)\n );\n } else if (typeof childList === 'object' && 'componentId' in childList) {\n // Template for dynamic children\n const template = childList;\n const listData = getDataAtPath(dataModel, template.path);\n\n if (Array.isArray(listData)) {\n children = listData.map((itemData, index) => {\n // Build the absolute path for this item in the data model\n const itemBasePath = `${template.path}/${index}`;\n return renderComponent(\n template.componentId,\n components,\n catalogId,\n dataModel,\n dispatch,\n onDataChange,\n itemData, // Pass item data as scope\n `${template.componentId}_${(itemData as any)?.id ?? index}`, // Unique key per item\n itemBasePath // Absolute path for two-way binding\n );\n });\n }\n }\n }\n\n // Resolve data bindings in component properties\n const resolvedProps = resolveDataBindings(componentDef, dataModel, catalogId, scopeData, scopeBasePath);\n\n // Visibility check: if `visible` resolves to exactly false, skip rendering.\n // Data-model override (from show/hide) takes precedence over component prop.\n const visibilityOverride = getDataAtPath(dataModel, `/__componentState/${componentId}/visible`);\n const effectiveVisible = visibilityOverride != null ? visibilityOverride : resolvedProps['visible'];\n if (effectiveVisible === false || effectiveVisible === 'false') {\n return null;\n }\n\n // Build props\n const props: FreesailComponentProps = {\n component: { ...componentDef, ...resolvedProps },\n children,\n dataModel,\n scopeData,\n onAction: (name, context) => {\n // Resolve data bindings in action context at dispatch time.\n const resolvedContext = resolveActionContext(context, dataModel, catalogId, scopeData);\n return dispatch(name, componentDef.id, resolvedContext);\n },\n onDataChange,\n onFunctionCall: (call) => {\n const result = evaluateFunction(call, dataModel, catalogId, scopeData);\n // Handle side-effect returns (e.g. show/hide writes to data model)\n if (result && typeof result === 'object' && '__sideEffect' in (result as Record<string, unknown>)) {\n const sideEffect = result as { __sideEffect: string; path: string; value: unknown };\n if (sideEffect.__sideEffect === 'dataModelUpdate') {\n onDataChange(sideEffect.path, sideEffect.value);\n }\n }\n },\n };\n\n try {\n const rendered = <Component key={keyOverride ?? componentId} {...props} />;\n // Apply weight as flex when the component has a weight property.\n // Uses a data attribute so parent layouts (e.g. GridLayout) can override\n // with display:contents if needed.\n const weight = componentDef['weight'] as number | undefined;\n if (weight != null) {\n return <div key={keyOverride ?? componentId} data-freesail-weight style={{ flex: `${weight} 1 auto`, minWidth: 0, minHeight: 0, display: 'flex', flexDirection: 'column', alignSelf: 'stretch' }}>{rendered}</div>;\n }\n return rendered;\n } catch (err) {\n console.error(`[Freesail] Component render error (${componentDef.component}):`, err);\n return <UnknownComponent component={componentDef} />;\n }\n}\n\n/**\n * Resolve data bindings in component properties.\n */\nfunction resolveDataBindings(\n component: A2UIComponent,\n dataModel: Record<string, unknown>,\n catalogId: string,\n scopeData?: unknown,\n scopeBasePath?: string,\n _depth = 0\n): Record<string, unknown> {\n if (_depth > 10) return {};\n const resolved: Record<string, unknown> = {};\n\n for (const [key, value] of Object.entries(component)) {\n if (key === 'id' || key === 'component' || key === 'children' || key === 'child') {\n continue;\n }\n\n // Robustness: Handle double-encoded bindings\n let effectiveValue = value;\n if (typeof value === 'string' && value.trim().startsWith('{') && value.includes('\"path\"')) {\n try {\n const parsed = JSON.parse(value);\n if (isDataBindingObject(parsed)) {\n effectiveValue = parsed;\n }\n } catch {\n // Ignore parse errors\n }\n }\n\n if (isFunctionCall(effectiveValue)) {\n // Don't eagerly evaluate function calls inside `action` — they are\n // deferred and executed by the component on user interaction (e.g. Button click).\n if (key === 'action') {\n resolved[key] = effectiveValue;\n } else {\n resolved[key] = evaluateFunction(effectiveValue, dataModel, catalogId, scopeData);\n }\n } else if (isDataBindingObject(effectiveValue)) {\n // Preserve the raw binding so components can find the path for two-way binding.\n // If inside a scoped template, convert relative paths to absolute paths\n // so onDataChange writes to the correct location in the data model.\n const rawBinding = { ...effectiveValue };\n if (scopeBasePath && !rawBinding.path.startsWith('/')) {\n rawBinding.path = `${scopeBasePath}/${rawBinding.path}`;\n }\n resolved[`__raw${key.charAt(0).toUpperCase()}${key.slice(1)}`] = rawBinding;\n // Resolve data binding\n resolved[key] = resolveSingleBinding(effectiveValue, dataModel, scopeData);\n\n } else if (typeof value === 'object' && value !== null) {\n // Prevent recursion into LocalAction definitions (which contain FunctionCalls that should NOT be evaluated yet)\n if ('functionCall' in value && isFunctionCall((value as any).functionCall)) {\n resolved[key] = value;\n continue;\n }\n\n // Recursively resolve bindings inside objects and arrays\n if (Array.isArray(value)) {\n resolved[key] = value.map(item => {\n if (typeof item === 'object' && item !== null) {\n // Check for LocalAction in array items too\n if ('functionCall' in item && isFunctionCall((item as any).functionCall)) {\n return item;\n }\n if (isFunctionCall(item)) {\n return evaluateFunction(item, dataModel, catalogId, scopeData);\n }\n if (isDataBindingObject(item)) {\n return resolveSingleBinding(item, dataModel, scopeData);\n }\n return resolveDataBindings(item as any, dataModel, catalogId, scopeData, undefined, _depth + 1);\n }\n return item;\n });\n } else {\n resolved[key] = resolveDataBindings(value as any, dataModel, catalogId, scopeData, undefined, _depth + 1);\n }\n } else {\n resolved[key] = value;\n }\n }\n\n return resolved;\n}\n\n/**\n * Helper to resolve a single binding object, following chains.\n */\nfunction resolveSingleBinding(\n binding: { path: string },\n dataModel: Record<string, unknown>,\n scopeData?: unknown\n): unknown {\n const path = binding.path;\n let resolvedValue: unknown;\n\n // \".\" or \"\" means \"the current scoped item\" — used when iterating scalar arrays\n if (path === '.' || path === '') {\n return scopeData !== undefined ? scopeData : getDataAtPath(dataModel, '/');\n }\n\n if (path.startsWith('/')) {\n resolvedValue = getDataAtPath(dataModel, path);\n } else if (scopeData !== undefined) {\n resolvedValue = getDataAtPath(scopeData as Record<string, unknown>, '/' + path);\n } else {\n resolvedValue = getDataAtPath(dataModel, '/' + path);\n }\n\n // Chained bindings (max depth 5)\n let depth = 0;\n while (isDataBindingObject(resolvedValue) && depth < 5) {\n const chainedPath = resolvedValue.path;\n resolvedValue = chainedPath.startsWith('/')\n ? getDataAtPath(dataModel, chainedPath)\n : getDataAtPath(dataModel, '/' + chainedPath);\n depth++;\n }\n\n return resolvedValue;\n}\n\nfunction isDataBindingObject(value: unknown): value is { path: string } {\n if (typeof value !== 'object' || value === null || !('path' in value)) return false;\n if (typeof (value as Record<string, unknown>)['path'] !== 'string') return false;\n if ('componentId' in value) return false; // ChildListTemplate\n if ('event' in value) return false; // ServerAction\n if ('call' in value) return false; // FunctionCall\n return true;\n}\n\n/**\n * Evaluate a function call.\n */\nfunction evaluateFunction(\n call: FunctionCall,\n dataModel: Record<string, unknown>,\n catalogId: string,\n scopeData?: unknown\n): unknown {\n const functionName = call.call;\n const funcImpl = registry.getFunction(catalogId, functionName);\n\n if (!funcImpl) {\n console.warn(`[Freesail] Function not found: ${functionName} in catalog ${catalogId}`);\n return undefined;\n }\n\n // Resolve arguments\n let rawArgs: unknown[] = [];\n if (Array.isArray(call.args)) {\n rawArgs = call.args;\n } else if (call.args && typeof call.args === 'object') {\n const entries = Object.entries(call.args);\n\n // Check if the registry declares paramNames for this function\n // and the keys are named (not numeric).\n // If so, reorder entries to match the declared parameter order.\n const paramNames = registry.getParamNames(catalogId as CatalogId, functionName);\n const hasNonNumericKeys = entries.some(([key]) => isNaN(parseInt(key.replace(/^'|'$/g, ''), 10)));\n\n if (paramNames && hasNonNumericKeys) {\n // Build a lookup from the entries\n const argMap = new Map(entries);\n // Reorder: first pull args matching declared param names in order,\n // then append any extra keys not in paramNames\n const ordered: unknown[] = [];\n const used = new Set<string>();\n for (const name of paramNames) {\n if (argMap.has(name)) {\n ordered.push(argMap.get(name));\n used.add(name);\n }\n }\n // Append remaining keys not in paramNames (preserves insertion order)\n for (const [key, value] of entries) {\n if (!used.has(key)) {\n ordered.push(value);\n }\n }\n rawArgs = ordered;\n } else {\n // Numeric keys or no paramNames — sort numerically as before\n entries.sort(([keyA], [keyB]) => {\n // Remove surrounding quotes if present to cleanly parse as number\n const numA = parseInt(keyA.replace(/^'|'$/g, ''), 10);\n const numB = parseInt(keyB.replace(/^'|'$/g, ''), 10);\n if (!isNaN(numA) && !isNaN(numB)) {\n return numA - numB;\n }\n return 0; // fallback to stable sort for non-numeric keys\n });\n rawArgs = entries.map(([, value]) => value);\n }\n\n // Robustness: agents sometimes wrap multiple positional args in a single-key\n // object as an array, e.g. { \"value\": [arg0, arg1] } instead of [arg0, arg1].\n // When there is exactly one entry and its value is an array, spread it so that\n // multi-arg functions like lte(a, b) receive two arguments, not one array.\n if (rawArgs.length === 1 && Array.isArray(rawArgs[0])) {\n rawArgs = rawArgs[0] as unknown[];\n }\n }\n\n const args = rawArgs.map(arg => {\n if (isFunctionCall(arg)) {\n return evaluateFunction(arg, dataModel, catalogId, scopeData);\n }\n if (isDataBindingObject(arg)) {\n return resolveSingleBinding(arg, dataModel, scopeData);\n }\n // Handle nested arrays/objects in args\n if (typeof arg === 'object' && arg !== null) {\n if (Array.isArray(arg)) {\n return arg.map(item => {\n if (isFunctionCall(item)) return evaluateFunction(item, dataModel, catalogId, scopeData);\n if (isDataBindingObject(item)) return resolveSingleBinding(item, dataModel, scopeData);\n return item;\n });\n }\n }\n return arg;\n });\n\n // formatString: pre-process the format string for ${...} template interpolation\n let callArgs = args;\n if (functionName === 'formatString' && callArgs.length > 0 && typeof callArgs[0] === 'string') {\n callArgs = [\n interpolateTemplate(\n callArgs[0] as string,\n dataModel,\n catalogId,\n scopeData,\n (nestedCall) => evaluateFunction(nestedCall, dataModel, catalogId, scopeData)\n ),\n ...callArgs.slice(1),\n ];\n }\n\n try {\n return funcImpl(...callArgs);\n } catch (error) {\n console.error(`[Freesail] Error evaluating function ${functionName}:`, error);\n return undefined;\n }\n}\n\n/**\n * Resolve data bindings in an action's context object.\n */\nfunction resolveActionContext(\n context: Record<string, unknown>,\n dataModel: Record<string, unknown>,\n catalogId: string,\n scopeData?: unknown\n): Record<string, unknown> {\n const resolved: Record<string, unknown> = {};\n\n for (const [key, value] of Object.entries(context)) {\n if (isFunctionCall(value)) {\n resolved[key] = evaluateFunction(value, dataModel, catalogId, scopeData);\n } else if (isDataBindingObject(value)) {\n const path = value.path;\n if (path.startsWith('/')) {\n resolved[key] = getDataAtPath(dataModel, path);\n } else if (scopeData !== undefined) {\n resolved[key] = getDataAtPath(scopeData as Record<string, unknown>, '/' + path);\n } else {\n // Relative path but no scope — normalize to absolute\n resolved[key] = getDataAtPath(dataModel, '/' + path);\n }\n } else {\n resolved[key] = value;\n }\n }\n\n return resolved;\n}\n\n// =============================================================================\n// Template Interpolation (for formatString ${...} syntax)\n// =============================================================================\n\n/**\n * Finds the position of the closing brace that matches the opening brace at openPos,\n * respecting nested braces and quoted strings.\n */\nfunction findMatchingBrace(str: string, openPos: number): number {\n let depth = 0;\n let inSingleQuote = false;\n let inDoubleQuote = false;\n for (let i = openPos; i < str.length; i++) {\n const ch = str[i];\n const escaped = i > 0 && str[i - 1] === '\\\\';\n if (ch === \"'\" && !inDoubleQuote && !escaped) inSingleQuote = !inSingleQuote;\n if (ch === '\"' && !inSingleQuote && !escaped) inDoubleQuote = !inDoubleQuote;\n if (!inSingleQuote && !inDoubleQuote) {\n if (ch === '{') depth++;\n else if (ch === '}') { depth--; if (depth === 0) return i; }\n }\n }\n return -1;\n}\n\n/** Converts a value to a display string for interpolation output. */\nfunction interpolatedValueToString(value: unknown): string {\n if (value === null || value === undefined) return '';\n if (typeof value === 'object') return JSON.stringify(value);\n return String(value);\n}\n\n/**\n * Splits a comma-separated args string into individual tokens,\n * respecting nested ${...} and quoted strings.\n */\nfunction splitInterpolationArgs(argsStr: string): string[] {\n const parts: string[] = [];\n let current = '';\n let depth = 0;\n let inSingleQuote = false;\n let inDoubleQuote = false;\n for (let i = 0; i < argsStr.length; i++) {\n const ch = argsStr[i];\n const escaped = i > 0 && argsStr[i - 1] === '\\\\';\n if (ch === \"'\" && !inDoubleQuote && !escaped) inSingleQuote = !inSingleQuote;\n else if (ch === '\"' && !inSingleQuote && !escaped) inDoubleQuote = !inDoubleQuote;\n else if (!inSingleQuote && !inDoubleQuote) {\n if (ch === '{') depth++;\n else if (ch === '}') depth--;\n else if (ch === ',' && depth === 0) { parts.push(current.trim()); current = ''; continue; }\n }\n current += ch;\n }\n if (current.trim()) parts.push(current.trim());\n return parts;\n}\n\n/**\n * Parses a single argument token from an interpolation expression.\n * Supports: 'string', \"string\", number, boolean, ${nested}, bare path.\n */\nfunction parseInterpolationValue(\n token: string,\n dataModel: Record<string, unknown>,\n catalogId: string,\n scopeData: unknown,\n evalFn: (call: FunctionCall) => unknown\n): unknown {\n token = token.trim();\n if ((token.startsWith(\"'\") && token.endsWith(\"'\")) || (token.startsWith('\"') && token.endsWith('\"')))\n return token.slice(1, -1);\n if (token.startsWith('${') && token.endsWith('}'))\n return evaluateInterpolationExpr(token.slice(2, -1), dataModel, catalogId, scopeData, evalFn);\n if (token === 'true') return true;\n if (token === 'false') return false;\n const num = Number(token);\n if (!isNaN(num) && token !== '') return num;\n if (token.startsWith('/')) return getDataAtPath(dataModel, token);\n if (scopeData !== undefined) return getDataAtPath(scopeData as Record<string, unknown>, '/' + token);\n return getDataAtPath(dataModel, '/' + token);\n}\n\n/**\n * Evaluates the expression inside ${...}: either a data path or a function call.\n */\nfunction evaluateInterpolationExpr(\n expr: string,\n dataModel: Record<string, unknown>,\n catalogId: string,\n scopeData: unknown,\n evalFn: (call: FunctionCall) => unknown\n): unknown {\n expr = expr.trim();\n // Function call: word(...)\n if (/^\\w[\\w.]*\\(.*\\)$/s.test(expr)) {\n const parenOpen = expr.indexOf('(');\n const funcName = expr.slice(0, parenOpen).trim();\n const argsStr = expr.slice(parenOpen + 1, -1).trim();\n const args: Record<string, unknown> = {};\n if (argsStr) {\n splitInterpolationArgs(argsStr).forEach((part, index) => {\n const colonIdx = part.indexOf(':');\n if (colonIdx > 0) {\n const potentialKey = part.slice(0, colonIdx).trim();\n if (/^[a-zA-Z_]\\w*$/.test(potentialKey)) {\n args[potentialKey] = parseInterpolationValue(\n part.slice(colonIdx + 1).trim(), dataModel, catalogId, scopeData, evalFn\n );\n return;\n }\n }\n args[String(index)] = parseInterpolationValue(part, dataModel, catalogId, scopeData, evalFn);\n });\n }\n return evalFn({ call: funcName, args } as unknown as FunctionCall);\n }\n // Data path\n if (expr.startsWith('/')) return getDataAtPath(dataModel, expr);\n if (scopeData !== undefined) return getDataAtPath(scopeData as Record<string, unknown>, '/' + expr);\n return getDataAtPath(dataModel, '/' + expr);\n}\n\n/**\n * Processes ${...} template expressions in a formatString format string.\n * Supports: ${/absolute/path}, ${relative/field}, ${funcName(args)},\n * nested expressions (${upper(${/name})}), and escaped literals (\\${).\n */\nfunction interpolateTemplate(\n template: string,\n dataModel: Record<string, unknown>,\n catalogId: string,\n scopeData: unknown,\n evalFn: (call: FunctionCall) => unknown\n): string {\n let result = '';\n let i = 0;\n while (i < template.length) {\n // Escaped: \\${ → literal ${\n if (template[i] === '\\\\' && template[i + 1] === '$' && template[i + 2] === '{') {\n result += '${';\n i += 3;\n continue;\n }\n // Expression: ${...}\n if (template[i] === '$' && template[i + 1] === '{') {\n const closeBrace = findMatchingBrace(template, i + 1);\n if (closeBrace === -1) { result += template[i++]; continue; }\n const expr = template.slice(i + 2, closeBrace);\n result += interpolatedValueToString(\n evaluateInterpolationExpr(expr, dataModel, catalogId, scopeData, evalFn)\n );\n i = closeBrace + 1;\n continue;\n }\n result += template[i++];\n }\n return result;\n}\n\n// =============================================================================\n// Default UI States\n// =============================================================================\n\nfunction DefaultLoading() {\n return (\n <div style={{\n display: 'flex',\n flexDirection: 'column',\n alignItems: 'center',\n justifyContent: 'center',\n padding: '40px 16px',\n gap: '16px',\n }}>\n <style>{`\n @keyframes freesail-pulse {\n 0%, 100% { opacity: 0.4; transform: scale(0.95); }\n 50% { opacity: 1; transform: scale(1); }\n }\n @keyframes freesail-spin {\n 0% { transform: rotate(0deg); }\n 100% { transform: rotate(360deg); }\n }\n `}</style>\n {FREESAIL_LOGO_DATA_URI ? (\n <img\n src={FREESAIL_LOGO_DATA_URI}\n alt=\"Loading\"\n style={{\n width: '48px',\n height: '48px',\n animation: 'freesail-pulse 1.5s ease-in-out infinite',\n }}\n />\n ) : (\n <div style={{\n width: '32px',\n height: '32px',\n border: '3px solid var(--freesail-border, #e2e8f0)',\n borderTopColor: 'var(--freesail-primary, #2563eb)',\n borderRadius: '50%',\n animation: 'freesail-spin 0.8s linear infinite',\n }} />\n )}\n <span style={{\n fontSize: '13px',\n color: 'var(--freesail-text-muted, #64748b)',\n letterSpacing: '0.05em',\n }}>Preparing…</span>\n </div>\n );\n}\n\nfunction DefaultError() {\n return (\n <div style={{ padding: '16px', color: '#c00' }}>\n Error: Unable to render surface\n </div>\n );\n}\n\nfunction UnknownComponent({ component }: { component: A2UIComponent }) {\n return (\n <div\n style={{\n padding: '8px',\n border: '1px dashed #f00',\n background: '#fee',\n margin: '4px',\n }}\n >\n <strong>Unknown Component:</strong> {component.component}\n <pre style={{ fontSize: '10px' }}>\n {JSON.stringify(component, null, 2)}\n </pre>\n </div>\n );\n}\n"]}
/**
* @fileoverview Freesail React Hooks
*
* Custom hooks for interacting with Freesail surfaces and data.
*/
import type { SurfaceId, Surface, JsonPointer, ComponentId } from '@freesail/core';
/**
* Hook to access and subscribe to a specific surface.
*/
export declare function useSurface(surfaceId: SurfaceId): Surface | undefined;
/**
* Hook to access data from a surface's data model.
*/
export declare function useSurfaceData<T = unknown>(surfaceId: SurfaceId, path?: JsonPointer): T | undefined;
/**
* Hook to send user actions (v0.9 format).
*/
export declare function useAction(surfaceId: SurfaceId): (name: string, sourceComponentId: ComponentId, context?: Record<string, unknown>) => Promise<void>;
/**
* Hook to get connection status.
*/
export declare function useConnectionStatus(): {
isConnected: boolean;
};
/**
* Hook to get all surfaces.
*/
export declare function useSurfaces(): Surface[];
/**
* Hook to access the current session ID assigned by the Gateway.
* This ID is available after the transport successfully connects.
*/
export declare function useSessionId(): string | null;
//# sourceMappingURL=hooks.d.ts.map
{"version":3,"file":"hooks.d.ts","sourceRoot":"","sources":["../src/hooks.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAGH,OAAO,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAInF;;GAEG;AACH,wBAAgB,UAAU,CAAC,SAAS,EAAE,SAAS,GAAG,OAAO,GAAG,SAAS,CA8CpE;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,CAAC,GAAG,OAAO,EACxC,SAAS,EAAE,SAAS,EACpB,IAAI,CAAC,EAAE,WAAW,GACjB,CAAC,GAAG,SAAS,CA8Bf;AAED;;GAEG;AACH,wBAAgB,SAAS,CAAC,SAAS,EAAE,SAAS,UAKlC,MAAM,qBACO,WAAW,YACrB,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,mBAQrC;AAED;;GAEG;AACH,wBAAgB,mBAAmB,IAAI;IACrC,WAAW,EAAE,OAAO,CAAC;CACtB,CAGA;AAED;;GAEG;AACH,wBAAgB,WAAW,IAAI,OAAO,EAAE,CAwBvC;AAED;;;GAGG;AACH,wBAAgB,YAAY,IAAI,MAAM,GAAG,IAAI,CAiB5C"}
/**
* @fileoverview Freesail React Hooks
*
* Custom hooks for interacting with Freesail surfaces and data.
*/
import { useState, useEffect, useCallback, useMemo } from 'react';
import { useFreesailContext } from './context.js';
import { getDataAtPath } from './utils.js';
/**
* Hook to access and subscribe to a specific surface.
*/
export function useSurface(surfaceId) {
const { surfaceManager, getSurface } = useFreesailContext();
const [surface, setSurface] = useState(() => getSurface(surfaceId));
useEffect(() => {
// Initial state
setSurface(getSurface(surfaceId));
// Subscribe to surface changes
const unsubCreate = surfaceManager.on('surfaceCreated', (created) => {
if (created.id === surfaceId) {
setSurface(created);
}
});
const unsubDelete = surfaceManager.on('surfaceDeleted', (deletedId) => {
if (deletedId === surfaceId) {
setSurface(undefined);
}
});
const unsubComponents = surfaceManager.on('componentsUpdated', (updatedId) => {
if (updatedId === surfaceId) {
const current = getSurface(surfaceId);
setSurface(current ? { ...current } : undefined);
}
});
const unsubData = surfaceManager.on('dataModelUpdated', (updatedId) => {
if (updatedId === surfaceId) {
const current = getSurface(surfaceId);
setSurface(current ? { ...current } : undefined);
}
});
return () => {
unsubCreate();
unsubDelete();
unsubComponents();
unsubData();
};
}, [surfaceId, surfaceManager, getSurface]);
return surface;
}
/**
* Hook to access data from a surface's data model.
*/
export function useSurfaceData(surfaceId, path) {
const { surfaceManager, getSurface } = useFreesailContext();
const [data, setData] = useState(() => {
const surface = getSurface(surfaceId);
if (!surface)
return undefined;
return getDataAtPath(surface.dataModel, path);
});
useEffect(() => {
const surface = getSurface(surfaceId);
if (surface) {
setData(getDataAtPath(surface.dataModel, path));
}
const unsub = surfaceManager.on('dataModelUpdated', (updatedId, updatedPath) => {
if (updatedId === surfaceId) {
// Check if the update affects our path
if (!path || updatedPath.startsWith(path) || path.startsWith(updatedPath)) {
const currentSurface = getSurface(surfaceId);
if (currentSurface) {
setData(getDataAtPath(currentSurface.dataModel, path));
}
}
}
});
return unsub;
}, [surfaceId, path, surfaceManager, getSurface]);
return data;
}
/**
* Hook to send user actions (v0.9 format).
*/
export function useAction(surfaceId) {
const { sendAction } = useFreesailContext();
const dispatch = useCallback(async (name, sourceComponentId, context = {}) => {
await sendAction(surfaceId, name, sourceComponentId, context);
}, [surfaceId, sendAction]);
return dispatch;
}
/**
* Hook to get connection status.
*/
export function useConnectionStatus() {
const { isConnected } = useFreesailContext();
return useMemo(() => ({ isConnected }), [isConnected]);
}
/**
* Hook to get all surfaces.
*/
export function useSurfaces() {
const { surfaceManager } = useFreesailContext();
const [surfaces, setSurfaces] = useState(() => surfaceManager.getAllSurfaces());
useEffect(() => {
setSurfaces(surfaceManager.getAllSurfaces());
const unsubCreate = surfaceManager.on('surfaceCreated', () => {
setSurfaces(surfaceManager.getAllSurfaces());
});
const unsubDelete = surfaceManager.on('surfaceDeleted', () => {
setSurfaces(surfaceManager.getAllSurfaces());
});
return () => {
unsubCreate();
unsubDelete();
};
}, [surfaceManager]);
return surfaces;
}
/**
* Hook to access the current session ID assigned by the Gateway.
* This ID is available after the transport successfully connects.
*/
export function useSessionId() {
const { transport } = useFreesailContext();
const [sessionId, setSessionId] = useState(() => transport?.sessionId ?? null);
useEffect(() => {
if (!transport)
return;
setSessionId(transport.sessionId);
const unsub = transport.on('sessionStart', (sid) => {
setSessionId(sid);
});
return unsub;
}, [transport]);
return sessionId;
}
//# sourceMappingURL=hooks.js.map
{"version":3,"file":"hooks.js","sourceRoot":"","sources":["../src/hooks.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * @fileoverview Freesail React Hooks\n *\n * Custom hooks for interacting with Freesail surfaces and data.\n */\n\nimport { useState, useEffect, useCallback, useMemo } from 'react';\nimport type { SurfaceId, Surface, JsonPointer, ComponentId } from '@freesail/core';\nimport { useFreesailContext } from './context.js';\nimport { getDataAtPath } from './utils.js';\n\n/**\n * Hook to access and subscribe to a specific surface.\n */\nexport function useSurface(surfaceId: SurfaceId): Surface | undefined {\n const { surfaceManager, getSurface } = useFreesailContext();\n const [surface, setSurface] = useState<Surface | undefined>(() =>\n getSurface(surfaceId)\n );\n\n useEffect(() => {\n // Initial state\n setSurface(getSurface(surfaceId));\n\n // Subscribe to surface changes\n const unsubCreate = surfaceManager.on('surfaceCreated', (created: Surface) => {\n if (created.id === surfaceId) {\n setSurface(created);\n }\n });\n\n const unsubDelete = surfaceManager.on('surfaceDeleted', (deletedId: SurfaceId) => {\n if (deletedId === surfaceId) {\n setSurface(undefined);\n }\n });\n\n const unsubComponents = surfaceManager.on('componentsUpdated', (updatedId: SurfaceId) => {\n if (updatedId === surfaceId) {\n const current = getSurface(surfaceId);\n setSurface(current ? { ...current } : undefined);\n }\n });\n\n const unsubData = surfaceManager.on('dataModelUpdated', (updatedId: SurfaceId) => {\n if (updatedId === surfaceId) {\n const current = getSurface(surfaceId);\n setSurface(current ? { ...current } : undefined);\n }\n });\n\n return () => {\n unsubCreate();\n unsubDelete();\n unsubComponents();\n unsubData();\n };\n }, [surfaceId, surfaceManager, getSurface]);\n\n return surface;\n}\n\n/**\n * Hook to access data from a surface's data model.\n */\nexport function useSurfaceData<T = unknown>(\n surfaceId: SurfaceId,\n path?: JsonPointer\n): T | undefined {\n const { surfaceManager, getSurface } = useFreesailContext();\n const [data, setData] = useState<T | undefined>(() => {\n const surface = getSurface(surfaceId);\n if (!surface) return undefined;\n return getDataAtPath(surface.dataModel, path) as T;\n });\n\n useEffect(() => {\n const surface = getSurface(surfaceId);\n if (surface) {\n setData(getDataAtPath(surface.dataModel, path) as T);\n }\n\n const unsub = surfaceManager.on('dataModelUpdated', (updatedId: SurfaceId, updatedPath: JsonPointer) => {\n if (updatedId === surfaceId) {\n // Check if the update affects our path\n if (!path || updatedPath.startsWith(path) || path.startsWith(updatedPath)) {\n const currentSurface = getSurface(surfaceId);\n if (currentSurface) {\n setData(getDataAtPath(currentSurface.dataModel, path) as T);\n }\n }\n }\n });\n\n return unsub;\n }, [surfaceId, path, surfaceManager, getSurface]);\n\n return data;\n}\n\n/**\n * Hook to send user actions (v0.9 format).\n */\nexport function useAction(surfaceId: SurfaceId) {\n const { sendAction } = useFreesailContext();\n\n const dispatch = useCallback(\n async (\n name: string,\n sourceComponentId: ComponentId,\n context: Record<string, unknown> = {}\n ) => {\n await sendAction(surfaceId, name, sourceComponentId, context);\n },\n [surfaceId, sendAction]\n );\n\n return dispatch;\n}\n\n/**\n * Hook to get connection status.\n */\nexport function useConnectionStatus(): {\n isConnected: boolean;\n} {\n const { isConnected } = useFreesailContext();\n return useMemo(() => ({ isConnected }), [isConnected]);\n}\n\n/**\n * Hook to get all surfaces.\n */\nexport function useSurfaces(): Surface[] {\n const { surfaceManager } = useFreesailContext();\n const [surfaces, setSurfaces] = useState<Surface[]>(() =>\n surfaceManager.getAllSurfaces()\n );\n\n useEffect(() => {\n setSurfaces(surfaceManager.getAllSurfaces());\n\n const unsubCreate = surfaceManager.on('surfaceCreated', () => {\n setSurfaces(surfaceManager.getAllSurfaces());\n });\n\n const unsubDelete = surfaceManager.on('surfaceDeleted', () => {\n setSurfaces(surfaceManager.getAllSurfaces());\n });\n\n return () => {\n unsubCreate();\n unsubDelete();\n };\n }, [surfaceManager]);\n\n return surfaces;\n}\n\n/**\n * Hook to access the current session ID assigned by the Gateway.\n * This ID is available after the transport successfully connects.\n */\nexport function useSessionId(): string | null {\n const { transport } = useFreesailContext();\n const [sessionId, setSessionId] = useState<string | null>(() => transport?.sessionId ?? null);\n\n useEffect(() => {\n if (!transport) return;\n \n setSessionId(transport.sessionId);\n \n const unsub = transport.on('sessionStart', (sid: string) => {\n setSessionId(sid);\n });\n \n return unsub;\n }, [transport]);\n\n return sessionId;\n}\n"]}
/**
* @fileoverview Freesail React - Public API
*/
export { FreesailProvider, type FreesailProviderProps } from './FreesailProvider.js';
export { FreesailSurface, type FreesailSurfaceProps } from './FreesailSurface.js';
export { FreesailContext, useFreesailContext, type FreesailContextValue } from './context.js';
export { useSurface, useSurfaceData, useAction, useConnectionStatus, useSurfaces, useSessionId, } from './hooks.js';
export { registry, withCatalog, registerCatalog, type FreesailComponent, type FreesailComponentProps, } from './registry.js';
export { type CatalogDefinition, type FunctionImplementation } from './types.js';
export type { SurfaceId, ComponentId, CatalogId, A2UIComponent, Surface, } from '@freesail/core';
export * from './theme.js';
//# sourceMappingURL=index.d.ts.map
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAGH,OAAO,EAAE,gBAAgB,EAAE,KAAK,qBAAqB,EAAE,MAAM,uBAAuB,CAAC;AAGrF,OAAO,EAAE,eAAe,EAAE,KAAK,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AAGlF,OAAO,EAAE,eAAe,EAAE,kBAAkB,EAAE,KAAK,oBAAoB,EAAE,MAAM,cAAc,CAAC;AAG9F,OAAO,EACL,UAAU,EACV,cAAc,EACd,SAAS,EACT,mBAAmB,EACnB,WAAW,EACX,YAAY,GACb,MAAM,YAAY,CAAC;AAGpB,OAAO,EACL,QAAQ,EACR,WAAW,EACX,eAAe,EACf,KAAK,iBAAiB,EACtB,KAAK,sBAAsB,GAC5B,MAAM,eAAe,CAAC;AAGvB,OAAO,EAAE,KAAK,iBAAiB,EAAE,KAAK,sBAAsB,EAAE,MAAM,YAAY,CAAC;AAGjF,YAAY,EACV,SAAS,EACT,WAAW,EACX,SAAS,EACT,aAAa,EACb,OAAO,GACR,MAAM,gBAAgB,CAAC;AAGxB,cAAc,YAAY,CAAC"}
/**
* @fileoverview Freesail React - Public API
*/
// Provider
export { FreesailProvider } from './FreesailProvider.js';
// Surface Component
export { FreesailSurface } from './FreesailSurface.js';
// Context
export { FreesailContext, useFreesailContext } from './context.js';
// Hooks
export { useSurface, useSurfaceData, useAction, useConnectionStatus, useSurfaces, useSessionId, } from './hooks.js';
// Registry
export { registry, withCatalog, registerCatalog, } from './registry.js';
// Theme
export * from './theme.js';
//# sourceMappingURL=index.js.map
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,WAAW;AACX,OAAO,EAAE,gBAAgB,EAA8B,MAAM,uBAAuB,CAAC;AAErF,oBAAoB;AACpB,OAAO,EAAE,eAAe,EAA6B,MAAM,sBAAsB,CAAC;AAElF,UAAU;AACV,OAAO,EAAE,eAAe,EAAE,kBAAkB,EAA6B,MAAM,cAAc,CAAC;AAE9F,QAAQ;AACR,OAAO,EACL,UAAU,EACV,cAAc,EACd,SAAS,EACT,mBAAmB,EACnB,WAAW,EACX,YAAY,GACb,MAAM,YAAY,CAAC;AAEpB,WAAW;AACX,OAAO,EACL,QAAQ,EACR,WAAW,EACX,eAAe,GAGhB,MAAM,eAAe,CAAC;AAcvB,QAAQ;AACR,cAAc,YAAY,CAAC","sourcesContent":["/**\n * @fileoverview Freesail React - Public API\n */\n\n// Provider\nexport { FreesailProvider, type FreesailProviderProps } from './FreesailProvider.js';\n\n// Surface Component\nexport { FreesailSurface, type FreesailSurfaceProps } from './FreesailSurface.js';\n\n// Context\nexport { FreesailContext, useFreesailContext, type FreesailContextValue } from './context.js';\n\n// Hooks\nexport {\n useSurface,\n useSurfaceData,\n useAction,\n useConnectionStatus,\n useSurfaces,\n useSessionId,\n} from './hooks.js';\n\n// Registry\nexport {\n registry,\n withCatalog,\n registerCatalog,\n type FreesailComponent,\n type FreesailComponentProps,\n} from './registry.js';\n\n// Types\nexport { type CatalogDefinition, type FunctionImplementation } from './types.js';\n\n// Re-export core types for convenience\nexport type {\n SurfaceId,\n ComponentId,\n CatalogId,\n A2UIComponent,\n Surface,\n} from '@freesail/core';\n\n// Theme\nexport * from './theme.js';\n"]}
export declare const FREESAIL_LOGO_DATA_URI = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAA2UAAAPyCAYAAAD8FXeoAAAACXBIWXMAAC4jAAAuIwF4pT92AAAAGXRFWHRTb2Z0d2FyZQB3d3cuaW5rc2NhcGUub3Jnm+48GgAAIABJREFUeJzs3W10lOd97/vfFYwQI2NJyGFiylRUdgfFCUi2HFJhW6IVKCm2ZJostNN6A/Lu4QVuvey11L6DBeeN33WZvc5DV846Z6Oe7rP2qs/qCa6zT89qSiycxE6cBwvs2CAbPLIUYAjyjKwHxFA658Vo7NEwMxpJM/c1931/P6903TPo/qerifn5uq7/3ySTSQEAAAAA7PiC7QIAAAAAwM8IZQAAAABgEaEMAAAAACwilAEAAACARYQyAAAAALCIUAYAAAAAFhHKAAAAAMAiQhkAAAAAWEQoAwAAAACLCGUAAAAAYBGhDAAAAAAsIpQBAAAAgEWEMgAAAACwiFAGAAAAABYRygAAAADAIkIZAAAAAFh0Vyl+iTGmVdIpSY0FvjYqKSIpLml4/tmwpOFkMhkpRR0AAAAA4DYmmUyu/JcYMySpc4W/5oxSoS0iaUipsBZf4e8EAAAAgIpWSaEsl1HN76aJoAYAAADAg0oVyk5Jeiq9rqltUE1dw4LvxK6O6dbNGyt+l1I7akOShpLJ5FApfiEAAAAA2FKqUPaCpJfS6+btXWrr7sv53Zn4hKYnJ5SYm1UsOqbo6Ihm4hOamZxY7uvTIe1UMpkcXuS7AAAAAFBRShXKWiW9nV7XBzdpz6GjS/odqZA2ngpqkQuKRceXE9RGNR/QlNpJ46gjAAAAgIpWklAmScaYuKTa9HrfX72kqurAin5nOqhFRy8odnVM4yNnl/orzujzgMYuGgAAAICKU8pQtuBeWce+wwptaS3J784UHR1RdPSCoqMjujY6spQ/OqpUQDvFXTQAAAAAlaKUoazoe2WlFB0d0fiF4dRuWnS82D82qfkdNKVCGsccAQAAAFhRylC24ntlK5WYm/1sB22JIe2MpEER0AAAAAA4rGShTCrPvbKVSIe08QvDGrswXGxL/lf0+TFHAhoAAACAsip1KHPkXtlyjV0Y1rXREY1dGC62syMBDQAAAEBZlTqULbhXtrXjSW3r6CnZ7y+lWHRMl86+uZRjjq9IGkwmk6fKXBoAAAAAHyl1KFtwr2xDY1i79w+U7PeXSzqgFbmDlm4ScoqABgAAAGClShrKpDvvlT195Lsl/f3lRkADAAAA4KRyhLIF98p27R9QsDFc0nc4ZZkBbZA5aAAAAACKVY5Q5pp7ZUsxdmFY4xeGdencm8V8fVSpFvuDyWQyUs66AAAAALhbOUKZK++VFSsxN6vxC8O6eO5NXRsdKeaPMAMNAAAAQF4lD2WSZIxZ8Evddq+sWDPxCV0894YunX2T440AAAAAlqVcoWxIUmd67eZ7ZcWKRcd0/menix1SzfFGAAAAAJLKF8qOSzqWXnvlXlmxLp19I3UHbeRsMV9n/hkAAADgY+UKZTslvZZee+1eWbFm4hMaGxnW+Z+dLuZ4I7tnAAAAgA+VJZRJ/rlXVqwlHm9k9wwAAADwiXKGsiFl3Cvbc+iI6oOhsrzLbS6dfaPY7o2jSjUHOcHuGQAAAOBN5Qxlx5Vxr6ytu0/N27vK8i63WmL3xr8TnRsBAAAAzylnKNupjHtlm8It6ux7tizv8oLo6IgunX2jmOHUZ5XaORssf1UAAAAAyq1soUxaeK9s9Zq16vvrE2V7l1ekh1Off+u0YtHxQl+dlHRCNAYBAAAAXK3coWxI3Ctbtpn4hM69/moxu2ccbQQAAABcqtyh7Li4V7ZiiblZnX/rdDF3zzjaCAAAALhMuUPZTnGvrKSK7NzI0UYAAADAJcoayiTulZVLeu4ZRxsBAAAAd3MilA2Je2Vlw9FGAAAAwN2cCGXHxb0yR3C0EQAAAHAfJ0LZTmXcK2va1q723v6yvtPvlnC08RWlds+Gyl8VAAAAgFycCGV1kmLpdU1tg/Y+92JZ34mUJRxtPCPpOOEMAAAAcF7ZQ5kkGWOGJbWk1/v+6iVVVQfK/l58rsijjdw7AwAAABzmVCgblHQwve7Yd1ihLa1lfy/ulD7aOHZhWLdu3sj3tVGlds4GnasMAAAA8CenQlm/pJPpdfP2LrV195X9vcgvfbTx/M9OLxbOBpXaPYs7VhwAAADgI06Fss2SPkqvNzSGtXv/QNnfi8Ul5mY1fmFY517/fqF7Z+mOjYQzAAAAoMQcCWWSZIyJS6pNr58+8l1H3oviFXnv7O+UOtoYcaYqAAAAwNucDGWnJD2VXu/aP6BgY9iRd2NpoqMjOvf6q4QzAAAAwAFfcPBdw5mLWHTMwVdjKYLzx0v3/uWLatrWnu9rByV9ZIwZnD+eCgAAAGAZnNwp26mMIdKbwi3q7HvWkXdjZWbiE7p47o3FmoIw6wwAAABYBsdCmSQZYz572eo1a9X31yccezdWrsiOjYQzAAAAYAmcDmVDkjrT671/+aJq6hocez9Kg3AGAAAAlI6Td8qkrHtl0dELDr8epVBVHdC2jh7tfe5FtfccVE1tzmDdKek1Y0xkfk4dAAAAgBycDmVDmYtYdNzh16OUqqoDamrZsVg4a5R0knAGAAAA5Ob08cXNyhgiXR/cpD2Hjjr2fpTfpbNvLDaIelSpY42DzlUFAAAAVC5HQ5kkGWMiSu2eSJL2/dVLqqoOOFoDym/swrDOv3W60KyzUUmDkk4kk8m4Y4UBAAAAFcZGKBtUasaVJIZIe10Rg6gnJZ0Q4QwAAAA+5fSdMolmH76SHkS9a/+ANuQO37WSjkmKGGOOG2PqnK0QAAAAsMvGTlmrpLfT6w3zf2mHPxS5czao1L0zds4AAADgeY6HMokh0uBYIwAAAJBmK5QNKWOI9J5DR1QfDDleB+wjnAEAAMDvbNwpk7LmlUXz/4UcHsedMwAAAPhdRYSy2NUxS2WgUqTDWYEh1OlwNswQagAAAHiJreOLdZJi6XVNbYP2Pvei43WgcjGEGgAAAH5hJZRJkjFmWFJLes0QaeRCOAMAAIDX2Tq+KN0xr4x7ZbhTU8sO7X3uRbV192n1mrW5vtIo6aQxJmKM2elsdQAAAMDK2QxlQ5mLAt33ADVv79Le517U1o4nC4Wz14wxQ4QzAAAAuInN44ubJX2UXjNEGsVKzM3q/Fundf5np3Xr5o18X/s7pY41RpyrDAAAAFg6a6FMkowxcaW66kmSnj7yXWu1wH2KDGf/WalwxowzAAAAVCSbxxcl5pVhBaqqA9rW0aMnDh1V07b2fF97Xsw4AwAAQAWrsFB2wVIZcLOauga19/Zr71++mC+cMeMMAAAAFct2KFvQgZEh0liJdDjbc+iINjSGc32FTo0AAACoOFbvlEmSMeazAhgijVKKjo7o3OuvFurseUap+2ZDzlUFAAAALFQJoYwh0iir6OiIfvkv/6BYdDzfV+jUCAAAAGtsH1+UGCKNMgs2hrXn0FG19xxUTW1Drq8clPSRMeYEzUAAAADgtEoIZUOZi1iUe2Uoj6aWHdr73IuFwhmdGgEAAOC4Sghl7JTBUelwtrXjSa1eszb7Yzo1AgAAwFHW75RJC5t9rF6zVn1/fcJmOfCRxNysfvkvL+vSuTfzfWVUUj/NQAAAAFAulbBTJqW64EmSbt28oZn4hM1a4CNV1YHPZpwVaKP/mjFmiDb6AAAAKIdKCWVZRxgZIg1n1dQ1aPf+Ae3aP5DvvlmnUuFs0Biz2dHiAAAA4GmVEsqGMhcFWpcDZRVsDH/WDCTHfTPp806NgzQDAQAAQClUSihbsFP2CR0YYVlmM5A8DirVqfEFB8sCAACAB1VEow9JMsbElep8J0l6+sh3LVYDfG4mPqFzr79KMxAAAACURaXslElZu2XMK0OlqKlrUHtvv3btHyimGchmR4sDAACA61VSKBvKXDCvDJUm2BjW7v0D6th3uFAzkI+MMSe4bwYAAIBiVWwoi11lpwyVKbSltdDwaUl6Xqn7Zv3OVgYAAAA3qqRQxvFFuMq2jh7tfe5FNW1rz/VxraSTxphh5psBAACgkIpp9CFJxpiIUvdzJEn7/uolVVUH7BUEFCkWHdMv/uVlXct/7PYVSS8kk8mIc1UBAADADSppp0xiXhlcqj4YWuy+2VNK3Tc7zn0zAAAAZKq0ULbgCGN09IKtOoBlKeK+2TFx3wwAAAAZKjqU0ewDblXkfbMhY0yrw6UBAACgwlTUnTJJMsZ8VlBNbYP2PveizXKAFSvivtl/lnQ8mUzGHSwLAAAAFaLSdsok6Wz6h5nJCc3EJ2zWAqxY+r7Zrv0D+e6b0UIfAADAxyoxlA1lLj6hNT48ItgYLnTfLPNI407nqwMAAIAtlRjKmFcGT9vW0aMnDh3VpnBLro87Jb1mjBmkSyMAAIA/VHwoi+a/hwO4Vk1dgzr7ni10pPGgUkcaX3C4NAAAADis4hp9SAubfaxes1Z9f33CZjlA2Z17/VWd/9lp3bp5I9fHZ5UaPD3kbFUAAABwQiXulEnSmfQPt27e4AgjPG+RFvot+vxI42ZHCwMAAEDZVWooG8pcMK8MflBVHVB7b7927R9QfXBTrq8clDTMkUYAAABvqdRQltXsY9xWHYDjgo1h7Tl0VG3dffm6NL5kjBmmSyMAAIA3uCKURUcv2KoDsKZ5e1exRxrp0ggAAOBiFRnKkslkRNJoes1OGfwqfaRxz6EjhY400qURAADAxSoylM2LZC5o9gE/qw+Gij3S2GqhPAAAAKxAJYeyocwFzT6Aoo40vm2MOcGRRgAAAPeo5FBGsw8ghyK6ND6v1JHGfmcrAwAAwHK4JpR9wvFFYIEiujSeNMYMcaQRAACgslVsKJtv9jGZXl8bHbFXDFDBmrd36YlDR7Up3JLr405xpBEAAKCiVWwom5d1hJHdMiCXmroGdfY9q137B1RT25DrK+kjjXsdLg0AAACLqPRQNpS5oNkHUFiwMay9z72orR1P5jvS+D1jzCl2zQAAACpHpYcymn0Ay7Cto6fQkcanRCMQAACAiuGqUEazD6B4ixxpzGwEstnx4gAAAPCZig5lNPsAVi7VpfGImrd35fq4U9KwMeYFh8sCAADAvIoOZfMW7JbNxCds1QG4VlV1QG3dfdpz6Eiu2Wa1kl4yxgzTPh8AAMB5rgtlHGEElq8+GCo026xFqfb5x52vDAAAwL9cF8poiw+s3CKzzY7N75rtdLgsAAAAX3JdKItyrwwoiXQjkI59h/Ptmr3G0GkAAIDyM8lk0nYNizLGfFbk6jVr1ffXJ2yWA3hOYm5W77z+fZ1/63Suj0cl9SeTySFnqwIAAPAHN+yUSdKZ9A+3bt6g2QdQYulGILv2D+RqBNKo1K4ZQ6cBAADKwC2hjGYfgANS7fOPamvHk7mONKaHTu+1UBoAAIBnuTKU0ewDKK9tHT164tBRbWgMZ39UK+l77JoBAACUjitDGc0+gPKrqWvQ7v0D+RqBpHfN+p2vDAAAwFtcEcqSyeTCnbKr7JQBTgltadXe517M1T6/VtJJY8yQMWaz44UBAAB4hCtC2bwFzT4Sc7M2awF8pao6UKh9fqekYWPMCxZKAwAAcD03hbJI5iIWHbdUBuBfi+yavcSuGQAAwNK5KZRl3Su7YKsOwNeK2DX7yBhz3PnKAAAA3Mm1oYx7ZYBdBXbNJOmYMWbYGNPqdF0AAABu45pQlkwmhzLXHF8E7Ftk16xF0tvsmgEAABTmmlA272z6h5nJCZp9ABWiiF2zCLtmAAAAubktlGUNkWa3DKgUi+yaNYpdMwAAgJxcHcpo9gFUHu6aAQAALI2rQxnNPoDKxF0zAACA4rkqlNHsA3CX0JZWPXHoqDY0hnN9zK4ZAACAXBbK5i1o9gGgstXUNWj3/gG1dfexawYAAJCDG0NZJHMRHR2xVAaApWje3sWuGQAAQA5uDGVZHRi5Vwa4RXrXbGvHk7k+ZtcMAAD4khtD2VDmYibOEUbAbbZ19GjPoSOqD27K9TG7ZgAAwFfcGMoimYtP2CkDXKk+GNKeQ0fZNQMAAL5nksmk7RqWzBgTl1SbXj995LsWqwGwUrHomN78p8F8HVXPSupPJpPDuT4EAABwOzfulEncKwM8pT4Y0q79A2re3pXr4/Su2QsOlwUAAOAIt4ayoczFNPfKANerqg6orbtPu/YPqKa2IddXXjLGDBlj6pyuDQAAoJzcGsoimQt2ygDvCDaGtefQkXy7Zp2SIsaYvQ6XBQAAUDZuDWULji8yqwzwlsxdsxwDp2slfc8Yc4JdMwAA4AWuDGXZF/5jV9kpA7wo2BjW3ude1KZwS66Pn5dE63wAAOB6rgxl886kf7h184YSc7M2awFQJlXVAXX2PauOfYdz7Zo1itb5AADA5dwcyiKZizyttAF4RGhLq544dFQbGsO5Pj423wRks7NVAQAArJybQ1nWvbILtuoA4JCaugbt3j+gtu6+XLtmnUodZ6QJCAAAcBXPhDLulQH+0by9S7sPDKg+uCn7o3QTkFM0AQEAAG7h2lCWTCaHMtczk8wqA/ykPhjSnkNHtbXjyVwfP6XUrtlOZ6sCAABYOteGsnmj6R+4Uwb407aOHu05dCTXwOlGSa/RBAQAAFQ6t4cy5pUBmN81yztw+pgxhtb5AACgYnkqlMWi3CsD/GqRgdMtkoaMMf3OVwYAAFCY20PZUOZiJs69MsDvCgycrpV0kiYgAACg0rg9lEUyF5+wUwZAiw6cTjcB4TgjAACoCK4OZclkMiJpMr2+xp0yABnSA6dztM5vlPQ2TUAAAEAlcHUom8e9MgB51dQ1FGqdf8wYM2SM2exsVQAAAJ/zQigbylxMc68MQA7bOnryNQHpVOo4414LZQEAAHgilEUyF+yUAchnkSYg3zPGnKAJCAAAcJoXQhmzygAULd0EpK27L9eu2fNKtc6nCQgAAHCM60NZMplceKfsKjtlABbXvL1Luw8M5GoC0qJUE5AXLJQFAAB8yPWhbN6Z9A+3bt5QYm7WZi0AXKI+GNKu/QNq3t6V6+OXmGkGAACc4JVQFslcxKLjlsoA4DZV1QG1dfcVmmkWMcbsdL4yAADgF14JZVn3yi7YqgOAS4W2tGrvcy9qQ2M4+6NaSa8ZY05YKAsAAPiAJ0MZ98oALEdVdUC79w/km2n2vDFmmJlmAACg1DwRypLJ5FDmemaSWWUAlm9bR4/2HDqimtqG7I9axEwzAABQYp4IZfNG0z9wpwzAStUHQ9pz6IiatrVnf/TZTDMLZQEAAA/yUiiLZC4YIg1gpaqqA2rv7Vdbd1+ujznOCAAASsJLoWwoczEd5wgjgNJo3t7FcUYAAFA2XgplkcwFO2UASil9nHFTuCX7I44zAgCAFfFuKKMDI4ASq6oOqLPvWY4zAgCAkvJMKKMDIwCncJwRAACUkmdC2Tw6MAJwBMcZAQBAqXgtlEUyF9wrA1BO6eOMDJsGAAAr4bVQNpS54F4ZACds6+jRrv0DWr1mbfZHHGcEAACL8looG85cTHOvDIBDgo1h7X3uRW1oDGd/9NlxRmNMnYXSAABAhfNaKItkLqKjI5bKAOBHVdUB7d4/kPc4o6QhjjMCAIBsngplyWRywU7ZDAOkAVjAcUYAALAUngpl886mf6AtPgBbijjOeNz5qgAAQCXyYiiLZC44wgjAlvRxxubtXbk+PmaMGeKeGQAA8GIoyzrCeN1WHQAgSWrr7lPHvsO5jjN2SooYY1otlAUAACqE50MZHRgBVILQllY9ceio6oObsj+qlfS2MeYFC2UBAIAK4MVQFslccHwRQKWoqWvQnkNH8x1nfMkYM8hxRgAA/MdzoYwOjAAqXVt3n9p7DuY6znhQqbb5HGcEAMBHPBfK5i3owJiYm7VZCwDcoallh3YfGMh1nLFFqWDW73xVAADABq+GsgW7ZbHouK06ACCv+mBIu/YPqGlbe/ZHtZJOGmNOWCgLAAA4zKuhLJK5iEXHLJUBAIVVVQfU3tuf7zjj88aYYe6ZAQDgbV4NZUOZC+6VAah06eOMNbUN2R+1KNU2f6fzVQEAACd4NZRFMhefsFMGwAXqgyHtOXREm8It2R/VSnrNGHPc+aoAAEC5eTKUJZPJSOY6dpVQBsAdqqoD6ux7Vm3dfbk+PmaMOcVxRgAAvMWToWzemfQPt27eoAMjAFdp3t6lPYeO5DrO+JRomw8AgKd4OZRFMhd0YATgNgWOM6bb5u+1UBYAACgxH4UyjjACcJ/0ccbm7V3ZH9VK+h73zAAAcD8vh7KhzAUdGAG4WVt3X762+dwzAwDA5bwcyiKZCzowAnC7Am3zuWcGAICLeTaUzXdgnEyvr42O2CsGAEokfc9sQ2M4+6P0PbN+56sCAAAr4dlQNm84c0EHRgBeUFUd0O79A/numZ00xpywUBYAAFgmr4eySOaCDowAvKTAPbPnjTFD3DMDAMAdfBbKuFcGwFvS98xyBLNOScPcMwMAoPJ5PZQNZS7owAjAi+qDIe197kXVBzdlf9Qo7pkBAFDxvB7K4pkLOjAC8Kqq6oD2HDqqpm3t2R9xzwwAgArn6VCWTCYXNPqIXSWUAfC29t5+tfcczPUR98wAAKhQng5l886mf7h18wYdGAF4XlPLDu05dCTfPbMI98wAAKgsfghlC44w0oERgB8UuGdWq9Q9s70WygIAADn4IZQNZS5m4tctlQEAzlrkntn3jDEvWCgLAABk8UMoi2QupifpwAjAXwrcM3vJGDPocDkAACCL70JZdHTEUhkAYE9Tyw7t2p9zntlBY8wwDUAAALDHD6FsQQdGZpUB8KtgY1i7DwzkumfWIgZNAwBgjedDWTKZjEuaTK9nOL4IwMfqgyHt2j+gTeGW7I/Sg6ZpAAIAgMM8H8rmLdgt4wgjAD+rqg6os+9ZNW/vyv6IBiAAAFjgl1AWyVzQgREApLbuPhqAAABQAXwZyujACAApBQZN0wAEAACH+CWUDWUuYlfHLJUBAJWnwKBpGoAAAOAAv4SyeOaCZh8AsFBVdUC79g/kGjRNAxAAAMrMF6EsmUwuaPQRi47bKgUAKlZVdUDtvf3a2vFk9kc0AAEAoIx8Ecrmnc1cxKIcYQSAXLZ19Khj3+Fc98xoAAIAQBn4KZQtOMI4zRBpAMgrtKVVuw8MqKa2IfsjGoAAAFBifgplQ5kLdsoAoLD6YEh7Dh3J1wBkiAYgAACUhp9CWSRzQQdGAFhcVXVAew4dzdUAhGAGAECJ+DaUJW7esFQGALhPe29/rkHTtZLeNsb0O18RAADe4adQtqAD47XREVt1AIArNbXsUHvPwVwNQE4aY45bKAkAAE/wTShLJpNxSZOZz2Zo9gEAS9LUskO7DwzkCmbH6MwIAMDy+CaUzVuwWzbNEGkAWLL6YEhPHDqaqwEInRkBAFgGv4WySOYiOnrBUhkA4G41dQ3atX8gX2fGYRqAAABQPF+HMo4vAsDyFejM2KhUZ8adzlcFAID7+C2UDWUuOL4IACvX3tuvrR1PZj+ulfQanRkBAFic30JZJHNBB0YAKI1tHT25WuZLqc6MJ5yuBwAAN/FVKEsmkxHbNQCAVzW17NCu/Tk7Mz5vjBmkAQgAALn5KpTNO5u5iLJbBgAlE2wMa/eBAdXUNmR/dFCpe2YEMwAAsvgxlMUzF4m5WVt1AIAn1QdD2nPoCJ0ZAQAokh9D2VDmIhYds1QGAHhXVXVAu/YPaFO4JfujdGfGvRbKAgCgIvkxlC3YKaMtPgCUR1V1QJ19z+ZqmV8r6Xt0ZgQAIMWPoWw4c0FbfAAor/be/kKdGY87XA4AABXHj6EskrmIXeX4IgCUW1PLDnXsO5yrM+MxY8yghZIAAKgYvgtl2W3xb928YakSAPCX0JZW7T6Qs2X+QWPMKTozAgD8ynehbN6Ctvg0+wAAZ9QHQ9p9YCBXZ8anRMt8AIBP+TWURTIXiTl2ywDAKfXBkHbtzxnMaJkPAPAlv4ayBc0+oqMXbNUBAL6UbpmfozNjumU+wQwA4Bt+DWWRzMUtdsoAwHFV1QG19/bna5k/RMt8AIBfEMokfcKdMgCwpr23X23dfdmPa5Vqmd/vfEUAADjLr6FswfFFBkgDgF3N27sKzTI74XQ9AAA4yZehLJlMxjPXMwyQBgDrmlp2aM+hI7la5j/PLDMAgJf5MpTNO5O5YLcMAOxLt8zPM8tsmJb5AAAv8nMoW7BbNs1uGQBUhPpgSHufezFfy3xmmQEAPMfPoWzBvTIGSANA5Ui3zN/QGM7+qEVShJb5AAAv8XMoi2QuEnOzlsoAAORSVR3Q7tyzzNIt83c6XxUAAKVHKJsXHR2xVAYAoJD23n41b+/Kflwr6TVa5gMAvMC3oSyZTA5lrm+xUwYAFautu69Qy/x+h8sBAKCkfBvK5k2mf4hFx23WAQBYRFPLDnXsO5yrM+NJY8xxCyUBAFASfg9lC5p9cK8MACpbaEtrvpb5x5hlBgBwK7+Hskjmgt0yAKh8i8wyG7RQEgAAK0IoyzATv26pDADAUtQHQ3ri0NFcs8wYMg0AcB2/h7IFxxcZIA0A7lFT16Bd+wcYMg0AcD2/h7J45iJ2lQHSAOAmiwyZHmLINADADXwdyrLb4idu3rBUCQBguQoMmSaYAQBcwdehbN5nbfGvMUAaAFyrvbc/VzCrFcEMAFDhCGW0xQcAz2jv7Vdbd1/243Qw63e+IgAAFkcoywpltMUHAHdr3t6l9p6D2Y9rlRoy3e98RQAAFEYoy2r2wU4ZALhfU8uOXMFMSgWzF5yuBwCAQghldwyQpgMjAHhBU8sO7Tl0JNeQ6ZcYMg0AqCSEsqxQdmuODowA4BX1wZB2HxjIFcwOEswAAJWCUJYVyj5hpwwAPCUdzHIMmT5ojGHINADAOt+HsmQyGclc3+JOGQB4Tn0wpF37cwazTqU6MxLMAADW+D6UzRtN/0D3RQDwpqrqQL5glh4yTTADAFhBKEuJZC5m4hOWygAAlFNVdUB7Dh3NNWSaYAYAsIZQlhLJXExPEsoAwMvae/sJZgCAikEoS4lkLmbi1y2VAQBwyiLnCfdUAAAgAElEQVTBbLPjBQEAfItQlhLJXLBTBgD+UCCYDRtjWi2UBADwIUJZSiRzwZ0yAPCPPMGsVqkdM4IZAKDsCGUpkcwFO2UA4C/tvf3a2vFk9mOCGQDAEYQy3TmrLHaVAdIA4DfbOnrU3nMw+zHBDABQdoSyz302q+zWzRs26wAAWNLUsoNgBgBwHKHsc5HMRSzKbhkA+NEiwazf+YoAAF5HKPtcPHORmGO3DAD8qkAwO0kwAwCUGqHsc8OZC3bKAMDf8gQziWAGACgxQtnnsnbKZm3VAQCoEE0tO7Tn0BGtXrM2+yOCGQCgZAhln1uwUxYdHbFVBwCggtQHQ9p9YIBgBgAoG0LZ5+KLfwUA4EeLBLPjFkoCAHgIoWxeMplcsFN2jZ0yAECGAsHsmDFm0EJJAACPIJQtNGm7AABA5SoQzA4SzAAAy0UoW4h7ZQCAguqDIT1x6Kjqg5uyPyKYAQCWhVC2EB0YAQCLqqlr0K79AwQzAEBJEMoWYlYZAKAoVdUBghkAoCQIZQst2Cm7NXfDVh0AABcgmAEASoFQttCCnbJP2CkDACyCYAYAWClC2UJZO2XcKQMALI5gBgBYCUJZhuxZZbHouK1SAAAuQzADACwXoexOC2aVzcQnbNUBAHAZghkAYDkIZXdasFs2PUkoAwAUj2AGAFgqQhkAACVGMAMALAWh7E5DmYvo6AVLZQAA3IxgBgAoFqEMAIAyIZgBAIpBKLvTwg6MV5lVBgBYPoIZAGAxhLI7LZhVlrh5w1YdAACPIJgBAAohlN0pkrlggDQAoBQWCWanbNQEAKgMhLIsyWQykrlmgDQAoFQKBLOn2DEDAP8ilOU2ufhXAABYOo4yAgCyEcpyW9DsIzo6YqsOAIAHVVUHtOfQUYIZAEASoSyf+OJfAQBgZdgxAwBIhLJ8FuyUzcSv26oDAOBhHGUEAEiEsqJMT07YLgEA4FEEMwAAoSy3oczFrTlmlQEAyodgBgD+RigrwifRMdslAAA8jmAGAP5FKMttePGvAABQWosEsxds1AQAKD9CWQ7JZHJB98XYVXbKAADOKBDMXjLG9FsoCQBQZoSy/EbTP9y6yZ0yAIBzCgSzkwQzAPAeQll+kczFTJwOjAAA5xDMAMA/CGX5LTjCSFt8AIDTCGYA4A+Esvxo9gEAsI5gBgDeRyjLb8FOWXT0gq06AAA+RzADAG8jlOXHThkAoGIQzADAuwhlRaItPgDANoIZAHgToSyPZDI5lLlO0BYfAFABCgSzE8aYVhs1AQBWhlBWpFtzs7ZLAABAUt5gVitpiGAGAO5DKCvsbPqHWHTcZh0AACyQDmar16zNfEwwAwAXIpQVFl/8KwAA2FFVHdDuAwQzAHA7QllhkcxFdHTEUhkAAORWHwwRzADA5QhlhUVsFwAAwGIWCWabrRQFACgaoaywSOYiFqUtPgCgMhUIZqeMMXWWygIAFIFQVlgkc5GgAyMAoILVB0N6pLsv+3GLUjtmBDMAqFCEMgAAPKSpZYfaew5mPyaYAUAFI5QVNpy5oNEHAMANCGYA4C6EsgKSySQt8QEArkQwAwD3IJQtbjL9w0x8wmYdAAAsSVPLDm3teDL7cYukIeerAQDkQyhb3GdHGGcmCWUAAHfZ1tGjpm3t2Y9bjDGDFsoBAORAKAMAwOPae/tzBbODBDMAqAyEssXR7AMA4HoEMwCoXISyxdHsAwDgCQQzAKhMhLLFLQhlM/HrtuoAAGDF2rr7VB/clP2YYAYAFhHKFrfg+OI0zT4AAC5WVR3Qrv0D+YLZCRs1AYDfEcoAAPCZAsHseWNMv4WSAMDXCGWLi2QuYlfHLJUBAEDpFAhmJwlmAOAsQtkikslkJHOduHnDUiUAAJRWOpitXrM2+6OTxphWGzUBgB8Rypbo1tys7RIAACiZquqAdh/IGcyGCGYA4AxCWXHOpH+IRcdt1gEAQMnVB0O5glmtCGYA4AhCGQAAUH0wpEe6+7If10oaNMbUWSgJAHyDUFacSOYiFqXZBwDAe5padqi952D24xaldswIZgBQJoSy4kQyF4k5mn0AALypqWWH2u7cMWuRNOR8NQDgD4SyZUjQ7AMA4GHN27vUtK09+3GLMWbQQjkA4HmEsuIMZS44vggA8Lr23v5cwewgwQwASo9QBgAAcmrv7c81XPqgMeYFG/UAgFcRyooTz1zMxCds1QEAgKN27R/IFcxeMsb0WygHADyJUFaEZDI5nLmeniSUAQD8oao6kC+YnSSYAUBpEMoAAEBBVdUBtff2Zw+XlqQTDJcGgJUjlBXvbPqHa6MjNusAAMBx9cGQdh8YyA5mtUrNMCOYAcAKEMqKF1/8KwAAeFd9MKTOvmezH6eD2WbHCwIAjyCUFY9mHwAA3ws2htXeczD7ca2kU8aYOgslAYDrEcqKR7MPAAAkNbXsyBXMWpTaMSOYAcASEcoAAMCSNbXsUPP2ruzHLZJOWSgHAFyNUFa8BTtl0dELtuoAAKAitHX3qWlbe/bjTmPMoIVyAMC1CGXFo9EHAABZ2nv7cwWzg8aY4xbKAQBXIpQBAIAVaevuyzVc+hjDpQGgOISy4kUyF7GrY5bKAACgslRVB7Rr/0CuYHbSGLPTQkkA4CqEsiIlk8lI5jpx84alSgAAqDxV1QG19/ZnD5eWUq3yGS4NAAUQygAAQEnUB0PafWAgO5gxXBoAFkEoW5rR9A8cXwQA4E71wZAe6e7LfsxwaQAogFC2NJH0D7c4vggAQE6Fhks7Xw0AVD5CGQAAKLl8w6WZYQYAdyKULU0kcxGLcoQRAIB88gyXPkgwA4CFCGVLE8lcJOY4wggAQCHtvf25WuUfZIYZAHyOUAYAAMqqwAyzfgvlAEDFIZQtTSRzwfFFAAAWlx4unWOG2QlmmAEAoWypIpmLxNyspTIAAHCXqupAoRlmBDMAvkYoAwAAjqgPhtTZ92z2Y2aYAfA9QtnSRDIXDJAGAGBpgo3hXDPMGpXaMSOYAfAlQtkSJJPJSOY6wQBpAACWrKllh9q6+7Ift0gadL4aALCPUAYAABzXvL0r1wyzp5hhBsCPCGVLN5n+YSY+YbMOAABcrb23X5vCLdmPDxpjjlsoBwCsIZQt3XD6h5lJQhkAACuRZ7j0MWaYAfATQhkAALAmPcMsRzBjhhkA3yCULV08c8ERRgAAVqaqOqD23v58M8zoyAjA8whlSzecuZjmCCMAACtWYIYZwQyA5xHKAABARcgzw6xF0gkL5QCAYwhlS5d1fPG6rToAAPCcppYduVrl05ERgKcRypaO44sAAJRRe2+/NjSGsx/TkRGAZxHKAABAxencd5iOjAB84y7bBbgQ3RdhXWJuVuMXhhWLjuv6+EXFf3tZ/3YrobtWV+me+gZJUuCeen2xsVkNG39PwTv/jfOKzcQnNDYyrPiVUU3Hrys6dlGSdPc9tbr7ntSd/PpgSHUb71f9l0KqD4ZKXkMsOqaxC8Oaujamiavjmpr/7+OGjZtUXR1QUtK9obDWbQhpfTCkmrqGktcAoDzSHRl/8H/+jW7dvJF+nG78sTmZTMYL/HEAcBWTTCZt1+A6xpjP/o+2oTGs3fsHbJYDH5mJT2j4h/+PoqMXtHbtWq1ZvUrr1q1TIBDQqlWrFnw3kUgoHo/r0+lZJW7dUqj5YT3w0GMrDkdjF4b10fCPFLs6po33fUkNDevV0NCgjRs33vHdSCSiy1eu6vKVq0p+YZWaWh9XKNy6onCUDqQf/OK0Vn9BerB5izZt2qRQKKRQaOF/ttnZWQ0PD+v9CyMauTCiuuAm3ff7rdq0pVVV1YFl1wDAOdHREf3r3/9N9uOzknYSzAB4BaFsGQhlcFosOqb3fvL/KR79WA1161RXt7Tu0IlEQtevX1csPqkNvxvWw7v7lhyMLp19Q+fO/JM2btyoRx7apnXr1i3pz09MTOidd97V5StX1dSyQ1t37l3Sn0/Mzer8W6d19YNh7d7Vpa893KpAYGnBanh4WD/6yRv6+ONxte7uU2gLp6AAN7h09g29+erfZT/+u2Qy2W+hHAAoOULZMhhj4kodoVBNbYP2Pvei5YrgVYm5Wb3xyn/RZHRMG7+0YclBKJeJiQlduRrV7zY/pNZd+xbdMYpFx/TmK/9F99QEtOMPvrbiGhKJhN555x19NDqmh7/xZwr+3pcX/TNjF4b1s1cH9Yd/1KVv7O5achjLNjExoVP/9KquXJtQ255+jjUCLvDmPw3q0rk3sx//j8lk8riFcgCgpAhly2CMGZLUmV4/feS79oqBZ0VHR3TmH/5nffGLX9R9XwqW/PdPTEwo+tvrav2jb6upZUfO75x/67TeOfOKdnZ2avPmzSWv4Y03f6rfxqe1deef5Lz3lpib1fAPXtb09TH9+TP9dxxPXKnZ2Vn9T//L32pVTYO+8ngP4QyocD/4+7/RtdGR7MfPJJPJQQvlAEDJEMqWgVCGcrt09g19+MvXdG9tzYp3hQpJJBIa/XhMv9fyqL7a0bvgszdfOam1X0joaw9tU1VVVdlquHz5st746c/08DeeXrBrlpib1Zv/+Lf6g0datXtXV9neL0k/+NfT+ukvhtX+7cPcNQMqWGJuVv/693+jWHQ88/GkUvfLhvP8MQCoeISyZSCUoZw+/NXr+mj4jEL3lX53LJ8rV6P691Vr9HjfX6qqOqCfvvK/a9O9tdry+02OvD+RSOi1M6+r9nd+X1t3fuuzQNb/dF/Jd8fyGRsb03/9by9ra1ef7tngzDsBLF0sOpbdkVFKBTM6MgJwLULZMmSHsr1/+SLHnlASH/7qdX30q9cU+p37HH/31NSUrkSvqy74O2raeK+2hH/f8RreeffXuhgZ1+qq1XrmP37HsUCWNjs7q//2Dy8rPid97cl+R98NoHh0ZATgNQyPXp4FRySmJ5lVhpWzGcgkad26dVq75i41bqi1EsgkaUv497Xa/JuVQCZJgUBAf/5Mv9ZXSz///qDj7wdQnGBjWO09B7Mft0g6YaEcAFgxQtny8G/hUFJXLr5rNZBJqeN7zc3NevDBB628P5FI6Ic//KGeeeYZK4Es0zPP9Ovr28J67b/+jRJzs1ZrAZBbU8sONW1rz3580Bhz3EI5ALAihDLAsuu/uaTzP3qlIgJZc3OzlfenA9mBAwesB7K0xx7dof/0H/v05j/+LcEMqFDtvf3acGfn1mPGmH4L5QDAshHKSiAWHbNdAlwqFh3Tz175P3Rf8Iv2aojFdO+991oLZJL01ltv6YknnqiYQJYWCoXU/zTBDKhknfsOqz64KfvxSWMM0+EBuAahbHkWHF/kL2tYjsTcrH74f52wukM2NTWlWCymxx57zFoNw8PDCgaDam2tzL8/pYPZL/77oO1SAORQVR1Qe2+/Vq9Zm/3RkDGmzkZNALBUhLLlYRYKVuxH//f/qt+5L1jWGWCF3L59W+Pj4/rmN79p5f1SakbZb37zG33nO9+xVkMxQqGQgrUBnTv9su1SAORQHwxp94GB7Me1koacrwYAlo5QBlgQOfemkjenVVdn71/ijo6O6rHHHtO6deusvD+RSOjHP/6x/uIv/sLK+5fqmWf6VZOc1W9+/YbtUgDkUB8M5ezIaIwZtFAOACwJoawEYle5U4biJeZm9e7rr2jT72y0VsO1a9e0ceNGbd682VoNp0+f1p/+6Z+qocE9M/6eeaZfc1dG9Ok1/jsPVKICHRlfsFEPABSLUFYCiZs3bJcAF/nJP/6tfjd0x6V0x8zOzmp6elqPPvqotRp+/etf64EHHqjYe2SF/If/0Kdf//BlzcSZTwhUovbe/lyNP14yxuy0UA4AFIVQtgzJZHLIdg1wp3df/ydVJRPW7pFJUjQa1R/90R9Ze//ExIQuXbqk3t5eazWsRCAQ0HN/cVi/+n8HafIDVKhd+wdUU3vHLvwpOjICqFSEMsAhM/EJXRl52+pxvU8++UThcNhqDT/60Y/053/+5woEAtZqWKlAIKADf9anX9KREahIVdUBdfYdzu7IWCtpkI6MACoRoawEro2O2C4BLvDG9/43bfzSBmvvTyQSunXrlrZt22athrfffltf+9rXKm4e2XKEQiHt6tyh9370qu1SAORQHwzpke6+7MctkgadrwYACiOUAQ6InHtT66pXadWqVdZqmJ2d1eOPP27t/YlEQuPj4649tphL20OtumtuQpdHmJIBVKKmlh3a2vFk9uOnjDHHLZQDAHkRypZv1HYBcIfE3Kw+Gj5jtf39zZs39cUvftFa+3vp82OLXvNn3+nT+z9+VbEoHRmBSrSto0ebwi3Zj48ZY/otlAMAORHKli+SueDCP/J558wr2rC+1moNc3NzVo8tRiIRhcNhTxxbzBYIBPQ//Kd+/eL7g7ZLAZBHno6MJ2j8AaBSEMpKJBYdt10CKlB0dEQ3Y1esHlucmJhQS8sd/5bYMYlEQufOnVN3d7e1GsotFArpkYdbuV8GVKiq6oDae/tzNf44ReMPAJWAUAaU0btnTml97d3W3p9IJFRdXW212+JPf/pTPfXUU67utliMp3p7NPmbEY4xAhWqPhhSZ9+z2Y8bJQ05Xw0ALEQoW7647QJQ2Ubf+7nW19q7wyWlji3+wR/8gbX3T01NadWqVXr44Yet1eCk5/7isN45/bLtMgDkEWwMqy1HR0ZjzKCFcgDgM4Sy5VvQbo07ZciUmJvVlZG3tbbK3rHFmzdv6r777rM6qPqtt97S008/be39TgsEAur7kx5d/Plp26UAyKN5e5eatrVnPz5I4w8ANhHKSoQjS8j03k/+WQGTsFrD7du31dzcbO39ly9ftj6o2oZwOKxbsTHNxCdslwIgjzyNP07S+AOALYQyoMRm4hOKX7lkdYdqdnZW999/v7X3S9I777zj6eYehXx7b49+/cN/sF0GgAJ27R/IbvwhSUPGmM3OVwPA7whlQIn96gcva/26O/5B76i77rpLGzdutPb+Dz/8UJ2dnZ5v7pFPQ0ODWr6yRSMcYwQqVlV1QLsPDGQ/piMjACsIZcu34E4ZR5UgpVrg/9vMJ1Z3yaampvTVr37V2vsTiYQuXbqkRx991FoNlWD3ri5dvzjMfVOggtUHQ2rvOZj9uEXSCQvlAPAxQtnyLei+OD1JKEOqBf6Ge9dbe//t27dVV1endevsdX1877339O1vf9va+yvJt57q0S//+6DtMgAU0NSyQ83bu7IfHzTGHLdQDgCfIpQBJRIdHdFdum11UPSNGzf04IMPWnt/IpHQ9PS0wuGwtRoqSTgcVuhL9+ryyPDiXwZgTVt3nzY03vG/W8eMMTstlAPAhwhlQIm8e+aU7l1v7xrC7du3VVtba/Xo5Hvvvac//uM/tvb+SrS390n96gcvc4wRqHCd+w7n6sjI/TIAjiCULV8kcxG7Skt8P4uOjqhmzWp2ydglu0MgENCffadP5xgqDVS0quqA2nv7szsy1koaslMRAD8hlC1TMpmMZK5v3bxhqRJUgvNv/rPq7qmx9n52ySpba2urbk1N0BAIqHD1wZAe6e7LftxijKHxB4CyIpQBKxQdHdEa8+9Wa2CXrPL9yVM9Onua2WVApcvT+ON5Y0y/hXIA+AShDFihi798jV0ydskWFQ6H9cXagKKjI7ZLAbCItu6+XPfLThhjWm3UA8D7CGXACkRHR7R2Fbtk7JIVZ29vjyK//FfbZQAowq79A7nulw3S+ANAORDKVmYyc8F9Ef/5+J03tLbKXnMPdsncpaGhQeHfCynyzhu2SwGwiKrqgHYfGMh+zGBpAGVBKFuZBcOHGCDtL9HREd11226Dl08++YRdMpfZvatLY++8absMAEWoD4bUdmfjj4PGmBds1APAuwhlwDK9e+aULG6SaWpqSuvXr2eXzGUCgYA6H2vXez961XYpAIrQvL1LTdvasx+/xP0yAKVEKAOWITo6ort02+pcsng8rtZWe38nYJds+R57dIduTIwxUBpwiTyNP4a4XwagVAhlwDK8e+aU7l1v75/Fs7Oz2rhxo9VdsosXL7JLtgJPfGOXzv/k+7bLAFCEAoOlT1kqCYDHEMpWJp65mIlft1UHHFQJu2SxWExf/vKXrb1fksbGxtglW4FwOKyq27M0CAJcoj4YUntvf/bjTgZLAygFQtnK0OjDh2zvkiUSCQUCAa1bt85aDR9++KE6Ojqsvd8rvr23R+//hLtlgFuEtrRqa8eT2Y+fN8bstVEPAO8glAFLEIuOWd8lm5iY0Ne//nVr75ek8fFxPfroo1Zr8IKGhgbdvZpxGoCbbOvo0YbGO04JDBpjNjtfDQCvIJQBS/Du699Xfa29Harbt29LktVdssuXL+v++++39n6vYbcMcJ/OfYdVU9uQ+ahW0ikafwBYLkIZUKSZ+ITmpq5bba4xMTGhhx9+2Nr7JWlkZETd3d1Wa/ASdssA96mqDqiz73D2YwZLA1g2QtnKZDX64C9VXvarH7ysYEO91Rpu376tjRs3Wnv/xMSE7r//fgUCAWs1eBG7ZYD71AdDau85mP34oDGm30I5AFyOULYyNPrwiUrYJYvFYnrggQesvV+S3n//fT3++ONWa/AidssAd2pq2ZFrsPRJBksDWCpCGVCEStglm5ycVHNzs7X3T01NKRAIqKGhYfEvY8nYLQPcqb23P9dgae6XAVgSQhmwiMTcrG5Ox6zuksXjcX3lK1+x9n5JOn/+vL71rW9ZrcHL2C0D3Ktz37PZg6UbxWBpAEtAKAMW8d5P/lm1NWus1jA1NaWmpiZr708kErp58ya7ZGX27b09Onv6H2yXAWCJauoa1Nn3bPbjTmPMcQvlAHAhQlkJ3ZqbtV0CyuDa6HmrLegTiYTWr19vdafu448/Vmdnp7X3+0VDQ4NCwXvZLQNcKNgYVlt3X/bjY8aYnRbKAeAyhLIVSCaTQ5nrWHTcUiUolw9/9brurrYXhiTpt7/9rR566CGrNVy6dEmtrdxbd8I3u7u4Wwa4VPP2rlyDpblfBmBRhDKggNF3f6r19bXW3n/79m2tWbPG+rBo27PR/IS7ZYC7de47nH2/rFbcLwOwCEIZkEcsOqa7dNtqDZOTk9q6davVGkZHR2mD7zA6MQLulRoszf0yAEtDKAPyePf176u+1t4OlSR9+umnVodFT01Nac2aNQyLdhi7ZYC7BRvD2trxZPZj7pcByItQVmIJmn14QmJuVrdmJ60215iamtL9999v7f2SdPHiRX3zm9+0WoNffXtvjy7+8rTtMgAs07aOHu6XASgaoWzlzmQuaPbhDR/8Ykjr1q62WsP09LQefPBB6zWEQiGrNfhVQ0ODbk1d51/0AC7G/TIAxSKUATl8/N5b1tvgV1dXW92p+/DDD/XII49Yez+kJ76xSx/+nN0ywK24XwagWIQyIMvYhWHV3l1jtYaJiQl9/etft1rD+Pi4Hn30Uas1+F04HNaNiTF2ywAX434ZgGIQyoAsIz/7F9Xec7ftMqy3wbd9nw0p7JYB7lfgftlm56sBUIkIZSXGv9F2t5n4hL7w77e0atUqazXEYjF99atftfZ+SYpEIuru7rZaA1LYLQO8gftlAAohlK3cUOYiFh2zVAZK4dc//r4aLA6LlqSZmRlt3rzZ2vsTiQRt8CvMHz6+Q5c/GLZdBoAVyHO/rMUYc8JGPQAqC6EMyBC7+rHV5hqzs7O67777rL1fkt577z3t3LnTag1YqLW1VWPvvGm7DAArFGwMq3l7V/bj540xe23UA6ByEMqAeR/+6nWtC1RbrSEWi+nLX/6y1Ro+/fRThcN33H2AZW0Ptyo6OmK7DAAr1Nbdp/rgpuzHg9wvA/yNUAbMG333p1pv8eji7du3tWbNGqsNPiKRiLZv327t/civ49F2RX75r7bLAFACnfue5X4ZgAUIZYA+b/Bh06effqotW7ZYreHKlSt66KGHrNaA3AKBgDZuuFcz8QnbpQBYoZq6BrX39mc/5n4Z4GOEMkA0+JCkqakpGnxUuG92d+n9n7xquwwAJRDa0sr9MgCfIZQBosGHJJ0/f17f+ta3rNaAwhoaGrT2LkZvAF7B/TIAaYSylYtnLjha5D5jF4atN/iYnJy03uDj5s2bamhosFoDFtfVsYNh0oCHcL8MgEQoK4UFw4OmJwllbnPp7TOqvedu22VYbfDx4Ycf6pFHHrH2fhQvHA5r9jrzEAGvKHC/bND5agDYQiiDr83EJ5SY/VSrVq2yVkMsFtMDDzxg7f2SND4+rkcffdRqDSje9rZWRd55w3YZAEokz/2yg9wvA/yDUAZf++CXQ2qotbdDJUnT09Nqbm629v6JiQndf//91t6PpXvs0R2KfjC8+BcBuEaB+2V1NuoB4CxCGXzt2uh5q90GE4mE1q9fb+39kvT+++/r8ccft1oDlu6BzSGGSQMew/0ywL8IZfCtsQvDurvaXsdFKbVLZXMuWCKRUHV1NQ0+XOgbu7v0m19zhBHwkpq6Bj3S3Zf9uNMY84KNegA4h1AG36LBh/Txxx/r61//urX3Y/kCgQDt8QEPamrZoaZt7dmPXzLGtNqoB4AzCGXwpcTcrG7dmLHa4CMej1dEg4/WVv4571Z/+Djt8QEvauvuU03tHScYBi2UAsAhhLKVW3DbPnaVVtVu8MEvhlRbs8ZqDTdu3FBTU5O199Pgw/1ojw94U1V1QJ19h7MftxhjTtioB0D5EcpWKJlMLhgefevmDVulYAk+fu8tq8cG03e5qqrs3Wm7dOkSDT48YHtbq8Yu0IkR8Jr6YEhtd94ve94Ys9NCOQDKjFAG34lFx7Tu7hqrNUxPT1tt8CFJN2/epMGHBzz8UKsu0/AD8KTm7V3a0BjOfnyKNvmA9xDK4Dvvvv593VOzdvEvltGnn35qNRBFIhE98sgj1t6P0gkEAtq44V7NxCdslwKgDDr3Hc7VJn/QTjUAyoVQBl9JzM3q1uyk1WODU1NT1u9yXQMJuPIAACAASURBVL582fpOHUrnm91dev8nr9ouA0AZpO6XPZv9+Cna5APeQiiDr3z83i8UqLL7//ZTU1N68MEHrb0/kUhozZo1Vodmo7QaGhpojw94WLAxrObtXdmPjxtjNjtfDYByIJTBV0bf/anq6uwdxb99+7aqqqqs7tR9/PHH2r59u7X3ozzaH2nV5Q9o+AF4VVt3n+qDmzIf1Uo6ZakcACVGKINvzMQn9IV/v2W1hk8//VRbtmyxWgOzybyptbVVY++8absMAGXUue/Z7PtlLcaY45bKAVBChLLSOJO5iI6O2KoDBfz6x99XQ32t1RpmZma0efNma++fmprSfffdZ+39KK+2h1v53x/Aw2rqGvTInW3yj9EmH3A/Qhl8I35t3OqxwUQiofr6emvvl6SLFy8ym8zDOh5t1xXa4wOe1tSyQ03b2rMfD9ImH3A3Qhl8YezCsO6uthfIJGliYsJ6x8NPP/1UoVDIag0on0AgoOq7RHt8wOPauvtUU7tgrEqjaJMPuBqhDL5w6e0zqr3nbttlaN26ddbePTExYbXrI5zxx91dGn2H3TLAy1Jt8g9nP37KGLPXRj0AVo5QBs9LzM3q1o0ZrVq1yloN8XhcDzzwgLX3S9L777/PwGgfCIVCmr0+ZrsMAGVWHwyp7c77ZYO0yQfciVAGz/vgF0OqrVljtYYbN26oqanJag3V1dVqaGhY/Itwve1trRq7QHt8wOuat3dpQ2M481GtOMYIuBKhDJ535cNzVo8NVsJsskgkoq9+9avW3g9nPfxQqyYuEsoAP+jcdzi7TX4nbfIB9yGUlUYkczETv26pDGSLRce0+gtJqzVMTk5aD0RXrlyx3mQEzqHhB+Afqftlz2Y/PmaMYSAl4CKEstKIZC6mJ/mLUKX44Oc/VH2tvV0ySZqdndXGjRutvT+RSKiqqkqBQMBaDXAeDT8A/wg2htW8vSv78Sna5APuQSiDpzGbLDWbbOfOnVZrgPNo+AH4S1t3n+qDmzIfNUo6bqcaAEtFKINnxaJjClieTTY9Pa2vfOUrVmuIRqMKh8OLfxGeQ8MPwF869z2bfb/seWPMTkvlAFgCQhk864Of/1D31Kxd/ItlNDs7a7Xj4dTUlO677z5r74ddNPwA/KWmrkHbOnuyH3OMEXABQhk8K3b1Y6tHF2dnZ60HovPnz+sb3/iG1RpgDw0/AP+hTT7gToQyeNLYhWGtC1RbrWFyclJf/vKXrdZw48YNZpP5HA0/AP/Z0dOffYzxKWPMXlv1AFgcoQye9NHZH6v2nrut1pBMJq3OR7t8+bIefPBBa+9HZQiFQroxQcMPwE/yHGMcNMZsdr4aAMUglMGT/u3GtFatWmXt/bOzswqFQtbeL6UGRj/++ONWa0Bl+NrDNPwA/IZjjIC7EMrgOWMXhlW92l4gk1JHF++//36rNTCbDGk0/AD8qXPf4exjjJ3GmBds1QMgP0IZPOfS2/8/e/cf1GZ+34v+/RgjZAmBhLBlMEJaMAL/AAR47TVrYydOvHXO2tkk3fXe9OyGM73N3mR6Jz7Tuf90zkx9p70zt9ObGZ+2p709aXrcm9PbdtOcutlNb7K77m78A8deY+Rf2MgGA8JgsB8jEDyAbFb3D1ZE/LL5IfR5JL1ff5mn3jyf2eI1H33fn8/3l+LRRQCi0cW7d+9i+/btYu8nfeHCD6L0ZDCasPtI4+zHxxVF8QqUQ0TPwKaMUkp4XMOTsVHR6GIwGMTmzZvF3g8ADx8+xMsvvyxaA+kLF34QpSdnuRdFnurYR4wxEukQmzJKKd2tl5FtXCtag6ZpKCkpEXt/OBwWvQqA9MnpdEJ7xIUfROlo95E52xirFUU5LlQOEc2DTRmllPv+FlitsndkGgwG0aaovb0d+/fvF3s/6dfWLeXo7/JLl0FECbZAjPEPGGMk0g82ZZQyotFFScFgEC6XS7SG/v5+eDye5/9GSjsNL+/G/ZuMMBKlI2e5FyVVu2c/PqUoiuwnmUQEgE1ZvASlCyBGFwEgFAqhoKBA7P2kbyaTCevWTn2AQUTpp+7gGzDn2mMfuQAcl6mGiGKxKYsP7prWgc5rTaLRxcnJSWRlZYlGF3t6evDKK6+IvZ/07wt76xG4fkG6DCISsECM8XuKouxPfDVEFItNGaWE0aCKDEyK1jA8PCweGxwaGoLdbn/+b6S05fF4oAbapMsgIiEOlwcVOw/MfswYI5EwNmWUEjpvXESuxSxaw/j4ONxut9j7Q6GQ+IXVlBxK3U4M9nMTI1G6qmx4dXaMkWvyiYSxKaOU0Hf3Gkwmk9j7JycnxdfQ9/T04MUXXxStgZJDw556tF8+LV0GEQlZIMb4VUVRXhMoh4jApoxSwGhQhcko2xANDw+jrq5OtAZGF2mx7HY7F34QpTmHy4PKhldnPz6pKIo78dUQEZsySno3z72P7HWyTdno6KhoQ8ToIi3V7h1e9N7hjiKidFbVcBg2R1HsI8YYiYSwKaOkFxzoEY0OhsNh2Gw2sfcDjC7S0nm9XvSzKSNKe/PEGPcpinJMoBSitMamjJLaYH9APLo4MjKCbdu2idbA6CItR+GGfIwGVekyiEiQzeGcL8Z4XFEUr0Q9ROmKTRkltTuf/htsOdmiNTx58oTRRUpKDXt2o+t6k3QZRCRsgRjjCaFyiNISmzJKahMjQWRkZIi9PxwOY+PGjWLvBxhdpOVzOp3QHnE1PhFNxRgzs9bFPmKMkSiB2JRR0urv8iNT+Uy0hmAwiLKyMtEaGF2kldi6pRz9XX7pMohImM3hRMWuOZdKH+c2RqLEYFNGSavt4gewmI2iNTx9+hQWi0Xs/Ywu0ko1vLwb928ywkhywuMaOq424dqZ98RqGA2quH3pNDquyv1ZGOwP4NqZ90Qvduc2RiI5a6ULIFq2p2FkZMjNk2maJt4Q9fT04NChQ6I1UHIzmUzIypj6wdhglLuAndLLaFBFwO9D981P8fD+PZizLcgy56Cq4XDCahjsD6DDdx79XbcxGnwMQ5YBlfu/nrD3A0CgzYc+vw/9XX6YzeswNjaGip1zTqsSaveRRvzrD/4o9tE+RVGORSIRzpgRrSI2ZZSUAm0+ZAl/9w4NDWHXrl3iNTC6SCu1e4cX1+744K6sly6FUthgfwAdVy+gr+MmRocew2bLQ47FjE1eL1RVRcHW1f/+C7T5cP/2FfR3tQGRz+B2FePlnXUoLCzEx2cvoKR6dWsIj2voafOh744PfZ1+lHk8qK/xovzoYdjtdvzpX50U/3Akuo3x+pn3Yx8fVxTlVCQS6RQqiyjlsSmjpNRz6zJsFtmti+vWrRO9H43RRYoXr9eLD3/5F2zKKO4CbT4EbjXjQWcbIpNPkZubA0deDiyuTTN+3+PBIF6qfCnu7482QT23m9HffRfZlmyUl5XB++UDMz7QCofD+Cxjdf57Hj0V7PP7oD4IoNrrxaEv1MPjaYTJ9OsGzOfzwer0rEoNS1XVcBgdVy9gdGj6yoxojHG/VE1EqY5NWRxEIpFPFEWZ/ppD86vviTYMZMlGFwsKCsTeDzC6SPEVvbPMbOXJKy1ftAnqbr2M/sBdGLOMsFlz4HYWzmhAZvwz4TCyrflxOyGKNkE9t5rRH2iH64USlLqKsWdH5YIzwPc6u7Bpy864vB+YOhW8d+0CHna34en4GGpqvNj/jcPweBZuui42+1Da8Ebcalip3Uca8dGPvh/7aJ+iKI2RSOSkUElEKY1NGSWdjqtNMAtnF0OhkHh0MRQKMbpIcdOwZzd+drYJW/cmbqaHUkO0Cbp75SyGHvUhL38DcrJN2FLuWVSaIBgMwrVtZae00fmwnrYWhMfH4Ha7Ub2lFIUH9i6qht7+R9i5Z2V3JUfnw7rbfMiz27H35Xp4vtwIp9O5qH9+4inEo4uxHC4PKnYewO1Lp2Mfn/g8xhiUqosoVbEpo6TzoP068kyyWxeNRqNodFFVVWzbtk3s/ZR6pu4sk9t+R8klOh/W1XoZTybGYLPlIT/XjM2uuiX/by03uhidDwv4r8JgMMDtKsYrs2KJi7Hc6GLsfFjn7avYXlWN+hovvtv4xoKnggvRU3QxVmXDqwi0+eaLMb4mVhRRimJTRkklPK4hrA0D63LFaggGg3jhhRfE3g8AHR0dePvtt0VroNQTvbPM4dLfD4ckLzofFvBfxdqMtcjNfXYscTGWEl2MnQ8L3LmBvPx8lJeVYefXv7aiq0mWEl2Mngp2XW9CaFCdng/z/sfvLvv9gP6ii1EGo2m+GONXFUV5LRKJnJKqiygVsSmjpNLdehk56zJFawiHwygpKRGtwWg0rugHIaL5NLy8G//1R++yKSMAUw1If1cbulsv4377TWRbcmGz5iw6lrgYz4suDvYH0N/lR4fvLAYH+qbnww683Bi3Gp4XXezv8uO+34f7bT6sUYCaGi/+l99efCxxMfQWXYzlcHlQUrUbHdcuxD4+qSiKmzFGovhhU0ZJZaDzFvKEm5GsrCzR96uqKt4UUmqK3llG6SvaBN29chajQypycq3IyTbB6/UiIyP+3xzzRRf7u/zouX0FPW0tQOQzFBYU4EVvJdzu+M87zhddDI9r6O/yz5kPe+urv7cqc7x6jS7Gqjv4BgJtPjyZGIs+YoyRKM7YlFHSYHRxCqOLtJoqt3jQ1eaDs3xlSw8oefR3+dHT5kNX62VEJp/CYrF8Ph9WuKrvjUYXgZnzYdkWCwo3OpY1H7ZU0ehi9FRw9v1hy5kPWyq9RhdjRWOMZ378l7GPGWMkiiM2ZZQ0GF2cwugirabaGi8u/+hdNmUpLHoSFJ0PM2YZYTabVjwftqQawmH09fUBa4348f/1H1FQuAluV/GK58OWQlVVtPnv4mnbHTwdH4On3DM1H+Zd2XzYUikGk26ji7Gc5V4UearR478a+5gxRqI4YVNGSYPRRUYXafUxwpiaogsqHrTfxP32m8i12Ze0tj4eNE1DMBhEKBTCxMQEHI6N2Ly5FO7f+FLCaujs7MSDBw/Q1dUFk8mEivJy7NmzJ67zYUsRCARgtheJvHs5dh9pxKk/+/3ZMcYTABrFiiJKEWzKKCmMBlVMjAwC6/LEahgcHBRviG7duoXf+Z3fEa2BUt/uHV7c9vtQ6OFpWTIb7A8g0OZDd2szRodU2Gx5MJuMqzYfNp9gMIjR0VEMDQ1BURSUlJSgsrISbrc7Ie8Ph8PTjdi9e/fgdDpRW1uLN998Uxf3PJ45dwGOHa9Kl7FoBqMJVfsOo/mDd2Mff0tRlJORSOQTobKIUgKbMkoKnTcuItcsezfZ+Pi4eFPG6CIlgtfrxcX/5102ZUko0ObDQJd/ej4sNzcH+bmmVZ8Pi5qcnEQwGISmaXj8+DEsFgtKSkrw8ssvJ6wJCoVC6OzsxMDAAO7fv4+qqirs2rUL77zzju7++zmq462LC6nYeWD6+yzGSUVRvIwxEi0fmzJKCn13r6HIIXdKNjk5KXpZNDAVu9m+fbtoDZRGnmgIj2tJ9wNjuone3fXg3q3p+TBLduLnw6KNmKqqKC4uRmlpKQ4cOJDQ+bDOzk4EAgGEw2HU1NTg4MGD8Hr1+8FCskUXY9UfbsTPfvCHsTFGF4DjAI6JFUWU5NiUke6NBlVkYFK0huHhYXg8siuLe3t7cejQIdEaKH3sqvPi2h0f3JUL3yFFMqLzYd03P8XD+/eQl78B5nVZCZ8PGxwcxMjICCYmJuB2u1FaWgq3253Q+bDu7m709fXBZDKhrq4Ohw4dEpsPW6oz5y4gb/sB6TKWxWy1zxdj/J6iKKcYYyRaHjZlpHudNy4i12IWrWF8fDxhMxALMRgMuoveUOryer04c/EkwKZMFwb7A+i4egF9HTcxOvQYNlsecixmbErwfFgoFEIoFJqeD9uxYwcKCxMTjYzOhwUCAfT09MDj8aCqqgpvv/22LubDlqpv4BGc1uSrO4oxRqL4YlNGusfoIqOLJMOeY2KEUVCgzYfArWY86Gybng9z5OXA4tqUkPdH58NCoRCGhoZgsVhQUVGBwsLChM+HBQIBPHr0CFVVVdizZw+8Xm9Sf0gVCARgd5ZLl7FiOw6+gX/9wR/FPmKMkWiZ2JSRrjG6OIXRRZLQsGc3zlz3wcnTsoSIzod1t15Gf+AujFlG2Kw5IvNhoVAIwWAQxcXFqKysREFBQULnw+7cuYMHDx5Mz4cdPXpU/L/D8XTm3AVsTNLoYiybw4nKhldx/cz7sY8ZYyRaBjZlpGuMLk5hdJEkOJ1OjH5yQbqMlBadD7t75SyGHvUhL3+DyP1hg4ODGBoawtOnT+F2u7FlyxYUFhYmfD7s3r17yMvLw969e3HkyJGkmQ9bqmSPLsaqajiMnjYfBvt7Yh+fBOAWKYgoSbEpI11jdJHRRZJlXgtGGOMsOh/W1XoZTybGYLPlIT/XjM2uuoTVED0Ne/z4MQwGQ8LX1sfOh7W3t6OyshK7du1K2vmwpVBVFetdyR9djLX7SOOcGKOiKMcjkchxoZKIkg6bMtItRhenMLpIkn7j4AG8f/YCXqhL/qiVpOh8WMB/FWsz1iI3N7GxxNj5MFVVYbPZUFFRkdC19dH5sPb2dgwPD6OqqgoHDx6Ex+NJqyTAp1d82FCq31X9y7FAjPHY55dKdwqVRZRU2JSRbjG6OIXRRZJkt9sx+jAgXUbSGQ2q6O9qQ3frZdxvv4lsSy5s1pyExxJHRkamV9dH58MSuba+t7cX3d3d6OrqgqIoqKmpwVtvvSX+YZekjs4Atlek3occFTsPoOPqBYwOqdFHuZiKMe6XqokombApI91idJHRRdKHErcTo0EV5hSZgVktg/0B9Hf5cffKWYwOqcjJtSIn2wRvAtfWh0IhDA8PY2hoCIqiYNOmTaivr0/Yh0vhcHi6Ebt37x7sdjv27NmDN998M+VjiYuhqirM61NzTs5gNGH3kUZ89KPvxz7epyjKa5FI5JRUXUTJgk0Z6RKji1MYXSQ9eLHWi/fP+hhhnEd/lx89bT50tV5GZPIpLBbL5/Nhibm7a3JycvrusMePH8NisWDTpk0JnQ8LhULo6+ubMx/2zjvv8JR/llSMLsZyuDwo8lSjx3819vEJRVE+4d1lRM/Gpox0idHFKYwukh4wwvhr4XEN/V3+6fkwY5YRZrMp4Wvro42YqqpwOBwoLS1N6HyYqqro7e2dMx/m9aZuwxEPqRpdjLX7SCNO/dnv48nEWPQR7y4jWgQ2ZaRLjC4yukj6UuJ2YrA/AJsjNaNXzxJdW/+g/Sbut99Ers0usrY+uqhjYmICBQUFCZ8P6+zsxIMHD9DV1QWTyYSKigp8+9vfTtm19fGWytHFWAajCVX7DqP5g3djH3/v86UfPqm6iPSOTRnpTnhcQ8Ya2RpCoZB4dPHRo0eMLpJuvFjrxT+8dzptmrLB/gACbT50tzZjdEiFzZYHs8mY0PmwYDCI0dHR6fmwkpKS6UYsEaJr6x88eIB79+7B6XSitraW82HLlOrRxVgVOw8g0ObDQJc/9vFJAOnxL4BoGdiUke50t17GukzZrkzTNBQWJmYm5Fk1MLpIemG322HOlK5idUV/iIzOh+Xm5iA/15TQ+bBgMAhN06bnwxJ9f1h0bf3AwADu37+PsrIyzofFSTpEF2PtOPjG7LvLqhVFORaJRE5I1USkZ2zKSHfu+1vgsFpFazAYDKLxRVVVsXXrVrH3E81ns7sIagpFGMPjGnrafHhw79b0fJglO/HzYdFGTFVVFBcXi8yHRS9yDofDqKio4HxYnKVLdDHWAneXHf88xsilH0SzsCkjXQmPa3gyNgrkrhOrIRgMwuVyib0fADo6OvD666+L1kA0W22NF3/74/eTuimLzod13/wUD+/fQ17+BpjXZSV8Pix6d9jExATcbjdKS0sTPh/W3d2Nvr4+mEwmbN26FYcOHeJ82Cq5dbsNpvz0+3f7jLvLXhMrikin2JSRrnS3Xka2UfbbUtM0lJSUiNYwNjbGmQ3SHZPJBDzRpMtYssH+ADquXkBfx02MDj2GzZaHHIsZmxI8HxbdmBidD9uxY0fCYtLR+bBAIICenh54PB5UVVXh7bff5n9rEuBSsw87vvZd6TISboG7y76qKMr+SCTyiVBZRLrEpox0hdFFRhdJ3yq3eNDV5oOzXN/RtkCbD4FbzXjQ2TY9H+bIy4HFtSkh74/Oh4VCIQwNDcFisaCiogKFhYUJnw8LBAJ49OgRqqqqsGfPHni9Xs6HJZCqqjDk5EuXIWaBu8tOKoriZYyR6NfYlMWBoigzughDllz0LpkxujiF0UXSs9oaL27+0/uAzpqy6HxYd+tl9AfuwphlhM2aIzIfFgqFEAwGUVxcjMrKShQUFCR0PuzOnTt48OABwuEwampqcPjwYc6HCfr0ig/O7bulyxC1wN1lxzB1fxkRgU1ZvMz42862Mf1y4/HQ3+UXjy5OTEyIRxcjkQjjRKRbJpMJwn9Mp0Xnw+5eOYuhR33Iy98gcn/Y4OAghoaG8PTpU7jdbmzZsgWFhYUJnw+7d+8e8vLyUFdXhyNHjnA+TCdab7Vhx9fSZ+vifBa4u+wPPl/60SlUFpGu6OSvViLg3tVzsCfo0+SFSF8aHQqFkJubK/Z+osWo3urBbb8PhZ7En75E58O6Wi/jycQYbLY85OeasdlVl7Aaoqdhjx8/hsFgSPja+tj5sPb2dlRWVmLXrl2cD9OhdI8uxnrG3WX7RQoi0hk2ZaQbT8dGkGHJE3u/pmninyz39PRg3759ojUQPY/X68WZvzqZsKYsOh8W8F/F2oy1yM1NbCwxdj5MVVXYbDZUVFQkdG19dD6svb0dw8PDqKqqwsGDB+HxeDgfpmOMLs40z91l+xRFaYxEIieFSiLSDTZlpAuBNh+MmYnZgraQoaEh8bmL/v5+8caQaDGy1k7NcRmM8W8IRoMq+rva0N16GffbbyLbkgubNSfhscSRkZHp1fXR+bBErq3v7e1Fd3c3urq6oCgKampq8NZbb8Hj8STk/bRyjC7OtMDdZScURTnFpR+U7tiUkS7cu3oO9pxs0RoikUjCPvWeTygUQkFBgdj7iZZiV50X1+744K6sj8v/3mB/AP1dfty9chajQypycq3IyTbBm8C19aFQCMPDwxgaGoKiKNi0aRPq6+vhdrsT8v5wODzdiN27dw92ux179uzhfFiSYnRxfgvcXXYCQKNYUUQ6wKaMdIHRRUYXKbl4vV5cuv7u83/jM/R3+dHT5kNX62VEJp/CYrF8Ph+WmLu7Jicnp+8Oe/z4MSwWCzZt2pTQ+bBQKIS+vj7Oh6UgRhfnt8DdZd/6fOnHJ0JlEYljU0biGF2cwugiJRvzEiOM4XEN/V3+6fkwY5YRZrMp4Wvro42YqqpwOBwoLS1N6HyYqqro7e2dMx8m/d8giq/mKz7s/Saji/NZ4O6yE5i1zZoonbApI3H321qQKxxdXLNmjWh0MRwOw+FwiL2faDka9uzGR59eQOmLC//gOXs+LNdmF1lbH50Pm5iYQEFBgeh82Jo1a+D1evHtb3+bH8SkqEAggMIy9hfPMs/dZdWKohyPRCLHBcsiEsOmjMQNP+qFtWC92PvD4TCys2Wbwu7ubmzfvl20BqKlcjqdUP/He3OassH+AAJtPnS3NovNhwWDQYyOjorOh3V2duLBgwcz5sPefPNNxhLTwJlzF7BxO0/JnmWBu8uO8e4ySldsykjUYH8AJqPcvWAAMDIygtraWtEaHj58iKNHj4rWQLQcBRvyMRpU8bg/gIEu//R8WG5uDvJzTQmdDwsGg9A0bXo+LNH3h0XX1g8MDMyYD3vnnXe4tj7N9A08gtPK5vt55rm7LBe8u4zSFJsyEnXn039DjnmdaA2apol+ch0Oh0UvrCZaiYY9u3HiP/+fABRYshM/HxZtxFRVRXFxsch8WPQi53A4jIqKCs6HpblAIAC7s1y6jKSxwN1lr0UikVNSNRFJYFNGooIDPSgWji7abDax9wNT0cWdO3eK1kC0XE6nE5sKCxIWAdY0bfoi54mJCbjdbpSWliZ0PiwaS+zq6oLJZMLWrVtx6NAhzocRAEYXl+oZd5d9wrvLKJ2wKSMxjC5OYXSRkl1FRQX8fv+qnZBFm7BQKARFUVBSUjK9qCMRovNhgUAAPT09cDqdqK2t5XwYzYvRxaWb5+4yF4BjAI6LFUWUYGzKSAyji4wuUmrYtWsXWlpa4taURefDQqEQhoaGYLFYUFFRgcLCwoTPhwUCATx69AhlZWXYs2cPvF4v58NoQYwuLo/BaELdwTdw5sd/Gfv4DxRFORWJRHxSdRElEpuy+LBKF5CMRoceISdPbg395OQkrFbZ/9f19vYyukhJz263r3irYnQ+LBQKIRgMori4GJWVlSgoKEjofNidO3fw4MEDhMNh1NTU4PDhw5wPo0VjdHH5nOVebHB5Ypd+AFN3l+2XqYgosdiUxceMv7EdLn5K9jyjQRV4Mg5ArikbHh7G5s2bxd4PTDVlhw4dEq2BKB6qqqqWHGHUNA2Dg4MYGRmZng/bsmULCgsLEzof1t3djb6+PphMJtTV1eHIkSOcD6NlYXRxZeoPN+JnP/jD2LvL9imK0hiJRE4KlkWUEGzKSETnjYvItZhFaxgfH0/YTMpCDAYDo1CUEnbt2oXm5ubnfj9HT8MeP34Mg8GAkpIS7NixA4WFiVmdHzsfFl1bX1VVhbfffpvzYbQifr+f0cUVMlvtqNh1YL6lH6e49INSHZsyEtF39xqKHHli75+cnBSf5ers7OSF0ZQy7HY7cnNz5zyPnQ9TVRU2mw0VFRUJXVsfnQ9rb2/H8PAwqqqqsGfPHvzu7/4uPxShuPn4bBNKG96QLiPpVTUcnr30IxdTCz+OiRVFlABsyijhRoMqMjApWsPw8DA8Ho9oDYwuUqqpqanBhQsXYDKZEAwGp6OJ0fmwRK6tj86HdXV1QVEU1NTUrj+k6gAAIABJREFU4Bvf+Abnw2jVTDydWlhBK7f7SCM++tH3Yx997/PTsk+ESiJadWzKKOEYXZzC6CKlmrq6Ovz85z9Hd3c33G436uvrE7q2vre3F93d3bh37x7y8vKwd+9ezodRQvh8Plidsh/0pRKHy4MiTzV6/FdjH5/ArBl+olTCpowSjtFFRhcpNZlMJmzatAlf//rXE/K+UCiEvr6+GfNhu3bt4nwYJdzFZh+ji3G2+0gjTv3Z78cu/ahWFOVYJBI5IVkX0WphU0YJFR7XkLFGtoZQKCQeXXz06BGji5SSqqur0dnZuWonZKqqore3d8Z82MGDB+HxeHjyTGIYXYw/g9GEqn2H0fzBu7GPj38eY+wUKoto1bApo4Tqbr2MdZmyXZmmaQnb9PasGvgDJKWimpoa/PCHP4xrUxaNJXZ1dWHNmjXwer146623xD9cIQIYXVxNFTsPoONqEwb7e6KPoks/GqVqIlotbMoooe77W+AQvrDZYDCIxhdVVcXWrVvF3k+0mkwm04r/fEXX1j948AD37t2D3W7Hnj17OB9GusTo4urafaQR//qDP4p99C1FUU5y6QelGjZllDDhcQ1PxkaB3HViNQSDQbhcLrH3A0BHRwdef/110RqIVtP27duXHGGMrq0fGBiYMR/2zjvv8FSZdI3RxdVlczhRUrUbHdcuxD7m0g9KOWzKKGG6Wy8j2yj7LadpGkpKSkRrGBsb4xICSmmLjTCqqjp9kfPw8DC8Xi8OHjzItfWUNBhdTIy6g28g0Obj0g9KaWzKKGEYXWR0kdLDsyKM0VhidD6strYWhw4dYiyRkhKji4nxjKUfJyORSFCqLqJ4YlNGCTM5MQaA0UVGFykdRCOMhYWF06dhPT09cDqdqK2txZtvvskTY0pqmqZhjNHFhFlg6ccJcOkHpQg2ZZQQgTYfjJkZojUwukiUGKqq4vHjx/jVr36FcDiMsrIy7NmzB16vl/NhlDKutPiwvpRR20SqO3gUH/3o+7GPvqUoyolIJOKTqokoXtiUUULcu3oO9pxs0RoyMzNFo4uhUGjV7m4ikhYIBHD+/Hncvn0bmqZh48aNMBqN+JM/+RPp0ohWxfVbfmx7pVG6jLTicHkWWvqxX6YiovhhUxYf+2O/sDmKhMrQr6djI8iw5Im9P/pDoqSenh7s27dPtAaiePL5fGhubobf74fBYMCGDRtQX18/fRp89+5d+Hw+Lu6glKNpGiYmpatIT1UNh2cv/dinKEpjJBI5KVgW0YqxKVsFzJfPpIfo4tDQkPgPhv39/VxmQElN0zT4fD5cuXIF169fR1FREZxOJw4dOgSLxTLn9xcXF+PSpUvif/aI4o3RRTlmqx0Vuw7g+pn3Yx+fUBTlFJd+UDJjU0ar7n5bC3KFo4uRSGTeHxoTJRQKoaCgQOz9RMulqip8Ph/Onj2Lx48f44UXXsDGjRvR2Nj43DiwwWBAOBxOUKVEicPooqyqhsPouHoBo0Nq9FEugOMAjokVRbRCbMpo1Q0/6oW1YL3Y+zVNEz+hYnSRkkl0PqylpQWRSAQulwuVlZXLmolcv349I4yUUhhd1IfdRxpnL/343ucr8rn0g5ISmzJaVYP9AZiMcss1AEYXiZ5H0zT4/X40Nzfj2rVryMnJgdPpxIEDB1a8LZQRRko1Z85fwKZt9dJlpD2Hy4MiTzV6/FdjH3PpByUtNmW0qu58+m/IMcvdTQYwukg0H1VV0dbWNj0fVlpaig0bNuBrX/taXP+8MMJIqab1Vht2fO2AdBkEYMfBo+jv8s9e+rE/Eol8IlgW0bKwKYuP6VwaNy/OFBzoQbFgdDEcDmP9ern3A1OnZDt27BCtgQiYiiX6/f4Z82HFxcWoq6tb1esiGGGkVKGqKgw5+dJl0OcWWPpxEoBbpCCiFWBTFmeZ3Lw4TQ/RxZGREdTW1orW8PDhQ3g8HtEaKH35/X5cvnwZV69exWeffQa32426ujoUFhYmrAZGGClVfHrFB+f23dJlUIyKnQdmL/1wKYpyLBKJnJCsi2ip2JTRqum9cx2mrEzRGjRNW/FMzEqEw2HRC6sp/UTX1t+8eRPXrl2D0WhEZmYm6urqUFpaKlITI4yUKhhd1B+D0YSqhldx4b2/jX18/POlH1yRT0mDTRmtmr6711DkkLswOhwOw2azib0fALq7u7Fz507RGij1RdfW37hxA62trcjPz0d2djbKy8unG6L79++LNWUAI4yU/Bhd1K+S6nq0X7uAgS5/9BFX5FPSYVNGq2I0qCIDsjuD9RJdPHr0qGgNlJoCgQB8Ph8uXbqEwcFB2Gw2WCwWeL1eZGTMvKzdYDBgYGBAqNIpjDBSsmN0Ud92HHwD//qDP4p99D1FUU5EIpFOoZKIloRNGa2KzhsXkWsxi9bA6CKlGp/Ph1u3buHKlSt4+vQpsrOzYbfbF3XdgslkgqqqYn8mGGGkZNd8xYe932R0Ua9sDidKqnaj49qF2McnwRX5lCTYlK2Qoij7Y7/Oc/AuKoDRRYDRRVq56HzYp59+irt37yIrKwtWqxUul2vJDX92djZu3ryJhoaGVar2+RhhpGQVCARQWMbvW72rO/gGAm0+rsinpMSmLM4yjbJ3culBeFxDxhrZGkZHR7F161bRGgYGBhhdpCWLzoddunQJnZ2d0/NhW7dunRNLXApGGImW78y5C9i4nadkemcwmrgin5IWmzKKu+7Wy1iXKduVjY+PJ3Tl93wYXaTFCgQCOHfuHFpbW2fMh9XV1cX1PYwwEi1P38AjOK1ycXhavKqGw1yRT0mJTRnF3X1/CxxWq9j7JycnxRuizs5ObN++XbQG0rdoLNHv90NRFGRlZS16Pmy5GGEkWrpAIAC7s1y6DFqC3Uca8dGPvh/7iCvySffYlFFchcc1PBkbBXLlYpzDw8PilzX39vbi0KFDojWQvkTnwy5duoRbt27BZrMhOzt7WfNhy2UwGNDf35+Qdy2kuLgYFy9eZFNGSYPRxeTjcHmwweXhinxKKmzKKK66Wy8j2yj7bTU+Pg632y1ag8FggMlkEq2B5EXnw86eb8JjVYW9oBgTI4Pzrq1PFLPZLB5hfPLkici7iZaD0cXkVH+4Eaf+/PdjH3FFPukam7KV2x/7hS3Nty8yusjoYroLBAI433QBLS0+fBYB1rs8KKs/DGf51MnQB3/zf4g1ZAAjjERL4ff7GV1MUmarHZUNr85e+nECwGtCJRE9E5uyODMY0/t0ZHJiDACji4wuphefz4fmFh+u+nyw2OwoKPOi/je/M++HNNYNRQiHQ2IfHnALI9HifXy2CaUNb0iXQctUsfMAbl88Hbsi/6tckU96xaaM4ibQ5oMxU+4EAADGxsbEo4tr165ldDHFqaqKtrY2NLf4cOPaVbgrqmEvLseh//kwzM+JOZW9+EXcPP0PyBc80eUWRqLFmXjKD1uTmcFoQtW+w2j+4N3YxycA8BMh0h02ZRQ3966egz0nW7QG6eiiqqooKSkRrYFWRyAQgN/vn54PKy73It/lxesHG5f0Q5vN4YQ2LtuQMMJI9Hw+nw9Wp2zyglYueloWsyK/WlGUxkgkclKwLKI52JRR3DwdG0GGJU/s/cFgEC6XS+z9ANDR0YHXX39dtAaKH7/fjystPrS0+DAZAYrKvTPmw5aLEUZGGEn/Ljb7GF1MEfOsyD+hKMoprsgnPWFTRnGhh+iipmnip1RjY2NikTBaOU3T4Pf7fz0fZrWjwLPwfNhyMcLICCPpH6OLqWOBFfnHMLUmn0gX2JSt3P7YL2yOIqEyZN1va0GuDqKLkvFFVVWxdetWsffT8kTX1rfebpueDyso8y5qPmy5GGGcwggj6RWji6lnnhX5f/D5hdKdQiURzcCmLM7S9VO14Ue9sBasF3s/o4u0FIFAYHpj4mNVRVG5F5vK65c8H7YSjDAywkj6xehi6jFb7VPzZZdOxz7minzSDTZltGKD/QGYjLILNhhdpOfx+Xy43eafng/b5PFi2xePwuGS+TScEUZGGEmfNE3DGKOLKamy4VW0X23iinzSJTZltGJ3Pv035Jjl7iYDgMzMTNHoYigUEl/FTzNpmgafz4dbbX5c9fmQbbXDXVUf9/mw5WKEcQojjKQ3V1p8WF/K78dUxBX5pGdsymjFggM9KBaMLmqaho0bN4q9HwB6enqwb98+0Rro1/Nhl6/40HHXD1d5NQo9qzsfthI5+YWYnBxHRobMkhyDwYDBwUGRd0cVFxfjxo0bbMpINy41+7Dja9+VLoNWCVfkk16xKaMV0UN0cWhoSPwHuv7+fjid8qcv6SgQCOB80wXcbmubng8rqjmA3W/+nnRpz7WpvAaB5g+RZ8sVq+Gzzz5DKBSCxWIReb/BYEB/f7/Iu4lmU1UVhpx86TJolXFFPukRm7KVm+4GzLn6+yR+tfXeuQ5TVqZoDZFIROwHSmAqulhQUCD2/nQUXdLhb/NPz4fVfKVRF7HEpXCWe3HnVz8XrSE3Nxft7e2iH2w4HA4EAgF+sEHifv7BaZTWHZAug1YZV+STHrEpW7npj7j1GI9abX13r6HIIXdhtKZp4j/IMbq4+qLzYc0tPtzx+6fnw/b/lj5jiUuxdl02JicnxSKMJpMJgUBAtCkrKirC2bNn8c1vflOsBiIA6Bt4BGeS/zeFFmeeFfnHFEU5wdMyksKmjJZtNKgiA5OiNTC6mLqi82Fnzzfhsapio8uDQo8XRxK4tj4RXqjeIx5hVBRFNMJosVjQ19cn8m6iKJ/Phw1lnG1MF2arHSVVu9Fx7UL0US6mln40ihVFaY1NGS1b542LyLWYRWtgdDG1ROfDWlp8+CwCrHd5UFZ/GM7y1P1BiRHGKYwwkjTeTZZ+qhoOxzZlAPAtRVGO80JpksCmjJZNOroYDoexfr3c1kdg6pRsx44dojUku2gs8arPB4vNjnxnuW7W1icKI4yMMJIs3k2WnsxWOyobXsX1M+/HPuaF0iSCTdkKKIoy4yeY7DRa9BEe15CxRraGkZER1NbWitbw8OFDeDwylw8nK1VV0dbWhuYWH25cu4oCt0fXa+sTgRFGRhhJFu8mS1/RFfm8UJqksSlbGWvsF+n0A2V362Wsy5TtyjRNg90u9+88HA6LXlidTAKBAPx+/5z5sNdTbD5suRhhnMIII0nh3WTpy2A0oWLXgdmnZccB7BcpiNIWmzJalvv+Fjis1uf/xlUSDodhs9nE3g8A3d3d2Llzp2gNeub3+3GlxYeWFh8mI0BRuTfl58NWghFGRhhJBu8mo4qdB9Bx9ULshdL7eKE0JRqbMlqy8LiGJ2OjQO46sRr0El08evSoaA16omka/H7/r+fDrHYUeLxpNx+2XIwwMsJIMng3GRmMJlQ1vIoL7/1t7OPjAE6KFERpiU0ZLVl362VkG2W/dRhd1Ifo2vrW2224ce0q3BXVsBeXp/V82HIxwjiFEUZKNN5NRgBQUl2Pa2fejz0tcymKciwSiZyQrIvSB5uylUnLRR+MLqZ3dDEQCExvTHysqigq92KDi/Nh8ZCRJXf6DExFGPv7+0Vr2LBhA1pbW9mUUUL4/X7YneXSZZBO1B18A2d+/Jexj44rinKSF0pTIrApW5lZiz7SI5M+OTEGQO6Hx9HRUWzdulXs/QAwMDCQVtFFn8+H223+6fmwTR4vtn3xKBwubp6Mp02eGjxq+xWswh96SJ4E2+12nDlzBq+88orI+ym9fHy2iXeT0TRnuRcbXB4MdPmjj3IBHMNUlJFoVbEpoyUJtPlgzJRZRBA1Pj6OwsJC0RpSPbqoaRp8Ph9utflx1edDttUOd1U958NWWfHWHei8eg5yLdnUaVlHRwcqKirEali3bh1UVRWNKFPq0zQNE7ybjGapajiMj370/dhHf/D5aVmnUEmUJtiU0ZLcu3oO9pxssfdPTk6KN0SdnZ3Yvn27aA2rITofdvmKDx13/XCVV6f9/WGJZjCakLnOLFqD1WpFV1eXaFNWUlKCy5cv87SMVtWVFh/svJuMZnG4PLNPy4Cpk7JGkYIobbApoyV5OjaCDEue2PuHh4fFL2vu7e3FoUOHRGuIl0AggPNNF3C7rW16Pqyo5gDqXvsOPz0WwggjI4yUGJ9e8aHuNd5NRnPVH27EqT///dhH31IU5ThPy2g1sSlbmbRa9KGX6KLb7RatwWAwwGRK3oYluqTD3+bnfJgOMcI4hRFGWk2qqiLTkh5z4LR0ZqsdJVW70XHtQuzj4+BpGa0iNmUrM2vRR2r/8HC/rQW5jC4mXXQxOh/W3OLDHb9/ej5s/28xlqhHjDBOYYSRVtOZc01wbt8tXQbpWFXD4dlN2bcURTkRiUR8UjVRamNTRos2/KgX1oL1cu9ndHHRovNhZ883oe9+z/R82BGurU8KjDAywkirq70zgJ21h6XLIB0zW+2obHgV18+8H/v4BID9MhVRqmNTRosy2B+AySh7SjU2NiYeXVy7dq1uo4vR+bCWFh/GxjQUlXtRVn8YXyznIHuyYYRxCiOMtBp4NxktVsXOA7h98TSeTIxFH+1TFGV/JBL5RLAsSlFsymhR7nz6b8gxy15sKx1dVFUVJSUlojXMFo0lXvX5YDCasMnj5dr6FMAI4xRGGGk18G4yWiyD0YSKXQdmn5YdB0/LaBWwKVuZ6SMIc4ov+QgO9KBYMLoYDAZRXFws9n4AuHv3rviF0aqqoq2tDc0tPty4dhUFbg/X1qcoRhgZYaT4491ktFQVOw+g4+oFjA6p0Uc8LaNVwaZsZXKjv0jlH4iloouTk5MIhUIYGhrGxMQ49u7dm/AaQqEQ+vr6cK+rG0/DEyIxqkAgAL/fj7Pnm/BYVbHRNdWIvc75sJRWvHUHAjeaxCOMvb29orFhk8kETdN0Gxum5MK7yWipDEYTqhpexYX3/jb28UkAbpGCKGWxKaPn6r1zHaaszIS8KxwOTzVioREMqo+QX+iGq/YLCHbdSNin9aqqore3F2132jESGoaj2ANb8TaU5hsT8n5gaubhSosPLS0+TEaADS4PyuoPw8n5sLRhMJow+ZlsDRaLBX6/X7Qpy8/PR0tLC15++WWxGih1XL/lx7ZXGqXLoCRTUl2Pa2fejz0tcymK0hiJRE4KlkUphk0ZPVff3WsocqzehdGapmFkZASPB4OYmJjABudmVNTvQ1G5FwajCYE2H7ILHKv2fmBqq2JnVzc6O7sQUdbA4SrH9i98Y7oJunb6XbxYt3rrkzVNg9/vn54Ps1jtyC8u53xYmivYXAWt3y92SpSRkYFwOCzy7ii3243Lly+zKaMVU1UVY0+lq6BkVXfwDZz58V/GPjqOqRMzorhgU0bPNBpUkYHJuP/vBoNBhEIhDIdGoGSshaPYg7qXXp33JOj+rUvYu6Myru8Ph8Po7OxEb18/Ojs7YM61w+HegoY3j8zbBIWHH8U9uhhdW996uw03rl2Fu6Ia9uJyzofRNPf2Xbh0t0U0umc0GtHZ2Sl6WhYOhxlhpBU7c64JpTsOSJdBScpZ7sUGlwcDXf7oI56WUVyxKVsmRVFmdA/ZKbroo/PGReRaVr4FbnJyEsFgECMjowgOBWHKscG1bSd2lHufexK05rOncYkuhkKhqUbsQT+67nXAWVaFDS9U4itffuuZTdBoUIXbFZ/TqkAgML0x8bGqoqjciw0uzofR/MxWOyaRIVpDTk6OeISxsLCQEUZaMd5NRitV1XAYH/3o+7GPTiiKcioSiQSlaqLUwaZs+WbM36fqycZKoovhcHiqEdPGMKg+QmHJVrhqd2KPx7vof1+D/QHk23KW9X5g6jSqs7MT97oCGAkNo8jjReH2vdj5jf910U3Qgzs+fOnF5c9y+Xw+3G7zT8+HbfJ4OR9Gi8YIIyOMtHK8m4ziweHyzD4tywVwDFNRRqIVYVNGCwqPa8hYs7R/RtM0BINBDIdGMDExgaKyKlR4t03Phy1VR8sZ1JQVLemfmYolPpieD3NW1GL7F3YuuwlSA21wfn3xkRdN0+Dz+XCrzY+rPh+yrXYU8v4wWiZGGKcwwkgrwbvJKF7qDzfi1J//fuyjY4qinOBpGa0UmzJaUHfrZazLfH5XFgwGMTQ0jJHRUSgZa+GsqEXZC1vichKkDfbDYnn25bXR+bB7Xd3o670Pc64dRRW1aHhp/vmwpRgNqijYkP/c3xedD7t8xYeOu364yquR7+J8GK0cI4xTGGGk5eLdZBRPZqsdJVW70XHtQvQRT8soLtiU0YLu+1vgmOfi2uh82FBoBKHhIZhybCir+wIcLk9cT4IG+wPYtHHDvP+36HzYve4AHtzvgbOsCkXb96Lm35XHtQl6cMeHL+2Zf+tiIBDA+aYLuN3WNj0fVlRzAHWvfYd/+VNcMcLICCMtH+8mo3irajgc25QBPC2jOGBTtnzu2C9S7Yfw8LiGJ2OjQO66qa8/nw8bDo1gKDiIwpKtqKjfB4crvk1QrNnRRVVV0ea/g96+B9PzYZ76w9jr8qzav//Z0cXokg5/m396PmzbF4/C4fKsyvuJAEYYoxhhpOX49IoPda99V7oMSiELnJadANAoVhQlPTZly+eO/SLVZoW6Wy9jzWdhBAIBjI6NY2J8HEVlVah+6VU4VrEJiqUN9kNVjWi+4kNvb+/0fFjtoS8npAkaDaqwWkxoampCc4sPd/x+ZFvtcFfVo/43D6Tc/89JvxhhnMIIIy2VqqrItDw/gk60VPOcln1LUZTjkUikU6gkSnJsymhejx90IxgahbOiFlVb6kROgh70dCEUCqHEuwcNDd9IeBM0MqTi04sXMBDUUOjx4lDDUc6HkRhGGBlhpKU7c64Jzu3zR9CJVmKe0zJgaq6sUaQgSnpsypZv7rBVCtn5lX+PnV/596I1vP6//WfR9ztcHvzWf/or0RqIogrLKnGz+yYkk3tZWVlQVTXuF6kvxZMnT8TeTcmHd5PRauJpGcXTEheeU4wZU8OcKSKi1WRzOKGNy55UZWdn4+bNm6I1rF+/Hj6fT7QGSg68m4xWW/S0bJaTAqVQCmBTRkSUJKwbikQjhAaDAYODg2LvB4Di4mJcunRJtAZKDh+fbYKzktFFWl1VDXNOYvcpirJfoBRKcmzKiIiSRNmLX8Tw6JhoDSaTCaqqir3fYDCIz7aR/vFuMkqUBU7LjguUQkmOTdny7Yv+wuYoetbvIyKKC0YYpzDCSM9z5vwFFGyrly6D0gRPyyge2JTFQSY/iSOiBGGEkRFGer7mKz7OelPCLHBadkKiFkpebMqIiJIII4yMMNKz+Xw+zpJRws1zWlatKEqjQCmUpNiULYOiKO7Yrw1Z62QKIaK0wwjjFEYYaSEXLvtQWOZ9/m8kiiOz1Y7KhldnPz4uUAolKTZly+OO/cK2MbGXGhNRemOEkRFGmp+qqhjjgg8SUrHzADJnflDv4mkZLRabMiKiJMMIIyOMNL+ff3AaW17mZdEkw2A0oWLXgdmPjwuUQkmITdnyWKULIKL0xQjjFEYYKZamaegdeASz1S5dCqUxnpbRcrEpW54ZYXWHq1yqDiJKU4wwMsJIM11p8aGQa/BJGE/LaLnYlBERJSE9RBjNZjNCoZDY+w0GAzIyMsTeT/pyqdkHZzkXfJA8npbRcrApIyJKQnqIMJrNZrS3t4vWYLFYEAgERGsgeX6/H6Z8Lt0ifeBpGS0Hm7LlmfFRXHYu8+tElHh6iDA+ePBA7P0A4HQ6cfbsWdEaSN7HZ5uw+cU5PwQTieFpGS0Vm7LlmbHog0PFRCRBDxHGtWvXikcYx8Zk/x2QLE3TuAafdIenZbRUbMqIiJIUI4xTGGFMb7/48DQ2ccEH6RBPy2gp2JQtjzv6i1l/2IiIEooRRkYY0117ZwAOl0e6DKI5eFpGS8GmbHlc0V/YNnKwmIjkMMLICGM68/l82FDGjYukXwuclh2Tqof0i00ZEVESY4RxCiOM6enjs00oZFNGOrbAaRmbMpqDTRkRUZJjhJERxnSkqioyLflc8EG6V7HzAMwzN3VztozmYFO2RIqi7I/9Os/B+CIRydq251VGGBlhTDs//+A0Suu4Bp/0z2A0oarh1dmPjwuUQjrGpmyFMo1c9EFEssxWO55MCtfACCMlkKZp6B14xCtpKGmUVNfztIyeiU0ZEVEKWO8qZ4SREca0caXFh0KuwackM89pGWfLaBqbsqWbMVGcnctP6YhI3gtVLzPCyAhj2rjU7IOznAs+KLnMc1pWPXsshtIXm7Kls8Z+YbbmS9VBRDTNbLVjbOKpbA2MMFIC+P1+mPI5z03JibNltBA2ZUREKaKwrBqapom9nxFGSoSPzzZh84tc8EHJaZ7Tsn08LSOATdlyWJ//W4iIEs+9fReGQqOiNTDCSKtJ0zSMPQXX4FNS42kZzYdN2dLNCLE7XB6pOoiIZjBb7ZhEhmwNjDDSKvrFh6exiQs+KMktcFrmlqmG9IJNGRFRCinYXMUIIyOMKUnTNNztDPDDUEoJPC2j2diULd30SVlmFu8oIyJ9KduxnxFGRhhT0pnzF+Cu+5J0GURxMc9p2bd4Wpbe2JQtXW70F7aN3P5ERPpiMJpgyLaJ1sAII62G5is+npJRSuFpGcViU0ZElGI2uCoYYWSEMaWcO98EZ+Vu6TKI4oqnZRSLTdkSzF5ZyoujiUiPXJUvMcLICGNKudTsg7uSCz4o9fC0jKLYlK2A2cqmjIj0hxHGKYwwpgZeFk2prKS6fvaOAp6WpSk2ZUvDO8qIKCkwwsgIY6r42S8+4mXRlNIqds35/j4uUAYJY1O2NDPuKLM5+MkdEekTI4yMMKYCVVWRacnnZdGU0ip2HuBpGbEpWwn+JUFEesUI4xRGGJPbT069h9I6npJRajMYTTwtIzZlS+SWLoCIaLE2uCrET6oYYaTlUlUVI084v03poWLnnKaMp2Vphk3Z0rhjv+B9KUSkZ2UvfhGj4c9Ea2CEkZY+dUmrAAAgAElEQVTrzLkmlO7gKRmlB4PRhJKqOdc+HBcohYSwKSMiSmEGU47o+xlhpOXQNA13OwOc3aa0UtVwePYjnpalETZlSzO96GPWQCYRkS5tqqhFMBgUez8jjLQcv/jwNNx1X5IugyihzFY7T8vSGJuypcmN/sK2kZ/eEZH+uba+iPFJRbSGtWvXQlVVsfczwph8rvh8HBGgtMTTsvTFpoyIKMUZTDmYnJwUe7/ZbMatW7fE3g9MRRj9fr9oDbQ45843oYz3klGaMlvtKPJUz358XKAUSjA2ZYukKMr+2K+zc7kNioiSg3PbLgwNj4i932AwiJ6UAVMRxk8++US0BlqcM+cvwF1ZL10GkZiKXXOiuzwtSwNsypaJK3qJKFk4y714igzRGiwWCzo7O8XebzAYsGYN/8rTu6amJuQVMbZI6c3h8mDD3PjucYFSKIH4N9TiWaULICJarkzhCGN2djbu3r0r9n4AyM/Ph8/nE62Bnu2X5y5gM6OLRAvNlvFn0RTGpmzxvLFfcE0vESWTit2viEYYMzIyEA6Hxd4PTEUYr1+/LloDLczv98OywQmD0SRdCpG4BU7LjknUQonBpmyZ+JcGESUTm8OJ8SdyJ2UAYDQaxZdtTExMQNM00Rpofv/8L++htI6nZERRpXPX4x/jaVnqYlO2eG7pAoiIViLbXiB6WpWdnY07d+6IvR8AbDYbWlpaRGuguQKBADItds5rE8Uoqa6HeeZiuVwAjTLV0GpjU7Z47tgveH8KESWbshe/iOFRufu6MjIy8OTJE9HG0O1248aNG2Lvp/l98NFplO7gKRnRbFUNr85+xAhjimJTRkSUJmwOJ7Rx2bmu7OxstLW1idYQDocZYdQRVVUxGuasNtF85jktcymK0ihUDq0iNmWLN73oIzNrnWQdRETLVri5UvSkymaziW9hLC8vZ4RRR0799D2U1c/ZNEdEn6vYNecU+bhAGbTK2JQtXm70F7aN/DSPiJLTC1UvY3AoJFpDZmYmQiG5Gux2OyOMOhE9JeMsGdHCSqp2zz4QcCmK8ppUPbQ62JQREaURs9WOJ58pojWsW7cOt2/fFq0hEolAVVXRGoinZESLYTCa5jst42xZimFTtgiKouyP/To7l5/oEVHyKthcJTpTZbVa0dHRIfZ+ACgpKcHly5dFa0h3qqriaYaJp2REi1Cx88Ds07J9s38+peTGpmwZ+BcIESUz9/ZdGAqNitZgMplET6rsdjtaW1vF3k/ALz48jdLdczbLEdE8eFqW+tiULQ4v6iOilGG22jGJDNEaTCYTrl27JlrDunXrGGEUoqoqwmvWwWA0SZdClDRKq+pnP/qqoijuxFdCq4FN2eJ4Y7/g2l4iSnaubTtFl21YrVYMDAyIvR8AKioqcPbsWdEa0tUvPjyNohreS0a0FGarHSVVu2c/Pi5QCq0CNmXLwE/2iCjZuSpfwtDohGgNZrMZnZ2dYu+3WCxob28Xe3+64ikZ0fJVNcxZjPMtnpalBjZli7M/9gsu+iCiZGcwmpC5zixaQ25urvjCD4fDgUAgIFpDuvnluSaekhEt0wKnZZwtSwFsypaBiz6IKBVs8tQgGAyKvd9kMqG3t1f0MuuioiJGGBNIVVU8Mdp5Ska0AvOcljUqisL9B0mOTdniTM+UzVpHSkSUtIq37sDI+FPRGqxWq3iEsa+vT+z96eafTr2Hgq1zlhUQ0RKYrXZscHliH+UCaJSphuKFTdni5EZ/YdvIJR9ElBqiEcbJyUmxGvQSYfT7/aI1pAO/34/sAs/zfyMRPVfFTq7HTzVsyp6Dw5NElMpKavZhaHhE7P0mkwlZWVli7weA0tJSfPLJJ6I1pIMf//N7cFbylIwoHpzlXphn7jhwKYrSKFQOxQGbsudzx37hcPFTPiJKHc5yL4ZG5C+Svn37ttj7DQYDxsbGeGfZKvrwo9Mo3cHlHkTxVNUw5/L1RoEyKE7YlD0fByeJKKUVb5W9s2zt2rXiGxC3bNnChR+rRNM0+G62odDjff5vJqJFKyr3zt51sE9RlP1C5dAKsSl7Pl4cTUQprWzHfoTGnojWkJWVJXpaZrfbeWfZKvnnf3kf7rovSZdBlHIMRhNKq+dEghsFSqE4YFO2RFzjS0SpxmA0IdOUK7qa3mw24+bNm2LvB6bW458/f160hlSjqirudgYY/SdaJfMs/OBl0kmKTdnzzTgpMxi5Ep+IUk/tl99AvzooWkNubq7oadnmzZtx5swZsfenov/+9/+IrXvn3KlERHHCy6RTB5uy55sxU8b4IhGlIrPVDoMpR3Q9vs1mw927d8XeDwButxu3bt0SrSFV+P1+jIa5IItotZXME2HkZdLJh03Z87mlCyAiSoSK3Yfw6HFQtIaMjAz09vaKvd/j8XA9fpz897//R9R8+ah0GUQpz+HywOYoin3Ey6STEJuy53NFf7GBn/YRUQpzuDx4igzRGux2O65fvy5aQ15eHrq6ukRrSHb/8tP3sLHMC7PV/vzfTEQrxsukkx+bsmfg0S8RpRvX9pfweHBI7P0ZGRmYmJgQXdG/efNmNDU1ib0/2WmahstXfNjOWTKihCmprudl0kmOTdmzzVjykcd5MiJKcZtrG8Qvk16/fj0uXrwoWsOaNWswMDAgWkOy+vt/fBcVe9iQESVaSTUXfiQzNmVLkMnNi0SUBsp2fFH0tMxgMEDTNPHTstOnT4u9P1n5/X70PFDhLOdF0USJVrHzwOzLpKt5mXTyYFP2bPtjv8jOZTaeiFIfT8um8LRs6f7ff/hH7Hy1UboMorRkMJrm+0CkUaAUWgY2ZUtgtuZLl0BElBA8LZs6LfvZz34m9v5k09TUhI2budyDSFJVw5zoMC+TThJsyp7NLV0AEZEEnpZNMZlMvLdsETRNw6mfvo/NL87ZAEdECWS22lHkqZ79mLNlSYBN2bO5Y7/gBZhElE54WjZ1WsZ7y57vh//tJF58tREGo0m6FKK0V7HrS7Mf8TLpJMCm7Nn4DUxEaWtzbQMePR7E5OSkWA3r168XX7iRl5eHn/70p6I16JnP54NizucHl0Q6scBl0q8JlUOLxKbs2abPf2d9cxMRpYWt9b+BgYePxN5vMBiwZs0a9Pb2itWwefNmNDc3Q9M0sRr0StM0/OTUe6h4+VXpUogoxjyXSR8XKIOWgE3ZImUykkFEaWhzbQPGn0bET8taWlrE3g8ANTU1+OCDD0Rr0KOf/Mv7qPrSUcYWiXRmgcukeVqmY2zKFjD7XgeuwyeidFV78E08ehwUe78eTsucTifa29t5Whbj1m0/Bsc4b02kV7xMOrmwKVskrvglonTlcHnwVMlEOBwWq8Fut+NXv/qV2PsBwOPx4NSpU6I16IWmafjxqfewdS9ji0R6Nc9l0vu4Hl+/2JQtbMbte4xmEFE6e+nwf0C/Oij2/oyMDOTk5OD27dtiNRQWFuLhw4dQVVWsBr14/xensWXPYf7dSKRjC1wmfVygFFoENmULm7F50eZwStVBRCTObLUjd0Ox6Hp6m82GGzduiJ7YVVdX4+/+7u/E3q8Hnzb70Ds4xtgiURJY4DJpbhfXITZlC+M3LBFRDO+XXsfDwWHRGvLz80VjjBaLBWazGVeuXBGrQZKqqvjZB6dR++U3pEshokXgZdLJg03Zwmac93IlPhGlO4PRBM+LB/DwkVx8z2KxIBgMikYIvV4vfvGLX6Td0g9N0/CXf30Su15tlC6FiJZgnsuk2ZTpEJuyhbljv2BunohoakV+GLJLPzZu3Ihf/vKXYu8HgO3bt6fd0o8f/f27eKHuABdfESUZh8uDDTPjxrmKojQKlUMLYFO2MFf0FzwlIyL6tZcO/wf0DchdKJ2RkQGbzYZLly6J1VBYWIjh4WH4/X6xGhLpl+eaMKbMuzSAiJJAaRXX4+sdm7J5zF4XyoujiYh+zWy1w7l9t2iMMScnBz09PaIxxurqavzkJz9J+RhjIBDALz7kHBlRMiuprp+9Hr969p28JItN2fzcsV/kcfMiEdEMW3e/Ih5jLCoqEo0xGgyGlI8xapqG//o3J7H3N78rXQoRrVBpdf3sR40CZdAC2JTNb0Y+I9O4bqHfR0SUtmoPHkXgfp/Y+zMyMmAymcRjjD09PSkbY/zjP/k+SjlHRpQSKnYemP3oW7xMWj/YlM2Pd5QRET2HzeFE+UuvoP+hXIRw/fr1uHfvHnp7e8Vq2Lt3L/76r/865WKMf/03J+Eo86Jk7qfrRJSEFliP3yhQCs2DTdn8ZpyUcfMiEdH8Ntc2YM06q2hD8sILL+DMmTNiUUqDwTDdmKWKDz86jcfjwPa9cy6eJaIkNs+HLFz4oRNsyuY366SM2xeJiBay9/XvYGh8EpOTkyLvz8jIwKZNm3DmzBmR9wNTMUaHw4EPP/xQrIZ4OXe+CdfuBPDS4UbpUogozpzlXphzZ8SRuR5fJ9iUzW9f7Bc8KSMieraXv/Ed9DyQW5NvMplgMplEG7PNmzejtbUVV65cEathpZqamnDlhh8v8oJoopRVsWvObBlPy3SATdlz8JSMiOj5DEYTvF8+it6Bx2I1ZGVlQdM03L59W6yGPXv24OOPP0YgEBCrYbkCgQCab/jh/UqjdClEtIpK5t5ZxvX4OsCmbJbZ35S8o4yIaHEcLg/c3gYMjoyL1bB+/Xrcvn0bAwMDYjXU19fjn/7pn5Jq8UcgEMDJv3sXW77Au8iIUp3BaJqvMWsUKIVisCmba8Y8Ge8oIyJavJLqekQyzRjWJsRqKCwsxMcffyzWmBkMBmzbtg1/+qd/mhSNmd/vx8m/exe7v/EdxvWJ0sQ8Cz+4Hl8Ym7K5eEcZEdEK1L/223iaYRJrzDIyMvDCCy+INmZ2ux21tbW6b8zOnW/C//jXj9iQEaUZh8sz34hOo0Ap9Dk2ZXPxjjIiohViY6b/xuzc+SZcvOZH/Te+y4aMKA3Nc5n0MUVRrPP9Xlp9bMrm4h1lRERxwMZMn42Zpmn4s//yFzh7yccti0RprKjci8ysGYmwXACvCZWT9tiUzeWO/YLbF4mIlq/+td+GYs5H4H6fyD1msY3ZrVu3Ev5+4NeN2R//8R+Lb2VUVRX/+x/+ETJsTrz8m98VrYWIZBmMJpTOnS1rFCiFwKZsPq7YL3hSRkS0Mi/+xv+EF2q/gM7uHrHToozMLPiu3cDHvzwr8v6JiQmERkbxF//3X+Hc+SaRGk6fPo0//pPvY8e/a8T2vYdFaiAifZknwriPCz9krJUuQE9mfxPylIyIKD421zbAvukF/OpffghbOAyrNTFjC6FQCIH7vdj68ldQsfMAOnzn8NOf/X94+aWdsNvtCanhcvMVtN1px+6vfRsOlwe+0+/idttJfPPNN2Ayrf4Hf6qq4of/7SQmM9bh4G//J37YSETTzFY7Nrg8GOjyxz4+Bl4onXBKJBKRrkE3Pr+j7OPo1xtcHnz5rd/7/9u7u9i4zvvO4/8nDl/HXnLErEb1zmQmVDrDYteayUtlUNi1TiCvC6RNxSxgt9giCHORXbRoABZJb4wEdZEiN1nDCmJ0UQSL0mvsjdvFyrEQLBwTpZWuCGvjeEgFC5FJaDIUHFMJQ6oOJZmqc/Zizhk+c+aF83LOnLfvByCiczjiPLIYan7z/z//x78FAUAElRf+p7z94xV58MS/lMHBQU+e45133pHtmz+XgdEx+bf/4T9JYvwwgO3v7cjSi/9N/lVqQj7+0VKLr9KbtbU1+f7rP5D01EflobPna8LQ1mpZrv/jS/If//AP5Lem8p48/+3bt2VhYUG++8qCfPx3npDcQ3VtSgAg68tXZOml5/Rbt0zTZOBHnxHKNEqpORF5xr6eOn1OPvYYB2kCgNt2t7fktUv/Xd733oGcSLkXzg4ODuTt7Z/Le+o++ehjfyipbPPAs758Rd58Y1EKH56UQv43XXl+EZG33npLXv/BGzJ67EF5yPh0TSCsWevd2/LD710Sc/8X8ru/86jk8+6FsytXrsjLryzIiQ+X5MO/fY7qGICWLn7zSdm/taPf+pxpmvM+LSeWCGUapdRTIvIX9vVDj/yenHqEvnsA8MrPfvJDKS/8vdwnpiTH/4U88MADHX+N9957T/b29uTOPVP++demfOTRx1uGMac33/ieXH/tZXnwN07IQ//mX3e1hnfeeUc2fnpD3tz8qSSSJ+Shs+ebhjGng7u3ZeP1Bdn/xZb89kdLUiqVumpr3Nrakv/7g7L84I2yPJgvSZ4wBqBNK5dfkmuXL+m3XjVN0/BpObFEKNMopS6KyHn7+pHH/1gyBe9aWwAAFbvbW/L//s//ll++vSmDA++XgfeJPPDAAzI6Oir33Xdf3eMPDg7k1j+9I7f+6R3Z3/+VZPJF+a3px3o6W3JrtSxvlr8n+3s/l4ljx+QDx8ZlYmJCHnzwwYaP39nZkdUf/VjeeutnYr7vPpks/TvJ5Etth7G6P9Pd2/LWj8qyenVB7h8dlQ9lM/LBTFoymYxkMo3/XOVyWb7/g7L8aG1NxlNp+Y3fLEm6UCKMAejI/t6OXHz2SeftD5mmueHDcmKJUKZRSi2KyFn7+tHPfLGjd1sBAL3bWi3L7vaW/OzHPxQREfPX/yzmrw/H6av7BuSB5HGZSE9KMpWRZCrtagg5uHtbbqyWZXtjVfb3fl55TvM9ETn899JU75fkiQ9aH5mewmAj+3s7srVWlp2frsrB3TsiIvJ+bV6yKSLv/Vpk4oN5SaYyciyV6ToMAoCIyNK352V9ZUm/9Q3TNBn40SeEMo1SquY/xuNfeoZ3GwEAABB525tr8srzT+u3GPjRR5xT1gKBDAAAAHGQyuYlMVZTcR9TSs36tJzYIZRZrHH4VZxRBgAAgDiZerjuMOlZH5YRS4SyQzXl2QGqZAAAAIiRyVPTMjA0ot86q5TK+bOaeCGUHaoZs3jM5U3bAAAAQJANDo82mjzOsI8+IJQdclTKRpo9DgAAAIgkWhj9QSg7VPO2gNvjjQEAAICgS6Yycrz2SCgGfvQBoexQTr+4n/NeAAAAEEMnT007b836sIxYIZQdyuoXVMoAAAAQR5PFMwz86DNCmYgopWpaFx1nNAAAAACxcrJ4xnmLgR8eIpRV1Az5SNC6CAAAgBibOs3Aj34ilFUY+gXj8AEAABBnifEJBn70EaGsgkoZAAAAoGHgR/8QyioYhw8AAABomgz8qDtdGr0jlFXk9Iv7GfQBAAAANDpMmoEfHiCUVdSMw6d9EQAAABA5eapuCuOMUmq80WPRvdiHMmcJNplK+7UUAAAAIFAS4xOSzhf1W2MiMuPTciIr9qFMnEM+aF0EAAAAqiY5s8xzhDLHOPzkCYZ8AAAAALZMoeQsXBQZ+OEuQpmjUsaQDwAAAKDWZLFuPD7VMhcRyhzj8BPjH/BrHQAAAEAgNRj48VkGfriHUOYYh8+gDwAAAKBWYnxCJusPk2bgh0sIZdo4/IGhERkcHvVzLQAAAEAgpQt128hoYXRJrENZ3Th8hnwAAAAADTUZ+JHzZzXREutQJgz5AAAAANrGwA9vxD2UGfpFYpxQBgAAADTTYODHrA/LiJy4h7KaSlkyRfsiAAAA0ExifELS+aJ+a0wpxcCPHsU9lNXsKbufShkAAADQUqZ+4MesD8uIlLiHspx+QaUMAAAAaG2yeEYGhkb0W+cZ+NGbuIey6jj8BEM+AAAAgLacLNbtLaOFsQexDWXOcfgM+QAAAADaM3X6nPMWUxh7ENtQJo4hH8doXQQAAADakhifkGQqrd/KKqUMn5YTenEOZYZ+QaUMAAAAaF+DatmsD8uIhDiHMsbhAwAAAF1KF0rOgR8zSqnxZo9Hc3EOZbXj8Bn0AQAAALRtcHjUOR5/TBj40ZU4h7KcfkH7IgAAANCZqYcZ+OGGWIYyq6xaHYfv2KQIAAAAoA3JVMb5WrrImWWdi2UoE0frIvvJAAAAgO5M1p9ZRrWsQ4QyoXURAAAA6FYmX3LeYl9Zh+IaynL6RSpb8GkZAAAAQLglxifkeDav38oqpQhmHYhrKGPyIgAAAOCSk6emnbdmfVhGaBHKhPZFAAAAoBfpQl0L43nOLGtf7EKZ9c0xZl87Sq0AAAAAOjQ4PCqTVMu6FrtQJrQuAgAAAK5rUC1jCmObYh/KaF0EAAAAepcplGRgaES/lVVK1SU11ItjKMvpF0xeBAAAANyRoVrWlTiGMtoXAQAAAA9MPXzOeWuGgR9Hi30oo30RAAAAcEcylZFEbdFjTDhM+kixCmVMXgQAAAC8NVlkCmOnYhXKhNZFAAAAwFMnT51x3jqrlMr1fyXhEetQRusiAAAA4K7E+IQkU2nnbQZ+tBC3UJbTL5i8CAAAALhv6nT9wA8/1hEWcQtltC8CAAAAHmtwkDRnlrUQ61BG+yIAAADgvsHhUUnni87btDA2EZtQxuRFAAAAoH8aHCRNC2MTsQllQusiAAAA0DeTxTMyMDSi3xpTShHMGohtKKN1EQAAAPBWg2rZrA/LCLw4hbKcfsHkRQAAAMBbk8W6M8vOW9uKoIlTKKN9EQAAAOijVDYvifrX3bQwOsQ2lNG+CAAAAHiPFsajxSKUMXkRAAAA8Mdkcdp566xSKtf/lQRXLEKZ0LoIAAAA+CKZykgylXbepoVRE8tQRusiAAAA0D8NBn5wkLQmLqEsp18weREAAADon0y+bl9ZVilVdzOu4hLKaF8EAAAAfJIYn5B0vui8PevDUgIplqGM9kUAAACgv5jC2FzkQ5k12YXJiwAAAICP0oWSDAyN6LfGlFIM/JAYhDJxVMmOpTJ+rQMAAACIrcHh0UbVMkKZxDCUNRjHCQAAAKAP0oSyhmIXyhLjH/BrHQAAAECsZWhhbCh2oSzFnjIAAADANyfrzywjlPm9AC8ppcZFJGtf07oIAAAA+GuyOO28RSjzewEec+wnY8gHAAAA4KdkKiOJ2nODY9/CGKtQxvlkAAAAgP+mHj7nvEUoizDHfrKCX+sAAAAAYMnkmcKoi1UoY08ZAAAA4L/E+ITztXmsWxijHsqK9i8SYxMyODzq51oAAAAAWKZO08Joi2woU0qxnwwAAAAIKA6SPhTZUCacTwYAAAAE1uDwqKTzRf1WbFsYoxzKcvoF4/ABAACAYJnkIGkRiXYoM/SL+2lfBAAAAAIlUyjJwNCIfmtGKTXu13r8EuVQxsHRAAAAQMBlaveWjUkMq2WRDGVKqZxU/kJFROQ4+8kAAACAQKKFMaKhTBz7yY5RJQMAAAACKZXNO1sYz8ethTGqoczQLxiHDwAAAARXJubj8aMaythPBgAAAIRE3M8si2ooy+kXnFEGAAAABFeDKYyxamGMaiirnkKXGKN1EQAAAAi6OLcwRi6UKaUM/TqZSvu0EgAAAADtinMLY+RCmThaF5Mn2E8GAAAABF2cWxijGMoY8gEAAACEUINZELGolkU+lHFGGQAAABAOcd1XFvlQxhllAAAAQDg02FcWixbGSIUypVRORMbs6+OMwgcAAABCY3B4VNL5ovN25KtlkQpl4hjyQesiAAAAEC5xbGGMWigz9AtaFwEAAIBwiWMLY6RDWYPpLQAAAAACLI4tjFELZYzDBwAAAEKuQQuj4cMy+iYyoYwhHwAAAEA0NGhhpFIWEjV/c7QuAgAAAOHUoIVxTCkV2WAW2VBG6yIAAAAQXnGawhilUGboF1TKAAAAgPCKUwtjlEJZ9W8tMTYhg8Ojfq4FAAAAQA+atDDWJbUoiEQocw75oEoGAAAAhF+DFsZZH5bhuUiEMnHuJzvBfjIAAAAg7OLSwhjJUEalDAAAAAi/Bi2M2Si2MEYllBn6BZMXAQAAgGiIQwtjVEJZ9W+KQ6MBAACA6GjQwmj4sAxPhT6UMeQDAAAAiK4GLYxFKwNERuhDmXBoNAAAABBpUT9IOgqhzNAvjhHKAAAAgEhp0MI468MyPBOFUFZzaHRifMLPtQAAAABwWdRbGKMQys7av0im0n6uAwAAAIBHotzCGOpQppQy9GsOjQYAAACiKcpTGEMdyqTu0OiCX+sAAAAA4KHB4VFnZ9x5pdS4X+txU9hDmaFf0L4IAAAARFeDalkkWhjDHspqhnwMDo/6uRYAAAAAHorqvrLQhjJr2krWvqZKBgAAAERbMpWRxFjNtHXDp6W4KrShTJyHRjPkAwAAAIi8VDavX44ppUJfLQtzKDP0C4Z8AAAAANEXxX1lYQ5ltZUy2hcBAACAyIvivrIwh7LqodEM+QAAAADiI50v6pdjSqm6pBYmoQxldYdGUyUDAAAAYiOVq9u6NOvDMlwTylAmDPkAAAAAYiuTj1YLYyRCGUM+AAAAgPhIjE84u+WyYW5hDGsoM/QL2hcBAACAeGlQmDF8WIYrQhfKlFLj4jg0miEfAAAAQLxMFqedt2Z9WIYrQhfKpK5Kxn4yAAAAIG6SqYwMDI3ot4pKqZw/q+lNGEOZYz9ZvtnjAAAAAERYVM4sC2MoM/QLJi8CAAAA8ZSuD2WGD8voWRhDWfXQ6IGhEdoXAQAAgJhq0DV33o919CpUocw55pIqGQAAABBfg8Ojks4Xa+4ppULXwhiqUCaOciT7yQAAAIB4i8K+srCFMg6NBgAAAFAVhX1lYQtlhn7BodEAAABAvA0OjzpzQda57SnoQhPKODQaAAAAQCOTxTPOW6FqYQxNKBMOjQYAAADQQCYf7n1lYQplHBoNAAAAoE5ifMLZwli0Ou1CIUyhzNAvGIcPAAAAwNZgCGBoqmVhCmW1Z5TRvggAAADAMlmcdt4ilLnJmp4yZl8fp3URAAAAgCaZykhibEK/Zfi0lI6FIpQJh0YDAAAAOILjIOkxpVQoqmUhDWUcGg0AAACgVoOOOsOHZXQspKGMShkAAACAWplCSQaGRvRbVMrcwH4yAAAAAO1ytDBmrTwRaO/3ewFtMPSLY0xdBIC+2t3ekoO7d7r8fbc7/31vb8QgsvYAABiZSURBVMnBu50/37FURgaGR45+oEOrlng6MwAgfNKFkqyvLOm3DBEp+7Oa9oQhlNUkWyplAFBve3Ot5vrg7m3Z3d6qube/tyO/urXT8Pfvvr0l97oIQkFy0/HfoF3X5FJXv6/Vv0etwlwylZHB4dHq9eDwCMe8AICLGvwMnhGRCz4spW1hCGWGfsG7lgCiSg9W+3u/qAlQtZ/bkf0m4Qr90yoEdhsQbYmxCUmM14x1rqkEDg6P1gS5ZCpdE/QAIM4qPyPTsrt9w751Vik1bprmnp/raiXQoUwplRORrH3NPzoAwkBv93NWrPTWvHt3b+v/YABV+7fqg3e7QW9gaESSJw4Dmx7m7FZNqnMAoi5dKDn/jTVE5KI/qzlaoEOZMAofQIDY1Sp7r5TeDthrZSTgNkVko8nnyiLS7J3HVp8LEqPLz511dxnuuPfunZrvR/3XjVo19aqcHuD0Nku6VACETSpbcP7MmxFCWdcM/SKZSvu0DABR1yxwhaiatSy1AWhP6jc1b0jzcLVhmmazz0XdottfUClltPi083M560NXM3nYS3pV7qg3F/Qq3P1amNMDHF0tAIIglc3LwNCIvl860KPxQxXKqJQB6EbAA9erjusNqQ9Oi47rPdM0Az1FKu5M01xs8elWn2vKEfRKIjJu/XpcaodieRbo9CrczSMea1fgBrUgZ4e3+xvsmQMAt6WyebmxtmxfjimlSkH99zOwocy5n6zRpmcA8XaghartzVUROdyz5XPgsoOWXq3akMOwVQ7yZmMEkyPoLTZ5WA2llB7YcnJYkdNDnSdtmHoFTntRVEOvvNmtk/YbsLRMAuhVKldw/vyZkYCOxlemafq9hoaUUjMi8r/s68lT0zL9+7P+LQhA39kVLmfg8mn6IEELkeYIcK3CXF/aKm320QOp6v8S2gC0Z39vRy4++6R+a9k0zUAeJB3YSpk495OdYEoUEDX2lEK7rdAOYX0emmGHLXsohR66CFqIDet7fVG71XJDvNZO2SzMuVKBu+n4ueAcVnI8m6+2SFbaIj/AvjYAIiKSGJ+QxNiE/kZuMaij8UMTyjL5QIZaAEfY3lyrjoW393L18aBiZ+DasD7YkwX0yNFO2TTAKaXsVkk9sBnW//ZcebPDWqMWSQIbgFQ2L+srS/qtGRGZ92c1zQUylFktFEX7mv1kQLDZYWt7c1Xu3b0jv7QCmMcthgQuIAQc/39sGN601slcg49so9/TjqMCmz1wJJUtMHwEiKh0oUQo64GhX9A3DgTD7vaW/GpvR3a3t2T37S3Zv7Xj5TCNV+WwlXBDCFxAZDVonaxhDf9q9tFVaLu5uVadIKm3ROrVtWQqI/ePT3DQNhBiDXKE4cMyjhTUUFbTq0goA/qrj+HLPpR4UbQAFuPzsgA0YP1M2Gj2ea1F0pDDNsmcdBHYmlXXkqm0DAyPSqpaYfsAr0+AEBgcHpVkKq2/jhlTShlHHF3Sd0ENZYZ+wflkgDf6FL5uSW21yw5eVLwAuEL7ebLo/Jxbgc3+2egcRJSotkAS1oCgShdKztc3M9LlmZFeCeRIfKVUdVGJsQmZ+cLX/FwOEAnbm2vVYRu/3N7yYsJhXbth0N6FAgCdNUEyZ33Yv+56D5tOD2uVd+ozhDXAJ9uba/LK80/rtzZN08z5tJyGAlcp00bsigiti0Cn7AOVtzdXvah+LUsleC3KYQBjbDyAUGr2xpEbYc0+PLtRZS2ZSlf3rB1LZRgwAngslc3LwNCIPvk5q5TKBWm7ROBCmTDkA2ibXfXa3d6S7c01tyYe2u2G9lTDRWHABoAYaRHW7NbHkhy2QRYbPbYZO6w596wdz+arAY2qGuC+VDbv/P+dIQGawhiCUMZ+MkBEqvu+KqPn19w468sOX4tCuyEAHMl6c6osjtH+boS1m5trLatqqWyBM9aAHqRyBWcoC9Ro/MDtKVNK7Yl1kCT7yRBXdgDb3b7h1v6vTTmsfi0KEw4BwHOOISNdhTUnghrQnf29Hbn47JP6rVumaY77tR6nQFXKrB9eY/Y1pXvEgQcBbFkOA1iZ6hcA+KPZVEhtz1pJ+xiTNujtj/b5agQ14GiJ8QlJjE3o2zzGlFKloGzPCFQoE/aTIeKce8BcaEF8VWoDWCB+sAAAmmv0Zpl2QLYhHVbVGgW1ZCpd3ZtmDxUB4i6Vzcv6ypJ+a0Yqr6F8F/BQxn4yhJdzCuL25lovAUzf/8U5XwAQMdoB2Yv6fauqplfU2gpqu9s3ZHf7RvUF6MDQiFVJy1fDGtU0xE26UHKGMsOnpdQJWigr2b+wz/cAwsI+B8wOYD1MQXQGsDL7vwAgnqyq2qJ+r5ugdu/dO3XDRBJjEzWVNDqUEHUNvsfPKqXGg3C0T2BCmbWfrHoGCD8YEGT6PrDtzdVezwHTWxAXCWAAgFbaCGqGtHGu2v6tnUrVQKsc2KP59RH9QFQMDo/K8WzeuX/fEMdEVT8EJpSJo3yYLpSaPAzoP3sP2PbGaq9tiPoQjkVaEAEAbnAGNaWUPvXREJGz7Xwdu5p2/eqCiNQPEeFNc4RdKqChLDAj8ZVSF0XkvH39+JeeodcZvnEphDnH0JeDUB4HAMST1ZVkh7S296c5JVPp6pRHhoggbHa3t+Q73/or/damaZo5n5ZTFchKGaNc0W8uhDD2gQEAAk07/HpepFpN00OaIW2M5reHiNjsvWmVjwItjwi0ZCojA0Mj+mu9rFIq5/frtkBUyqx3bt6wr6dOn5OPPfaEjytC1O3v7cj2ZiWAba2Wuwlhy1IbwGhDBACEnjWa35DDkNZxNU0PaelCiTfaEThL3553TmH8nGma8z4tR0SCE8rmROQZ+/qRx/9YMuwpg4v0ENblZEQ7hC1KZS8YbYgAgFiwhogY0kE1TWe3Ox63ghohDX5bX74iSy89p9960TTNGb/WIxKc9kVDv2ATKXpFCAMAwB0Nhojk5DCkzcgRkx7tdkd7eIgd0tKFEq/54IsGZyEbPiyjRlAqZdVFJFNp+eTnv+LnchBCB3dvy/bmmtxYLRPCAADoIy2k2R9HjuPXHdf2oxHS0C/f+dZXnUcafcTP7Si+V8qskngVo/DRDjuE3dxc6/acsE2pDWEb7q4QAIB4sP4NnZfDASI5qYSzGWmj3dEew39NLomISDpflFSuEtCY7AivpLIF5+vHGanMCvCF76FM6loX68qJACEMAICQaBDS7L1o9kfLkHZjbVlurC2LiMjA0EilikZIg8vShVK1pdZi+LQUEQlkKKNsjYqt1TIhDACAkNNG8V8QqYY0u4rW8lDre+/eqQlp9mRHez8aQ0PQrQaZo60D1r3i+54yfT/Z8Wxe/v1nvujncuAjezjH1mq5+sO3A7fkMIRdJIQBABAO2nRHQzp8YZxMpSVdKEmmUKKKho599/mn5ebmmn7rE9Zgm77ztVLm3E9GlSx+dre3KiFstdxpNUwPYYucEwYAQDjp0x2tA60N7aPlOWn2ZMdrly9VWx0zhRKHWKMtmULJGcoM0SaN9pPf7YuGfsF+sniwQ1gXUxJflcMQtujF2gAAgH+s6ccXrQ9nSGs5ft/Z6qifj8b5t2ikQUHI8GEZIuJz+6JSqizaOyB/9OW/8W0t8E4PbYn2mPqLhDAAAGBNdrT3oxnS5kHWehUtXSixFw1VL3x9Tu69e6d6bZqm8mMdvoUy652PXfs6nS/K2Sf+xJe1wH09tCW+KOwLAwAAbbC2wtghrWWro469aLC9+sJfO4sGvuwr87N90dAvUjlaF8POnpa4tVrupC3xlhy2KXBoMwAAaFuD/Wh2QJuRFlU0fS+aPtGRNsf4yRRKzlBmiA/7yvwMZTP6BUM+wufg7u3q3rCt1XJN6fcIdlviPAM6AACAG6w3duel/ny0GWkx1XH/1o6sryzJ+sqSiBweXp3JlxgWEgMNZloYPizD1/bFDbE2aw4MjcgTf37Bl3WgM/t7O7K1VpbtjdVO94fRlggAAHyhDQyxK2lNB4boaHOMh4vffLKmy8uPfWW+hDJrk+ab9jX7yYLNDmLry1c62R9GWyIAAAikdqtoOtoco+v1l1+Q61cX9Ft931fmV/tibesi+8kCp8sgRlsiAAAIPOt1SllELrRbRWvU5siZaNFwPJt3hjJD+ryvzK9QZugX7CcLhi6DGG2JAAAgtBqcjZaTSkCblRYTHZ1noqULJTl56gwBLYSCcF6ZX+2Le2JNxGE/mb+6GF1PWyIAAIiFdgOaLplKy2TxDINCQuY73/pqzWvhfu8r63sos86T+Af7mv1k/be7vSXry0udjK7flMMQdtHb1QEAAASPFdAMqYS08+38HgJaeKxcfkmuXb6k3+rrvjI/QtlTIvIX9vXHHntCpk6f6+sa4qiLIMb+MAAAgAa0M9HaDmj2HrR0oSSDw6Oerg+d295ck1eef1q/9Q3TNOf69fx+hLKyaOXfT37+y4wY9UiXQWxe2B8GAADQFsegkJaHVtsIaMH0wtfn9HN3l03T7NuYzb6GMuubdte+Zj+Z+whiAAAA/lFK2eGsrYA2eWqaMfsB8d3nn5abm2v6rWS/5if0e/qioV8wddEd+3s7cv3qAkEMAADAZ9b+e3uSoz1mf0aajNq3x+wPDI1Uq2cENH+ksnlnKDPE+rv0mr+hjPPJutbF+Hp7WAd7xAAAAPpAC2hz1oHVs9IkoN179w4BzWepbEGuSc2wD0P6FMr63b64Ido3IfvJOnNw97bcWC3LT1aWnCm+GYIYAABAwFgBzR6137CCZiOg9df/+Kv/rF/2bV9Z30KZNUb0Tfs6MTYhM1/4Wl+eO+y2VisVMfuAwiNUzxFjfD0AAECwHVVB09kBbbJ4hm1AHvFrX1k/2xdn9AuSfmv2wI6fLF/Rp8C08qJUgti8tysDAACAW6xupjnpsMUxMTYhk8VpOXnqDGegucivfWX9DGWGfnGcdF/Hbk+8fnWh3X1i9sCO+X5NhgEAAIA3HAGt5RTH/Vs7cu3yJbl2+ZIkU2mZOn2OEfsuaLC1ypA+hLJ+ti/uifYN9Udf/pu+PG8YbG+uyfryFVlfWWrn4fY+sQtMTgQAAIi+Tsbsp/NFmSyeoSutSwd3b8vf/Zc/02/1ZV9ZXyplSilDtG+gdL7Y/MExsb+3Iz9ZuSLry0vtjLG394nNm6a56PniAAAAEBiOMfuzUgln5xs99sbastxYW67uP5t6+ByD9TowODwqyVRa71orKqXGve5K61f7oqFfxDm5dzi040WpBDEGdgAAAECs+QHz1hC9Gam0O7L/zEWpbMG5lcgQj1sY+9K+qJQqi0i1PDbzp1+L1TdEh1WxZRG5IJWhHewTAwAAQEvWgJA5ob3RFVurZbn8d/9Vv/UN0zTnvHxOzytlSqlx0QJZMpWOTSDroCq2KYcDOza8XhcAAACiwxoQMivSfnsj1bPmjjUe9uEpzytl1jfG39rXU6fPyccee8LT5/RTB1Uxe5/YBQ52BgAAgJu09sZZ0QokjRzP5uXkqWmZLJ7xfmEhcfGbTzpfy3t6Xlk/Qtm8iHzWvv7k578cyc2G25trcv21V9qpitGeCAAAgL5pt71xYGhEThbPyNTpc7Gvni19e945Gf3TXs556Eco2xBr8+HA0Ig88ecXPH2+fjq4e1vWV5bk+msLVMUAAAAQeFYX26yInG31OPvss7hWz9aXr8jSS8/ptzzdV+ZpKLNS+Rv29eSpaZn+/VnPnq9fdre35PprC+2cK0ZVDAAAAIFjtTfOWh910xttca2e7e/tyMVnn9RveXpemdehbE5EnrGvpz/12dCm7YO7t+XGalmuX11wjsh0oioGAACA0NAOp/5sq8fFbe+Zc1+ZaZrKq+fyOpRdFG3yy+NfekYGh0c9ez4v7O/tyPWrC/KT5Sty7907rR66KZWq2DxVMQAAAISNNTV9Vo4YDhKX6tmrL/y1c17EJ0zTXPTiubwOZdUvnkyl5ZOf/4pnz+W2LasqdnNz7aiHPieVILbo/aoAAAAA7ymlDKmEs9hWz65fXZDXX35Bv/WXpmk+5cVzeXZOmVUGrUqH4IA6u0Vx5fKlowZ3cK4YAAAAIssqOCxa25FmpTK9sW7v2c3NNbm5uSbff/mFyFXPUtm885bh1XN5VilzjsJ/9DNfbPQHCwT7bLHrry0c1aL4qlT2ink2DhMAAAAIIqvoMitNDqa2pfNFmXr40cC+9u/EC1+fq8kHXu0r86xSJlqSHBgaCeRfSptTFG9JpSp2gaoYAAAA4soqTFzUJjfOSYNzz26sLcuNtWVJjE3I1MPnZPLUdOjmStiSJzI125mUUiUvhvl5UilzjsJP54ty9ok/cf15utXmfrFNEXlKGGcPAAAANNTOuWcDQyOSKZTk1COfCl1r48rll+Ta5Uv6rT8zTdP1g5e9qpTV7CdL5QoePU37OtgvRosiAAAA0AbTNOdFZN6qnj0llRxQUz279+4dWV9ZkvWVpdANBkllC3JNakKZIZWJ667qSyjL5P0b8tHBfrHnhLPFAAAAgI5Z23xmtbH6LQeDrFy+JJPFaTl56kygq2f9Gvbhevui9Rexa18nxiZk5gtfc/U52tHBfjH7bLGNviwMAAAAiAFrrP6cHDEYZPLUdKBbG7/7/NPObU8fcjs7eFEpq21d7POAD/aLAQAAAP7TxurnpBLOZqXBYBC7tTGoUxuPpTLObGFIZRCgazwPZf04n4z9YgAAAEAwWVWlORGZswaDzIlI0fk4e2rj8Wxepk6fk0xAzjk+ns3L9asL+i1DQhDKDP3Cy6R7cPe2XL+60O5+sXkrrQMAAADwgTYYpCSVcPZZ52PsfWeJsQk59cjv+T4UpB/7ylzdU2b1jf6DfZ1MpeWTn/+Ka1/f1mYYuyUiF0XkKfaLAQAAAMHTamqjLTE2IZPFaZk6fc63886+862vyu72Df1W0s1tUG5XyjxtXewgjF2QSpsi+8UAAACAgHJMbZyTBgdS79/akWuXL8n11xbkZPGMTJ0+1/ehIMlUxhnKDKkUgFzhdqWsLFp/6KOf+aIr7YtthrFNqVTF5nt+QgAAAAB9Z4WzGalUz+pG6tv6PbFxffmKLL30nH7rG6Zpzrn19V2rlFmlx5oNe70GsjbDGMM7AAAAgAiwOt3mpbLvbFaaDAXRD6M+9cinPJ/YmMoWnLcMN7++m+2Lta2L+br/dm3rIIw9xfAOAAAAIHq0oSCGVCpnZ52Pubm5Jq88/7Qcz+bl5Klpz4aCJMYnJDE2oU967z7sNOBmKDP0i25GWO7v7cjK5Zdka7XcKoy9KJXK2GLHTwAAAAAgVKzX/YY2FKTpxMaVy5c8m9iYTKVrjt9SShluZRLX9pQppWq+0ONfeqbt6Sh2GFtfWWr1sOeESYoAAABArLUKZ7aBoRGZevicqxMbr19dkNdffkG/9ZemaT7lxtd2pVKmlKppXTyezbf1hyeMAQAAAOiENrHRntZYN7Hx3rt3qhMbM4WSK0NBvDyvzK32xZpQdlTrImEMAAAAQC+soSBPKaUuSItwZg8F6XViYzKVcd6q2+PWLVfaF5VSG6KNrJz50681/MMSxgAAAAB4xZrY+JR4NE7/u88/LTc31/RbHzFNs9zxF3LouVKmlCqJ9odOptJ1f0DCGAAAAACvaRMbZ+WIcfrdhLNUNu8MZYaI+B/KxNFLqc/wJ4wBAAAA6Ld2xul3E85S2YJck0v6LUNELvS6XjdC2ax+MVmcrp4zdu3ypSa/RUQIYwAAAAA8pI3TN8SFcJZMpZ23DDfW2dOeMqXUuIjs2tf26MkjDn1+UUTmCGMAAAAA+qlVOLOl80X5+GN/0DScfedbX5Xd7Rv6rQ/1mm16DWWzIvK3bT78ValUxha7fkIAAAAA6FE74axZ5ez1l1+Q61cX9Fufs9olu/a+Xn6ztFeue1VEPmGapmsnXgMAAABAt0zTXDRN0xCRT0glr9RZX1mSi88+KUvfnpf9vZ3qfS9aGHutlO2J4ywADZUxAAAAAIFnVc7mROR8s8fYlTMRkYvPPql/atM0zVxPz99tKLNG4b/R4FOEMQAAAACh025b49Zq2TlDI2kdZt3d8/YQysZFZEMOK2WEMQAAAACh1044c/i0aZoXu36+HtsXZ0SkJCLlXhYBAAAAAEHTQTj7hmmac10/Ty+hDAAAAACiro1wtmyaZqnrr08oAwAAAICjtQpnpmmqbr9uryPxAQAAACAWWozSf66Xr0ulDAAAAAC6oJTKici4aZrlnr4OoQwAAAAA/EP7IgAAAAD4iFAGAAAAAD4ilAEAAACAjwhlAAAAAOAjQhkAAAAA+IhQBgAAAAA+IpQBAAAAgI8IZQAAAADgI0IZAAAAAPiIUAYAAAAAPiKUAQAAAICPCGUAAAAA4CNCGQAAAAD4iFAGAAAAAD4ilAEAAACAj/4/1TPGTiP/GFwAAAAASUVORK5CYII=";
//# sourceMappingURL=logo.d.ts.map
{"version":3,"file":"logo.d.ts","sourceRoot":"","sources":["../src/logo.ts"],"names":[],"mappings":"AACA,eAAO,MAAM,sBAAsB,uy7DAAuy7D,CAAC"}
// Auto-generated by scripts/generate-logo-base64.ts — do not edit manually
export const FREESAIL_LOGO_DATA_URI = 'data:image/png;base64,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';
//# sourceMappingURL=logo.js.map
{"version":3,"file":"logo.js","sourceRoot":"","sources":["../src/logo.ts"],"names":[],"mappings":"AAAA,2EAA2E;AAC3E,MAAM,CAAC,MAAM,sBAAsB,GAAG,oy7DAAoy7D,CAAC","sourcesContent":["// Auto-generated by scripts/generate-logo-base64.ts — do not edit manually\nexport const FREESAIL_LOGO_DATA_URI = 'data:image/png;base64,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';\n"]}
/**
* @fileoverview Component Registry
*
* Maps component names from the catalog to React components.
* This enables the renderer to dynamically instantiate components
* based on A2UI messages.
*/
import type { ComponentType, ReactNode } from 'react';
import type { A2UIComponent, CatalogId, FunctionCall } from '@freesail/core';
import type { FunctionImplementation } from './types.js';
/**
* Props passed to all Freesail components.
*/
export interface FreesailComponentProps {
/** The component definition from the A2UI message (with resolved data bindings) */
component: A2UIComponent;
/** Rendered children (for container components) */
children?: ReactNode;
/** Full data model for the surface (server → client, kept in sync by two-way binding) */
dataModel?: Record<string, unknown>;
/** Scope data when inside a template iteration */
scopeData?: unknown;
/** Callback to dispatch user actions (client → server) */
onAction?: (name: string, context: Record<string, unknown>) => void;
/**
* Write a value to the local data model at the given JSON Pointer path.
* This is the "Write" half of A2UI two-way binding — input components
* call this on every user interaction (keystroke, toggle, etc.).
* The update is LOCAL only; it does NOT send a message to the server.
* The updated data model reaches the server when an action is dispatched
* (either via resolved data bindings in the action context, or via
* the sendDataModel metadata mechanism).
*/
onDataChange?: (path: string, value: unknown) => void;
/**
* Execute a function call definition.
* This is for LocalAction handling (client-side logic).
*/
onFunctionCall?: (call: FunctionCall) => void;
}
/**
* A React component that can render an A2UX component.
*/
export type FreesailComponent = ComponentType<FreesailComponentProps>;
/**
* Component map within a catalog.
*/
export type ComponentMap = Map<string, FreesailComponent>;
/**
* Registry of all catalogs and their components.
*/
declare class ComponentRegistry {
private catalogs;
private functions;
/** Positional parameter names per function, extracted from the catalog schema. */
private paramNames;
private fallbackComponent;
/**
* Register a catalog with its components, functions, and optional schema.
* When a schema is provided, parameter names are extracted from
* `functions.*.args.properties` keys so `evaluateFunction` can
* reorder named-key argument objects from the LLM.
*/
registerCatalog(catalogId: CatalogId, components: Record<string, FreesailComponent>, functions?: Record<string, FunctionImplementation>, schema?: Record<string, unknown>): void;
/**
* Extract positional parameter names from a catalog schema's function definitions.
*/
private extractParamNames;
/**
* Register a single component in a catalog.
*/
registerComponent(catalogId: CatalogId, componentName: string, component: FreesailComponent): void;
/**
* Get a component from a catalog.
*/
getComponent(catalogId: CatalogId, componentName: string): FreesailComponent | null;
/**
* Get a function from a catalog.
*/
getFunction(catalogId: CatalogId, functionName: string): FunctionImplementation | null;
/**
* Get the declared positional parameter names for a function.
* Returns undefined if no schema was registered or the function has no named params.
*/
getParamNames(catalogId: CatalogId, functionName: string): string[] | undefined;
/**
* Check if a catalog is registered.
*/
hasCatalog(catalogId: CatalogId): boolean;
/**
* Get all registered catalog IDs.
*/
getCatalogIds(): CatalogId[];
/**
* Set a fallback component for unknown components.
*/
setFallbackComponent(component: FreesailComponent): void;
/**
* Clear all registrations.
*/
clear(): void;
}
/**
* Global component registry instance.
*/
export declare const registry: ComponentRegistry;
/**
* Higher-order function to create a component with catalog binding.
* This ensures the component is registered when imported.
*/
export declare function withCatalog<P extends FreesailComponentProps>(catalogId: CatalogId, componentName: string, Component: ComponentType<P>): ComponentType<P>;
/**
* Register multiple components for a catalog at once.
*/
export declare function registerCatalog(catalogId: CatalogId, components: Record<string, FreesailComponent>, functions?: Record<string, FunctionImplementation>, schema?: Record<string, unknown>): void;
export {};
//# sourceMappingURL=registry.d.ts.map
{"version":3,"file":"registry.d.ts","sourceRoot":"","sources":["../src/registry.ts"],"names":[],"mappings":"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"}
/**
* @fileoverview Component Registry
*
* Maps component names from the catalog to React components.
* This enables the renderer to dynamically instantiate components
* based on A2UI messages.
*/
/**
* Registry of all catalogs and their components.
*/
class ComponentRegistry {
catalogs = new Map();
functions = new Map();
/** Positional parameter names per function, extracted from the catalog schema. */
paramNames = new Map();
fallbackComponent = null;
/**
* Register a catalog with its components, functions, and optional schema.
* When a schema is provided, parameter names are extracted from
* `functions.*.args.properties` keys so `evaluateFunction` can
* reorder named-key argument objects from the LLM.
*/
registerCatalog(catalogId, components, functions, schema) {
const map = new Map(Object.entries(components));
this.catalogs.set(catalogId, map);
if (functions) {
this.functions.set(catalogId, functions);
}
if (schema) {
this.extractParamNames(catalogId, schema);
}
}
/**
* Extract positional parameter names from a catalog schema's function definitions.
*/
extractParamNames(catalogId, schema) {
const funcs = schema['functions'];
if (!funcs)
return;
const names = {};
for (const [funcName, funcDef] of Object.entries(funcs)) {
const propsField = funcDef['properties'];
const argsDef = propsField?.['args'];
if (argsDef) {
const props = argsDef['properties'];
if (props && Object.keys(props).length > 0) {
names[funcName] = Object.keys(props);
}
}
}
if (Object.keys(names).length > 0) {
this.paramNames.set(catalogId, names);
}
}
/**
* Register a single component in a catalog.
*/
registerComponent(catalogId, componentName, component) {
if (!this.catalogs.has(catalogId)) {
this.catalogs.set(catalogId, new Map());
}
this.catalogs.get(catalogId).set(componentName, component);
}
/**
* Get a component from a catalog.
*/
getComponent(catalogId, componentName) {
const catalog = this.catalogs.get(catalogId);
if (!catalog) {
console.warn(`Catalog not found: ${catalogId}`);
return this.fallbackComponent;
}
const component = catalog.get(componentName);
if (!component) {
console.warn(`Component not found: ${componentName} in catalog ${catalogId}`);
return this.fallbackComponent;
}
return component;
}
/**
* Get a function from a catalog.
*/
getFunction(catalogId, functionName) {
const catalogFunctions = this.functions.get(catalogId);
if (!catalogFunctions) {
return null;
}
// Direct lookup first
if (catalogFunctions[functionName] != null) {
return catalogFunctions[functionName];
}
// Fallback: try snake_case -> camelCase conversion (e.g. open_url -> openUrl)
if (functionName.includes('_')) {
const camelName = functionName.replace(/_([a-z])/g, (_match, p1) => p1.toUpperCase());
return catalogFunctions[camelName] ?? null;
}
return null;
}
/**
* Get the declared positional parameter names for a function.
* Returns undefined if no schema was registered or the function has no named params.
*/
getParamNames(catalogId, functionName) {
return this.paramNames.get(catalogId)?.[functionName];
}
/**
* Check if a catalog is registered.
*/
hasCatalog(catalogId) {
return this.catalogs.has(catalogId);
}
/**
* Get all registered catalog IDs.
*/
getCatalogIds() {
return Array.from(this.catalogs.keys());
}
/**
* Set a fallback component for unknown components.
*/
setFallbackComponent(component) {
this.fallbackComponent = component;
}
/**
* Clear all registrations.
*/
clear() {
this.catalogs.clear();
this.functions.clear();
this.paramNames.clear();
this.fallbackComponent = null;
}
}
/**
* Global component registry instance.
*/
export const registry = new ComponentRegistry();
/**
* Higher-order function to create a component with catalog binding.
* This ensures the component is registered when imported.
*/
export function withCatalog(catalogId, componentName, Component) {
registry.registerComponent(catalogId, componentName, Component);
return Component;
}
/**
* Register multiple components for a catalog at once.
*/
export function registerCatalog(catalogId, components, functions, schema) {
registry.registerCatalog(catalogId, components, functions, schema);
}
//# sourceMappingURL=registry.js.map
{"version":3,"file":"registry.js","sourceRoot":"","sources":["../src/registry.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * @fileoverview Component Registry\n *\n * Maps component names from the catalog to React components.\n * This enables the renderer to dynamically instantiate components\n * based on A2UI messages.\n */\n\nimport type { ComponentType, ReactNode } from 'react';\nimport type { A2UIComponent, CatalogId, FunctionCall } from '@freesail/core';\nimport type { FunctionImplementation } from './types.js';\n\n/**\n * Props passed to all Freesail components.\n */\nexport interface FreesailComponentProps {\n /** The component definition from the A2UI message (with resolved data bindings) */\n component: A2UIComponent;\n /** Rendered children (for container components) */\n children?: ReactNode;\n /** Full data model for the surface (server → client, kept in sync by two-way binding) */\n dataModel?: Record<string, unknown>;\n /** Scope data when inside a template iteration */\n scopeData?: unknown;\n /** Callback to dispatch user actions (client → server) */\n onAction?: (name: string, context: Record<string, unknown>) => void;\n /**\n * Write a value to the local data model at the given JSON Pointer path.\n * This is the \"Write\" half of A2UI two-way binding — input components\n * call this on every user interaction (keystroke, toggle, etc.).\n * The update is LOCAL only; it does NOT send a message to the server.\n * The updated data model reaches the server when an action is dispatched\n * (either via resolved data bindings in the action context, or via\n * the sendDataModel metadata mechanism).\n */\n onDataChange?: (path: string, value: unknown) => void;\n /**\n * Execute a function call definition.\n * This is for LocalAction handling (client-side logic).\n */\n onFunctionCall?: (call: FunctionCall) => void;\n}\n\n/**\n * A React component that can render an A2UX component.\n */\nexport type FreesailComponent = ComponentType<FreesailComponentProps>;\n\n/**\n * Component map within a catalog.\n */\nexport type ComponentMap = Map<string, FreesailComponent>;\n\n/**\n * Registry of all catalogs and their components.\n */\nclass ComponentRegistry {\n private catalogs: Map<CatalogId, ComponentMap> = new Map();\n private functions: Map<CatalogId, Record<string, FunctionImplementation>> = new Map();\n /** Positional parameter names per function, extracted from the catalog schema. */\n private paramNames: Map<CatalogId, Record<string, string[]>> = new Map();\n private fallbackComponent: FreesailComponent | null = null;\n\n /**\n * Register a catalog with its components, functions, and optional schema.\n * When a schema is provided, parameter names are extracted from\n * `functions.*.args.properties` keys so `evaluateFunction` can\n * reorder named-key argument objects from the LLM.\n */\n registerCatalog(\n catalogId: CatalogId,\n components: Record<string, FreesailComponent>,\n functions?: Record<string, FunctionImplementation>,\n schema?: Record<string, unknown>\n ): void {\n const map: ComponentMap = new Map(Object.entries(components));\n this.catalogs.set(catalogId, map);\n if (functions) {\n this.functions.set(catalogId, functions);\n }\n if (schema) {\n this.extractParamNames(catalogId, schema);\n }\n }\n\n /**\n * Extract positional parameter names from a catalog schema's function definitions.\n */\n private extractParamNames(catalogId: CatalogId, schema: Record<string, unknown>): void {\n const funcs = schema['functions'] as Record<string, Record<string, unknown>> | undefined;\n if (!funcs) return;\n const names: Record<string, string[]> = {};\n for (const [funcName, funcDef] of Object.entries(funcs)) {\n const propsField = funcDef['properties'] as Record<string, unknown> | undefined;\n const argsDef = propsField?.['args'] as Record<string, unknown> | undefined;\n if (argsDef) {\n const props = argsDef['properties'] as Record<string, unknown> | undefined;\n if (props && Object.keys(props).length > 0) {\n names[funcName] = Object.keys(props);\n }\n }\n }\n if (Object.keys(names).length > 0) {\n this.paramNames.set(catalogId, names);\n }\n }\n\n /**\n * Register a single component in a catalog.\n */\n registerComponent(\n catalogId: CatalogId,\n componentName: string,\n component: FreesailComponent\n ): void {\n if (!this.catalogs.has(catalogId)) {\n this.catalogs.set(catalogId, new Map());\n }\n this.catalogs.get(catalogId)!.set(componentName, component);\n }\n\n /**\n * Get a component from a catalog.\n */\n getComponent(catalogId: CatalogId, componentName: string): FreesailComponent | null {\n const catalog = this.catalogs.get(catalogId);\n if (!catalog) {\n console.warn(`Catalog not found: ${catalogId}`);\n return this.fallbackComponent;\n }\n\n const component = catalog.get(componentName);\n if (!component) {\n console.warn(`Component not found: ${componentName} in catalog ${catalogId}`);\n return this.fallbackComponent;\n }\n\n return component;\n }\n\n /**\n * Get a function from a catalog.\n */\n getFunction(catalogId: CatalogId, functionName: string): FunctionImplementation | null {\n const catalogFunctions = this.functions.get(catalogId);\n if (!catalogFunctions) {\n return null;\n }\n // Direct lookup first\n if (catalogFunctions[functionName] != null) {\n return catalogFunctions[functionName];\n }\n // Fallback: try snake_case -> camelCase conversion (e.g. open_url -> openUrl)\n if (functionName.includes('_')) {\n const camelName = functionName.replace(/_([a-z])/g, (_match, p1) => p1.toUpperCase());\n return catalogFunctions[camelName] ?? null;\n }\n return null;\n }\n\n /**\n * Get the declared positional parameter names for a function.\n * Returns undefined if no schema was registered or the function has no named params.\n */\n getParamNames(catalogId: CatalogId, functionName: string): string[] | undefined {\n return this.paramNames.get(catalogId)?.[functionName];\n }\n\n /**\n * Check if a catalog is registered.\n */\n hasCatalog(catalogId: CatalogId): boolean {\n return this.catalogs.has(catalogId);\n }\n\n /**\n * Get all registered catalog IDs.\n */\n getCatalogIds(): CatalogId[] {\n return Array.from(this.catalogs.keys());\n }\n\n /**\n * Set a fallback component for unknown components.\n */\n setFallbackComponent(component: FreesailComponent): void {\n this.fallbackComponent = component;\n }\n\n /**\n * Clear all registrations.\n */\n clear(): void {\n this.catalogs.clear();\n this.functions.clear();\n this.paramNames.clear();\n this.fallbackComponent = null;\n }\n}\n\n/**\n * Global component registry instance.\n */\nexport const registry = new ComponentRegistry();\n\n/**\n * Higher-order function to create a component with catalog binding.\n * This ensures the component is registered when imported.\n */\nexport function withCatalog<P extends FreesailComponentProps>(\n catalogId: CatalogId,\n componentName: string,\n Component: ComponentType<P>\n): ComponentType<P> {\n registry.registerComponent(catalogId, componentName, Component as FreesailComponent);\n return Component;\n}\n\n/**\n * Register multiple components for a catalog at once.\n */\nexport function registerCatalog(\n catalogId: CatalogId,\n components: Record<string, FreesailComponent>,\n functions?: Record<string, FunctionImplementation>,\n schema?: Record<string, unknown>\n): void {\n registry.registerCatalog(catalogId, components, functions, schema);\n}\n"]}
import React from 'react';
export type FreesailThemeMode = 'light' | 'dark';
export interface FreesailThemeTokens {
bgRoot: string;
bgSurface: string;
bgCard: string;
bgMuted: string;
textMain: string;
textMuted: string;
primary: string;
primaryHover: string;
primaryText: string;
border: string;
radiusSm: string;
radiusMd: string;
radiusLg: string;
shadowSm: string;
shadowMd: string;
}
export interface FreesailTheme {
mode: FreesailThemeMode;
tokens: FreesailThemeTokens;
}
export declare const defaultLightTheme: FreesailThemeTokens;
export declare const defaultDarkTheme: FreesailThemeTokens;
export declare const useFreesailTheme: () => FreesailTheme;
export interface ThemeProviderProps {
theme?: FreesailThemeMode | Partial<FreesailThemeTokens>;
children: React.ReactNode;
}
export declare function FreesailThemeProvider({ theme, children }: ThemeProviderProps): import("react/jsx-runtime").JSX.Element;
//# sourceMappingURL=theme.d.ts.map
{"version":3,"file":"theme.d.ts","sourceRoot":"","sources":["../src/theme.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAwD,MAAM,OAAO,CAAC;AAE7E,MAAM,MAAM,iBAAiB,GAAG,OAAO,GAAG,MAAM,CAAC;AAEjD,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,EAAE,MAAM,CAAC;IACrB,WAAW,EAAE,MAAM,CAAC;IACpB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,iBAAiB,CAAC;IACxB,MAAM,EAAE,mBAAmB,CAAC;CAC7B;AAED,eAAO,MAAM,iBAAiB,EAAE,mBAgB/B,CAAC;AAEF,eAAO,MAAM,gBAAgB,EAAE,mBAgB9B,CAAC;AAOF,eAAO,MAAM,gBAAgB,qBAAiC,CAAC;AAE/D,MAAM,WAAW,kBAAkB;IACjC,KAAK,CAAC,EAAE,iBAAiB,GAAG,OAAO,CAAC,mBAAmB,CAAC,CAAC;IACzD,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B;AAED,wBAAgB,qBAAqB,CAAC,EAAE,KAAe,EAAE,QAAQ,EAAE,EAAE,kBAAkB,2CA2CtF"}
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
import { createContext, useContext, useMemo } from 'react';
export const defaultLightTheme = {
bgRoot: '#f8fafc',
bgSurface: '#ffffff',
bgCard: '#ffffff',
bgMuted: '#f1f5f9',
textMain: '#0f172a',
textMuted: '#64748b',
primary: '#2563eb',
primaryHover: '#1d4ed8',
primaryText: '#ffffff',
border: '#cbd5e1',
radiusSm: '0.25rem',
radiusMd: '0.5rem',
radiusLg: '0.75rem',
shadowSm: '0 1px 3px 0 rgb(0 0 0 / 0.1), 0 1px 2px -1px rgb(0 0 0 / 0.1)',
shadowMd: '0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1)',
};
export const defaultDarkTheme = {
bgRoot: '#020617',
bgSurface: '#0f172a',
bgCard: '#1e293b',
bgMuted: '#1e293b',
textMain: '#f8fafc',
textMuted: '#94a3b8',
primary: '#3b82f6',
primaryHover: '#2563eb',
primaryText: '#ffffff',
border: '#334155',
radiusSm: '0.25rem',
radiusMd: '0.5rem',
radiusLg: '0.75rem',
shadowSm: '0 1px 2px 0 rgb(0 0 0 / 0.05)',
shadowMd: '0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1)',
};
const ThemeContext = createContext({
mode: 'light',
tokens: defaultLightTheme,
});
export const useFreesailTheme = () => useContext(ThemeContext);
export function FreesailThemeProvider({ theme = 'light', children }) {
const currentTheme = useMemo(() => {
if (theme === 'dark') {
return { mode: 'dark', tokens: defaultDarkTheme };
}
if (theme === 'light') {
return { mode: 'light', tokens: defaultLightTheme };
}
// Custom partial theme
return {
mode: 'light', // Custom themes default to light baseline unless specified otherwise
tokens: { ...defaultLightTheme, ...theme },
};
}, [theme]);
// Inject CSS variables into the body or a wrapper
const styleString = `
:root {
color-scheme: ${currentTheme.mode};
--freesail-bg-root: ${currentTheme.tokens.bgRoot};
--freesail-bg-surface: ${currentTheme.tokens.bgSurface};
--freesail-bg-card: ${currentTheme.tokens.bgCard};
--freesail-bg-muted: ${currentTheme.tokens.bgMuted};
--freesail-text-main: ${currentTheme.tokens.textMain};
--freesail-text-muted: ${currentTheme.tokens.textMuted};
--freesail-primary: ${currentTheme.tokens.primary};
--freesail-primary-hover: ${currentTheme.tokens.primaryHover};
--freesail-primary-text: ${currentTheme.tokens.primaryText};
--freesail-border: ${currentTheme.tokens.border};
--freesail-radius-sm: ${currentTheme.tokens.radiusSm};
--freesail-radius-md: ${currentTheme.tokens.radiusMd};
--freesail-radius-lg: ${currentTheme.tokens.radiusLg};
--freesail-shadow-sm: ${currentTheme.tokens.shadowSm};
--freesail-shadow-md: ${currentTheme.tokens.shadowMd};
}
`.trim();
return (_jsxs(ThemeContext.Provider, { value: currentTheme, children: [_jsx("style", { children: styleString }), children] }));
}
//# sourceMappingURL=theme.js.map
{"version":3,"file":"theme.js","sourceRoot":"","sources":["../src/theme.tsx"],"names":[],"mappings":"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","sourcesContent":["import React, { createContext, useContext, useEffect, useMemo } from 'react';\n\nexport type FreesailThemeMode = 'light' | 'dark';\n\nexport interface FreesailThemeTokens {\n bgRoot: string;\n bgSurface: string;\n bgCard: string;\n bgMuted: string;\n textMain: string;\n textMuted: string;\n primary: string;\n primaryHover: string;\n primaryText: string;\n border: string;\n radiusSm: string;\n radiusMd: string;\n radiusLg: string;\n shadowSm: string;\n shadowMd: string;\n}\n\nexport interface FreesailTheme {\n mode: FreesailThemeMode;\n tokens: FreesailThemeTokens;\n}\n\nexport const defaultLightTheme: FreesailThemeTokens = {\n bgRoot: '#f8fafc',\n bgSurface: '#ffffff',\n bgCard: '#ffffff',\n bgMuted: '#f1f5f9',\n textMain: '#0f172a',\n textMuted: '#64748b',\n primary: '#2563eb',\n primaryHover: '#1d4ed8',\n primaryText: '#ffffff',\n border: '#cbd5e1',\n radiusSm: '0.25rem',\n radiusMd: '0.5rem',\n radiusLg: '0.75rem',\n shadowSm: '0 1px 3px 0 rgb(0 0 0 / 0.1), 0 1px 2px -1px rgb(0 0 0 / 0.1)',\n shadowMd: '0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1)',\n};\n\nexport const defaultDarkTheme: FreesailThemeTokens = {\n bgRoot: '#020617',\n bgSurface: '#0f172a',\n bgCard: '#1e293b',\n bgMuted: '#1e293b',\n textMain: '#f8fafc',\n textMuted: '#94a3b8',\n primary: '#3b82f6',\n primaryHover: '#2563eb',\n primaryText: '#ffffff',\n border: '#334155',\n radiusSm: '0.25rem',\n radiusMd: '0.5rem',\n radiusLg: '0.75rem',\n shadowSm: '0 1px 2px 0 rgb(0 0 0 / 0.05)',\n shadowMd: '0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1)',\n};\n\nconst ThemeContext = createContext<FreesailTheme>({\n mode: 'light',\n tokens: defaultLightTheme,\n});\n\nexport const useFreesailTheme = () => useContext(ThemeContext);\n\nexport interface ThemeProviderProps {\n theme?: FreesailThemeMode | Partial<FreesailThemeTokens>;\n children: React.ReactNode;\n}\n\nexport function FreesailThemeProvider({ theme = 'light', children }: ThemeProviderProps) {\n const currentTheme = useMemo<FreesailTheme>(() => {\n if (theme === 'dark') {\n return { mode: 'dark', tokens: defaultDarkTheme };\n }\n if (theme === 'light') {\n return { mode: 'light', tokens: defaultLightTheme };\n }\n // Custom partial theme\n return {\n mode: 'light', // Custom themes default to light baseline unless specified otherwise\n tokens: { ...defaultLightTheme, ...theme },\n };\n }, [theme]);\n\n // Inject CSS variables into the body or a wrapper\n const styleString = `\n :root {\n color-scheme: ${currentTheme.mode};\n --freesail-bg-root: ${currentTheme.tokens.bgRoot};\n --freesail-bg-surface: ${currentTheme.tokens.bgSurface};\n --freesail-bg-card: ${currentTheme.tokens.bgCard};\n --freesail-bg-muted: ${currentTheme.tokens.bgMuted};\n --freesail-text-main: ${currentTheme.tokens.textMain};\n --freesail-text-muted: ${currentTheme.tokens.textMuted};\n --freesail-primary: ${currentTheme.tokens.primary};\n --freesail-primary-hover: ${currentTheme.tokens.primaryHover};\n --freesail-primary-text: ${currentTheme.tokens.primaryText};\n --freesail-border: ${currentTheme.tokens.border};\n --freesail-radius-sm: ${currentTheme.tokens.radiusSm};\n --freesail-radius-md: ${currentTheme.tokens.radiusMd};\n --freesail-radius-lg: ${currentTheme.tokens.radiusLg};\n --freesail-shadow-sm: ${currentTheme.tokens.shadowSm};\n --freesail-shadow-md: ${currentTheme.tokens.shadowMd};\n }\n `.trim();\n\n return (\n <ThemeContext.Provider value={currentTheme}>\n <style>{styleString}</style>\n {children}\n </ThemeContext.Provider>\n );\n}\n"]}
/**
* @fileoverview Freesail React - Type Definitions
*
* Public interfaces for custom catalog integration.
*/
import type { ComponentType } from 'react';
import type { FreesailComponentProps } from './registry.js';
/**
* Definition of a custom catalog that can be registered with Freesail.
*
* Developers create a CatalogDefinition to bundle their JSON schema
* and React component implementations together, then pass them to
* FreesailProvider for registration.
*
* @example
* ```ts
* import catalog from './catalog.json';
* import MyCustomCard from './components/MyCustomCard';
*
* export const MyOwnCatalog: CatalogDefinition = {
* namespace: 'myown',
* schema: catalog,
* components: {
* 'MyCustomCard': MyCustomCard,
* },
* };
* ```
*/
export interface CatalogDefinition {
/** Unique namespace for the catalog (e.g., 'myown' or a full URI) */
namespace: string;
/** The JSON schema object (catalog.json content) describing available components */
schema: any;
/** Map of component names to React components implementing FreesailComponentProps */
components: Record<string, ComponentType<FreesailComponentProps>>;
/** Map of function names to their implementations */
functions?: Record<string, FunctionImplementation>;
}
/**
* A function implementation that can be called from the data model.
*/
export type FunctionImplementation = (...args: any[]) => any;
//# sourceMappingURL=types.d.ts.map
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,OAAO,CAAC;AAC3C,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,eAAe,CAAC;AAE5D;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,MAAM,WAAW,iBAAiB;IAChC,qEAAqE;IACrE,SAAS,EAAE,MAAM,CAAC;IAClB,oFAAoF;IACpF,MAAM,EAAE,GAAG,CAAC;IACZ,qFAAqF;IACrF,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,aAAa,CAAC,sBAAsB,CAAC,CAAC,CAAC;IAClE,qDAAqD;IACrD,SAAS,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,sBAAsB,CAAC,CAAC;CACpD;AAED;;GAEG;AACH,MAAM,MAAM,sBAAsB,GAAG,CAAC,GAAG,IAAI,EAAE,GAAG,EAAE,KAAK,GAAG,CAAC"}
/**
* @fileoverview Freesail React - Type Definitions
*
* Public interfaces for custom catalog integration.
*/
export {};
//# sourceMappingURL=types.js.map
{"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;;;GAIG","sourcesContent":["/**\n * @fileoverview Freesail React - Type Definitions\n *\n * Public interfaces for custom catalog integration.\n */\n\nimport type { ComponentType } from 'react';\nimport type { FreesailComponentProps } from './registry.js';\n\n/**\n * Definition of a custom catalog that can be registered with Freesail.\n *\n * Developers create a CatalogDefinition to bundle their JSON schema\n * and React component implementations together, then pass them to\n * FreesailProvider for registration.\n *\n * @example\n * ```ts\n * import catalog from './catalog.json';\n * import MyCustomCard from './components/MyCustomCard';\n *\n * export const MyOwnCatalog: CatalogDefinition = {\n * namespace: 'myown',\n * schema: catalog,\n * components: {\n * 'MyCustomCard': MyCustomCard,\n * },\n * };\n * ```\n */\nexport interface CatalogDefinition {\n /** Unique namespace for the catalog (e.g., 'myown' or a full URI) */\n namespace: string;\n /** The JSON schema object (catalog.json content) describing available components */\n schema: any;\n /** Map of component names to React components implementing FreesailComponentProps */\n components: Record<string, ComponentType<FreesailComponentProps>>;\n /** Map of function names to their implementations */\n functions?: Record<string, FunctionImplementation>;\n}\n\n/**\n * A function implementation that can be called from the data model.\n */\nexport type FunctionImplementation = (...args: any[]) => any;\n"]}
import type { JsonPointer } from '@freesail/core';
/**
* Traverse a nested object/array by JSON pointer or relative path.
* Returns undefined if the path doesn't exist or data is nullish.
*/
export declare function getDataAtPath(data: unknown, path?: JsonPointer | string): unknown;
//# sourceMappingURL=utils.d.ts.map
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../src/utils.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAElD;;;GAGG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,OAAO,EAAE,IAAI,CAAC,EAAE,WAAW,GAAG,MAAM,GAAG,OAAO,CAejF"}
/**
* Traverse a nested object/array by JSON pointer or relative path.
* Returns undefined if the path doesn't exist or data is nullish.
*/
export function getDataAtPath(data, path) {
if (data === null || data === undefined)
return undefined;
if (!path || path === '/')
return data;
const parts = path.split('/').filter((p) => p !== '');
let current = data;
for (const part of parts) {
if (current === null || typeof current !== 'object') {
return undefined;
}
current = current[part];
}
return current;
}
//# sourceMappingURL=utils.js.map
{"version":3,"file":"utils.js","sourceRoot":"","sources":["../src/utils.ts"],"names":[],"mappings":"AAEA;;;GAGG;AACH,MAAM,UAAU,aAAa,CAAC,IAAa,EAAE,IAA2B;IACtE,IAAI,IAAI,KAAK,IAAI,IAAI,IAAI,KAAK,SAAS;QAAE,OAAO,SAAS,CAAC;IAC1D,IAAI,CAAC,IAAI,IAAI,IAAI,KAAK,GAAG;QAAE,OAAO,IAAI,CAAC;IAEvC,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC;IACtD,IAAI,OAAO,GAAY,IAAI,CAAC;IAE5B,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,IAAI,OAAO,KAAK,IAAI,IAAI,OAAO,OAAO,KAAK,QAAQ,EAAE,CAAC;YACpD,OAAO,SAAS,CAAC;QACnB,CAAC;QACD,OAAO,GAAI,OAAmC,CAAC,IAAI,CAAC,CAAC;IACvD,CAAC;IAED,OAAO,OAAO,CAAC;AACjB,CAAC","sourcesContent":["import type { JsonPointer } from '@freesail/core';\n\n/**\n * Traverse a nested object/array by JSON pointer or relative path.\n * Returns undefined if the path doesn't exist or data is nullish.\n */\nexport function getDataAtPath(data: unknown, path?: JsonPointer | string): unknown {\n if (data === null || data === undefined) return undefined;\n if (!path || path === '/') return data;\n\n const parts = path.split('/').filter((p) => p !== '');\n let current: unknown = data;\n\n for (const part of parts) {\n if (current === null || typeof current !== 'object') {\n return undefined;\n }\n current = (current as Record<string, unknown>)[part];\n }\n\n return current;\n}\n"]}
+6
-5
{
"name": "@freesail/react",
"version": "0.4.5",
"version": "0.4.6",
"description": "React implementation for Freesail - Agent-driven UI SDK",

@@ -26,6 +26,7 @@ "type": "module",

"keywords": [
"a2ui",
"freesail",
"react",
"agent-driven-ui",
"a2ux"
"agent-driven ui",
"generative ui",
"ai agent"
],

@@ -37,3 +38,3 @@ "peerDependencies": {

"dependencies": {
"@freesail/core": "^0.4.5",
"@freesail/core": "^0.4.6",
"vite": "7.3.1"

@@ -40,0 +41,0 @@ },