Make 'mappings' CLI output user friendly
[lispflowmapping.git] / mappingservice / implementation / src / main / java / org / opendaylight / lispflowmapping / implementation / MappingService.java
index 0928f2098932930a24537cd31c923456caa89bdf..0cd50e7632c4a801699b24acffe3ccd490fdbef1 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015 Cisco Systems, Inc.  All rights reserved.
+ * Copyright (c) 2015, 2017 Cisco Systems, Inc.  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,
@@ -14,16 +14,18 @@ import java.util.List;
 import java.util.concurrent.Future;
 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
 import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
+import org.opendaylight.lispflowmapping.config.ConfigIni;
 import org.opendaylight.lispflowmapping.dsbackend.DataStoreBackEnd;
-import org.opendaylight.lispflowmapping.implementation.config.ConfigIni;
 import org.opendaylight.lispflowmapping.implementation.mdsal.AuthenticationKeyDataListener;
 import org.opendaylight.lispflowmapping.implementation.mdsal.MappingDataListener;
 import org.opendaylight.lispflowmapping.implementation.util.DSBEInputUtil;
 import org.opendaylight.lispflowmapping.implementation.util.RPCInputConvertorUtil;
 import org.opendaylight.lispflowmapping.interfaces.dao.ILispDAO;
 import org.opendaylight.lispflowmapping.interfaces.mappingservice.IMappingService;
+import org.opendaylight.lispflowmapping.lisp.type.MappingData;
 import org.opendaylight.lispflowmapping.lisp.util.LispAddressUtil;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.SiteId;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.XtrId;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.eid.container.Eid;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.locatorrecords.LocatorRecord;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.locatorrecords.LocatorRecordBuilder;
@@ -44,6 +46,9 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev15090
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingInput;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingOutput;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingOutputBuilder;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingWithXtrIdInput;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingWithXtrIdOutput;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingWithXtrIdOutputBuilder;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingsInput;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.GetMappingsOutput;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.mappingservice.rev150906.MappingOrigin;
@@ -87,7 +92,7 @@ public class MappingService implements OdlMappingserviceService, IMappingService
     private final DataBroker dataBroker;
     private final NotificationPublishService notificationPublishService;
 
-    private boolean overwritePolicy = ConfigIni.getInstance().mappingOverwriteIsSet();
+    private boolean mappingMergePolicy = ConfigIni.getInstance().mappingMergeIsSet();
     private boolean notificationPolicy = ConfigIni.getInstance().smrIsSet();
     private boolean iterateMask = true;
     private boolean isMaster = false;
@@ -104,11 +109,11 @@ public class MappingService implements OdlMappingserviceService, IMappingService
 
 
     @Override
-    public void setMappingOverwrite(boolean overwrite) {
-        this.overwritePolicy = overwrite;
+    public void setMappingMerge(boolean mergeMapping) {
+        this.mappingMergePolicy = mergeMapping;
         if (mappingSystem != null) {
-            mappingSystem.setOverwritePolicy(overwrite);
-            ConfigIni.getInstance().setMappingOverwrite(overwrite);
+            mappingSystem.setMappingMerge(mergeMapping);
+            ConfigIni.getInstance().setMappingMerge(mappingMergePolicy);
         }
     }
 
@@ -121,7 +126,7 @@ public class MappingService implements OdlMappingserviceService, IMappingService
         LOG.info("Mapping Service initializing...");
         dsbe = new DataStoreBackEnd(dataBroker);
 
-        mappingSystem = new MappingSystem(dao, iterateMask, notificationPolicy, overwritePolicy);
+        mappingSystem = new MappingSystem(dao, iterateMask, notificationPublishService, mappingMergePolicy);
         mappingSystem.setDataStoreBackEnd(dsbe);
         mappingSystem.initialize();
 
@@ -167,24 +172,29 @@ public class MappingService implements OdlMappingserviceService, IMappingService
     }
 
     @Override
-    public void addMapping(MappingOrigin origin, Eid key, SiteId siteId, Object data, boolean merge) {
+    public void addMapping(MappingOrigin origin, Eid key, SiteId siteId, MappingData mappingData) {
         // SB registrations are first written to the MappingSystem and only afterwards are persisted to the datastore
         if (origin.equals(MappingOrigin.Southbound)) {
             // Store data first in MapCache and only afterwards persist to datastore. This should be used only for SB
             // registrations
-            mappingSystem.addMapping(origin, key, data, merge);
-            dsbe.addMapping(DSBEInputUtil.toMapping(origin, key, siteId, (MappingRecord) data));
-            if (((MappingRecord) data).getXtrId() != null) {
-                dsbe.addXtrIdMapping(DSBEInputUtil.toXtrIdMapping((MappingRecord) data));
+            mappingSystem.addMapping(origin, key, mappingData);
+            dsbe.addMapping(DSBEInputUtil.toMapping(origin, key, siteId, mappingData));
+            if (mappingData.getXtrId() != null) {
+                dsbe.addXtrIdMapping(DSBEInputUtil.toXtrIdMapping(mappingData));
             }
         } else {
-            dsbe.addMapping(DSBEInputUtil.toMapping(origin, key, siteId, (MappingRecord) data));
+            dsbe.addMapping(DSBEInputUtil.toMapping(origin, key, siteId, mappingData));
         }
     }
 
     @Override
-    public void updateMappingRegistration(MappingOrigin origin, Eid key, Long timestamp) {
-        mappingSystem.updateMappingRegistration(origin, key, timestamp);
+    public MappingData addNegativeMapping(Eid key) {
+        return mappingSystem.addNegativeMapping(key);
+    }
+
+    @Override
+    public void refreshMappingRegistration(Eid key, XtrId xtrId, Long timestamp) {
+        mappingSystem.refreshMappingRegistration(key, xtrId, timestamp);
     }
 
     @Override
@@ -214,14 +224,14 @@ public class MappingService implements OdlMappingserviceService, IMappingService
 
         RpcResultBuilder<GetMappingOutput> rpcResultBuilder;
 
-        MappingRecord reply = (MappingRecord) mappingSystem.getMapping(convertToBinaryIfNecessary(input.getEid()));
+        MappingData reply = mappingSystem.getMapping(convertToBinaryIfNecessary(input.getEid()));
 
         if (reply == null) {
             String message = "No mapping was found in the mapping database";
             rpcResultBuilder = RpcResultBuilder.<GetMappingOutput>failed()
                     .withError(RpcError.ErrorType.APPLICATION, NOT_FOUND_TAG, message);
         } else {
-            final MappingRecord convertedReply = convertFromBinaryIfNecessary(reply);
+            final MappingRecord convertedReply = convertFromBinaryIfNecessary(reply.getRecord());
             rpcResultBuilder = RpcResultBuilder.success(new GetMappingOutputBuilder().setMappingRecord(convertedReply));
         }
 
@@ -229,20 +239,43 @@ public class MappingService implements OdlMappingserviceService, IMappingService
     }
 
     @Override
-    public Object getMapping(MappingOrigin origin, Eid key) {
+    public MappingData getMapping(MappingOrigin origin, Eid key) {
         return mappingSystem.getMapping(origin, key);
     }
 
     @Override
-    public Object getMapping(Eid key) {
+    public MappingData getMapping(Eid key) {
         return mappingSystem.getMapping(key);
     }
 
     @Override
-    public Object getMapping(Eid srcKey, Eid dstKey) {
+    public MappingData getMapping(Eid srcKey, Eid dstKey) {
         return mappingSystem.getMapping(srcKey, dstKey);
     }
 
+    @Override
+    public Future<RpcResult<GetMappingWithXtrIdOutput>> getMappingWithXtrId(GetMappingWithXtrIdInput input) {
+        Preconditions.checkNotNull(input, "get-mapping RPC input must be not null!");
+        LOG.trace("RPC received to get the following mapping: " + input.toString());
+
+        RpcResultBuilder<GetMappingWithXtrIdOutput> rpcResultBuilder;
+
+        MappingData reply = mappingSystem.getMapping(null, convertToBinaryIfNecessary(input.getEid()),
+                input.getXtrId());
+
+        if (reply == null) {
+            String message = "No mapping was found in the mapping database";
+            rpcResultBuilder = RpcResultBuilder.<GetMappingWithXtrIdOutput>failed()
+                    .withError(RpcError.ErrorType.APPLICATION, NOT_FOUND_TAG, message);
+        } else {
+            final MappingRecord convertedReply = convertFromBinaryIfNecessary(reply.getRecord());
+            rpcResultBuilder = RpcResultBuilder.success(new GetMappingWithXtrIdOutputBuilder()
+                    .setMappingRecord(convertedReply));
+        }
+
+        return Futures.immediateFuture(rpcResultBuilder.build());
+    }
+
     @Override
     public Future<RpcResult<Void>> removeKey(RemoveKeyInput input) {
         Preconditions.checkNotNull(input, "remove-key RPC input must be not null!");
@@ -385,6 +418,24 @@ public class MappingService implements OdlMappingserviceService, IMappingService
         return null;
     }
 
+    @Override
+    public Future<RpcResult<Void>> removeAllOperationalContent() {
+        RpcResultBuilder<Void> rpcResultBuilder;
+
+        /*
+         * Since master nodes ignore datastore changes for southbound originated mappings, they need to be removed
+         * explicitly.
+         */
+        if (isMaster) {
+            mappingSystem.cleanSBMappings();
+        }
+        dsbe.removeAllOperationalDatastoreContent();
+
+        rpcResultBuilder = RpcResultBuilder.success();
+
+        return Futures.immediateFuture(rpcResultBuilder.build());
+    }
+
     @Override
     public Eid getWidestNegativePrefix(Eid key) {
         return mappingSystem.getWidestNegativePrefix(key);
@@ -420,16 +471,32 @@ public class MappingService implements OdlMappingserviceService, IMappingService
         mappingSystem.removeData(origin, key, subKey);
     }
 
+    @Override
+    public Eid getParentPrefix(Eid key) {
+        return mappingSystem.getParentPrefix(key);
+    }
+
     @Override
     public String printMappings() {
         return mappingSystem.printMappings();
     }
 
+    @Override
+    public String prettyPrintMappings() {
+        return mappingSystem.prettyPrintMappings();
+    }
+
+    @Override
+    public String printKeys() {
+        return mappingSystem.printKeys();
+    }
+
     @Override
     public void close() throws Exception {
         LOG.info("Mapping Service is being destroyed!");
         keyListener.closeDataChangeListener();
         mappingListener.closeDataChangeListener();
+        mappingSystem.destroy();
     }
 
     @Override