summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarek Gradzki <mgradzki@cisco.com>2017-02-06 07:11:20 +0100
committerMarek Gradzki <mgradzki@cisco.com>2017-02-07 12:19:57 +0000
commit6e8aff729668c8e7d90e27b37240cfeabae550fa (patch)
tree62ceff2a5cb1e679bb01512b412e688f8e9bccc7
parent52812370c20d7f6628da5c7680fb42cbd60a21b9 (diff)
Fix snat mapping creation
The https://gerrit.fd.io/r/#/c/4828/2 introduces external_sw_if_index. If given, external ip address is ignored. Hc2vpp needs to set external_sw_if_index to -1. Change-Id: I9631e52aebbf7e70eb5168aa646fb44d3b82ef85 Signed-off-by: Marek Gradzki <mgradzki@cisco.com>
-rw-r--r--nat/nat2vpp/pom.xml6
-rw-r--r--nat/nat2vpp/src/main/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizer.java1
-rw-r--r--nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/NatTestSchemaContext.java41
-rw-r--r--nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizerTest.java108
-rw-r--r--nat/nat2vpp/src/test/resources/nat/static-mapping.json11
5 files changed, 167 insertions, 0 deletions
diff --git a/nat/nat2vpp/pom.xml b/nat/nat2vpp/pom.xml
index a136961aa..4cd4ab6e4 100644
--- a/nat/nat2vpp/pom.xml
+++ b/nat/nat2vpp/pom.xml
@@ -122,5 +122,11 @@
<artifactId>hamcrest-all</artifactId>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>io.fd.honeycomb.infra</groupId>
+ <artifactId>test-tools</artifactId>
+ <version>${project.version}</version>
+ <scope>test</scope>
+ </dependency>
</dependencies>
</project>
diff --git a/nat/nat2vpp/src/main/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizer.java b/nat/nat2vpp/src/main/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizer.java
index c5417d925..b2852fa4f 100644
--- a/nat/nat2vpp/src/main/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizer.java
+++ b/nat/nat2vpp/src/main/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizer.java
@@ -150,6 +150,7 @@ final class MappingEntryCustomizer implements ListWriterCustomizer<MappingEntry,
request.localIpAddress =
ipv4AddressNoZoneToArray(dataAfter.getInternalSrcAddress().getIpv4Address().getValue());
request.externalIpAddress = ipv4AddressNoZoneToArray(dataAfter.getExternalSrcAddress().getValue());
+ request.externalSwIfIndex = -1; // external ip address is ignored if externalSwIfIndex is given
Optional<Short> internalPortNumber = getPortNumber(id, dataAfter,
(entry) -> Optional.fromNullable(entry.getInternalSrcPort()).transform(PortNumber::getPortType));
diff --git a/nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/NatTestSchemaContext.java b/nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/NatTestSchemaContext.java
new file mode 100644
index 000000000..fea58dee9
--- /dev/null
+++ b/nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/NatTestSchemaContext.java
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.hc2vpp.nat;
+
+import com.google.common.collect.ImmutableSet;
+import io.fd.honeycomb.test.tools.annotations.SchemaContextProvider;
+import org.opendaylight.yangtools.sal.binding.generator.impl.ModuleInfoBackedContext;
+
+public interface NatTestSchemaContext {
+
+ @SchemaContextProvider
+ default ModuleInfoBackedContext context() {
+ ModuleInfoBackedContext context = ModuleInfoBackedContext.create();
+ context.addModuleInfos(ImmutableSet
+ .of(org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.$YangModuleInfoImpl
+ .getInstance(),
+ org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.$YangModuleInfoImpl
+ .getInstance(),
+ org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.$YangModuleInfoImpl
+ .getInstance(),
+ org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.$YangModuleInfoImpl
+ .getInstance(),
+ org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang._interface.nat.rev161214.$YangModuleInfoImpl
+ .getInstance()));
+ return context;
+ }
+}
diff --git a/nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizerTest.java b/nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizerTest.java
new file mode 100644
index 000000000..2627cba4d
--- /dev/null
+++ b/nat/nat2vpp/src/test/java/io/fd/hc2vpp/nat/write/MappingEntryCustomizerTest.java
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.hc2vpp.nat.write;
+
+import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+
+import io.fd.hc2vpp.common.test.write.WriterCustomizerTest;
+import io.fd.hc2vpp.nat.NatTestSchemaContext;
+import io.fd.hc2vpp.nat.util.MappingEntryContext;
+import io.fd.honeycomb.test.tools.HoneycombTestRunner;
+import io.fd.honeycomb.test.tools.annotations.InjectTestData;
+import io.fd.honeycomb.translate.write.WriteFailedException;
+import io.fd.vpp.jvpp.snat.dto.SnatAddStaticMapping;
+import io.fd.vpp.jvpp.snat.dto.SnatAddStaticMappingReply;
+import io.fd.vpp.jvpp.snat.future.FutureJVppSnatFacade;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.NatConfig;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.nat.config.NatInstances;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.nat.config.nat.instances.NatInstance;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.nat.config.nat.instances.NatInstanceKey;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.nat.config.nat.instances.nat.instance.MappingTable;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.nat.config.nat.instances.nat.instance.mapping.table.MappingEntry;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.nat.rev150908.nat.config.nat.instances.nat.instance.mapping.table.MappingEntryKey;
+import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
+
+@RunWith(HoneycombTestRunner.class)
+public class MappingEntryCustomizerTest extends WriterCustomizerTest implements NatTestSchemaContext {
+
+ private static final long NAT_INSTANCE_ID = 1;
+ private static final long MAPPING_ID = 22;
+ private static final InstanceIdentifier<MappingEntry> IID = InstanceIdentifier.create(NatConfig.class)
+ .child(NatInstances.class).child(NatInstance.class, new NatInstanceKey(NAT_INSTANCE_ID))
+ .child(MappingTable.class).child(MappingEntry.class, new MappingEntryKey(MAPPING_ID));
+
+ private static final String MAPPING_TABLE_PATH = "/ietf-nat:nat-config/ietf-nat:nat-instances/"
+ + "ietf-nat:nat-instance[ietf-nat:id='" + NAT_INSTANCE_ID + "']/ietf-nat:mapping-table";
+
+ @Mock
+ private FutureJVppSnatFacade jvppSnat;
+ @Mock
+ private MappingEntryContext mappingContext;
+ private MappingEntryCustomizer customizer;
+
+ @Override
+ public void setUpTest() {
+ customizer = new MappingEntryCustomizer(jvppSnat, mappingContext);
+ when(jvppSnat.snatAddStaticMapping(any())).thenReturn(future(new SnatAddStaticMappingReply()));
+ }
+
+ @Test
+ public void testWrite(
+ @InjectTestData(resourcePath = "/nat/static-mapping.json", id = MAPPING_TABLE_PATH) MappingTable data)
+ throws WriteFailedException {
+ customizer.writeCurrentAttributes(IID, extractMappingEntry(data), writeContext);
+ final SnatAddStaticMapping expectedRequest = getExpectedRequest();
+ expectedRequest.isAdd = 1;
+ verify(jvppSnat).snatAddStaticMapping(expectedRequest);
+ }
+
+ @Test(expected = WriteFailedException.UpdateFailedException.class)
+ public void testUpdate() throws WriteFailedException {
+ final MappingEntry data = mock(MappingEntry.class);
+ customizer.updateCurrentAttributes(IID, data, data, writeContext);
+ }
+
+ @Test
+ public void testDelete(
+ @InjectTestData(resourcePath = "/nat/static-mapping.json", id = MAPPING_TABLE_PATH) MappingTable data)
+ throws WriteFailedException {
+ customizer.deleteCurrentAttributes(IID, extractMappingEntry(data), writeContext);
+ verify(jvppSnat).snatAddStaticMapping(getExpectedRequest());
+ }
+
+ private static MappingEntry extractMappingEntry(MappingTable data) {
+ // assumes single nat instance and single mapping entry
+ return data.getMappingEntry().get(0);
+ }
+
+ private static SnatAddStaticMapping getExpectedRequest() {
+ final SnatAddStaticMapping expectedRequest = new SnatAddStaticMapping();
+ expectedRequest.isIp4 = 1;
+ expectedRequest.addrOnly = 1;
+ expectedRequest.vrfId = (int) NAT_INSTANCE_ID;
+ expectedRequest.externalSwIfIndex = -1;
+ expectedRequest.localIpAddress = new byte[] {(byte) 192, (byte) 168, 1, 87};
+ expectedRequest.externalIpAddress = new byte[] {45, 1, 5, 7};
+ return expectedRequest;
+ }
+} \ No newline at end of file
diff --git a/nat/nat2vpp/src/test/resources/nat/static-mapping.json b/nat/nat2vpp/src/test/resources/nat/static-mapping.json
new file mode 100644
index 000000000..293e5be2b
--- /dev/null
+++ b/nat/nat2vpp/src/test/resources/nat/static-mapping.json
@@ -0,0 +1,11 @@
+{
+ "mapping-table" : {
+ "mapping-entry": {
+ "index": 22,
+ "type": "static",
+ "internal-src-address": "192.168.1.87",
+ "external-src-address": "45.1.5.7"
+ }
+ }
+}
+