This is an automated email from the ASF dual-hosted git repository. exceptionfactory pushed a commit to branch main in repository https://gitbox.apache.org/repos/asf/nifi.git
The following commit(s) were added to refs/heads/main by this push: new d237fd228f NIFI-10738 Updated SNMP tests to retry BindExceptions d237fd228f is described below commit d237fd228f9189e1c605525598923f5ad905a275 Author: Nathan Gough <thena...@gmail.com> AuthorDate: Mon Oct 31 15:40:25 2022 -0400 NIFI-10738 Updated SNMP tests to retry BindExceptions This closes #6606 Co-authored-by: David Handermann <exceptionfact...@apache.org> Signed-off-by: David Handermann <exceptionfact...@apache.org> --- .../nifi/snmp/factory/core/SNMPSocketSupport.java | 77 ++++++++++++++++++++++ .../snmp/factory/core/V1V2cSNMPFactoryTest.java | 26 +++----- .../nifi/snmp/factory/core/V3SNMPFactoryTest.java | 46 ++----------- 3 files changed, 91 insertions(+), 58 deletions(-) diff --git a/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/SNMPSocketSupport.java b/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/SNMPSocketSupport.java new file mode 100644 index 0000000000..151ba23417 --- /dev/null +++ b/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/SNMPSocketSupport.java @@ -0,0 +1,77 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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 org.apache.nifi.snmp.factory.core; + +import org.apache.nifi.remote.io.socket.NetworkUtils; +import org.apache.nifi.snmp.configuration.SNMPConfiguration; +import org.snmp4j.security.SecurityLevel; +import java.net.BindException; +import java.util.function.Function; + +import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.SECURITY_NAME; +import static org.apache.nifi.snmp.helper.configurations.SNMPConfigurationFactory.LOCALHOST; +import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.AUTH_PASSPHRASE; +import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.AUTH_PROTOCOL; +import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.PRIV_PASSPHRASE; +import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.PRIV_PROTOCOL; + +public class SNMPSocketSupport { + + protected static final int RETRIES = 3; + + protected SNMPConfiguration getSnmpConfiguration(int managerPort, String targetPort) { + return new SNMPConfiguration.Builder() + .setRetries(RETRIES) + .setManagerPort(managerPort) + .setTargetHost(LOCALHOST) + .setTargetPort(targetPort) + .setSecurityLevel(SecurityLevel.authPriv.name()) + .setSecurityName(SECURITY_NAME) + .setAuthProtocol(AUTH_PROTOCOL) + .setAuthPassphrase(AUTH_PASSPHRASE) + .setPrivacyProtocol(PRIV_PROTOCOL) + .setPrivacyPassphrase(PRIV_PASSPHRASE) + .build(); + } + + protected <T> T createInstanceWithRetries(final Function<SNMPConfiguration, T> runnable, final int retries) { + int attempts = 0; + while (attempts < retries) { + try { + return runnable.apply(getSnmpConfiguration(NetworkUtils.getAvailableUdpPort(), String.valueOf(NetworkUtils.getAvailableUdpPort()))); + } catch (Exception e) { + if (isBindException(e)) { + attempts++; + if (attempts == retries) { + throw e; + } + } else { + throw e; + } + } + } + throw new IllegalStateException("Failed to bind ports for SNMP manager"); + } + + private boolean isBindException(final Throwable throwable) { + Throwable rootCause = throwable; + while (rootCause.getCause() != null && rootCause.getCause() != rootCause) { + rootCause = rootCause.getCause(); + } + return rootCause instanceof BindException; + } +} diff --git a/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V1V2cSNMPFactoryTest.java b/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V1V2cSNMPFactoryTest.java index 666c934b1e..372fbd931a 100644 --- a/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V1V2cSNMPFactoryTest.java +++ b/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V1V2cSNMPFactoryTest.java @@ -25,31 +25,25 @@ import org.snmp4j.Snmp; import org.snmp4j.Target; import org.snmp4j.security.SecurityLevel; -import java.util.regex.Pattern; - import static org.apache.nifi.snmp.helper.configurations.SNMPConfigurationFactory.LOCALHOST; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.core.IsInstanceOf.instanceOf; +import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertTrue; import static org.mockito.Mockito.spy; import static org.mockito.Mockito.verify; -class V1V2cSNMPFactoryTest { +class V1V2cSNMPFactoryTest extends SNMPSocketSupport { private static final int RETRIES = 3; @Test void testFactoryCreatesV1V2Configuration() { final V1V2cSNMPFactory snmpFactory = new V1V2cSNMPFactory(); - final int managerPort = NetworkUtils.getAvailableUdpPort(); - final String targetPort = String.valueOf(NetworkUtils.getAvailableUdpPort()); - final SNMPConfiguration snmpConfiguration = getSnmpConfiguration(managerPort, targetPort); - - final Target target = snmpFactory.createTargetInstance(snmpConfiguration); + final Target target = createInstanceWithRetries(snmpFactory::createTargetInstance, 5); assertThat(target, instanceOf(CommunityTarget.class)); - assertEquals(LOCALHOST + "/" + targetPort, target.getAddress().toString()); + assertNotNull(target.getAddress().toString()); assertEquals(RETRIES, target.getRetries()); assertEquals(1, target.getSecurityLevel()); assertEquals(StringUtils.EMPTY, target.getSecurityName().toString()); @@ -58,14 +52,9 @@ class V1V2cSNMPFactoryTest { @Test void testFactoryCreatesSnmpManager() { final V1V2cSNMPFactory snmpFactory = new V1V2cSNMPFactory(); - final int managerPort = NetworkUtils.getAvailableUdpPort(); - final String targetPort = String.valueOf(NetworkUtils.getAvailableUdpPort()); - final SNMPConfiguration snmpConfiguration = getSnmpConfiguration(managerPort, targetPort); - - final Snmp snmpManager = snmpFactory.createSnmpManagerInstance(snmpConfiguration); - + final Snmp snmpManager = createInstanceWithRetries(snmpFactory::createSnmpManagerInstance, 5); final String address = snmpManager.getMessageDispatcher().getTransportMappings().iterator().next().getListenAddress().toString(); - assertTrue(Pattern.compile("0.+?0/" + managerPort).matcher(address).matches()); + assertNotNull(address); } @Test @@ -81,7 +70,8 @@ class V1V2cSNMPFactoryTest { verify(snmpFactory).createSnmpManagerInstance(snmpConfiguration); } - private SNMPConfiguration getSnmpConfiguration(int managerPort, String targetPort) { + @Override + protected SNMPConfiguration getSnmpConfiguration(int managerPort, String targetPort) { return new SNMPConfiguration.Builder() .setRetries(RETRIES) .setManagerPort(managerPort) diff --git a/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V3SNMPFactoryTest.java b/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V3SNMPFactoryTest.java index 940f0a722e..16abbc7af5 100644 --- a/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V3SNMPFactoryTest.java +++ b/nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/test/java/org/apache/nifi/snmp/factory/core/V3SNMPFactoryTest.java @@ -22,43 +22,30 @@ import org.junit.jupiter.api.Test; import org.snmp4j.Snmp; import org.snmp4j.Target; import org.snmp4j.UserTarget; -import org.snmp4j.security.SecurityLevel; import org.snmp4j.security.SecurityModels; import org.snmp4j.security.USM; import org.snmp4j.smi.Integer32; import org.snmp4j.smi.OctetString; -import java.util.regex.Pattern; - -import static org.apache.nifi.snmp.helper.configurations.SNMPConfigurationFactory.LOCALHOST; -import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.AUTH_PASSPHRASE; -import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.AUTH_PROTOCOL; -import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.PRIV_PASSPHRASE; -import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.PRIV_PROTOCOL; import static org.apache.nifi.snmp.helper.configurations.SNMPV3ConfigurationFactory.SECURITY_NAME; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.core.IsInstanceOf.instanceOf; import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertTrue; import static org.mockito.Mockito.spy; import static org.mockito.Mockito.verify; -class V3SNMPFactoryTest { +class V3SNMPFactoryTest extends SNMPSocketSupport { - private static final int RETRIES = 3; private static final int EXPECTED_SECURITY_LEVEL = 3; @Test void testFactoryCreatesTarget() { final V3SNMPFactory snmpFactory = new V3SNMPFactory(); - final int managerPort = NetworkUtils.getAvailableUdpPort(); - final String targetPort = String.valueOf(NetworkUtils.getAvailableUdpPort()); - final SNMPConfiguration snmpConfiguration = getSnmpConfiguration(managerPort, targetPort); - - final Target target = snmpFactory.createTargetInstance(snmpConfiguration); - + final Target target = createInstanceWithRetries(snmpFactory::createTargetInstance, 5); assertThat(target, instanceOf(UserTarget.class)); - assertEquals(LOCALHOST + "/" + targetPort, target.getAddress().toString()); + assertNotNull(target.getAddress().toString()); assertEquals(RETRIES, target.getRetries()); assertEquals(EXPECTED_SECURITY_LEVEL, target.getSecurityLevel()); assertEquals(SECURITY_NAME, target.getSecurityName().toString()); @@ -67,15 +54,10 @@ class V3SNMPFactoryTest { @Test void testFactoryCreatesSnmpManager() { final V3SNMPFactory snmpFactory = new V3SNMPFactory(); - final int managerPort = NetworkUtils.getAvailableUdpPort(); - final String targetPort = String.valueOf(NetworkUtils.getAvailableUdpPort()); - final SNMPConfiguration snmpConfiguration = getSnmpConfiguration(managerPort, targetPort); - - final Snmp snmpManager = snmpFactory.createSnmpManagerInstance(snmpConfiguration); - + final Snmp snmpManager = createInstanceWithRetries(snmpFactory::createSnmpManagerInstance, 5); final String address = snmpManager.getMessageDispatcher().getTransportMappings().iterator().next().getListenAddress().toString(); USM usm = (USM) SecurityModels.getInstance().getSecurityModel(new Integer32(3)); - assertTrue(Pattern.compile("0.+?0/" + managerPort).matcher(address).matches()); + assertNotNull(address); assertTrue(usm.hasUser(null, new OctetString("SHAAES128"))); } @@ -90,20 +72,4 @@ class V3SNMPFactoryTest { verify(snmpFactory).createTargetInstance(snmpConfiguration); verify(snmpFactory).createSnmpManagerInstance(snmpConfiguration); } - - private SNMPConfiguration getSnmpConfiguration(int managerPort, String targetPort) { - return new SNMPConfiguration.Builder() - .setRetries(RETRIES) - .setManagerPort(managerPort) - .setTargetHost(LOCALHOST) - .setTargetPort(targetPort) - .setSecurityLevel(SecurityLevel.authPriv.name()) - .setSecurityName(SECURITY_NAME) - .setAuthProtocol(AUTH_PROTOCOL) - .setAuthPassphrase(AUTH_PASSPHRASE) - .setPrivacyProtocol(PRIV_PROTOCOL) - .setPrivacyPassphrase(PRIV_PASSPHRASE) - .build(); - } - }