Disconnect netconf-topology from threadpool-config-api
[netconf.git] / apps / netconf-topology-impl / src / main / java / org / opendaylight / netconf / topology / impl / NetconfTopologyImpl.java
1 /*
2  * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.netconf.topology.impl;
9
10 import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
11 import java.util.Collection;
12 import java.util.concurrent.Executor;
13 import java.util.concurrent.ScheduledExecutorService;
14 import javax.annotation.PreDestroy;
15 import javax.inject.Inject;
16 import javax.inject.Singleton;
17 import org.opendaylight.aaa.encrypt.AAAEncryptionService;
18 import org.opendaylight.controller.config.threadpool.ScheduledThreadPool;
19 import org.opendaylight.controller.config.threadpool.ThreadPool;
20 import org.opendaylight.mdsal.binding.api.DataBroker;
21 import org.opendaylight.mdsal.binding.api.DataTreeChangeListener;
22 import org.opendaylight.mdsal.binding.api.DataTreeIdentifier;
23 import org.opendaylight.mdsal.binding.api.DataTreeModification;
24 import org.opendaylight.mdsal.binding.api.RpcProviderService;
25 import org.opendaylight.mdsal.common.api.LogicalDatastoreType;
26 import org.opendaylight.mdsal.dom.api.DOMMountPointService;
27 import org.opendaylight.netconf.client.NetconfClientFactory;
28 import org.opendaylight.netconf.client.mdsal.api.BaseNetconfSchemas;
29 import org.opendaylight.netconf.client.mdsal.api.DeviceActionFactory;
30 import org.opendaylight.netconf.client.mdsal.api.SchemaResourceManager;
31 import org.opendaylight.netconf.topology.spi.AbstractNetconfTopology;
32 import org.opendaylight.netconf.topology.spi.NetconfClientConfigurationBuilderFactory;
33 import org.opendaylight.netconf.topology.spi.NetconfNodeUtils;
34 import org.opendaylight.netconf.topology.spi.NetconfTopologyRPCProvider;
35 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NetworkTopology;
36 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.TopologyId;
37 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.Topology;
38 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.TopologyKey;
39 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
40 import org.opendaylight.yangtools.concepts.Registration;
41 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
42 import org.osgi.service.component.annotations.Activate;
43 import org.osgi.service.component.annotations.Component;
44 import org.osgi.service.component.annotations.Deactivate;
45 import org.osgi.service.component.annotations.Reference;
46 import org.slf4j.Logger;
47 import org.slf4j.LoggerFactory;
48
49 // Non-final for testing
50 @Singleton
51 @Component(service = { })
52 public class NetconfTopologyImpl extends AbstractNetconfTopology
53         implements DataTreeChangeListener<Node>, AutoCloseable {
54     private static final Logger LOG = LoggerFactory.getLogger(NetconfTopologyImpl.class);
55
56     private Registration dtclReg;
57     private NetconfTopologyRPCProvider rpcProvider;
58
59     @Inject
60     @Activate
61     public NetconfTopologyImpl(
62             @Reference(target = "(type=netconf-client-factory)") final NetconfClientFactory clientFactory,
63             @Reference(target = "(type=global-netconf-ssh-scheduled-executor)")
64             final ScheduledThreadPool scheduledThreadPool,
65             @Reference(target = "(type=global-netconf-processing-executor)") final ThreadPool processingThreadPool,
66             @Reference final SchemaResourceManager schemaRepositoryProvider, @Reference final DataBroker dataBroker,
67             @Reference final DOMMountPointService mountPointService,
68             @Reference final AAAEncryptionService encryptionService,
69             @Reference(target = "(type=default)") final NetconfClientConfigurationBuilderFactory builderFactory,
70             @Reference final RpcProviderService rpcProviderService, @Reference final BaseNetconfSchemas baseSchemas,
71             @Reference final DeviceActionFactory deviceActionFactory) {
72         this(NetconfNodeUtils.DEFAULT_TOPOLOGY_NAME, clientFactory, scheduledThreadPool.getExecutor(),
73             processingThreadPool.getExecutor(), schemaRepositoryProvider, dataBroker, mountPointService,
74             encryptionService, builderFactory, rpcProviderService, baseSchemas, deviceActionFactory);
75     }
76
77     public NetconfTopologyImpl(final String topologyId, final NetconfClientFactory clientclientFactory,
78             final ScheduledExecutorService scheduledExecutor, final Executor processingExecutor,
79             final SchemaResourceManager schemaRepositoryProvider, final DataBroker dataBroker,
80             final DOMMountPointService mountPointService, final AAAEncryptionService encryptionService,
81             final NetconfClientConfigurationBuilderFactory builderFactory, final RpcProviderService rpcProviderService,
82             final BaseNetconfSchemas baseSchemas) {
83         this(topologyId, clientclientFactory, scheduledExecutor, processingExecutor, schemaRepositoryProvider,
84             dataBroker, mountPointService, encryptionService, builderFactory, rpcProviderService, baseSchemas, null);
85     }
86
87     @SuppressFBWarnings(value = "MC_OVERRIDABLE_METHOD_CALL_IN_CONSTRUCTOR",
88         justification = "DTCL registration of 'this'")
89     public NetconfTopologyImpl(final String topologyId, final NetconfClientFactory clientFactory,
90             final ScheduledExecutorService scheduledExecutor, final Executor processingExecutor,
91             final SchemaResourceManager schemaRepositoryProvider, final DataBroker dataBroker,
92             final DOMMountPointService mountPointService, final AAAEncryptionService encryptionService,
93             final NetconfClientConfigurationBuilderFactory builderFactory, final RpcProviderService rpcProviderService,
94             final BaseNetconfSchemas baseSchemas, final DeviceActionFactory deviceActionFactory) {
95         super(topologyId, clientFactory, scheduledExecutor, processingExecutor,
96             schemaRepositoryProvider, dataBroker, mountPointService, builderFactory, deviceActionFactory, baseSchemas);
97
98         LOG.debug("Registering datastore listener");
99         dtclReg = dataBroker.registerDataTreeChangeListener(DataTreeIdentifier.create(
100             LogicalDatastoreType.CONFIGURATION, InstanceIdentifier.builder(NetworkTopology.class)
101                 .child(Topology.class, new TopologyKey(new TopologyId(topologyId)))
102                 .child(Node.class)
103                 .build()), this);
104         rpcProvider = new NetconfTopologyRPCProvider(rpcProviderService, dataBroker, encryptionService, topologyId);
105     }
106
107     @PreDestroy
108     @Deactivate
109     @Override
110     public void close() {
111         if (rpcProvider != null) {
112             rpcProvider.close();
113             rpcProvider = null;
114         }
115
116         // close all existing connectors, delete whole topology in datastore?
117         deleteAllNodes();
118
119         if (dtclReg != null) {
120             dtclReg.close();
121             dtclReg = null;
122         }
123     }
124
125     @Override
126     public void onDataTreeChanged(final Collection<DataTreeModification<Node>> changes) {
127         for (var change : changes) {
128             final var rootNode = change.getRootNode();
129             final var modType = rootNode.getModificationType();
130             switch (modType) {
131                 case SUBTREE_MODIFIED -> ensureNode("updated", rootNode.getDataAfter());
132                 case WRITE -> ensureNode("created", rootNode.getDataAfter());
133                 case DELETE -> {
134                     final var nodeId = InstanceIdentifier.keyOf(change.getRootPath().getRootIdentifier()).getNodeId();
135                     LOG.debug("Config for node {} deleted", nodeId);
136                     deleteNode(nodeId);
137                 }
138                 default -> LOG.debug("Unsupported modification type: {}.", modType);
139             }
140         }
141     }
142
143     private void ensureNode(final String operation, final Node node) {
144         final var nodeId = node.getNodeId();
145         LOG.debug("Config for node {} {}", nodeId, operation);
146         ensureNode(node);
147     }
148 }