Merge pull request #25900 from backstage/blam/nfs/callabck

NFS: Support callback options with `params` in `createExtensionBlueprint`
This commit is contained in:
Ben Lambert
2024-08-06 12:52:16 +02:00
committed by GitHub
4 changed files with 88 additions and 7 deletions
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/frontend-plugin-api': patch
---
Added support for using the `params` in other properties of the `createExtensionBlueprint` options by providing a callback.
+3 -2
View File
@@ -662,7 +662,7 @@ export type CreateExtensionBlueprintOptions<
},
> = {
kind: string;
namespace?: string;
namespace?: string | ((params: TParams) => string);
attachTo: {
id: string;
input: string;
@@ -670,8 +670,9 @@ export type CreateExtensionBlueprintOptions<
disabled?: boolean;
inputs?: TInputs;
output: Array<UOutput>;
name?: string | ((params: TParams) => string);
config?: {
schema: TConfigSchema;
schema: TConfigSchema | ((params: TParams) => TConfigSchema);
};
factory(
params: TParams,
@@ -326,4 +326,62 @@ describe('createExtensionBlueprint', () => {
expect(true).toBe(true);
});
it('should allow providing callback for properties to set with params', () => {
type TestParams = { test: string };
const Blueprint = createExtensionBlueprint({
kind: 'test-extension',
attachTo: { id: 'test', input: 'default' },
name: (params: TestParams) => `${params.test}-name`,
output: [coreExtensionData.reactElement],
namespace: (props: TestParams) => props.test,
config: {
schema: (props: TestParams) => ({
test: z => z.string().default(props.test),
}),
},
factory(params: TestParams) {
return [coreExtensionData.reactElement(<div>{params.test}</div>)];
},
});
expect(Blueprint.make({ params: { test: 'hello' } }))
.toMatchInlineSnapshot(`
{
"$$type": "@backstage/ExtensionDefinition",
"attachTo": {
"id": "test",
"input": "default",
},
"configSchema": {
"parse": [Function],
"schema": {
"$schema": "http://json-schema.org/draft-07/schema#",
"additionalProperties": false,
"properties": {
"test": {
"default": "hello",
"type": "string",
},
},
"type": "object",
},
},
"disabled": false,
"factory": [Function],
"inputs": {},
"kind": "test-extension",
"name": "hello-name",
"namespace": "hello",
"output": [
[Function],
],
"toString": [Function],
"version": "v2",
}
`);
expect(true).toBe(true);
});
});
@@ -48,13 +48,14 @@ export type CreateExtensionBlueprintOptions<
TDataRefs extends { [name in string]: AnyExtensionDataRef },
> = {
kind: string;
namespace?: string;
namespace?: string | ((params: TParams) => string);
attachTo: { id: string; input: string };
disabled?: boolean;
inputs?: TInputs;
output: Array<UOutput>;
name?: string | ((params: TParams) => string);
config?: {
schema: TConfigSchema;
schema: TConfigSchema | ((params: TParams) => TConfigSchema);
};
factory(
params: TParams,
@@ -250,14 +251,30 @@ class ExtensionBlueprintImpl<
>
>
> {
const optionsSchema =
typeof this.options.config?.schema === 'function'
? this.options.config?.schema(args.params!)
: this.options.config?.schema;
const schema = {
...this.options.config?.schema,
...optionsSchema,
...args.config?.schema,
} as TConfigSchema & TExtensionConfigSchema;
const namespace =
typeof this.options.namespace === 'function'
? this.options.namespace(args.params!)
: this.options.namespace;
const name =
typeof this.options.name === 'function'
? this.options.name(args.params!)
: this.options.name;
return createExtension({
kind: this.options.kind,
namespace: args.namespace ?? this.options.namespace,
name: args.name,
namespace: args.namespace ?? namespace,
name: args.name ?? name,
attachTo: args.attachTo ?? this.options.attachTo,
disabled: args.disabled ?? this.options.disabled,
inputs: args.inputs ?? this.options.inputs,