Convert mdsal-netconf-impl to OSGi DS 05/104305/4
authorRobert Varga <robert.varga@pantheon.tech>
Wed, 8 Feb 2023 12:37:52 +0000 (13:37 +0100)
committerRobert Varga <nite@hq.sk>
Wed, 8 Feb 2023 17:50:38 +0000 (17:50 +0000)
The blueprint here is just picking up config admin tuneables and wires
things together. This patch converts this wiring to OSGi DS.
Unfortunately the config admin bits are jumbled together, hence we use
factory components to split them up.

JIRA: NETCONF-951
Change-Id: Icdabc7b2e62cb77a6bf5659274955463be993f88
Signed-off-by: Robert Varga <robert.varga@pantheon.tech>
netconf/mdsal-netconf-impl/pom.xml
netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/DefaultNetconfMonitoringService.java [new file with mode: 0644]
netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/DefaultNetconfServerDispatcher.java [new file with mode: 0644]
netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/NetconfMapperAggregator.java
netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/OSGiNetconfServer.java [new file with mode: 0644]
netconf/mdsal-netconf-impl/src/main/resources/OSGI-INF/blueprint/mdsal-netconf-impl.xml [deleted file]

index 04796b77f5f75b9b7a6c503578507033b2c404e2..bed678a6331917fe5a7392d762b9a8283416d275 100644 (file)
 
   <dependencies>
     <dependency>
-      <groupId>${project.groupId}</groupId>
+      <groupId>com.google.guava</groupId>
+      <artifactId>guava</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>io.netty</groupId>
+      <artifactId>netty-common</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>io.netty</groupId>
+      <artifactId>netty-transport</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.opendaylight.controller</groupId>
+      <artifactId>threadpool-config-api</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.opendaylight.netconf</groupId>
+      <artifactId>netconf-api</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.opendaylight.netconf</groupId>
       <artifactId>netconf-impl</artifactId>
     </dependency>
+    <dependency>
+      <groupId>org.opendaylight.netconf</groupId>
+      <artifactId>netconf-mapping-api</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.osgi</groupId>
+      <artifactId>org.osgi.framework</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.osgi</groupId>
+      <artifactId>org.osgi.service.component</artifactId>
+    </dependency>
     <dependency>
       <groupId>org.osgi</groupId>
       <artifactId>org.osgi.service.component.annotations</artifactId>
     </dependency>
+    <dependency>
+      <groupId>org.osgi</groupId>
+      <artifactId>org.osgi.service.metatype.annotations</artifactId>
+    </dependency>
   </dependencies>
 
   <build>
         <configuration>
           <instructions>
             <Bundle-SymbolicName>${project.artifactId}</Bundle-SymbolicName>
-            <Import-Package>
-                io.netty.channel,
-                io.netty.util,
-                org.opendaylight.controller.config.threadpool,
-                org.opendaylight.netconf.api.monitoring,
-                org.opendaylight.netconf.impl,
-                org.opendaylight.netconf.impl.osgi,
-                org.opendaylight.netconf.mapping.api,
-                *
-            </Import-Package>
           </instructions>
         </configuration>
       </plugin>
diff --git a/netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/DefaultNetconfMonitoringService.java b/netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/DefaultNetconfMonitoringService.java
new file mode 100644 (file)
index 0000000..1b91865
--- /dev/null
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2023 PANTHEON.tech, s.r.o. and others.  All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.netconf.impl.mdsal;
+
+import static java.util.Objects.requireNonNull;
+
+import java.util.Map;
+import org.opendaylight.controller.config.threadpool.ScheduledThreadPool;
+import org.opendaylight.netconf.api.monitoring.NetconfMonitoringService;
+import org.opendaylight.netconf.impl.osgi.NetconfMonitoringServiceImpl;
+import org.opendaylight.netconf.mapping.api.NetconfOperationServiceFactory;
+import org.osgi.service.component.annotations.Activate;
+import org.osgi.service.component.annotations.Component;
+import org.osgi.service.component.annotations.Deactivate;
+
+@Component(factory = DefaultNetconfMonitoringService.FACTORY_NAME, service = NetconfMonitoringService.class)
+public final class DefaultNetconfMonitoringService extends NetconfMonitoringServiceImpl {
+    static final String FACTORY_NAME = "org.opendaylight.netconf.impl.mdsal.DefaultNetconfMonitoringService";
+
+    private static final String OP_PROVIDER_PROP = ".opProvider";
+    private static final String THREAD_POOL_PROP = ".threadPool";
+    private static final String UPDATE_INTERVAL_PROP = ".updateInterval";
+
+    @Activate
+    public DefaultNetconfMonitoringService(final Map<String, ?> properties) {
+        super(OSGiNetconfServer.extractProp(properties, OP_PROVIDER_PROP, NetconfOperationServiceFactory.class),
+            OSGiNetconfServer.extractProp(properties, THREAD_POOL_PROP, ScheduledThreadPool.class),
+            OSGiNetconfServer.extractProp(properties, UPDATE_INTERVAL_PROP, Long.class));
+    }
+
+    @Override
+    @Deactivate
+    public void close() {
+        super.close();
+    }
+
+    static Map<String, ?> props(final NetconfOperationServiceFactory opProvider, final ScheduledThreadPool threadPool,
+            final long updateInterval) {
+        return Map.of(
+            "type", "netconf-server-monitoring",
+            OP_PROVIDER_PROP, requireNonNull(opProvider),
+            THREAD_POOL_PROP, requireNonNull(threadPool),
+            UPDATE_INTERVAL_PROP, updateInterval);
+    }
+}
diff --git a/netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/DefaultNetconfServerDispatcher.java b/netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/DefaultNetconfServerDispatcher.java
new file mode 100644 (file)
index 0000000..a60317b
--- /dev/null
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 2023 PANTHEON.tech, s.r.o. and others.  All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.netconf.impl.mdsal;
+
+import static java.util.Objects.requireNonNull;
+
+import io.netty.channel.EventLoopGroup;
+import java.util.Map;
+import org.opendaylight.netconf.api.NetconfServerDispatcher;
+import org.opendaylight.netconf.impl.NetconfServerDispatcherImpl;
+import org.opendaylight.netconf.impl.ServerChannelInitializer;
+import org.osgi.service.component.annotations.Activate;
+import org.osgi.service.component.annotations.Component;
+
+@Component(factory = DefaultNetconfServerDispatcher.FACTORY_NAME, service = NetconfServerDispatcher.class)
+public final class DefaultNetconfServerDispatcher extends NetconfServerDispatcherImpl {
+    static final String FACTORY_NAME = "org.opendaylight.netconf.impl.mdsal.DefaultNetconfServerDispatcher";
+
+    private static final String BOSS_PROP = ".bossGroup";
+    private static final String WORKER_PROP = ".workerGroup";
+    private static final String INITIALIZER_PROP = ".initializer";
+
+    @Activate
+    public DefaultNetconfServerDispatcher(final Map<String, ?> properties) {
+        super(OSGiNetconfServer.extractProp(properties, INITIALIZER_PROP, ServerChannelInitializer.class),
+            OSGiNetconfServer.extractProp(properties, BOSS_PROP, EventLoopGroup.class),
+            OSGiNetconfServer.extractProp(properties, WORKER_PROP, EventLoopGroup.class));
+    }
+
+    static Map<String, ?> props(final EventLoopGroup bossGroup, final EventLoopGroup workerGroup,
+            final ServerChannelInitializer initializer) {
+        return Map.of(
+            "type", "netconf-server-dispatcher",
+            BOSS_PROP, requireNonNull(bossGroup),
+            WORKER_PROP, requireNonNull(workerGroup),
+            INITIALIZER_PROP, requireNonNull(initializer));
+    }
+}
index 44c624fdd9dec69aab82317d5cd9ea52590f0edf..cf3637a13fe49423b40c72ad9ab564c196aeef88 100644 (file)
@@ -15,8 +15,10 @@ import org.osgi.service.component.annotations.Component;
 import org.osgi.service.component.annotations.Deactivate;
 
 @Component(service = { NetconfOperationServiceFactory.class, NetconfOperationServiceFactoryListener.class },
-           property = "type=mapper-aggregator-registry", immediate = true)
+           property = NetconfMapperAggregator.OSGI_TYPE, immediate = true)
 public final class NetconfMapperAggregator extends AggregatedNetconfOperationServiceFactory {
+    static final String OSGI_TYPE = "type=mapper-aggregator-registry";
+
     @Activate
     public NetconfMapperAggregator() {
         super();
diff --git a/netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/OSGiNetconfServer.java b/netconf/mdsal-netconf-impl/src/main/java/org/opendaylight/netconf/impl/mdsal/OSGiNetconfServer.java
new file mode 100644 (file)
index 0000000..e4bb3ba
--- /dev/null
@@ -0,0 +1,82 @@
+/*
+ * Copyright (c) 2023 PANTHEON.tech, s.r.o. and others.  All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.netconf.impl.mdsal;
+
+import static com.google.common.base.Verify.verifyNotNull;
+import static java.util.Objects.requireNonNull;
+
+import io.netty.channel.EventLoopGroup;
+import io.netty.util.Timer;
+import java.util.Map;
+import org.opendaylight.controller.config.threadpool.ScheduledThreadPool;
+import org.opendaylight.netconf.impl.NetconfServerSessionNegotiatorFactory;
+import org.opendaylight.netconf.impl.ServerChannelInitializer;
+import org.opendaylight.netconf.impl.SessionIdProvider;
+import org.opendaylight.netconf.impl.osgi.AggregatedNetconfOperationServiceFactory;
+import org.opendaylight.netconf.mapping.api.NetconfOperationServiceFactory;
+import org.osgi.framework.FrameworkUtil;
+import org.osgi.service.component.ComponentFactory;
+import org.osgi.service.component.ComponentInstance;
+import org.osgi.service.component.annotations.Activate;
+import org.osgi.service.component.annotations.Component;
+import org.osgi.service.component.annotations.Deactivate;
+import org.osgi.service.component.annotations.Reference;
+import org.osgi.service.metatype.annotations.AttributeDefinition;
+import org.osgi.service.metatype.annotations.Designate;
+import org.osgi.service.metatype.annotations.ObjectClassDefinition;
+
+@Component(service = { }, configurationPid = "org.opendaylight.netconf.impl")
+@Designate(ocd = OSGiNetconfServer.Configuration.class)
+public final class OSGiNetconfServer {
+    @ObjectClassDefinition
+    public @interface Configuration {
+        @AttributeDefinition(min = "0")
+        long connection$_$timeout$_$millis() default 20000;
+        @AttributeDefinition
+        long monitoring$_$update$_$interval() default 6;
+    }
+
+    private final AggregatedNetconfOperationServiceFactory mappers = new AggregatedNetconfOperationServiceFactory();
+    private final ComponentInstance<DefaultNetconfMonitoringService> monitoring;
+    private final ComponentInstance<DefaultNetconfServerDispatcher> dispatcher;
+
+    @Activate
+    public OSGiNetconfServer(
+            @Reference(target = "(component.factory=" + DefaultNetconfMonitoringService.FACTORY_NAME + ")")
+            final ComponentFactory<DefaultNetconfMonitoringService> monitoringFactory,
+            @Reference(target = "(component.factory=" + DefaultNetconfServerDispatcher.FACTORY_NAME + ")")
+            final ComponentFactory<DefaultNetconfServerDispatcher> dispatcherFactory,
+            @Reference(target = "(" + NetconfMapperAggregator.OSGI_TYPE + ")")
+            final NetconfOperationServiceFactory mapperAggregatorRegistry,
+            @Reference(target = "(type=global-netconf-ssh-scheduled-executor)")
+            final ScheduledThreadPool sshScheduledExecutor,
+            @Reference(target = "(type=global-boss-group)") final EventLoopGroup bossGroup,
+            @Reference(target = "(type=global-boss-group)") final EventLoopGroup workerGroup,
+            @Reference(target = "(type=global-timer)") final Timer timer,
+            @Reference final SessionIdProvider sessionIdProvider,
+            final Configuration configuration) {
+        mappers.onAddNetconfOperationServiceFactory(mapperAggregatorRegistry);
+        monitoring = monitoringFactory.newInstance(FrameworkUtil.asDictionary(DefaultNetconfMonitoringService.props(
+            mapperAggregatorRegistry, sshScheduledExecutor, configuration.monitoring$_$update$_$interval())));
+        dispatcher = dispatcherFactory.newInstance(FrameworkUtil.asDictionary(DefaultNetconfServerDispatcher.props(
+            bossGroup, workerGroup, new ServerChannelInitializer(new NetconfServerSessionNegotiatorFactory(timer,
+                mappers, sessionIdProvider, configuration.connection$_$timeout$_$millis(),
+                monitoring.getInstance())))));
+    }
+
+    @Deactivate
+    public void deactivate() {
+        dispatcher.dispose();
+        monitoring.dispose();
+        mappers.close();
+    }
+
+    static <T> T extractProp(final Map<String, ?> properties, final String key, final Class<T> valueType) {
+        return valueType.cast(verifyNotNull(properties.get(requireNonNull(key))));
+    }
+}
diff --git a/netconf/mdsal-netconf-impl/src/main/resources/OSGI-INF/blueprint/mdsal-netconf-impl.xml b/netconf/mdsal-netconf-impl/src/main/resources/OSGI-INF/blueprint/mdsal-netconf-impl.xml
deleted file mode 100644 (file)
index 288991d..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
- Copyright (c) 2016 Inocybe Technologies Inc. and others.  All rights reserved.
-
- This program and the accompanying materials are made available under the
- terms of the Eclipse Public License v1.0 which accompanies this distribution,
- and is available at http://www.eclipse.org/legal/epl-v10.html
--->
-<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"
-           xmlns:odl="http://opendaylight.org/xmlns/blueprint/v1.0.0"
-           xmlns:cm="http://aries.apache.org/blueprint/xmlns/blueprint-cm/v1.3.0"
-           odl:restart-dependents-on-updates="true"
-           odl:use-default-for-reference-types="true">
-
-    <!--This is the MD-SAL netconf server implementation blueprint xml file-->
-
-    <reference id="globalBossGroup"
-               interface="io.netty.channel.EventLoopGroup"
-               odl:type="global-boss-group"/>
-    <reference id="globalWorkerGroup"
-               interface="io.netty.channel.EventLoopGroup"
-               odl:type="global-worker-group"/>
-    <reference id="global-timer"
-               interface="io.netty.util.Timer"
-               odl:type="global-timer"/>
-    <reference id="scheduledThreadPool"
-               interface="org.opendaylight.controller.config.threadpool.ScheduledThreadPool"
-               odl:type="global-netconf-ssh-scheduled-executor"/>
-    <reference id="sessionIdProvider"
-               interface="org.opendaylight.netconf.impl.SessionIdProvider"/>
-    <reference id="aggregatedNetconfOperationServiceFactory"
-               interface="org.opendaylight.netconf.mapping.api.NetconfOperationServiceFactory"
-               odl:type="mapper-aggregator-registry"/>
-
-    <cm:property-placeholder persistent-id="org.opendaylight.netconf.impl" update-strategy="none">
-        <cm:default-properties>
-            <cm:property name="connection-timeout-millis" value="20000"/>
-            <cm:property name="monitoring-update-interval" value="6"/>
-        </cm:default-properties>
-    </cm:property-placeholder>
-
-    <!--NetconfServerDispatcher -->
-
-    <bean id="aggregatedNetconfOperationServiceFactoryMappers"
-          class="org.opendaylight.netconf.impl.osgi.AggregatedNetconfOperationServiceFactory"
-          destroy-method="close">
-        <argument>
-            <list value-type="org.opendaylight.netconf.mapping.api.NetconfOperationServiceFactory">
-                <ref component-id="aggregatedNetconfOperationServiceFactory"/>
-            </list>
-        </argument>
-    </bean>
-
-    <bean id="netconfServerDispatcherImpl"
-          class="org.opendaylight.netconf.impl.NetconfServerDispatcherImpl">
-        <argument>
-            <bean class="org.opendaylight.netconf.impl.ServerChannelInitializer">
-                <argument>
-                    <bean class="org.opendaylight.netconf.impl.NetconfServerSessionNegotiatorFactory">
-                        <argument ref="global-timer"/>
-                        <argument ref="aggregatedNetconfOperationServiceFactoryMappers"/>
-                        <argument ref="sessionIdProvider"/>
-                        <argument value="${connection-timeout-millis}"/>
-                        <argument ref="netconfMonitoringService"/>
-                    </bean>
-                </argument>
-            </bean>
-        </argument>
-        <argument ref="globalBossGroup"/>
-        <argument ref="globalWorkerGroup"/>
-    </bean>
-    <service ref="netconfServerDispatcherImpl"
-             interface="org.opendaylight.netconf.api.NetconfServerDispatcher"
-             odl:type="netconf-server-dispatcher">
-    </service>
-
-    <!--NetconfServerMonitoring -->
-
-    <bean id="netconfMonitoringService"
-          class="org.opendaylight.netconf.impl.osgi.NetconfMonitoringServiceImpl"
-          destroy-method="close">
-        <argument ref="aggregatedNetconfOperationServiceFactory"/>
-        <argument ref="scheduledThreadPool"/>
-        <argument value="${monitoring-update-interval}"/>
-    </bean>
-    <service ref="netconfMonitoringService"
-             interface="org.opendaylight.netconf.api.monitoring.NetconfMonitoringService"
-             odl:type="netconf-server-monitoring">
-    </service>
-
-</blueprint>