This is an automated email from the ASF dual-hosted git repository.

exceptionfactory pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/nifi.git


The following commit(s) were added to refs/heads/main by this push:
     new a25c4a7b40 NIFI-13230 Add support for Flow Registry Clients embedded 
documentation (#10390)
a25c4a7b40 is described below

commit a25c4a7b40c567aff1947c32a9b9e551a773b1ca
Author: Pierre Villard <[email protected]>
AuthorDate: Fri Oct 24 23:28:46 2025 +0200

    NIFI-13230 Add support for Flow Registry Clients embedded documentation 
(#10390)
    
    Signed-off-by: David Handermann <[email protected]>
---
 .../protocol/component/api/ComponentManifest.java  | 10 +++
 .../api/FlowRegistryClientDefinition.java          | 24 +++++++
 .../org/apache/nifi/web/NiFiServiceFacade.java     |  3 +
 .../apache/nifi/web/StandardNiFiServiceFacade.java | 10 +++
 .../java/org/apache/nifi/web/api/FlowResource.java | 53 ++++++++++++++
 .../nifi/web/controller/ControllerFacade.java      | 10 +++
 .../feature/documentation-routing.module.ts        |  5 ++
 .../feature/documentation.component.html           | 13 ++++
 .../feature/documentation.component.ts             |  8 +++
 .../documentation/feature/documentation.module.ts  |  2 +
 .../documentation/service/documentation.service.ts |  7 ++
 .../flow-registry-client-definition.actions.ts     | 41 +++++++++++
 .../flow-registry-client-definition.effects.ts     | 55 ++++++++++++++
 .../flow-registry-client-definition.reducer.ts     | 55 ++++++++++++++
 .../flow-registry-client-definition.selectors.ts   | 25 +++++++
 .../state/flow-registry-client-definition/index.ts | 28 ++++++++
 .../src/app/pages/documentation/state/index.ts     |  7 ++
 .../ui/common/see-also/see-also.component.ts       | 10 +++
 .../flow-registry-client-definition.component.html | 33 +++++++++
 .../flow-registry-client-definition.component.scss | 16 +++++
 .../flow-registry-client-definition.component.ts   | 83 ++++++++++++++++++++++
 .../extension-types/extension-types.effects.ts     |  3 +
 .../extension-types/extension-types.reducer.ts     |  1 +
 .../extension-types/extension-types.selectors.ts   |  4 ++
 .../nifi/src/app/state/extension-types/index.ts    |  1 +
 .../runtime/manifest/ComponentManifestBuilder.java |  7 ++
 .../impl/StandardComponentManifestBuilder.java     | 12 ++++
 .../impl/StandardRuntimeManifestBuilder.java       | 13 ++++
 .../java/org/apache/nifi/nar/ExtensionMapping.java |  2 +-
 .../command/registry/extension/ListExtensions.java |  8 +--
 30 files changed, 544 insertions(+), 5 deletions(-)

diff --git 
a/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/ComponentManifest.java
 
b/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/ComponentManifest.java
index 3c15969611..1bb5fb07d9 100644
--- 
a/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/ComponentManifest.java
+++ 
b/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/ComponentManifest.java
@@ -31,6 +31,7 @@ public class ComponentManifest implements Serializable {
     private List<ProcessorDefinition> processors;
     private List<ReportingTaskDefinition> reportingTasks;
     private List<ParameterProviderDefinition> parameterProviders;
+    private List<FlowRegistryClientDefinition> flowRegistryClients;
     private List<FlowAnalysisRuleDefinition> flowAnalysisRules;
 
     @Schema(description = "Public interfaces defined in this bundle")
@@ -87,4 +88,13 @@ public class ComponentManifest implements Serializable {
         this.flowAnalysisRules = flowAnalysisRules;
     }
 
+    @Schema(description = "Flow Registry Clients provided in this bundle")
+    public List<FlowRegistryClientDefinition> getFlowRegistryClients() {
+        return (flowRegistryClients != null ? 
Collections.unmodifiableList(flowRegistryClients) : null);
+    }
+
+    public void setFlowRegistryClients(List<FlowRegistryClientDefinition> 
flowRegistryClients) {
+        this.flowRegistryClients = flowRegistryClients;
+    }
+
 }
diff --git 
a/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/FlowRegistryClientDefinition.java
 
b/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/FlowRegistryClientDefinition.java
new file mode 100644
index 0000000000..89a4afdf8d
--- /dev/null
+++ 
b/c2/c2-protocol/c2-protocol-component-api/src/main/java/org/apache/nifi/c2/protocol/component/api/FlowRegistryClientDefinition.java
@@ -0,0 +1,24 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.nifi.c2.protocol.component.api;
+
+/**
+ * Definition describing a Flow Registry Client extension.
+ */
+public class FlowRegistryClientDefinition extends 
ConfigurableExtensionDefinition {
+    private static final long serialVersionUID = 1L;
+}
diff --git 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiServiceFacade.java
 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiServiceFacade.java
index c66a124281..ff78ad29f3 100644
--- 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiServiceFacade.java
+++ 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiServiceFacade.java
@@ -23,6 +23,7 @@ import org.apache.nifi.authorization.user.NiFiUser;
 import org.apache.nifi.bundle.BundleCoordinate;
 import org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorDefinition;
 import org.apache.nifi.c2.protocol.component.api.ReportingTaskDefinition;
@@ -502,6 +503,8 @@ public interface NiFiServiceFacade {
      */
     Set<DocumentedTypeDTO> getFlowRegistryTypes();
 
+    FlowRegistryClientDefinition getFlowRegistryClientDefinition(String group, 
String artifact, String version, String type);
+
     /**
      * Returns the RuntimeManifest for this NiFi instance.
      *
diff --git 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/StandardNiFiServiceFacade.java
 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/StandardNiFiServiceFacade.java
index a50cfed673..319f795985 100644
--- 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/StandardNiFiServiceFacade.java
+++ 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/StandardNiFiServiceFacade.java
@@ -55,6 +55,7 @@ import org.apache.nifi.bundle.Bundle;
 import org.apache.nifi.bundle.BundleCoordinate;
 import org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorDefinition;
 import org.apache.nifi.c2.protocol.component.api.ReportingTaskDefinition;
@@ -3983,6 +3984,15 @@ public class StandardNiFiServiceFacade implements 
NiFiServiceFacade {
         return controllerFacade.getFlowRegistryTypes();
     }
 
+    @Override
+    public FlowRegistryClientDefinition getFlowRegistryClientDefinition(String 
group, String artifact, String version, String type) {
+        final FlowRegistryClientDefinition flowRegistryClientDefinition = 
controllerFacade.getFlowRegistryClientDefinition(group, artifact, version, 
type);
+        if (flowRegistryClientDefinition == null) {
+            throw new ResourceNotFoundException("Unable to find definition for 
[%s:%s:%s:%s]".formatted(group, artifact, version, type));
+        }
+        return flowRegistryClientDefinition;
+    }
+
     @Override
     public RuntimeManifest getRuntimeManifest() {
         return controllerFacade.getRuntimeManifest();
diff --git 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/api/FlowResource.java
 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/api/FlowResource.java
index bf14f7421f..124687dd3d 100644
--- 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/api/FlowResource.java
+++ 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/api/FlowResource.java
@@ -55,6 +55,7 @@ import org.apache.nifi.bundle.BundleCoordinate;
 import org.apache.nifi.bundle.BundleDetails;
 import org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorDefinition;
 import org.apache.nifi.c2.protocol.component.api.ReportingTaskDefinition;
@@ -1879,6 +1880,58 @@ public class FlowResource extends ApplicationResource {
         return generateOkResponse(entity).build();
     }
 
+    @GET
+    @Consumes(MediaType.WILDCARD)
+    @Produces(MediaType.APPLICATION_JSON)
+    
@Path("flow-registry-client-definition/{group}/{artifact}/{version}/{type}")
+    @Operation(
+            summary = "Retrieves the Flow Registry Client Definition for the 
specified component type.",
+            description = NON_GUARANTEED_ENDPOINT,
+            responses = {
+                    @ApiResponse(responseCode = "200", content = 
@Content(schema = @Schema(implementation = 
FlowRegistryClientDefinition.class))),
+                    @ApiResponse(responseCode = "400", description = "NiFi was 
unable to complete the request because it was invalid. The request should not 
be retried without modification."),
+                    @ApiResponse(responseCode = "401", description = "Client 
could not be authenticated."),
+                    @ApiResponse(responseCode = "403", description = "Client 
is not authorized to make this request."),
+                    @ApiResponse(responseCode = "404", description = "The flow 
registry client definition for the coordinates could not be located.")
+            },
+            security = {
+                    @SecurityRequirement(name = "Read - /flow")
+            }
+    )
+    public Response getFlowRegistryClientDefinition(
+            @Parameter(
+                    description = "The bundle group",
+                    required = true
+            )
+            @PathParam("group") String group,
+            @Parameter(
+                    description = "The bundle artifact",
+                    required = true
+            )
+            @PathParam("artifact") String artifact,
+            @Parameter(
+                    description = "The bundle version",
+                    required = true
+            )
+            @PathParam("version") String version,
+            @Parameter(
+                    description = "The flow registry client type",
+                    required = true
+            )
+            @PathParam("type") String type
+    ) throws InterruptedException {
+
+        authorizeFlow();
+
+        if (isReplicateRequest()) {
+            return replicate(HttpMethod.GET);
+        }
+
+        final FlowRegistryClientDefinition entity = 
serviceFacade.getFlowRegistryClientDefinition(group, artifact, version, type);
+
+        return generateOkResponse(entity).build();
+    }
+
     @GET
     @Consumes(MediaType.WILDCARD)
     @Produces(MediaType.APPLICATION_JSON)
diff --git 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/controller/ControllerFacade.java
 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/controller/ControllerFacade.java
index b734586d03..ae1d9e2a88 100644
--- 
a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/controller/ControllerFacade.java
+++ 
b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/controller/ControllerFacade.java
@@ -35,6 +35,7 @@ import org.apache.nifi.bundle.BundleCoordinate;
 import org.apache.nifi.c2.protocol.component.api.ComponentManifest;
 import org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorDefinition;
 import org.apache.nifi.c2.protocol.component.api.ReportingTaskDefinition;
@@ -643,6 +644,15 @@ public class ControllerFacade implements Authorizable {
         return 
componentManifest.getParameterProviders().stream().filter(parameterProviderDefinition
 -> 
type.equals(parameterProviderDefinition.getType())).findFirst().orElse(null);
     }
 
+    public FlowRegistryClientDefinition getFlowRegistryClientDefinition(String 
group, String artifact, String version, String type) {
+        final ComponentManifest componentManifest = 
getComponentManifest(group, artifact, version);
+        final List<FlowRegistryClientDefinition> flowRegistryClientDefinitions 
= componentManifest.getFlowRegistryClients();
+        if (flowRegistryClientDefinitions == null) {
+            return null;
+        }
+        return 
flowRegistryClientDefinitions.stream().filter(flowRegistryClientDefinition -> 
type.equals(flowRegistryClientDefinition.getType())).findFirst().orElse(null);
+    }
+
     public FlowAnalysisRuleDefinition getFlowAnalysisRuleDefinition(String 
group, String artifact, String version, String type) {
         final ComponentManifest componentManifest = 
getComponentManifest(group, artifact, version);
         return 
componentManifest.getFlowAnalysisRules().stream().filter(flowAnalysisRuleDefinition
 -> type.equals(flowAnalysisRuleDefinition.getType())).findFirst().orElse(null);
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation-routing.module.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation-routing.module.ts
index bb4dda1228..544dd8106c 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation-routing.module.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation-routing.module.ts
@@ -25,6 +25,7 @@ import { ReportingTaskDefinition } from 
'../ui/reporting-task-definition/reporti
 import { ParameterProviderDefinition } from 
'../ui/parameter-provider-definition/parameter-provider-definition.component';
 import { FlowAnalysisRuleDefinition } from 
'../ui/flow-analysis-rule-definition/flow-analysis-rule-definition.component';
 import { Overview } from '../ui/overview/overview.component';
+import { FlowRegistryClientDefinition } from 
'../ui/flow-registry-client-definition/flow-registry-client-definition.component';
 
 const routes: Routes = [
     {
@@ -44,6 +45,10 @@ const routes: Routes = [
                 path: 
`${ComponentType.ReportingTask}/:group/:artifact/:version/:type`,
                 component: ReportingTaskDefinition
             },
+            {
+                path: 
`${ComponentType.FlowRegistryClient}/:group/:artifact/:version/:type`,
+                component: FlowRegistryClientDefinition
+            },
             {
                 path: 
`${ComponentType.ParameterProvider}/:group/:artifact/:version/:type`,
                 component: ParameterProviderDefinition
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.html
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.html
index 676fab2673..22109056a2 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.html
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.html
@@ -99,6 +99,19 @@
                                     }
                                 "></ng-container>
                         </mat-expansion-panel>
+                        <mat-expansion-panel 
[expanded]="registryClientsExpanded">
+                            <mat-expansion-panel-header>
+                                <mat-panel-title>Flow Registry 
Clients</mat-panel-title>
+                            </mat-expansion-panel-header>
+                            <ng-container
+                                *ngTemplateOutlet="
+                                    extensionLinks;
+                                    context: {
+                                        $implicit: 
filterExtensions((registryClientTypes$ | async)!),
+                                        componentType: 
ComponentType.FlowRegistryClient
+                                    }
+                                "></ng-container>
+                        </mat-expansion-panel>
                         <mat-expansion-panel>
                             <mat-expansion-panel-header>
                                 <mat-panel-title>Flow Analysis 
Rules</mat-panel-title>
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.ts
index a66dc3077d..ff14eb6379 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.component.ts
@@ -33,6 +33,7 @@ import {
     selectFlowAnalysisRuleTypes,
     selectParameterProviderTypes,
     selectProcessorTypes,
+    selectRegistryClientTypes,
     selectReportingTaskTypes
 } from '../../../state/extension-types/extension-types.selectors';
 import { ComponentType, isDefinedAndNotNull, NiFiCommon, selectCurrentRoute } 
from '@nifi/shared';
@@ -72,6 +73,9 @@ export class Documentation implements OnInit, AfterViewInit {
     reportingTaskTypes$ = this.store
         .select(selectReportingTaskTypes)
         .pipe(map((extensionTypes) => this.sortExtensions(extensionTypes)));
+    registryClientTypes$ = this.store
+        .select(selectRegistryClientTypes)
+        .pipe(map((extensionTypes) => this.sortExtensions(extensionTypes)));
     parameterProviderTypes$ = this.store
         .select(selectParameterProviderTypes)
         .pipe(map((extensionTypes) => this.sortExtensions(extensionTypes)));
@@ -93,6 +97,7 @@ export class Documentation implements OnInit, AfterViewInit {
     controllerServicesExpanded = false;
     reportingTasksExpanded = false;
     parameterProvidersExpanded = false;
+    registryClientsExpanded = false;
 
     constructor() {
         this.store
@@ -127,6 +132,9 @@ export class Documentation implements OnInit, AfterViewInit 
{
                     case ComponentType.ParameterProvider:
                         this.parameterProvidersExpanded = true;
                         break;
+                    case ComponentType.FlowRegistryClient:
+                        this.registryClientsExpanded = true;
+                        break;
                 }
             });
 
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.module.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.module.ts
index 95ad4efe55..0766ac00a8 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.module.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/feature/documentation.module.ts
@@ -35,6 +35,7 @@ import { DocumentationEffects } from 
'../state/documentation/documentation.effec
 import { ReportingTaskDefinitionEffects } from 
'../state/reporting-task-definition/reporting-task-definition.effects';
 import { ParameterProviderDefinitionEffects } from 
'../state/parameter-provider-definition/parameter-provider-definition.effects';
 import { FlowAnalysisRuleDefinitionEffects } from 
'../state/flow-analysis-rule-definition/flow-analysis-rule-definition.effects';
+import { FlowRegistryClientDefinitionEffects } from 
'../state/flow-registry-client-definition/flow-registry-client-definition.effects';
 
 @NgModule({
     declarations: [Documentation],
@@ -47,6 +48,7 @@ import { FlowAnalysisRuleDefinitionEffects } from 
'../state/flow-analysis-rule-d
             ProcessorDefinitionEffects,
             ControllerServiceDefinitionEffects,
             ReportingTaskDefinitionEffects,
+            FlowRegistryClientDefinitionEffects,
             ParameterProviderDefinitionEffects,
             FlowAnalysisRuleDefinitionEffects,
             AdditionalDetailsEffects,
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/service/documentation.service.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/service/documentation.service.ts
index 68e17dd0f6..a9955bf6bd 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/service/documentation.service.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/service/documentation.service.ts
@@ -25,6 +25,7 @@ import { AdditionalDetailsEntity } from 
'../state/additional-details';
 import { ReportingTaskDefinition } from '../state/reporting-task-definition';
 import { ParameterProviderDefinition } from 
'../state/parameter-provider-definition';
 import { FlowAnalysisRuleDefinition } from 
'../state/flow-analysis-rule-definition';
+import { FlowRegistryClientDefinition } from 
'../state/flow-registry-client-definition';
 
 @Injectable({ providedIn: 'root' })
 export class DocumentationService {
@@ -50,6 +51,12 @@ export class DocumentationService {
         );
     }
 
+    getFlowRegistryClientDefinition(coordinates: DefinitionCoordinates): 
Observable<FlowRegistryClientDefinition> {
+        return this.httpClient.get<FlowRegistryClientDefinition>(
+            
`${DocumentationService.API}/flow/flow-registry-client-definition/${coordinates.group}/${coordinates.artifact}/${coordinates.version}/${coordinates.type}`
+        );
+    }
+
     getParameterProviderDefinition(coordinates: DefinitionCoordinates): 
Observable<ParameterProviderDefinition> {
         return this.httpClient.get<ParameterProviderDefinition>(
             
`${DocumentationService.API}/flow/parameter-provider-definition/${coordinates.group}/${coordinates.artifact}/${coordinates.version}/${coordinates.type}`
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.actions.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.actions.ts
new file mode 100644
index 0000000000..4f97309058
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.actions.ts
@@ -0,0 +1,41 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import { createAction, props } from '@ngrx/store';
+import { FlowRegistryClientDefinition } from './index';
+import { DefinitionCoordinates } from '../index';
+
+const FLOW_REGISTRY_CLIENT_DEFINITION_PREFIX = '[Flow Registry Client 
Definition]';
+
+export const loadFlowRegistryClientDefinition = createAction(
+    `${FLOW_REGISTRY_CLIENT_DEFINITION_PREFIX} Load Flow Registry Client 
Definition`,
+    props<{ coordinates: DefinitionCoordinates }>()
+);
+
+export const loadFlowRegistryClientDefinitionSuccess = createAction(
+    `${FLOW_REGISTRY_CLIENT_DEFINITION_PREFIX} Load Flow Registry Client 
Definition Success`,
+    props<{ flowRegistryClientDefinition: FlowRegistryClientDefinition }>()
+);
+
+export const flowRegistryClientDefinitionApiError = createAction(
+    `${FLOW_REGISTRY_CLIENT_DEFINITION_PREFIX} Load Flow Registry Client 
Definition Error`,
+    props<{ error: string }>()
+);
+
+export const resetFlowRegistryClientDefinitionState = createAction(
+    `${FLOW_REGISTRY_CLIENT_DEFINITION_PREFIX} Reset Flow Registry Client 
Definition State`
+);
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.effects.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.effects.ts
new file mode 100644
index 0000000000..5a08981365
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.effects.ts
@@ -0,0 +1,55 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import { Injectable, inject } from '@angular/core';
+import { Actions, createEffect, ofType } from '@ngrx/effects';
+import * as FlowRegistryClientDefinitionActions from 
'./flow-registry-client-definition.actions';
+import { catchError, from, map, of, switchMap } from 'rxjs';
+import { DocumentationService } from '../../service/documentation.service';
+import { FlowRegistryClientDefinition } from './index';
+import { ErrorHelper } from '../../../../service/error-helper.service';
+import { HttpErrorResponse } from '@angular/common/http';
+
+@Injectable()
+export class FlowRegistryClientDefinitionEffects {
+    private actions$ = inject(Actions);
+    private documentationService = inject(DocumentationService);
+    private errorHelper = inject(ErrorHelper);
+
+    loadFlowRegistryClientDefinition$ = createEffect(() =>
+        this.actions$.pipe(
+            
ofType(FlowRegistryClientDefinitionActions.loadFlowRegistryClientDefinition),
+            map((action) => action.coordinates),
+            switchMap((coordinates) =>
+                
from(this.documentationService.getFlowRegistryClientDefinition(coordinates)).pipe(
+                    map((flowRegistryClientDefinition: 
FlowRegistryClientDefinition) =>
+                        
FlowRegistryClientDefinitionActions.loadFlowRegistryClientDefinitionSuccess({
+                            flowRegistryClientDefinition
+                        })
+                    ),
+                    catchError((errorResponse: HttpErrorResponse) =>
+                        of(
+                            
FlowRegistryClientDefinitionActions.flowRegistryClientDefinitionApiError({
+                                error: 
this.errorHelper.getErrorString(errorResponse)
+                            })
+                        )
+                    )
+                )
+            )
+        )
+    );
+}
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.reducer.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.reducer.ts
new file mode 100644
index 0000000000..a281bdc345
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.reducer.ts
@@ -0,0 +1,55 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import { createReducer, on } from '@ngrx/store';
+import { FlowRegistryClientDefinitionState } from './index';
+import {
+    flowRegistryClientDefinitionApiError,
+    loadFlowRegistryClientDefinition,
+    loadFlowRegistryClientDefinitionSuccess,
+    resetFlowRegistryClientDefinitionState
+} from './flow-registry-client-definition.actions';
+
+export const initialFlowRegistryClientDefinitionState: 
FlowRegistryClientDefinitionState = {
+    flowRegistryClientDefinition: null,
+    error: null,
+    status: 'pending'
+};
+
+export const flowRegistryClientDefinitionReducer = createReducer(
+    initialFlowRegistryClientDefinitionState,
+    on(loadFlowRegistryClientDefinition, (state) => ({
+        ...state,
+        flowRegistryClientDefinition: null,
+        error: null,
+        status: 'loading' as const
+    })),
+    on(loadFlowRegistryClientDefinitionSuccess, (state, { 
flowRegistryClientDefinition }) => ({
+        ...state,
+        flowRegistryClientDefinition,
+        error: null,
+        status: 'success' as const
+    })),
+    on(flowRegistryClientDefinitionApiError, (state, { error }) => ({
+        ...state,
+        error,
+        status: 'error' as const
+    })),
+    on(resetFlowRegistryClientDefinitionState, () => ({
+        ...initialFlowRegistryClientDefinitionState
+    }))
+);
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.selectors.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.selectors.ts
new file mode 100644
index 0000000000..c89a5dcf40
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/flow-registry-client-definition.selectors.ts
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import { createSelector } from '@ngrx/store';
+import { DocumentationState, selectDocumentationState } from '../index';
+import { flowRegistryClientDefinitionFeatureKey } from './index';
+
+export const selectFlowRegistryClientDefinitionState = createSelector(
+    selectDocumentationState,
+    (state: DocumentationState) => 
state[flowRegistryClientDefinitionFeatureKey]
+);
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/index.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/index.ts
new file mode 100644
index 0000000000..12a84a57a6
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/flow-registry-client-definition/index.ts
@@ -0,0 +1,28 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import { ConfigurableExtensionDefinition } from '../index';
+
+export const flowRegistryClientDefinitionFeatureKey = 
'flowRegistryClientDefinition';
+
+export interface FlowRegistryClientDefinition extends 
ConfigurableExtensionDefinition {}
+
+export interface FlowRegistryClientDefinitionState {
+    flowRegistryClientDefinition: FlowRegistryClientDefinition | null;
+    error: string | null;
+    status: 'pending' | 'loading' | 'success' | 'error';
+}
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/index.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/index.ts
index 5478a66d61..10b02d5de0 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/index.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/state/index.ts
@@ -23,6 +23,11 @@ import {
     ControllerServiceDefinitionState
 } from './controller-service-definition';
 import { controllerServiceDefinitionReducer } from 
'./controller-service-definition/controller-service-definition.reducer';
+import {
+    flowRegistryClientDefinitionFeatureKey,
+    FlowRegistryClientDefinitionState
+} from './flow-registry-client-definition';
+import { flowRegistryClientDefinitionReducer } from 
'./flow-registry-client-definition/flow-registry-client-definition.reducer';
 import { additionalDetailsFeatureKey, AdditionalDetailsState } from 
'./additional-details';
 import { additionalDetailsReducer } from 
'./additional-details/additional-details.reducer';
 import { externalDocumentationFeatureKey, ExternalDocumentationState } from 
'./external-documentation';
@@ -188,6 +193,7 @@ export interface DocumentationState {
     [processorDefinitionFeatureKey]: ProcessorDefinitionState;
     [controllerServiceDefinitionFeatureKey]: ControllerServiceDefinitionState;
     [reportingTaskDefinitionFeatureKey]: ReportingTaskDefinitionState;
+    [flowRegistryClientDefinitionFeatureKey]: 
FlowRegistryClientDefinitionState;
     [parameterProviderDefinitionFeatureKey]: ParameterProviderDefinitionState;
     [flowAnalysisRuleDefinitionFeatureKey]: FlowAnalysisRuleDefinitionState;
     [additionalDetailsFeatureKey]: AdditionalDetailsState;
@@ -199,6 +205,7 @@ export function reducers(state: DocumentationState | 
undefined, action: Action)
         [processorDefinitionFeatureKey]: processorDefinitionReducer,
         [controllerServiceDefinitionFeatureKey]: 
controllerServiceDefinitionReducer,
         [reportingTaskDefinitionFeatureKey]: reportingTaskDefinitionReducer,
+        [flowRegistryClientDefinitionFeatureKey]: 
flowRegistryClientDefinitionReducer,
         [parameterProviderDefinitionFeatureKey]: 
parameterProviderDefinitionReducer,
         [flowAnalysisRuleDefinitionFeatureKey]: 
flowAnalysisRuleDefinitionReducer,
         [additionalDetailsFeatureKey]: additionalDetailsReducer,
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/common/see-also/see-also.component.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/common/see-also/see-also.component.ts
index 7b87264d3d..c99d16fe03 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/common/see-also/see-also.component.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/common/see-also/see-also.component.ts
@@ -77,6 +77,16 @@ export class SeeAlsoComponent {
             };
         }
 
+        documentedType = documentedTypes.registryClientTypes.find(
+            (documentedType) => extensionType === documentedType.type
+        );
+        if (documentedType) {
+            return {
+                documentedType,
+                componentType: ComponentType.FlowRegistryClient
+            };
+        }
+
         documentedType = documentedTypes.parameterProviderTypes.find(
             (documentedType) => extensionType === documentedType.type
         );
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.html
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.html
new file mode 100644
index 0000000000..3bc32df12d
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.html
@@ -0,0 +1,33 @@
+<!--
+  ~ Licensed to the Apache Software Foundation (ASF) under one or more
+  ~ contributor license agreements.  See the NOTICE file distributed with
+  ~ this work for additional information regarding copyright ownership.
+  ~ The ASF licenses this file to You under the Apache License, Version 2.0
+  ~ (the "License"); you may not use this file except in compliance with
+  ~ the License.  You may obtain a copy of the License at
+  ~
+  ~    http://www.apache.org/licenses/LICENSE-2.0
+  ~
+  ~ Unless required by applicable law or agreed to in writing, software
+  ~ distributed under the License is distributed on an "AS IS" BASIS,
+  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  ~ See the License for the specific language governing permissions and
+  ~ limitations under the License.
+  -->
+
+@if (flowRegistryClientDefinitionState) {
+    @if (isInitialLoading(flowRegistryClientDefinitionState)) {
+        <ngx-skeleton-loader count="3"></ngx-skeleton-loader>
+    } @else {
+        @if (flowRegistryClientDefinitionState.flowRegistryClientDefinition; 
as flowRegistryClientDefinition) {
+            <div class="flex flex-col gap-y-4 p-4">
+                <configurable-extension-definition
+                    
[configurableExtensionDefinition]="flowRegistryClientDefinition"></configurable-extension-definition>
+            </div>
+        } @else if (flowRegistryClientDefinitionState.error) {
+            <div class="p-4">
+                {{ flowRegistryClientDefinitionState.error }}
+            </div>
+        }
+    }
+}
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.scss
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.scss
new file mode 100644
index 0000000000..b33f7cac34
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.scss
@@ -0,0 +1,16 @@
+/*!
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.ts
new file mode 100644
index 0000000000..63a26530fe
--- /dev/null
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/pages/documentation/ui/flow-registry-client-definition/flow-registry-client-definition.component.ts
@@ -0,0 +1,83 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import { Component, OnDestroy, inject } from '@angular/core';
+import { Store } from '@ngrx/store';
+import { NiFiState } from '../../../../state';
+import { NgxSkeletonLoaderModule } from 'ngx-skeleton-loader';
+import { ComponentType, isDefinedAndNotNull } from '@nifi/shared';
+import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
+import { ConfigurableExtensionDefinitionComponent } from 
'../common/configurable-extension-definition/configurable-extension-definition.component';
+import { selectDefinitionCoordinatesFromRouteForComponentType } from 
'../../state/documentation/documentation.selectors';
+import { distinctUntilChanged } from 'rxjs';
+import { FlowRegistryClientDefinitionState } from 
'../../state/flow-registry-client-definition';
+import {
+    loadFlowRegistryClientDefinition,
+    resetFlowRegistryClientDefinitionState
+} from 
'../../state/flow-registry-client-definition/flow-registry-client-definition.actions';
+import { selectFlowRegistryClientDefinitionState } from 
'../../state/flow-registry-client-definition/flow-registry-client-definition.selectors';
+
+@Component({
+    selector: 'flow-registry-client-definition',
+    imports: [NgxSkeletonLoaderModule, 
ConfigurableExtensionDefinitionComponent],
+    templateUrl: './flow-registry-client-definition.component.html',
+    styleUrl: './flow-registry-client-definition.component.scss'
+})
+export class FlowRegistryClientDefinition implements OnDestroy {
+    private store = inject<Store<NiFiState>>(Store);
+
+    flowRegistryClientDefinitionState: FlowRegistryClientDefinitionState | 
null = null;
+
+    constructor() {
+        this.store
+            
.select(selectDefinitionCoordinatesFromRouteForComponentType(ComponentType.FlowRegistryClient))
+            .pipe(
+                isDefinedAndNotNull(),
+                distinctUntilChanged(
+                    (a, b) =>
+                        a.group === b.group && a.artifact === b.artifact && 
a.version === b.version && a.type === b.type
+                ),
+                takeUntilDestroyed()
+            )
+            .subscribe((coordinates) => {
+                this.store.dispatch(
+                    loadFlowRegistryClientDefinition({
+                        coordinates
+                    })
+                );
+            });
+
+        this.store
+            .select(selectFlowRegistryClientDefinitionState)
+            .pipe(takeUntilDestroyed())
+            .subscribe((flowRegistryClientDefinitionState) => {
+                this.flowRegistryClientDefinitionState = 
flowRegistryClientDefinitionState;
+
+                if (flowRegistryClientDefinitionState.status === 'loading') {
+                    window.scrollTo({ top: 0, left: 0 });
+                }
+            });
+    }
+
+    isInitialLoading(state: FlowRegistryClientDefinitionState): boolean {
+        return state.flowRegistryClientDefinition === null && state.error === 
null;
+    }
+
+    ngOnDestroy(): void {
+        this.store.dispatch(resetFlowRegistryClientDefinitionState());
+    }
+}
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.effects.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.effects.ts
index 961e35e5f6..256d15e192 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.effects.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.effects.ts
@@ -134,6 +134,7 @@ export class ExtensionTypesEffects {
                     this.extensionTypesService.getProcessorTypes(),
                     this.extensionTypesService.getControllerServiceTypes(),
                     this.extensionTypesService.getReportingTaskTypes(),
+                    this.extensionTypesService.getRegistryClientTypes(),
                     this.extensionTypesService.getParameterProviderTypes(),
                     this.extensionTypesService.getFlowAnalysisRuleTypes()
                 ]).pipe(
@@ -142,6 +143,7 @@ export class ExtensionTypesEffects {
                             processorTypes,
                             controllerServiceTypes,
                             reportingTaskTypes,
+                            registryClientTypes,
                             parameterProviderTypes,
                             flowAnalysisRuleTypes
                         ]) =>
@@ -150,6 +152,7 @@ export class ExtensionTypesEffects {
                                     processorTypes: 
processorTypes.processorTypes,
                                     controllerServiceTypes: 
controllerServiceTypes.controllerServiceTypes,
                                     reportingTaskTypes: 
reportingTaskTypes.reportingTaskTypes,
+                                    registryClientTypes: 
registryClientTypes.flowRegistryClientTypes,
                                     parameterProviderTypes: 
parameterProviderTypes.parameterProviderTypes,
                                     flowAnalysisRuleTypes: 
flowAnalysisRuleTypes.flowAnalysisRuleTypes
                                 }
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.reducer.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.reducer.ts
index 3543dbfa8b..a06944ca42 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.reducer.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.reducer.ts
@@ -89,6 +89,7 @@ export const extensionTypesReducer = createReducer(
         processorTypes: response.processorTypes,
         controllerServiceTypes: response.controllerServiceTypes,
         reportingTaskTypes: response.reportingTaskTypes,
+        registryClientTypes: response.registryClientTypes,
         parameterProviderTypes: response.parameterProviderTypes,
         flowAnalysisRuleTypes: response.flowAnalysisRuleTypes,
         status: 'success' as const
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.selectors.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.selectors.ts
index fabcf161e5..65cc3e4f57 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.selectors.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/extension-types.selectors.ts
@@ -75,6 +75,9 @@ export const selectTypesToIdentifyComponentRestrictions = 
createSelector(
         if (state.reportingTaskTypes) {
             types.push(...state.reportingTaskTypes);
         }
+        if (state.registryClientTypes) {
+            types.push(...state.registryClientTypes);
+        }
         if (state.parameterProviderTypes) {
             types.push(...state.parameterProviderTypes);
         }
@@ -134,6 +137,7 @@ export const selectExtensionFromTypes = (extensionTypes: 
string[]) =>
             processorTypes: state.processorTypes.filter(typeFilter),
             controllerServiceTypes: 
state.controllerServiceTypes.filter(typeFilter),
             reportingTaskTypes: state.reportingTaskTypes.filter(typeFilter),
+            registryClientTypes: state.registryClientTypes.filter(typeFilter),
             parameterProviderTypes: 
state.parameterProviderTypes.filter(typeFilter),
             flowAnalysisRuleTypes: 
state.flowAnalysisRuleTypes.filter(typeFilter)
         } as LoadExtensionTypesForDocumentationResponse;
diff --git 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/index.ts
 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/index.ts
index 7a37a5593a..05d2d351d0 100644
--- 
a/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/index.ts
+++ 
b/nifi-frontend/src/main/frontend/apps/nifi/src/app/state/extension-types/index.ts
@@ -47,6 +47,7 @@ export interface LoadExtensionTypesForDocumentationResponse {
     processorTypes: DocumentedType[];
     controllerServiceTypes: DocumentedType[];
     reportingTaskTypes: DocumentedType[];
+    registryClientTypes: DocumentedType[];
     flowAnalysisRuleTypes: DocumentedType[];
     parameterProviderTypes: DocumentedType[];
 }
diff --git 
a/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/ComponentManifestBuilder.java
 
b/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/ComponentManifestBuilder.java
index 204f6c4f96..9eb3f697ff 100644
--- 
a/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/ComponentManifestBuilder.java
+++ 
b/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/ComponentManifestBuilder.java
@@ -19,6 +19,7 @@ package org.apache.nifi.runtime.manifest;
 import org.apache.nifi.c2.protocol.component.api.ComponentManifest;
 import org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorDefinition;
 import org.apache.nifi.c2.protocol.component.api.ReportingTaskDefinition;
@@ -58,6 +59,12 @@ public interface ComponentManifestBuilder {
      */
     ComponentManifestBuilder addFlowAnalysisRule(FlowAnalysisRuleDefinition 
flowAnalysisRuleDefinition);
 
+    /**
+     * @param flowRegistryClientDefinition a flow registry client definition 
to add
+     * @return the builder
+     */
+    ComponentManifestBuilder 
addFlowRegistryClient(FlowRegistryClientDefinition 
flowRegistryClientDefinition);
+
     /**
      * @return a component manifest containing all the added definitions
      */
diff --git 
a/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardComponentManifestBuilder.java
 
b/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardComponentManifestBuilder.java
index 368a0ee5f4..b6b67181bc 100644
--- 
a/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardComponentManifestBuilder.java
+++ 
b/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardComponentManifestBuilder.java
@@ -19,6 +19,7 @@ package org.apache.nifi.runtime.manifest.impl;
 import org.apache.nifi.c2.protocol.component.api.ComponentManifest;
 import org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorDefinition;
 import org.apache.nifi.c2.protocol.component.api.ReportingTaskDefinition;
@@ -37,6 +38,7 @@ public class StandardComponentManifestBuilder implements 
ComponentManifestBuilde
     private final List<ReportingTaskDefinition> reportingTasks = new 
ArrayList<>();
     private final List<ParameterProviderDefinition> parameterProviders = new 
ArrayList<>();
     private final List<FlowAnalysisRuleDefinition> flowAnalysisRules = new 
ArrayList<>();
+    private final List<FlowRegistryClientDefinition> flowRegistryClients = new 
ArrayList<>();
 
     @Override
     public ComponentManifestBuilder addProcessor(final ProcessorDefinition 
processorDefinition) {
@@ -83,6 +85,15 @@ public class StandardComponentManifestBuilder implements 
ComponentManifestBuilde
         return this;
     }
 
+    @Override
+    public ComponentManifestBuilder addFlowRegistryClient(final 
FlowRegistryClientDefinition flowRegistryClientDefinition) {
+        if (flowRegistryClientDefinition == null) {
+            throw new IllegalArgumentException("Flow Registry Client 
definition cannot be null");
+        }
+        flowRegistryClients.add(flowRegistryClientDefinition);
+        return this;
+    }
+
     @Override
     public ComponentManifest build() {
         final ComponentManifest componentManifest = new ComponentManifest();
@@ -91,6 +102,7 @@ public class StandardComponentManifestBuilder implements 
ComponentManifestBuilde
         componentManifest.setReportingTasks(new ArrayList<>(reportingTasks));
         componentManifest.setParameterProviders(new 
ArrayList<>(parameterProviders));
         componentManifest.setFlowAnalysisRules(new 
ArrayList<>(flowAnalysisRules));
+        componentManifest.setFlowRegistryClients(new 
ArrayList<>(flowRegistryClients));
         return componentManifest;
     }
 
diff --git 
a/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardRuntimeManifestBuilder.java
 
b/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardRuntimeManifestBuilder.java
index 28a124a0d0..9e5fce9306 100644
--- 
a/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardRuntimeManifestBuilder.java
+++ 
b/nifi-manifest/nifi-runtime-manifest-core/src/main/java/org/apache/nifi/runtime/manifest/impl/StandardRuntimeManifestBuilder.java
@@ -24,6 +24,7 @@ import 
org.apache.nifi.c2.protocol.component.api.ControllerServiceDefinition;
 import org.apache.nifi.c2.protocol.component.api.DefinedType;
 import org.apache.nifi.c2.protocol.component.api.ExtensionComponent;
 import org.apache.nifi.c2.protocol.component.api.FlowAnalysisRuleDefinition;
+import org.apache.nifi.c2.protocol.component.api.FlowRegistryClientDefinition;
 import org.apache.nifi.c2.protocol.component.api.MultiProcessorUseCase;
 import org.apache.nifi.c2.protocol.component.api.ParameterProviderDefinition;
 import org.apache.nifi.c2.protocol.component.api.ProcessorConfiguration;
@@ -220,6 +221,9 @@ public class StandardRuntimeManifestBuilder implements 
RuntimeManifestBuilder {
             case PARAMETER_PROVIDER:
                 addParameterProviderDefinition(extensionManifest, extension, 
additionalDetails, componentManifestBuilder);
                 break;
+            case FLOW_REGISTRY_CLIENT:
+                addFlowRegistryClientDefinition(extensionManifest, extension, 
additionalDetails, componentManifestBuilder);
+                break;
         }
     }
 
@@ -395,6 +399,15 @@ public class StandardRuntimeManifestBuilder implements 
RuntimeManifestBuilder {
         
componentManifestBuilder.addParameterProvider(parameterProviderDefinition);
     }
 
+    private void addFlowRegistryClientDefinition(final ExtensionManifest 
extensionManifest, final Extension extension, final String additionalDetails,
+                                                 final 
ComponentManifestBuilder componentManifestBuilder) {
+        final FlowRegistryClientDefinition flowRegistryClientDefinition = new 
FlowRegistryClientDefinition();
+        populateDefinedType(extensionManifest, extension, 
flowRegistryClientDefinition);
+        populateExtensionComponent(extensionManifest, extension, 
additionalDetails, flowRegistryClientDefinition);
+        populateConfigurableComponent(extension, flowRegistryClientDefinition);
+        
componentManifestBuilder.addFlowRegistryClient(flowRegistryClientDefinition);
+    }
+
     private void addFlowAnalysisRuleDefinition(final ExtensionManifest 
extensionManifest, final Extension extension, final String additionalDetails,
                                                 final ComponentManifestBuilder 
componentManifestBuilder) {
         final FlowAnalysisRuleDefinition flowAnalysisRuleDefinition = new 
FlowAnalysisRuleDefinition();
diff --git 
a/nifi-server-api/src/main/java/org/apache/nifi/nar/ExtensionMapping.java 
b/nifi-server-api/src/main/java/org/apache/nifi/nar/ExtensionMapping.java
index 5b366d7249..851fefecb7 100644
--- a/nifi-server-api/src/main/java/org/apache/nifi/nar/ExtensionMapping.java
+++ b/nifi-server-api/src/main/java/org/apache/nifi/nar/ExtensionMapping.java
@@ -93,7 +93,7 @@ public class ExtensionMapping {
     }
 
     void addFlowRegistryClient(final BundleCoordinate coordinate, final String 
flowRegistryClientName) {
-        parameterProviderNames.computeIfAbsent(flowRegistryClientName, name -> 
new HashSet<>()).add(coordinate);
+        flowRegistryClientNames.computeIfAbsent(flowRegistryClientName, name 
-> new HashSet<>()).add(coordinate);
     }
 
     void addAllFlowRegistryClients(final BundleCoordinate coordinate, final 
Collection<String> flowRegistryClientNames) {
diff --git 
a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/extension/ListExtensions.java
 
b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/extension/ListExtensions.java
index 1f5288b52e..18fc71661d 100644
--- 
a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/extension/ListExtensions.java
+++ 
b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/extension/ListExtensions.java
@@ -96,10 +96,10 @@ public class ListExtensions extends 
AbstractNiFiRegistryCommand<ExtensionMetadat
                 final ExtensionType extensionType = 
ExtensionType.valueOf(extensionTypeArg);
                 builder.extensionType(extensionType);
             } catch (Exception e) {
-                throw new NiFiRegistryException("Invalid extension type, 
should be one of "
-                        + ExtensionType.PROCESSOR.toString() + ", "
-                        + ExtensionType.CONTROLLER_SERVICE.toString() + ", or "
-                        + ExtensionType.REPORTING_TASK.toString());
+                final String supportedTypes = 
Arrays.stream(ExtensionType.values())
+                        .map(Enum::toString)
+                        .collect(Collectors.joining(", "));
+                throw new NiFiRegistryException("Invalid extension type, 
should be one of " + supportedTypes);
             }
         }
 

Reply via email to