Bug 7469: Advertise CDS DOMDataTreeCommitCohortRegistry 65/50365/1
authorTom Pantelis <tpanteli@brocade.com>
Fri, 6 Jan 2017 15:59:06 +0000 (10:59 -0500)
committerTom Pantelis <tpanteli@brocade.com>
Thu, 12 Jan 2017 14:27:40 +0000 (09:27 -0500)
Advertised the CDS DOMDataTreeCommitCohortRegistry implementation
via the DOMDataBrokerExtension mechanism.

I needed to add a DOMDataTreeCommitCohortRegistry interface version
in the controller DOM API package that extends the controller
DOMDataBrokerExtension since the mdsal DOMDataTreeCommitCohortRegistry
version extends the mdsal DOMDataBrokerExtension.

Change-Id: I71daac1cd7c231d071c376206d85786c333bac68
Signed-off-by: Tom Pantelis <tpanteli@brocade.com>
opendaylight/md-sal/sal-distributed-datastore/src/main/java/org/opendaylight/controller/cluster/databroker/AbstractDOMBroker.java
opendaylight/md-sal/sal-distributed-datastore/src/main/java/org/opendaylight/controller/cluster/databroker/ConcurrentDOMDataBroker.java
opendaylight/md-sal/sal-distributed-datastore/src/test/java/org/opendaylight/controller/cluster/databroker/ConcurrentDOMDataBrokerTest.java
opendaylight/md-sal/sal-dom-api/pom.xml
opendaylight/md-sal/sal-dom-api/src/main/java/org/opendaylight/controller/md/sal/dom/api/DOMDataTreeCommitCohortRegistry.java [new file with mode: 0644]

index 52837183b5c933a4b71f491d63d16961e75899ac..23f8e6d7b3a622f334239d16d92d6f1e10a7f46e 100644 (file)
@@ -10,7 +10,7 @@ package org.opendaylight.controller.cluster.databroker;
 
 import static com.google.common.base.Preconditions.checkState;
 import com.google.common.collect.ImmutableMap;
-import java.util.Collections;
+import com.google.common.collect.ImmutableMap.Builder;
 import java.util.EnumMap;
 import java.util.Map;
 import java.util.concurrent.atomic.AtomicLong;
@@ -21,11 +21,14 @@ import org.opendaylight.controller.md.sal.dom.api.DOMDataBrokerExtension;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataChangeListener;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataTreeChangeListener;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataTreeChangeService;
+import org.opendaylight.controller.md.sal.dom.api.DOMDataTreeCommitCohortRegistry;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataTreeIdentifier;
 import org.opendaylight.controller.md.sal.dom.api.DOMTransactionChain;
 import org.opendaylight.controller.sal.core.spi.data.DOMStore;
 import org.opendaylight.controller.sal.core.spi.data.DOMStoreTransactionChain;
 import org.opendaylight.controller.sal.core.spi.data.DOMStoreTreeChangePublisher;
+import org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohort;
+import org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohortRegistration;
 import org.opendaylight.yangtools.concepts.ListenerRegistration;
 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier;
 import org.slf4j.Logger;
@@ -44,27 +47,60 @@ abstract class AbstractDOMBroker extends AbstractDOMTransactionFactory<DOMStore>
     protected AbstractDOMBroker(final Map<LogicalDatastoreType, DOMStore> datastores) {
         super(datastores);
 
-        boolean treeChange = true;
-        for (DOMStore ds : datastores.values()) {
-            if (!(ds instanceof DOMStoreTreeChangePublisher)) {
-                treeChange = false;
-                break;
-            }
+        Builder<Class<? extends DOMDataBrokerExtension>, DOMDataBrokerExtension> extBuilder = ImmutableMap.builder();
+        if (isSupported(datastores, DOMStoreTreeChangePublisher.class)) {
+            extBuilder.put(DOMDataTreeChangeService.class, new DOMDataTreeChangeService() {
+                @Override
+                public <L extends DOMDataTreeChangeListener> ListenerRegistration<L> registerDataTreeChangeListener(
+                        final DOMDataTreeIdentifier treeId, final L listener) {
+                    DOMStore store = getTxFactories().get(treeId.getDatastoreType());
+                    checkState(store != null, "Requested logical data store is not available.");
+
+                    return ((DOMStoreTreeChangePublisher) store).registerTreeChangeListener(
+                            treeId.getRootIdentifier(), listener);
+                }
+            });
         }
 
-        if (treeChange) {
-            extensions = ImmutableMap.<Class<? extends DOMDataBrokerExtension>, DOMDataBrokerExtension>of(DOMDataTreeChangeService.class, new DOMDataTreeChangeService() {
+        if (isSupported(datastores, org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohortRegistry.class)) {
+            extBuilder.put(DOMDataTreeCommitCohortRegistry.class, new DOMDataTreeCommitCohortRegistry() {
                 @Override
-                public <L extends DOMDataTreeChangeListener> ListenerRegistration<L> registerDataTreeChangeListener(final DOMDataTreeIdentifier treeId, final L listener) {
-                    DOMStore publisher = getTxFactories().get(treeId.getDatastoreType());
-                    checkState(publisher != null, "Requested logical data store is not available.");
+                public <T extends DOMDataTreeCommitCohort> DOMDataTreeCommitCohortRegistration<T> registerCommitCohort(
+                        org.opendaylight.mdsal.dom.api.DOMDataTreeIdentifier path, T cohort) {
+                    DOMStore store = getTxFactories().get(toLegacy(path.getDatastoreType()));
+                    checkState(store != null, "Requested logical data store is not available.");
 
-                    return ((DOMStoreTreeChangePublisher) publisher).registerTreeChangeListener(treeId.getRootIdentifier(), listener);
+                    return ((org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohortRegistry) store)
+                            .registerCommitCohort(path, cohort);
                 }
             });
-        } else {
-            extensions = Collections.emptyMap();
         }
+
+        extensions = extBuilder.build();
+    }
+
+    private static LogicalDatastoreType toLegacy(org.opendaylight.mdsal.common.api.LogicalDatastoreType datastoreType) {
+        switch (datastoreType) {
+            case CONFIGURATION:
+                return LogicalDatastoreType.CONFIGURATION;
+            case OPERATIONAL:
+                return LogicalDatastoreType.OPERATIONAL;
+            default:
+                throw new IllegalArgumentException("Unsupported data store type: " + datastoreType);
+        }
+    }
+
+    private boolean isSupported(Map<LogicalDatastoreType, DOMStore> datastores,
+            Class<?> expDOMStoreInterface) {
+        boolean supported = true;
+        for (DOMStore ds : datastores.values()) {
+            if (!expDOMStoreInterface.isAssignableFrom(ds.getClass())) {
+                supported = false;
+                break;
+            }
+        }
+
+        return supported;
     }
 
     public void setCloseable(final AutoCloseable closeable) {
index 4794e2ad6aa9fce7bc9e7c7c1c3de2f0651ad720..af1aad504c5138bbce0aac5c103b2678bdce0e53 100644 (file)
@@ -29,10 +29,6 @@ import org.opendaylight.controller.md.sal.dom.api.DOMDataWriteTransaction;
 import org.opendaylight.controller.md.sal.dom.broker.impl.TransactionCommitFailedExceptionMapper;
 import org.opendaylight.controller.sal.core.spi.data.DOMStore;
 import org.opendaylight.controller.sal.core.spi.data.DOMStoreThreePhaseCommitCohort;
-import org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohort;
-import org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohortRegistration;
-import org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohortRegistry;
-import org.opendaylight.mdsal.dom.api.DOMDataTreeIdentifier;
 import org.opendaylight.yangtools.util.DurationStatisticsTracker;
 import org.opendaylight.yangtools.util.concurrent.MappingCheckedFuture;
 import org.slf4j.Logger;
@@ -46,7 +42,7 @@ import org.slf4j.LoggerFactory;
  * @author Thomas Pantelis
  */
 @Beta
-public class ConcurrentDOMDataBroker extends AbstractDOMBroker implements DOMDataTreeCommitCohortRegistry {
+public class ConcurrentDOMDataBroker extends AbstractDOMBroker {
     private static final Logger LOG = LoggerFactory.getLogger(ConcurrentDOMDataBroker.class);
     private static final String CAN_COMMIT = "CAN_COMMIT";
     private static final String PRE_COMMIT = "PRE_COMMIT";
@@ -331,23 +327,7 @@ public class ConcurrentDOMDataBroker extends AbstractDOMBroker implements DOMDat
     }
 
     @Override
-    public <T extends DOMDataTreeCommitCohort> DOMDataTreeCommitCohortRegistration<T> registerCommitCohort(
-            DOMDataTreeIdentifier path, T cohort) {
-        DOMStore store = getTxFactories().get(toLegacy(path.getDatastoreType()));
-        if (store instanceof DOMDataTreeCommitCohortRegistry) {
-            return ((DOMDataTreeCommitCohortRegistry) store).registerCommitCohort(path, cohort);
-        }
-        throw new UnsupportedOperationException("Commit cohort is not supported for " + path);
-    }
-
-    private static LogicalDatastoreType toLegacy(org.opendaylight.mdsal.common.api.LogicalDatastoreType datastoreType) {
-        switch (datastoreType) {
-            case CONFIGURATION:
-                return LogicalDatastoreType.CONFIGURATION;
-            case OPERATIONAL:
-                return LogicalDatastoreType.OPERATIONAL;
-            default:
-                throw new IllegalArgumentException("Unsupported data store type: " + datastoreType);
-        }
+    public String toString() {
+        return "Clustered ConcurrentDOMDataBroker";
     }
 }
index 3a88a729cc8d56b8029159fe0bf2f29de6b2112d..064e4a8d7d192f5ec289b694e5cfa4c67b5e5e60 100644 (file)
@@ -31,6 +31,7 @@ import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collection;
 import java.util.List;
+import java.util.Map;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.ExecutionException;
 import java.util.concurrent.SynchronousQueue;
@@ -44,13 +45,17 @@ import org.junit.Test;
 import org.mockito.InOrder;
 import org.mockito.invocation.InvocationOnMock;
 import org.mockito.stubbing.Answer;
+import org.opendaylight.controller.cluster.datastore.DistributedDataStore;
 import org.opendaylight.controller.cluster.datastore.exceptions.NoShardLeaderException;
 import org.opendaylight.controller.md.sal.common.api.data.DataStoreUnavailableException;
 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
 import org.opendaylight.controller.md.sal.common.api.data.TransactionChainListener;
 import org.opendaylight.controller.md.sal.common.api.data.TransactionCommitFailedException;
+import org.opendaylight.controller.md.sal.dom.api.DOMDataBrokerExtension;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataReadOnlyTransaction;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataReadWriteTransaction;
+import org.opendaylight.controller.md.sal.dom.api.DOMDataTreeChangeService;
+import org.opendaylight.controller.md.sal.dom.api.DOMDataTreeCommitCohortRegistry;
 import org.opendaylight.controller.md.sal.dom.api.DOMDataWriteTransaction;
 import org.opendaylight.controller.md.sal.dom.api.DOMTransactionChain;
 import org.opendaylight.controller.md.sal.dom.store.impl.InMemoryDOMDataStore;
@@ -60,6 +65,8 @@ import org.opendaylight.controller.sal.core.spi.data.DOMStoreReadWriteTransactio
 import org.opendaylight.controller.sal.core.spi.data.DOMStoreThreePhaseCommitCohort;
 import org.opendaylight.controller.sal.core.spi.data.DOMStoreTransactionChain;
 import org.opendaylight.controller.sal.core.spi.data.DOMStoreWriteTransaction;
+import org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohort;
+import org.opendaylight.mdsal.dom.api.DOMDataTreeIdentifier;
 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier;
 import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNode;
 
@@ -563,4 +570,29 @@ public class ConcurrentDOMDataBrokerTest {
         }
     }
 
+    @Test
+    public void testExtensions() {
+        DistributedDataStore mockConfigStore = mock(DistributedDataStore.class);
+        DistributedDataStore mockOperStore = mock(DistributedDataStore.class);
+        try (ConcurrentDOMDataBroker dataBroker = new ConcurrentDOMDataBroker(ImmutableMap.of(
+                LogicalDatastoreType.OPERATIONAL, mockOperStore,
+                LogicalDatastoreType.CONFIGURATION, mockConfigStore), futureExecutor)) {
+
+            Map<Class<? extends DOMDataBrokerExtension>, DOMDataBrokerExtension> supportedExtensions =
+                    dataBroker.getSupportedExtensions();
+            assertNotNull(supportedExtensions.get(DOMDataTreeChangeService.class));
+
+            DOMDataTreeCommitCohortRegistry cohortRegistry =
+                    (DOMDataTreeCommitCohortRegistry) supportedExtensions.get(DOMDataTreeCommitCohortRegistry.class);
+            assertNotNull(cohortRegistry);
+
+            DOMDataTreeCommitCohort mockCohort = mock(DOMDataTreeCommitCohort.class);
+            DOMDataTreeIdentifier path = new DOMDataTreeIdentifier(
+                    org.opendaylight.mdsal.common.api.LogicalDatastoreType.CONFIGURATION,
+                    YangInstanceIdentifier.EMPTY);
+            cohortRegistry.registerCommitCohort(path, mockCohort);
+
+            verify(mockConfigStore).registerCommitCohort(path, mockCohort);
+        }
+    }
 }
index 8be91f676ef52f65d3595634782b89351013ac79..f0a8239f51ebfd6925af7fe7ef8b1bf313c61a01 100644 (file)
       <groupId>org.opendaylight.controller</groupId>
       <artifactId>sal-test-model</artifactId>
     </dependency>
+    <dependency>
+      <groupId>org.opendaylight.mdsal</groupId>
+      <artifactId>mdsal-dom-api</artifactId>
+    </dependency>
     <dependency>
       <groupId>org.opendaylight.yangtools</groupId>
       <artifactId>yang-data-impl</artifactId>
diff --git a/opendaylight/md-sal/sal-dom-api/src/main/java/org/opendaylight/controller/md/sal/dom/api/DOMDataTreeCommitCohortRegistry.java b/opendaylight/md-sal/sal-dom-api/src/main/java/org/opendaylight/controller/md/sal/dom/api/DOMDataTreeCommitCohortRegistry.java
new file mode 100644 (file)
index 0000000..15795eb
--- /dev/null
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2017 2015 Brocade Communications Systems, 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
+ */
+package org.opendaylight.controller.md.sal.dom.api;
+
+/**
+ * Interface for a DOM commit cohort registry.
+ *
+ * @author Thomas Pantelis
+ */
+public interface DOMDataTreeCommitCohortRegistry extends DOMDataBrokerExtension,
+        org.opendaylight.mdsal.dom.api.DOMDataTreeCommitCohortRegistry {
+}