@memberjunction/ng-react
Version:
Angular components for hosting React components in MemberJunction applications
237 lines (236 loc) • 8.94 kB
TypeScript
/**
* @fileoverview Angular component that hosts React components with proper memory management.
* Provides a bridge between Angular and React ecosystems in MemberJunction applications.
* @module @memberjunction/ng-react
*/
import { EventEmitter, ElementRef, AfterViewInit, OnDestroy, ChangeDetectorRef } from '@angular/core';
import { ComponentSpec, ComponentStyles } from '@memberjunction/interactive-component-types';
import { ReactBridgeService } from '../services/react-bridge.service';
import { AngularAdapterService } from '../services/angular-adapter.service';
import { CompositeKey } from '@memberjunction/core';
import { MJNotificationService } from '@memberjunction/ng-notifications';
import * as i0 from "@angular/core";
/**
* Event emitted by React components
*/
export interface ReactComponentEvent {
type: string;
payload: any;
}
/**
* State change event emitted when component state updates
*/
export interface StateChangeEvent {
path: string;
value: any;
}
/**
* User settings changed event emitted when component saves user preferences
*/
export interface UserSettingsChangedEvent {
settings: Record<string, any>;
componentName?: string;
timestamp: Date;
}
/**
* Angular component that hosts React components with proper memory management.
* This component provides a bridge between Angular and React, allowing React components
* to be used seamlessly within Angular applications.
*/
export declare class MJReactComponent implements AfterViewInit, OnDestroy {
private reactBridge;
private adapter;
private cdr;
private notificationService;
private _component;
/**
* The component specification to render.
* When this changes after initialization, the component will be reinitialized
* to load and render the new specification.
*/
set component(value: ComponentSpec);
get component(): ComponentSpec;
/**
* Controls verbose logging for component lifecycle and operations.
* Note: This does NOT control which React build (dev/prod) is loaded.
* To control React builds, use ReactDebugConfig.setDebugMode() at app startup.
*/
enableLogging: boolean;
useComponentManager: boolean;
private _utilities;
set utilities(value: any);
get utilities(): any;
private _styles?;
set styles(value: Partial<ComponentStyles> | undefined);
get styles(): Partial<ComponentStyles>;
private _savedUserSettings;
set savedUserSettings(value: any);
get savedUserSettings(): any;
stateChange: EventEmitter<StateChangeEvent>;
componentEvent: EventEmitter<ReactComponentEvent>;
refreshData: EventEmitter<void>;
openEntityRecord: EventEmitter<{
entityName: string;
key: CompositeKey;
}>;
userSettingsChanged: EventEmitter<UserSettingsChangedEvent>;
container: ElementRef<HTMLDivElement>;
private reactRootId;
private compiledComponent;
private loadedDependencies;
private destroyed$;
private currentCallbacks;
isInitialized: boolean;
private isRendering;
private pendingRender;
private isDestroying;
private componentId;
private componentVersion;
hasError: boolean;
/**
* Public property containing the fully resolved component specification.
* This includes all external code fetched from registries, allowing consumers
* to inspect the complete resolved specification including dependencies.
* Only populated after successful component initialization.
*/
resolvedComponentSpec: ComponentSpec | null;
constructor(reactBridge: ReactBridgeService, adapter: AngularAdapterService, cdr: ChangeDetectorRef, notificationService: MJNotificationService);
ngAfterViewInit(): Promise<void>;
ngOnDestroy(): void;
/**
* Reinitialize the component when the input spec changes.
* Cleans up the current component and initializes with the new spec.
*/
private reinitializeComponent;
/**
* Initialize the React component
*/
private initializeComponent;
/**
* Generate a hash from component code for versioning
* Uses a simple hash function that's fast and sufficient for version differentiation
*/
private generateComponentHash;
/**
* Resolve components using the runtime's resolver
*/
private resolveComponentsWithVersion;
/**
* NEW: Load component using unified ComponentManager - MUCH SIMPLER!
*/
private loadComponentWithManager;
/**
* Register all components in the hierarchy
* @deprecated Use loadComponentWithManager() instead
*/
private registerComponentHierarchy;
/**
* Post-process resolved spec to ensure all components show their true registry source.
* This enriches the spec for UI display purposes to show where components actually came from.
* Applied to all resolved specs so any consumer of this wrapper benefits.
*/
private enrichSpecWithRegistryInfo;
/**
* Render the React component
*/
private renderComponent;
/**
* Create callbacks for the React component
*/
private createCallbacks;
/**
* Handle React component errors
*/
private handleReactError;
/**
* Handle onSaveUserSettings from components
* This implements the SavedUserSettings pattern
*/
private handleSaveUserSettings;
/**
* Clean up resources
*/
private cleanup;
/**
* Public method to refresh the component
* @deprecated Components manage their own state and data now
*/
refresh(): void;
/**
* Public method to update state programmatically
* @param path - State path to update
* @param value - New value
* @deprecated Components manage their own state now
*/
updateState(path: string, value: any): void;
/**
* Gets the current data state of the component
* Used by AI agents to understand what data is currently displayed
* @returns The current data state, or undefined if not implemented
*/
getCurrentDataState(): any;
/**
* Gets the history of data state changes in the component
* @returns Array of timestamped state snapshots, or empty array if not implemented
*/
getDataStateHistory(): Array<{
timestamp: Date;
state: any;
}>;
/**
* Validates the current state of the component
* @returns true if valid, false or validation errors otherwise
*/
validate(): boolean | {
valid: boolean;
errors?: string[];
};
/**
* Checks if the component has unsaved changes
* @returns true if dirty, false otherwise
*/
isDirty(): boolean;
/**
* Resets the component to its initial state
*/
reset(): void;
/**
* Scrolls to a specific element or position within the component
* @param target - Element selector, element reference, or scroll options
*/
scrollTo(target: string | HTMLElement | {
top?: number;
left?: number;
}): void;
/**
* Sets focus to a specific element within the component
* @param target - Element selector or element reference
*/
focus(target?: string | HTMLElement): void;
/**
* Invokes a custom method on the component
* @param methodName - Name of the method to invoke
* @param args - Arguments to pass to the method
* @returns The result of the method call, or undefined if method doesn't exist
*/
invokeMethod(methodName: string, ...args: any[]): any;
/**
* Checks if a method is available on the component
* @param methodName - Name of the method to check
* @returns true if the method exists
*/
hasMethod(methodName: string): boolean;
/**
* Print the component content
* Uses component's print method if available, otherwise uses window.print()
*/
print(): void;
/**
* Force clear component registries
* Used by Component Studio for fresh loads
* This is a static method that can be called without a component instance
*/
static forceClearRegistries(): void;
static ɵfac: i0.ɵɵFactoryDeclaration<MJReactComponent, never>;
static ɵcmp: i0.ɵɵComponentDeclaration<MJReactComponent, "mj-react-component", never, { "component": { "alias": "component"; "required": false; }; "enableLogging": { "alias": "enableLogging"; "required": false; }; "useComponentManager": { "alias": "useComponentManager"; "required": false; }; "utilities": { "alias": "utilities"; "required": false; }; "styles": { "alias": "styles"; "required": false; }; "savedUserSettings": { "alias": "savedUserSettings"; "required": false; }; }, { "stateChange": "stateChange"; "componentEvent": "componentEvent"; "refreshData": "refreshData"; "openEntityRecord": "openEntityRecord"; "userSettingsChanged": "userSettingsChanged"; }, never, never, false, never>;
}