phase-6: add registry-driven dynamic page-section-widget rendering engine
This commit is contained in:
20
src/app/widgets/contracts/widget-component.contract.ts
Normal file
20
src/app/widgets/contracts/widget-component.contract.ts
Normal file
@@ -0,0 +1,20 @@
|
||||
import { Type } from '@angular/core';
|
||||
|
||||
export interface WidgetRenderContext {
|
||||
pageId: string;
|
||||
sectionId: string;
|
||||
locale?: string;
|
||||
}
|
||||
|
||||
export interface RegisteredWidget {
|
||||
type: string;
|
||||
version: string;
|
||||
component: Type<unknown>;
|
||||
}
|
||||
|
||||
export interface ResolvedWidget {
|
||||
type: string;
|
||||
version: string;
|
||||
component: Type<unknown>;
|
||||
props: Record<string, unknown>;
|
||||
}
|
||||
38
src/app/widgets/registry/widget-registry.service.ts
Normal file
38
src/app/widgets/registry/widget-registry.service.ts
Normal file
@@ -0,0 +1,38 @@
|
||||
import { Injectable } from '@angular/core';
|
||||
import { RegisteredWidget } from '../contracts/widget-component.contract';
|
||||
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class WidgetRegistryService {
|
||||
private readonly widgets = new Map<string, RegisteredWidget>();
|
||||
|
||||
register(widget: RegisteredWidget): void {
|
||||
this.widgets.set(this.toKey(widget.type, widget.version), widget);
|
||||
}
|
||||
|
||||
registerMany(widgets: RegisteredWidget[]): void {
|
||||
for (const widget of widgets) {
|
||||
this.register(widget);
|
||||
}
|
||||
}
|
||||
|
||||
resolve(type: string, version: string): RegisteredWidget | null {
|
||||
const exact = this.widgets.get(this.toKey(type, version));
|
||||
if (exact) {
|
||||
return exact;
|
||||
}
|
||||
|
||||
const sameType = Array.from(this.widgets.values())
|
||||
.filter(widget => widget.type === type)
|
||||
.sort((a, b) => b.version.localeCompare(a.version));
|
||||
|
||||
return sameType[0] ?? null;
|
||||
}
|
||||
|
||||
list(): RegisteredWidget[] {
|
||||
return Array.from(this.widgets.values());
|
||||
}
|
||||
|
||||
private toKey(type: string, version: string): string {
|
||||
return `${type}@${version}`;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user