Keep internal array attachTo support, only simplify public types
Signed-off-by: Patrik Oldsberg <poldsberg@gmail.com> Made-with: Cursor
This commit is contained in:
@@ -488,36 +488,40 @@ export function createExtension<
|
||||
if (options.name) {
|
||||
parts.push(`name=${options.name}`);
|
||||
}
|
||||
const a = options.attachTo;
|
||||
let attachTo: string;
|
||||
if (OpaqueExtensionInput.isType(a)) {
|
||||
const { context } = OpaqueExtensionInput.toInternal(a);
|
||||
if (!context) {
|
||||
attachTo = '<detached-input>';
|
||||
} else {
|
||||
let id = '<plugin>';
|
||||
if (context?.kind) {
|
||||
id = `${context?.kind}:${id}`;
|
||||
const attachTo = [options.attachTo]
|
||||
.flat()
|
||||
.map(aAny => {
|
||||
const a = aAny as ExtensionDefinitionAttachTo;
|
||||
if (OpaqueExtensionInput.isType(a)) {
|
||||
const { context } = OpaqueExtensionInput.toInternal(a);
|
||||
if (!context) {
|
||||
return '<detached-input>';
|
||||
}
|
||||
let id = '<plugin>';
|
||||
if (context?.kind) {
|
||||
id = `${context?.kind}:${id}`;
|
||||
}
|
||||
if (context?.name) {
|
||||
id = `${id}/${context?.name}`;
|
||||
}
|
||||
return `${id}@${context.input}`;
|
||||
}
|
||||
if (context?.name) {
|
||||
id = `${id}/${context?.name}`;
|
||||
if ('relative' in a && a.relative) {
|
||||
let id = '<plugin>';
|
||||
if (a.relative.kind) {
|
||||
id = `${a.relative.kind}:${id}`;
|
||||
}
|
||||
if (a.relative.name) {
|
||||
id = `${id}/${a.relative.name}`;
|
||||
}
|
||||
return `${id}@${a.input}`;
|
||||
}
|
||||
attachTo = `${id}@${context.input}`;
|
||||
}
|
||||
} else if ('relative' in a && a.relative) {
|
||||
let id = '<plugin>';
|
||||
if (a.relative.kind) {
|
||||
id = `${a.relative.kind}:${id}`;
|
||||
}
|
||||
if (a.relative.name) {
|
||||
id = `${id}/${a.relative.name}`;
|
||||
}
|
||||
attachTo = `${id}@${a.input}`;
|
||||
} else if ('id' in a) {
|
||||
attachTo = `${a.id}@${a.input}`;
|
||||
} else {
|
||||
throw new Error('Invalid attachment point specification');
|
||||
}
|
||||
if ('id' in a) {
|
||||
return `${a.id}@${a.input}`;
|
||||
}
|
||||
throw new Error('Invalid attachment point specification');
|
||||
})
|
||||
.join('+');
|
||||
parts.push(`attachTo=${attachTo}`);
|
||||
return `ExtensionDefinition{${parts.join(',')}}`;
|
||||
},
|
||||
|
||||
@@ -139,6 +139,43 @@ describe('resolveExtensionDefinition', () => {
|
||||
id: 'test',
|
||||
input: 'children',
|
||||
});
|
||||
|
||||
// Test for backward compatibility - runtime still supports multiple attachment points
|
||||
expect(
|
||||
resolveExtensionDefinition(
|
||||
OpaqueExtensionDefinition.toInternal({
|
||||
...baseDef,
|
||||
attachTo: [
|
||||
baseInpuf.withContext?.({
|
||||
kind: 'k1',
|
||||
input: 'children',
|
||||
}),
|
||||
baseInpuf.withContext?.({
|
||||
kind: 'k2',
|
||||
input: 'children',
|
||||
}),
|
||||
baseInpuf.withContext?.({
|
||||
kind: 'k3',
|
||||
input: 'children',
|
||||
}),
|
||||
] as any,
|
||||
}),
|
||||
{ namespace: 'test' },
|
||||
).attachTo,
|
||||
).toEqual([
|
||||
{
|
||||
id: 'k1:test',
|
||||
input: 'children',
|
||||
},
|
||||
{
|
||||
id: 'k2:test',
|
||||
input: 'children',
|
||||
},
|
||||
{
|
||||
id: 'k3:test',
|
||||
input: 'children',
|
||||
},
|
||||
]);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -141,35 +141,45 @@ function resolveExtensionId(
|
||||
}
|
||||
|
||||
function resolveAttachTo(
|
||||
attachTo: ExtensionDefinitionAttachTo,
|
||||
attachTo: ExtensionDefinitionAttachTo | ExtensionDefinitionAttachTo[],
|
||||
namespace?: string,
|
||||
): ExtensionAttachTo {
|
||||
if (OpaqueExtensionInput.isType(attachTo)) {
|
||||
const { context } = OpaqueExtensionInput.toInternal(attachTo);
|
||||
if (!context) {
|
||||
throw new Error(
|
||||
'Invalid input object without a parent extension used as attachment point',
|
||||
);
|
||||
): ExtensionAttachTo | ExtensionAttachTo[] {
|
||||
const resolveSpec = (
|
||||
spec: ExtensionDefinitionAttachTo,
|
||||
): { id: string; input: string } => {
|
||||
if (OpaqueExtensionInput.isType(spec)) {
|
||||
const { context } = OpaqueExtensionInput.toInternal(spec);
|
||||
if (!context) {
|
||||
throw new Error(
|
||||
'Invalid input object without a parent extension used as attachment point',
|
||||
);
|
||||
}
|
||||
return {
|
||||
id: resolveExtensionId(context.kind, namespace, context.name),
|
||||
input: context.input,
|
||||
};
|
||||
}
|
||||
return {
|
||||
id: resolveExtensionId(context.kind, namespace, context.name),
|
||||
input: context.input,
|
||||
};
|
||||
if ('relative' in spec && spec.relative) {
|
||||
return {
|
||||
id: resolveExtensionId(
|
||||
spec.relative.kind,
|
||||
namespace,
|
||||
spec.relative.name,
|
||||
),
|
||||
input: spec.input,
|
||||
};
|
||||
}
|
||||
if ('id' in spec) {
|
||||
return { id: spec.id, input: spec.input };
|
||||
}
|
||||
throw new Error('Invalid attachment point specification');
|
||||
};
|
||||
|
||||
if (Array.isArray(attachTo)) {
|
||||
return attachTo.map(resolveSpec);
|
||||
}
|
||||
if ('relative' in attachTo && attachTo.relative) {
|
||||
return {
|
||||
id: resolveExtensionId(
|
||||
attachTo.relative.kind,
|
||||
namespace,
|
||||
attachTo.relative.name,
|
||||
),
|
||||
input: attachTo.input,
|
||||
};
|
||||
}
|
||||
if ('id' in attachTo) {
|
||||
return { id: attachTo.id, input: attachTo.input };
|
||||
}
|
||||
throw new Error('Invalid attachment point specification');
|
||||
|
||||
return resolveSpec(attachTo);
|
||||
}
|
||||
|
||||
/** @internal */
|
||||
@@ -195,7 +205,7 @@ export function resolveExtensionDefinition<
|
||||
|
||||
return {
|
||||
...rest,
|
||||
attachTo: resolveAttachTo(attachTo, namespace),
|
||||
attachTo: resolveAttachTo(attachTo, namespace) as ExtensionAttachTo,
|
||||
$$type: '@backstage/Extension',
|
||||
version: internalDefinition.version,
|
||||
id,
|
||||
|
||||
Reference in New Issue
Block a user