From 7e1907047f307d7615e9bd9235ca07dd9d90bcf4 Mon Sep 17 00:00:00 2001 From: Patrik Oldsberg Date: Tue, 21 Nov 2023 16:49:25 +0100 Subject: [PATCH] frontend-plugin-api: add ExtensionDefinition IR Co-authored-by: Philipp Hugenroth Co-authored-by: Camila Belo Co-authored-by: Vincenzo Scamporlino Signed-off-by: Patrik Oldsberg --- .../src/wiring/createExtension.ts | 29 +++++++++++++++++-- .../src/wiring/createPlugin.ts | 21 ++++++++++++-- 2 files changed, 44 insertions(+), 6 deletions(-) diff --git a/packages/frontend-plugin-api/src/wiring/createExtension.ts b/packages/frontend-plugin-api/src/wiring/createExtension.ts index 9443caeb66..3c876a5c00 100644 --- a/packages/frontend-plugin-api/src/wiring/createExtension.ts +++ b/packages/frontend-plugin-api/src/wiring/createExtension.ts @@ -73,7 +73,9 @@ export interface CreateExtensionOptions< TInputs extends AnyExtensionInputMap, TConfig, > { - id: string; + namespace?: string; + name?: string; + kind?: string; attachTo: { id: string; input: string }; disabled?: boolean; inputs?: TInputs; @@ -86,6 +88,27 @@ export interface CreateExtensionOptions< }): Expand>; } +/** @public */ +export interface ExtensionDefinition { + $$type: '@backstage/ExtensionDefinition'; + namespace?: string; + name?: string; + kind?: string; + attachTo: { id: string; input: string }; + disabled: boolean; + inputs: AnyExtensionInputMap; + output: AnyExtensionDataMap; + configSchema?: PortableSchema; + factory(options: { + node: AppNode; + config: TConfig; + inputs: Record< + string, + undefined | Record | Array> + >; + }): ExtensionDataValues; +} + /** @public */ export interface Extension { $$type: '@backstage/Extension'; @@ -112,11 +135,11 @@ export function createExtension< TConfig = never, >( options: CreateExtensionOptions, -): Extension { +): ExtensionDefinition { return { ...options, disabled: options.disabled ?? false, - $$type: '@backstage/Extension', + $$type: '@backstage/ExtensionDefinition', inputs: options.inputs ?? {}, factory({ inputs, ...rest }) { // TODO: Simplify this, but TS wouldn't infer the input type for some reason diff --git a/packages/frontend-plugin-api/src/wiring/createPlugin.ts b/packages/frontend-plugin-api/src/wiring/createPlugin.ts index 5e2a55ab88..3ded409fa7 100644 --- a/packages/frontend-plugin-api/src/wiring/createPlugin.ts +++ b/packages/frontend-plugin-api/src/wiring/createPlugin.ts @@ -14,7 +14,7 @@ * limitations under the License. */ -import { Extension } from './createExtension'; +import { Extension, ExtensionDefinition } from './createExtension'; import { ExternalRouteRef, RouteRef } from '../routing'; import { FeatureFlagConfig } from './types'; @@ -32,7 +32,7 @@ export interface PluginOptions< id: string; routes?: Routes; externalRoutes?: ExternalRoutes; - extensions?: Extension[]; + extensions?: ExtensionDefinition[]; featureFlags?: FeatureFlagConfig[]; } @@ -70,8 +70,23 @@ export function createPlugin< id: options.id, routes: options.routes ?? ({} as Routes), externalRoutes: options.externalRoutes ?? ({} as ExternalRoutes), - extensions: options.extensions ?? [], featureFlags: options.featureFlags ?? [], + extensions: (options.extensions ?? []).map(definition => { + const { name, namespace: _, kind, ...rest } = definition; + + let id; + if (kind && name) { + id = `${kind}:${options.id}/${name}`; + } else if (kind) { + id = `${kind}:${options.id}`; + } else if (name) { + id = `${options.id}/${name}`; + } else { + id = options.id; + } + + return { id, ...rest, $$type: '@backstage/Extension' }; + }), } as InternalBackstagePlugin; }