diff --git a/spec/components.api.yaml b/spec/components.api.yaml index 0e9bbc7..24f48f6 100644 --- a/spec/components.api.yaml +++ b/spec/components.api.yaml @@ -237,6 +237,11 @@ components: items: $ref: "#/components/schemas/RelatedResource" description: 'Resolved related resource definitions in display order. Backend populates from both legacy and new presentation definitions.' + links: + type: array + items: + $ref: "#/components/schemas/ComponentPresentationLink" + description: 'Resolved presentation links in display order. Backend populates from matching presentation definitions.' events: $ref: "#/components/schemas/ComponentEvents" data: @@ -260,6 +265,7 @@ components: - fields - synced - relatedResources + - links - data - actions - summary @@ -579,6 +585,63 @@ components: in the stql field, and derives the name from the referenced presentation's PresentationName. Array order in the response determines display order. + ComponentPresentationLink: + discriminator: + propertyName: _type + oneOf: + - $ref: '#/components/schemas/ResolvedComponentPresentationLink' + - $ref: '#/components/schemas/ErrorComponentPresentationLink' + description: 'A resolved link definition returned in the FullComponent response.' + + ResolvedComponentPresentationLink: + type: object + properties: + _type: + type: string + enum: [ResolvedPresentationComponentLink] + linkId: + type: string + description: 'Identity key for this link.' + title: + type: string + description: 'Displayed link title.' + target: + type: string + description: 'Relative or fully-qualified link target.' + openInNewTab: + type: boolean + description: 'Whether the link opens in a new tab.' + tooltip: + type: string + description: 'Optional tooltip text.' + required: + - _type + - linkId + - title + - target + - openInNewTab + + ErrorComponentPresentationLink: + type: object + properties: + _type: + type: string + enum: [ErrorPresentationComponentLink] + linkId: + type: string + description: 'Identity key for this link.' + title: + type: string + description: 'Displayed link title, or the link identity when the title could not be resolved.' + message: + type: string + description: 'Reason why the link could not be resolved.' + required: + - _type + - linkId + - title + - message + ComponentEvents: properties: showEvents: diff --git a/spec_domain/settings.yaml b/spec_domain/settings.yaml index ac444f1..b0001ed 100644 --- a/spec_domain/settings.yaml +++ b/spec_domain/settings.yaml @@ -161,6 +161,10 @@ components: type: array items: $ref: '#/components/schemas/PresentationRelatedResource' + links: + type: array + items: + $ref: '#/components/schemas/PresentationLink' events: $ref: '#/components/schemas/PresentationHighlightEvents' metrics: @@ -171,6 +175,7 @@ components: Highlight presentation definition. The `fields` define the fields to show in the highlight page. If multiple ComponentPresentations match, fields are merged by `fieldId` according to binding rank. Related resources follow the same merge semantics using `resourceId` as the identity key. + Links follow the same merge semantics using `linkId` as the identity key. required: - title - fields @@ -232,6 +237,48 @@ components: - Different resourceId entries are appended. - Display order is determined by the order field. + PresentationLink: + type: object + properties: + linkId: + type: string + description: 'Stable identity key for merging across presentations, analogous to fieldId and resourceId.' + title: + type: string + description: 'CEL expression that returns the displayed link title.' + target: + type: string + description: 'CEL expression that returns a relative or fully-qualified link target.' + openInNewTab: + type: boolean + default: false + description: 'Whether the link opens in a new tab. Defaults to false.' + tooltip: + type: string + description: 'Optional CEL expression that returns tooltip text.' + filter: + type: string + description: 'Optional CEL boolean expression deciding whether the link is shown. Missing filters default to true.' + order: + type: number + format: double + description: 'Display order. Higher value means it shows first in UI.' + required: + - linkId + - title + - target + - order + description: | + Link definition for the highlight page. Each entry defines a navigation link shown for a component. + Merge semantics follow related resource rules: + - All presentations whose binding matches the component contribute links. + - Same linkId with higher specificity wins (override). + - Different linkId entries are appended. + - Display order is determined by the order field. + CEL expressions are evaluated against the component presentation context. The filter is evaluated first; + if it evaluates to false the link is omitted. If the filter includes the link but required data cannot be + evaluated, the resolved highlight response reports an error link. + ComponentHighlightProjection: discriminator: propertyName: _type @@ -1462,4 +1509,4 @@ components: connectedComponents: type: boolean neighboringComponents: - type: boolean \ No newline at end of file + type: boolean