Skip to content

feat: pivot boost plugins to new entity kinds (AiResource/agent, AiModelServerAPI) #4259

Description

@gabemontero

Summary

Update the boost frontend plugin, OGX entity providers, and Kagenti entity provider to use the new upstream-aligned entity kinds introduced in the ai-integrations workspace (#4209, PR #4211):

  • Agents: Component / ai-agentAiResource / agent
  • AI Model Servers: per-model Resource / ai-model → single AiModelServerAPI / ai-model-server with spec.serverUrl and spec.models.available[]
  • AI Models: no longer separate entities — absorbed into AiModelServerAPI's spec.models.available array

Skills, Rules, MCP Servers, Tools, and Vector Stores are unchanged.

Why

The ai-integrations workspace now provides AiResource (from upstream Backstage @backstage/plugin-catalog-backend-module-ai-model) and AiModelServerAPI (a temporary dedicated kind mirroring upstream backstage/backstage#34476). The boost workspace must consume these new kinds so its frontend catalog UI, entity providers, and fixtures all align with the new entity model.

Depends on

  • #4209 — the ai-integrations workspace must have the AiModelServerAPI kind and backend module available

What to change (17 files)

1. isAiAsset.ts — Single source of truth for AI asset kind/type mapping

File: workspaces/boost/plugins/boost/src/utils/isAiAsset.ts

Update the AI_ASSET_SPEC_TYPES record. This is the single source of truth used by isAiAsset() and buildCatalogFilter().

Before:

export const AI_ASSET_SPEC_TYPES: Record<string, Set<string>> = {
  airesource: new Set(['skill', 'rule']),
  api: new Set(['mcp-server']),
  component: new Set(['ai-agent']),
  resource: new Set(['ai-model', 'ai-tool', 'vector-store']),
};

After:

export const AI_ASSET_SPEC_TYPES: Record<string, Set<string>> = {
  airesource: new Set(['skill', 'rule', 'agent']),
  aimodelserverapi: new Set(['ai-model-server']),
  api: new Set(['mcp-server']),
  resource: new Set(['ai-tool', 'vector-store']),
};

Update the JSDoc table above the constant to match.

2. categoryMeta.ts — UI metadata for entity categories

File: workspaces/boost/plugins/boost/src/utils/categoryMeta.ts

Two key changes in the categoryMetaMap:

  • Rename 'ai-agent' key → 'agent', keep label 'Agents', icon RiRobotLine
  • Rename 'ai-model' key → 'ai-model-server', change label to 'Model Servers', change icon from RiBrainLine to RiServerLine, change CSS var from --boost-color-model to --boost-color-model-server

3. SummaryCard.tsx — Display available models for AiModelServerAPI entities

File: workspaces/boost/plugins/boost/src/components/catalog/entity/SummaryCard.tsx

Add a helper function and UI section to display models from AiModelServerAPI entities:

function getModelsAvailable(entity: { spec?: unknown }): string[] {
  const spec = entity.spec as Record<string, unknown> | undefined;
  const models = spec?.models as Record<string, unknown> | undefined;
  const available = models?.available;
  return Array.isArray(available) ? (available as string[]) : [];
}

In the SummaryCard component:

  • Call getModelsAvailable(entity) alongside existing description and rationale
  • Update the null-guard: if (!description && !rationale && modelsAvailable.length === 0) return null;
  • After the rationale section, add a conditional "Available Models (N)" section with a scrollable container (maxHeight: '300px', overflowY: 'auto') listing each model name

4. OgxAgentEntityProvider.ts — Emit AiResource/agent instead of Component/ai-agent

File: workspaces/boost/plugins/ogx-entity-provider/src/providers/OgxAgentEntityProvider.ts

  • Change kind: 'Component'kind: 'AiResource'
  • Change type: 'ai-agent'type: 'agent'
  • In handoffTargets loop, change dependsOn refs from component:default/...airesource:default/...
  • Update JSDoc comments accordingly

5. OgxModelEntityProvider.ts — Emit single AiModelServerAPI instead of per-model Resources

File: workspaces/boost/plugins/ogx-entity-provider/src/providers/OgxModelEntityProvider.ts

Major restructure. The provider currently emits one Resource entity per model. Change it to emit a single AiModelServerAPI entity per server with all models listed in spec.models.available.

Key changes:

  • Change cachedEntities: Entity[]cachedEntity: Entity | undefined
  • Replace modelToEntity(model) with modelsToServerEntity(models: OgxModelEntry[]):
    • Entity name: sanitizeEntityName('ogx-model-server')
    • kind: 'AiModelServerAPI'
    • spec.type: 'ai-model-server'
    • spec.serverType: 'openai-v1'
    • spec.serverUrl: this.config.baseUrl
    • spec.models: { discoverable: true, available: models.map(m => m.id) }
    • spec.owner: use first model's owned_by via mapOwner()
    • Title: 'OGX Model Server'
    • Description: `OGX model server at ${this.config.baseUrl} serving ${modelNames.length} models`
    • Remove model-specific annotations (boost.redhat.com/model-id, boost.redhat.com/model-owned-by)
  • In run(): call this.modelsToServerEntity(models) instead of models.map(...), update log messages
  • In applyMutation: emit this.cachedEntity ? [{ entity: this.cachedEntity, locationKey: PROVIDER_ID }] : []

6. KagentiAgentEntityProvider.ts — Emit AiResource/agent instead of Component/ai-agent

File: workspaces/boost/plugins/kagenti-entity-provider/src/providers/KagentiAgentEntityProvider.ts

  • Change kind: 'Component'kind: 'AiResource'
  • Change type: 'ai-agent'type: 'agent'
  • Update JSDoc comments accordingly

7. ai-catalog-fixtures.yaml — Update fixture entities

File: workspaces/boost/fixtures/ai-catalog-fixtures.yaml

  • Agent fixture: Change kind: Componentkind: AiResource, type: ai-agenttype: agent
  • Skill fixture: Update agents ref from component:default/developer-assistantairesource:default/developer-assistant
  • Model fixture: Replace the Resource/ai-model entity (granite-3-code) with a commented-out AiModelServerAPI/ai-model-server entity (granite-model-server) — commented out because the AiModelServerAPI kind is not yet registered in the boost dev catalog backend. Include spec.serverType, spec.serverUrl, spec.models.available fields
  • Remove: the Resource/ai-tool (web-search-tool) and Resource/vector-store (docs-vector-store) fixture entries — these categories are real but the fixtures are not useful for dev testing

8. Test files — Update all test fixtures and assertions (10 files)

Every test file that creates mock entities or asserts on entity properties needs updating:

File Changes
plugins/boost/src/components/catalog/AiAssetCard.test.tsx Agent mock: ComponentAiResource, ai-agentagent, test name update
plugins/boost/src/components/catalog/AiCatalogPage.test.tsx Agent mock: ComponentAiResource, ai-agentagent
plugins/boost/src/components/catalog/entity/AdoptionCard.test.tsx OCI entity mock: change from ai-model to ai-tool (fixture was removed), update name/source/url assertions to match
plugins/boost/src/filters/builtInFilterDefinitions.test.ts Agent mock: ComponentAiResource, ai-agentagent, update filter option assertions
plugins/boost/src/hooks/useAiAssets.test.ts Agent mock: ComponentAiResource, ai-agentagent
plugins/boost/src/utils/entityHelpers.test.ts Agent mock: ComponentAiResource, ai-agentagent; OCI tests: ai-modelai-tool
plugins/boost/src/utils/isAiAsset.test.ts Update it.each table: add AiResource/agent, AiModelServerAPI/ai-model-server, remove Component/ai-agent, Resource/ai-model
plugins/ogx-entity-provider/src/providers/OgxAgentEntityProvider.test.ts Assert AiResource/agent, update dependsOn ref to airesource:default/...
plugins/ogx-entity-provider/src/providers/OgxModelEntityProvider.test.ts Expect single entity (not 2), assert AiModelServerAPI/ai-model-server, serverType, serverUrl, models.available array
plugins/kagenti-entity-provider/src/providers/KagentiAgentEntityProvider.test.ts Assert AiResource/agent

Acceptance criteria

  • AI_ASSET_SPEC_TYPES in isAiAsset.ts maps airesource→{skill, rule, agent}, aimodelserverapi→{ai-model-server}, api→{mcp-server}, resource→{ai-tool, vector-store} — no component or ai-model entries remain
  • categoryMeta.ts has agent key (not ai-agent) and ai-model-server key (not ai-model)
  • SummaryCard.tsx displays "Available Models (N)" with a scrollable list when spec.models.available is present
  • OGX agent entity provider emits kind: AiResource, spec.type: agent with airesource:default/... refs
  • OGX model entity provider emits a single AiModelServerAPI entity with spec.serverType, spec.serverUrl, and spec.models.available[]
  • Kagenti agent entity provider emits kind: AiResource, spec.type: agent
  • Fixture YAML uses new kinds/types, model server entry is commented out
  • All tests pass: yarn test --watchAll=false from each plugin directory
  • No references to Component/ai-agent or Resource/ai-model remain in the boost workspace (grep for these to verify)

How to run tests

cd workspaces/boost/plugins/boost && yarn test --watchAll=false
cd workspaces/boost/plugins/ogx-entity-provider && yarn test --watchAll=false
cd workspaces/boost/plugins/kagenti-entity-provider && yarn test --watchAll=false

Do NOT use backstage-cli repo test or npx backstage-cli package test — they have Babel issues with import type syntax in this workspace. Use yarn test --watchAll=false directly.

Notes

  • The AiModelServerAPI kind registration is handled by the ai-integrations workspace's npm packages. Until those packages are published, the AiModelServerAPI fixture entry in ai-catalog-fixtures.yaml must remain commented out (the catalog will reject it without the kind module loaded).
  • The app-config.yaml catalog rules already include AiResource — no config changes needed for agents. AiModelServerAPI is NOT added to catalog rules since the kind module isn't wired into the boost dev backend yet.
  • This is a breaking change for the OGX model entity provider — consumers expecting per-model Resource entities will get a single AiModelServerAPI entity instead.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions