Switch CatalogEntity and CatalogCategory abstract classes (#2612)

This commit is contained in:
Sebastian Malton authored and GitHub committed 2021-04-23 16:08:21 -04:00
1 parent 4d10e07087
commit 339502cf4f
23 files changed
+194 -184

No files matched your search

@@ -0,0 +1,56 @@
import { action, computed, observable, toJS } from "mobx";
import { CatalogCategory, CatalogEntityData, CatalogEntityKindData } from "./catalog-entity";
export class CatalogCategoryRegistry {
@observable protected categories: CatalogCategory[] = [];
@action add(category: CatalogCategory) {
this.categories.push(category);
}
@action remove(category: CatalogCategory) {
this.categories = this.categories.filter((cat) => cat.apiVersion !== category.apiVersion && cat.kind !== category.kind);
}
@computed get items() {
return toJS(this.categories);
}
getForGroupKind<T extends CatalogCategory>(group: string, kind: string) {
return this.categories.find((c) => c.spec.group === group && c.spec.names.kind === kind) as T;
}
getEntityForData(data: CatalogEntityData & CatalogEntityKindData) {
const category = this.getCategoryForEntity(data);
if (!category) {
return null;
}
const splitApiVersion = data.apiVersion.split("/");
const version = splitApiVersion[1];
const specVersion = category.spec.versions.find((v) => v.name === version);
if (!specVersion) {
return null;
}
return new specVersion.entityClass(data);
}
getCategoryForEntity<T extends CatalogCategory>(data: CatalogEntityData & CatalogEntityKindData) {
const splitApiVersion = data.apiVersion.split("/");
const group = splitApiVersion[0];
const category = this.categories.find((category) => {
return category.spec.group === group && category.spec.names.kind === data.kind;
});
if (!category) return null;
return category as T;
}
}
export const catalogCategoryRegistry = new CatalogCategoryRegistry();
@@ -0,0 +1,26 @@
import { action, computed, observable, IObservableArray } from "mobx";
import { CatalogEntity } from "./catalog-entity";
export class CatalogEntityRegistry {
protected sources = observable.map<string, IObservableArray<CatalogEntity>>([], { deep: true });
@action addSource(id: string, source: IObservableArray<CatalogEntity>) {
this.sources.set(id, source);
}
@action removeSource(id: string) {
this.sources.delete(id);
}
@computed get items(): CatalogEntity[] {
return Array.from(this.sources.values()).flat();
}
getItemsForApiKind<T extends CatalogEntity>(apiVersion: string, kind: string): T[] {
const items = this.items.filter((item) => item.apiVersion === apiVersion && item.kind === kind);
return items as T[];
}
}
export const catalogEntityRegistry = new CatalogEntityRegistry();
+143
View File
@@ -0,0 +1,143 @@
import { EventEmitter } from "events";
import { observable } from "mobx";
type ExtractEntityMetadataType<Entity> = Entity extends CatalogEntity<infer Metadata> ? Metadata : never;
type ExtractEntityStatusType<Entity> = Entity extends CatalogEntity<any, infer Status> ? Status : never;
type ExtractEntitySpecType<Entity> = Entity extends CatalogEntity<any, any, infer Spec> ? Spec : never;
export type CatalogEntityConstructor<Entity extends CatalogEntity> = (
(new (data: CatalogEntityData<
ExtractEntityMetadataType<Entity>,
ExtractEntityStatusType<Entity>,
ExtractEntitySpecType<Entity>
>) => Entity)
);
export interface CatalogCategoryVersion<Entity extends CatalogEntity> {
name: string;
entityClass: CatalogEntityConstructor<Entity>;
}
export interface CatalogCategorySpec {
group: string;
versions: CatalogCategoryVersion<CatalogEntity>[];
names: {
kind: string;
};
}
export abstract class CatalogCategory extends EventEmitter {
abstract readonly apiVersion: string;
abstract readonly kind: string;
abstract metadata: {
name: string;
icon: string;
};
abstract spec: CatalogCategorySpec;
public getId(): string {
return `${this.spec.group}/${this.spec.names.kind}`;
}
}
export interface CatalogEntityMetadata {
uid: string;
name: string;
description?: string;
source?: string;
labels: Record<string, string>;
[key: string]: string | object;
}
export interface CatalogEntityStatus {
phase: string;
reason?: string;
message?: string;
active?: boolean;
}
export interface CatalogEntityActionContext {
navigate: (url: string) => void;
setCommandPaletteContext: (context?: CatalogEntity) => void;
}
export interface CatalogEntityContextMenu {
icon: string;
title: string;
onlyVisibleForSource?: string; // show only if empty or if matches with entity source
onClick: () => Promise<void>;
confirm?: {
message: string;
}
}
export interface CatalogEntitySettingsMenu {
group?: string;
title: string;
components: {
View: React.ComponentType<any>
};
}
export interface CatalogEntityContextMenuContext {
navigate: (url: string) => void;
menuItems: CatalogEntityContextMenu[];
}
export interface CatalogEntitySettingsContext {
menuItems: CatalogEntityContextMenu[];
}
export interface CatalogEntityAddMenuContext {
navigate: (url: string) => void;
menuItems: CatalogEntityContextMenu[];
}
export type CatalogEntitySpec = Record<string, any>;
export interface CatalogEntityData<
Metadata extends CatalogEntityMetadata = CatalogEntityMetadata,
Status extends CatalogEntityStatus = CatalogEntityStatus,
Spec extends CatalogEntitySpec = CatalogEntitySpec,
> {
metadata: Metadata;
status: Status;
spec: Spec;
}
export interface CatalogEntityKindData {
readonly apiVersion: string;
readonly kind: string;
}
export abstract class CatalogEntity<
Metadata extends CatalogEntityMetadata = CatalogEntityMetadata,
Status extends CatalogEntityStatus = CatalogEntityStatus,
Spec extends CatalogEntitySpec = CatalogEntitySpec,
> implements CatalogEntityKindData {
public abstract readonly apiVersion: string;
public abstract readonly kind: string;
@observable metadata: Metadata;
@observable status: Status;
@observable spec: Spec;
constructor(data: CatalogEntityData<Metadata, Status, Spec>) {
this.metadata = data.metadata;
this.status = data.status;
this.spec = data.spec;
}
public getId(): string {
return this.metadata.uid;
}
public getName(): string {
return this.metadata.name;
}
public abstract onRun?(context: CatalogEntityActionContext): void | Promise<void>;
public abstract onDetailsOpen(context: CatalogEntityActionContext): void | Promise<void>;
public abstract onContextMenuOpen(context: CatalogEntityContextMenuContext): void | Promise<void>;
public abstract onSettingsOpen(context: CatalogEntitySettingsContext): void | Promise<void>;
}
+3
View File
@@ -0,0 +1,3 @@
export * from "./catalog-category-registry";
export * from "./catalog-entity";
export * from "./catalog-entity-registry";