turcsanyip commented on a change in pull request #5028:
URL: https://github.com/apache/nifi/pull/5028#discussion_r622299989



##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/factory/V3SNMPFactory.java
##########
@@ -0,0 +1,71 @@
+/*
+ * 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;
+
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.Snmp;
+import org.snmp4j.Target;
+import org.snmp4j.mp.MPv3;
+import org.snmp4j.mp.SnmpConstants;
+import org.snmp4j.security.SecurityModels;
+import org.snmp4j.security.SecurityProtocols;
+import org.snmp4j.security.USM;
+import org.snmp4j.security.UsmUser;
+import org.snmp4j.smi.OctetString;
+
+public class V3SNMPFactory extends AbstractSNMPFactory implements SNMPFactory {
+
+    @Override
+    public boolean supports(int version) {
+        return SnmpConstants.version3 == version;
+    }
+
+    @Override
+    public Snmp createSnmpManagerInstance(SNMPConfiguration configuration) {
+        final Snmp snmp = createSimpleSnmpClient();
+
+        // If there's a USM instance associated with the MPv3 bound to this 
Snmp instance (like an agent running
+        // on the same host) it is not null.
+        if (snmp.getUSM() == null) {
+            final OctetString localEngineId = new 
OctetString(MPv3.createLocalEngineID());
+            final USM usm = new USM(SecurityProtocols.getInstance(), 
localEngineId, 0);
+            SecurityModels.getInstance().addSecurityModel(usm);
+        }
+
+        final String username = configuration.getSecurityName();
+        final String authProtocol = configuration.getAuthProtocol();
+        final String authPassword = configuration.getAuthPassword();
+        final String privacyProtocol = configuration.getPrivacyProtocol();
+        final String privacyPassword = configuration.getPrivacyPassword();
+        final OctetString authPasswordOctet = authPassword != null ? new 
OctetString(authPassword) : null;
+        final OctetString privacyPasswordOctet = privacyPassword != null ? new 
OctetString(privacyPassword) : null;
+
+        // Add user information.
+        snmp.getUSM().addUser(

Review comment:
       It seems SNMP4J library stores the authenticated users in static context 
in the JVM.
   Eg. when I configure a processor instance with valid user credentials and 
start it up, then other processors using the same username but invalid 
credentials can also authenticate to the agent and run without error.
   To avoid this interference, `@RequiresInstanceClassLoading` may need to be 
used.

##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/processors/AbstractSNMPProcessor.java
##########
@@ -16,413 +16,249 @@
  */
 package org.apache.nifi.snmp.processors;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
+import org.apache.nifi.annotation.lifecycle.OnScheduled;
 import org.apache.nifi.annotation.lifecycle.OnStopped;
+import org.apache.nifi.components.AllowableValue;
 import org.apache.nifi.components.PropertyDescriptor;
-import org.apache.nifi.components.ValidationContext;
-import org.apache.nifi.components.ValidationResult;
+import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.AbstractProcessor;
 import org.apache.nifi.processor.ProcessContext;
 import org.apache.nifi.processor.ProcessSession;
-import org.apache.nifi.processor.Processor;
-import org.apache.nifi.processor.exception.ProcessException;
 import org.apache.nifi.processor.util.StandardValidators;
-import org.snmp4j.AbstractTarget;
-import org.snmp4j.CommunityTarget;
-import org.snmp4j.Snmp;
-import org.snmp4j.TransportMapping;
-import org.snmp4j.UserTarget;
-import org.snmp4j.mp.MPv3;
-import org.snmp4j.mp.SnmpConstants;
-import org.snmp4j.security.SecurityModels;
-import org.snmp4j.security.SecurityProtocols;
-import org.snmp4j.security.USM;
-import org.snmp4j.security.UsmUser;
-import org.snmp4j.smi.OctetString;
-import org.snmp4j.smi.UdpAddress;
-import org.snmp4j.transport.DefaultUdpTransportMapping;
+import org.apache.nifi.reporting.InitializationException;
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.configuration.SNMPConfigurationBuilder;
+import org.apache.nifi.snmp.logging.SLF4JLogFactory;
+import org.apache.nifi.snmp.operations.SNMPRequestHandler;
+import org.apache.nifi.snmp.operations.SNMPRequestHandlerFactory;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.log.LogFactory;
+
+import java.util.HashMap;
+import java.util.Map;
 
 /**
- * Base processor that uses SNMP4J client API
+ * Base processor that uses SNMP4J client API.
  * (http://www.snmp4j.org/)
- *
- * @param <T> the type of {@link SNMPWorker}. Please see {@link SNMPSetter}
- *            and {@link SNMPGetter}
  */
-abstract class AbstractSNMPProcessor<T extends SNMPWorker> extends 
AbstractProcessor {
+abstract class AbstractSNMPProcessor extends AbstractProcessor {
+
+    static {
+        LogFactory.setLogFactory(new SLF4JLogFactory());
+    }
 
-    /** property to define host of the SNMP agent */
-    public static final PropertyDescriptor HOST = new 
PropertyDescriptor.Builder()
+    // SNMP versions
+    public static final AllowableValue SNMP_V1 = new AllowableValue("SNMPv1", 
"v1", "SNMP version 1");
+    public static final AllowableValue SNMP_V2C = new 
AllowableValue("SNMPv2c", "v2c", "SNMP version 2c");
+    public static final AllowableValue SNMP_V3 = new AllowableValue("SNMPv3", 
"v3", "SNMP version 3 with improved security");
+
+    // SNMPv3 privacy protocols
+    public static final AllowableValue NO_AUTH_NO_PRIV = new 
AllowableValue("noAuthNoPriv", "No authentication or encryption",
+            "No authentication or encryption.");
+    public static final AllowableValue AUTH_NO_PRIV = new 
AllowableValue("authNoPriv", "Authentication without encryption",
+            "Authentication without encryption.");
+    public static final AllowableValue AUTH_PRIV = new 
AllowableValue("authPriv", "Authentication and encryption",
+            "Authentication and encryption.");
+
+    // SNMPv3 authentication protocols
+    public static final AllowableValue MD5 = new AllowableValue("MD5", "MD5 
based authentication",
+            "Provides authentication based on the HMAC-MD5 algorithm.");
+    public static final AllowableValue SHA = new AllowableValue("SHA", "SHA 
based authentication",
+            "Provides authentication based on the HMAC-SHA algorithm.");
+    public static final AllowableValue NO_AUTHENTICATION = new 
AllowableValue("", "None",
+            "Sends SNMP requests without authentication.");
+
+    // SNMPv3 encryption
+    public static final AllowableValue DES = new AllowableValue("DES", "DES",
+            "Symmetric-key algorithm for the encryption of digital data.");
+    public static final AllowableValue DES3 = new AllowableValue("3DES", 
"3DES",
+            "Symmetric-key block cipher, which applies the DES cipher 
algorithm three times to each data block.");
+
+    private static final String AES_DESCRIPTION = "AES is a symmetric 
algorithm which uses the same 128, 192, or 256 bit" +
+            " key for both encryption and decryption (the security of an AES 
system increases exponentially with key length).";
+
+    public static final AllowableValue AES128 = new AllowableValue("AES128", 
"AES128", AES_DESCRIPTION);
+    public static final AllowableValue AES192 = new AllowableValue("AES192", 
"AES192", AES_DESCRIPTION);
+    public static final AllowableValue AES256 = new AllowableValue("AES256", 
"AES256", AES_DESCRIPTION);
+    public static final AllowableValue NO_ENCRYPTION = new AllowableValue("", 
"None",
+            "Sends SNMP requests without encryption.");
+
+
+    public static final PropertyDescriptor AGENT_HOST = new 
PropertyDescriptor.Builder()
             .name("snmp-hostname")
-            .displayName("Host Name")
-            .description("Network address of SNMP Agent (e.g., localhost)")
+            .displayName("SNMP Agent Hostname")
+            .description("Network address of the SNMP Agent.")
             .required(true)
             .defaultValue("localhost")
-            .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .addValidator(StandardValidators.NETWORK_ADDRESS_VALIDATOR)
             .build();
 
-    /** property to define port of the SNMP agent */
-    public static final PropertyDescriptor PORT = new 
PropertyDescriptor.Builder()
+    public static final PropertyDescriptor AGENT_PORT = new 
PropertyDescriptor.Builder()
             .name("snmp-port")
-            .displayName("Port")
-            .description("Numeric value identifying Port of SNMP Agent (e.g., 
161)")
+            .displayName("SNMP Agent Port")
+            .description("Numeric value identifying the port of SNMP Agent.")
             .required(true)
             .defaultValue("161")
             .addValidator(StandardValidators.PORT_VALIDATOR)
             .build();
 
-    /** property to define SNMP version to use */
     public static final PropertyDescriptor SNMP_VERSION = new 
PropertyDescriptor.Builder()
             .name("snmp-version")
             .displayName("SNMP Version")
-            .description("SNMP Version to use")
+            .description("Three significant versions of SNMP have been 
developed and deployed. " +
+                    "SNMPv1 is the original version of the protocol. More 
recent versions, " +
+                    "SNMPv2c and SNMPv3, feature improvements in performance, 
flexibility and security.")
             .required(true)
-            .allowableValues("SNMPv1", "SNMPv2c", "SNMPv3")
-            .defaultValue("SNMPv1")
+            .allowableValues(SNMP_V1, SNMP_V2C, SNMP_V3)
+            .defaultValue(SNMP_V1.getValue())
             .build();
 
-    /** property to define SNMP community to use */
     public static final PropertyDescriptor SNMP_COMMUNITY = new 
PropertyDescriptor.Builder()
             .name("snmp-community")
-            .displayName("SNMP Community (v1 & v2c)")
-            .description("SNMP Community to use (e.g., public)")
-            .required(false)
+            .displayName("SNMP Community")
+            .description("SNMPv1 and SNMPv2 use communities to establish trust 
between managers and agents." +
+                    " Most agents support three community names, one each for 
read-only, read-write and trap." +
+                    " These three community strings control different types of 
activities. The read-only community" +
+                    " applies to get requests. The read-write community string 
applies to set requests. The trap" +
+                    " community string applies to receipt of traps.")
+            .required(true)
+            .sensitive(true)
             .defaultValue("public")
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V1, SNMP_V2C)
             .build();
 
-    /** property to define SNMP security level to use */
     public static final PropertyDescriptor SNMP_SECURITY_LEVEL = new 
PropertyDescriptor.Builder()
             .name("snmp-security-level")
             .displayName("SNMP Security Level")
-            .description("SNMP Security Level to use")
+            .description("SNMP version 3 provides extra security with User 
Based Security Model (USM). The three levels of security is " +
+                    "1. Communication without authentication and encryption 
(NoAuthNoPriv). " +
+                    "2. Communication with authentication and without 
encryption (AuthNoPriv). " +
+                    "3. Communication with authentication and encryption 
(AuthPriv). ")
             .required(true)
-            .allowableValues("noAuthNoPriv", "authNoPriv", "authPriv")
-            .defaultValue("authPriv")
+            .allowableValues(NO_AUTH_NO_PRIV, AUTH_NO_PRIV, AUTH_PRIV)
+            .defaultValue(NO_AUTH_NO_PRIV.getValue())
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP security name to use */
     public static final PropertyDescriptor SNMP_SECURITY_NAME = new 
PropertyDescriptor.Builder()
             .name("snmp-security-name")
-            .displayName("SNMP Security name / user name")
-            .description("Security name used for SNMP exchanges")
-            .required(false)
+            .displayName("SNMP Security Name / Username for SNMP v3 
Authentication")
+            .description("Security name / User name used for SNMP exchanges.")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP authentication protocol to use */
-    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-protocol")
-            .displayName("SNMP Authentication Protocol")
-            .description("SNMP Authentication Protocol to use")
+    public static final PropertyDescriptor SNMP_PRIVACY_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol")
+            .displayName("SNMP Privacy Protocol")
+            .description("Privacy allows for encryption of SNMP v3 messages to 
ensure confidentiality of data.")
             .required(true)
-            .allowableValues("MD5", "SHA", "")
+            .allowableValues(DES, DES3, AES128, AES192, AES256, NO_ENCRYPTION)
             .defaultValue("")
+            .dependsOn(SNMP_SECURITY_LEVEL, AUTH_PRIV)
             .build();
 
-    /** property to define SNMP authentication password to use */
-    public static final PropertyDescriptor SNMP_AUTH_PASSWORD = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-passphrase")
-            .displayName("SNMP Authentication pass phrase")
-            .description("Pass phrase used for SNMP authentication protocol")
-            .required(false)
+    public static final PropertyDescriptor SNMP_PRIVACY_PASSWORD = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol-passphrase")
+            .displayName("SNMP Privacy Protocol Passphrase")
+            .description("Pass phrase used for SNMP privacy protocol")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
             .sensitive(true)
+            .dependsOn(SNMP_SECURITY_LEVEL, AUTH_PRIV)
             .build();
 
-    /** property to define SNMP private protocol to use */
-    public static final PropertyDescriptor SNMP_PRIV_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-private-protocol")
-            .displayName("SNMP Private Protocol")
-            .description("SNMP Private Protocol to use")
+    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-authentication-protocol")
+            .displayName("SNMP Authentication Protocol")
+            .description("Hash based auhentication protocols for secure 
authentication.")
             .required(true)
-            .allowableValues("DES", "3DES", "AES128", "AES192", "AES256", "")
+            .allowableValues(MD5, SHA, NO_AUTHENTICATION)

Review comment:
       `None` option seems to be obsolete because this property depends on 
Security Level and when the property is visible, it is mandatory.

##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/processors/AbstractSNMPProcessor.java
##########
@@ -16,413 +16,249 @@
  */
 package org.apache.nifi.snmp.processors;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
+import org.apache.nifi.annotation.lifecycle.OnScheduled;
 import org.apache.nifi.annotation.lifecycle.OnStopped;
+import org.apache.nifi.components.AllowableValue;
 import org.apache.nifi.components.PropertyDescriptor;
-import org.apache.nifi.components.ValidationContext;
-import org.apache.nifi.components.ValidationResult;
+import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.AbstractProcessor;
 import org.apache.nifi.processor.ProcessContext;
 import org.apache.nifi.processor.ProcessSession;
-import org.apache.nifi.processor.Processor;
-import org.apache.nifi.processor.exception.ProcessException;
 import org.apache.nifi.processor.util.StandardValidators;
-import org.snmp4j.AbstractTarget;
-import org.snmp4j.CommunityTarget;
-import org.snmp4j.Snmp;
-import org.snmp4j.TransportMapping;
-import org.snmp4j.UserTarget;
-import org.snmp4j.mp.MPv3;
-import org.snmp4j.mp.SnmpConstants;
-import org.snmp4j.security.SecurityModels;
-import org.snmp4j.security.SecurityProtocols;
-import org.snmp4j.security.USM;
-import org.snmp4j.security.UsmUser;
-import org.snmp4j.smi.OctetString;
-import org.snmp4j.smi.UdpAddress;
-import org.snmp4j.transport.DefaultUdpTransportMapping;
+import org.apache.nifi.reporting.InitializationException;
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.configuration.SNMPConfigurationBuilder;
+import org.apache.nifi.snmp.logging.SLF4JLogFactory;
+import org.apache.nifi.snmp.operations.SNMPRequestHandler;
+import org.apache.nifi.snmp.operations.SNMPRequestHandlerFactory;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.log.LogFactory;
+
+import java.util.HashMap;
+import java.util.Map;
 
 /**
- * Base processor that uses SNMP4J client API
+ * Base processor that uses SNMP4J client API.
  * (http://www.snmp4j.org/)
- *
- * @param <T> the type of {@link SNMPWorker}. Please see {@link SNMPSetter}
- *            and {@link SNMPGetter}
  */
-abstract class AbstractSNMPProcessor<T extends SNMPWorker> extends 
AbstractProcessor {
+abstract class AbstractSNMPProcessor extends AbstractProcessor {
+
+    static {
+        LogFactory.setLogFactory(new SLF4JLogFactory());
+    }
 
-    /** property to define host of the SNMP agent */
-    public static final PropertyDescriptor HOST = new 
PropertyDescriptor.Builder()
+    // SNMP versions
+    public static final AllowableValue SNMP_V1 = new AllowableValue("SNMPv1", 
"v1", "SNMP version 1");
+    public static final AllowableValue SNMP_V2C = new 
AllowableValue("SNMPv2c", "v2c", "SNMP version 2c");
+    public static final AllowableValue SNMP_V3 = new AllowableValue("SNMPv3", 
"v3", "SNMP version 3 with improved security");
+
+    // SNMPv3 privacy protocols
+    public static final AllowableValue NO_AUTH_NO_PRIV = new 
AllowableValue("noAuthNoPriv", "No authentication or encryption",
+            "No authentication or encryption.");
+    public static final AllowableValue AUTH_NO_PRIV = new 
AllowableValue("authNoPriv", "Authentication without encryption",
+            "Authentication without encryption.");
+    public static final AllowableValue AUTH_PRIV = new 
AllowableValue("authPriv", "Authentication and encryption",
+            "Authentication and encryption.");
+
+    // SNMPv3 authentication protocols
+    public static final AllowableValue MD5 = new AllowableValue("MD5", "MD5 
based authentication",
+            "Provides authentication based on the HMAC-MD5 algorithm.");
+    public static final AllowableValue SHA = new AllowableValue("SHA", "SHA 
based authentication",
+            "Provides authentication based on the HMAC-SHA algorithm.");
+    public static final AllowableValue NO_AUTHENTICATION = new 
AllowableValue("", "None",
+            "Sends SNMP requests without authentication.");
+
+    // SNMPv3 encryption
+    public static final AllowableValue DES = new AllowableValue("DES", "DES",
+            "Symmetric-key algorithm for the encryption of digital data.");
+    public static final AllowableValue DES3 = new AllowableValue("3DES", 
"3DES",
+            "Symmetric-key block cipher, which applies the DES cipher 
algorithm three times to each data block.");
+
+    private static final String AES_DESCRIPTION = "AES is a symmetric 
algorithm which uses the same 128, 192, or 256 bit" +
+            " key for both encryption and decryption (the security of an AES 
system increases exponentially with key length).";
+
+    public static final AllowableValue AES128 = new AllowableValue("AES128", 
"AES128", AES_DESCRIPTION);
+    public static final AllowableValue AES192 = new AllowableValue("AES192", 
"AES192", AES_DESCRIPTION);
+    public static final AllowableValue AES256 = new AllowableValue("AES256", 
"AES256", AES_DESCRIPTION);
+    public static final AllowableValue NO_ENCRYPTION = new AllowableValue("", 
"None",
+            "Sends SNMP requests without encryption.");
+
+
+    public static final PropertyDescriptor AGENT_HOST = new 
PropertyDescriptor.Builder()
             .name("snmp-hostname")
-            .displayName("Host Name")
-            .description("Network address of SNMP Agent (e.g., localhost)")
+            .displayName("SNMP Agent Hostname")
+            .description("Network address of the SNMP Agent.")
             .required(true)
             .defaultValue("localhost")
-            .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .addValidator(StandardValidators.NETWORK_ADDRESS_VALIDATOR)
             .build();
 
-    /** property to define port of the SNMP agent */
-    public static final PropertyDescriptor PORT = new 
PropertyDescriptor.Builder()
+    public static final PropertyDescriptor AGENT_PORT = new 
PropertyDescriptor.Builder()
             .name("snmp-port")
-            .displayName("Port")
-            .description("Numeric value identifying Port of SNMP Agent (e.g., 
161)")
+            .displayName("SNMP Agent Port")
+            .description("Numeric value identifying the port of SNMP Agent.")
             .required(true)
             .defaultValue("161")
             .addValidator(StandardValidators.PORT_VALIDATOR)
             .build();
 
-    /** property to define SNMP version to use */
     public static final PropertyDescriptor SNMP_VERSION = new 
PropertyDescriptor.Builder()
             .name("snmp-version")
             .displayName("SNMP Version")
-            .description("SNMP Version to use")
+            .description("Three significant versions of SNMP have been 
developed and deployed. " +
+                    "SNMPv1 is the original version of the protocol. More 
recent versions, " +
+                    "SNMPv2c and SNMPv3, feature improvements in performance, 
flexibility and security.")
             .required(true)
-            .allowableValues("SNMPv1", "SNMPv2c", "SNMPv3")
-            .defaultValue("SNMPv1")
+            .allowableValues(SNMP_V1, SNMP_V2C, SNMP_V3)
+            .defaultValue(SNMP_V1.getValue())
             .build();
 
-    /** property to define SNMP community to use */
     public static final PropertyDescriptor SNMP_COMMUNITY = new 
PropertyDescriptor.Builder()
             .name("snmp-community")
-            .displayName("SNMP Community (v1 & v2c)")
-            .description("SNMP Community to use (e.g., public)")
-            .required(false)
+            .displayName("SNMP Community")
+            .description("SNMPv1 and SNMPv2 use communities to establish trust 
between managers and agents." +
+                    " Most agents support three community names, one each for 
read-only, read-write and trap." +
+                    " These three community strings control different types of 
activities. The read-only community" +
+                    " applies to get requests. The read-write community string 
applies to set requests. The trap" +
+                    " community string applies to receipt of traps.")
+            .required(true)
+            .sensitive(true)
             .defaultValue("public")
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V1, SNMP_V2C)
             .build();
 
-    /** property to define SNMP security level to use */
     public static final PropertyDescriptor SNMP_SECURITY_LEVEL = new 
PropertyDescriptor.Builder()
             .name("snmp-security-level")
             .displayName("SNMP Security Level")
-            .description("SNMP Security Level to use")
+            .description("SNMP version 3 provides extra security with User 
Based Security Model (USM). The three levels of security is " +
+                    "1. Communication without authentication and encryption 
(NoAuthNoPriv). " +
+                    "2. Communication with authentication and without 
encryption (AuthNoPriv). " +
+                    "3. Communication with authentication and encryption 
(AuthPriv). ")
             .required(true)
-            .allowableValues("noAuthNoPriv", "authNoPriv", "authPriv")
-            .defaultValue("authPriv")
+            .allowableValues(NO_AUTH_NO_PRIV, AUTH_NO_PRIV, AUTH_PRIV)
+            .defaultValue(NO_AUTH_NO_PRIV.getValue())
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP security name to use */
     public static final PropertyDescriptor SNMP_SECURITY_NAME = new 
PropertyDescriptor.Builder()
             .name("snmp-security-name")
-            .displayName("SNMP Security name / user name")
-            .description("Security name used for SNMP exchanges")
-            .required(false)
+            .displayName("SNMP Security Name / Username for SNMP v3 
Authentication")

Review comment:
       This property name is too long and does not fit into the cell on the UI. 
I would use `SNMP Security Name` only and add the explanation in the 
description.

##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/processors/AbstractSNMPProcessor.java
##########
@@ -16,413 +16,249 @@
  */
 package org.apache.nifi.snmp.processors;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
+import org.apache.nifi.annotation.lifecycle.OnScheduled;
 import org.apache.nifi.annotation.lifecycle.OnStopped;
+import org.apache.nifi.components.AllowableValue;
 import org.apache.nifi.components.PropertyDescriptor;
-import org.apache.nifi.components.ValidationContext;
-import org.apache.nifi.components.ValidationResult;
+import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.AbstractProcessor;
 import org.apache.nifi.processor.ProcessContext;
 import org.apache.nifi.processor.ProcessSession;
-import org.apache.nifi.processor.Processor;
-import org.apache.nifi.processor.exception.ProcessException;
 import org.apache.nifi.processor.util.StandardValidators;
-import org.snmp4j.AbstractTarget;
-import org.snmp4j.CommunityTarget;
-import org.snmp4j.Snmp;
-import org.snmp4j.TransportMapping;
-import org.snmp4j.UserTarget;
-import org.snmp4j.mp.MPv3;
-import org.snmp4j.mp.SnmpConstants;
-import org.snmp4j.security.SecurityModels;
-import org.snmp4j.security.SecurityProtocols;
-import org.snmp4j.security.USM;
-import org.snmp4j.security.UsmUser;
-import org.snmp4j.smi.OctetString;
-import org.snmp4j.smi.UdpAddress;
-import org.snmp4j.transport.DefaultUdpTransportMapping;
+import org.apache.nifi.reporting.InitializationException;
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.configuration.SNMPConfigurationBuilder;
+import org.apache.nifi.snmp.logging.SLF4JLogFactory;
+import org.apache.nifi.snmp.operations.SNMPRequestHandler;
+import org.apache.nifi.snmp.operations.SNMPRequestHandlerFactory;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.log.LogFactory;
+
+import java.util.HashMap;
+import java.util.Map;
 
 /**
- * Base processor that uses SNMP4J client API
+ * Base processor that uses SNMP4J client API.
  * (http://www.snmp4j.org/)
- *
- * @param <T> the type of {@link SNMPWorker}. Please see {@link SNMPSetter}
- *            and {@link SNMPGetter}
  */
-abstract class AbstractSNMPProcessor<T extends SNMPWorker> extends 
AbstractProcessor {
+abstract class AbstractSNMPProcessor extends AbstractProcessor {
+
+    static {
+        LogFactory.setLogFactory(new SLF4JLogFactory());
+    }
 
-    /** property to define host of the SNMP agent */
-    public static final PropertyDescriptor HOST = new 
PropertyDescriptor.Builder()
+    // SNMP versions
+    public static final AllowableValue SNMP_V1 = new AllowableValue("SNMPv1", 
"v1", "SNMP version 1");
+    public static final AllowableValue SNMP_V2C = new 
AllowableValue("SNMPv2c", "v2c", "SNMP version 2c");
+    public static final AllowableValue SNMP_V3 = new AllowableValue("SNMPv3", 
"v3", "SNMP version 3 with improved security");
+
+    // SNMPv3 privacy protocols
+    public static final AllowableValue NO_AUTH_NO_PRIV = new 
AllowableValue("noAuthNoPriv", "No authentication or encryption",
+            "No authentication or encryption.");
+    public static final AllowableValue AUTH_NO_PRIV = new 
AllowableValue("authNoPriv", "Authentication without encryption",
+            "Authentication without encryption.");
+    public static final AllowableValue AUTH_PRIV = new 
AllowableValue("authPriv", "Authentication and encryption",
+            "Authentication and encryption.");
+
+    // SNMPv3 authentication protocols
+    public static final AllowableValue MD5 = new AllowableValue("MD5", "MD5 
based authentication",
+            "Provides authentication based on the HMAC-MD5 algorithm.");
+    public static final AllowableValue SHA = new AllowableValue("SHA", "SHA 
based authentication",
+            "Provides authentication based on the HMAC-SHA algorithm.");
+    public static final AllowableValue NO_AUTHENTICATION = new 
AllowableValue("", "None",
+            "Sends SNMP requests without authentication.");
+
+    // SNMPv3 encryption
+    public static final AllowableValue DES = new AllowableValue("DES", "DES",
+            "Symmetric-key algorithm for the encryption of digital data.");
+    public static final AllowableValue DES3 = new AllowableValue("3DES", 
"3DES",
+            "Symmetric-key block cipher, which applies the DES cipher 
algorithm three times to each data block.");
+
+    private static final String AES_DESCRIPTION = "AES is a symmetric 
algorithm which uses the same 128, 192, or 256 bit" +
+            " key for both encryption and decryption (the security of an AES 
system increases exponentially with key length).";
+
+    public static final AllowableValue AES128 = new AllowableValue("AES128", 
"AES128", AES_DESCRIPTION);
+    public static final AllowableValue AES192 = new AllowableValue("AES192", 
"AES192", AES_DESCRIPTION);
+    public static final AllowableValue AES256 = new AllowableValue("AES256", 
"AES256", AES_DESCRIPTION);
+    public static final AllowableValue NO_ENCRYPTION = new AllowableValue("", 
"None",
+            "Sends SNMP requests without encryption.");
+
+
+    public static final PropertyDescriptor AGENT_HOST = new 
PropertyDescriptor.Builder()
             .name("snmp-hostname")
-            .displayName("Host Name")
-            .description("Network address of SNMP Agent (e.g., localhost)")
+            .displayName("SNMP Agent Hostname")
+            .description("Network address of the SNMP Agent.")
             .required(true)
             .defaultValue("localhost")
-            .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .addValidator(StandardValidators.NETWORK_ADDRESS_VALIDATOR)
             .build();
 
-    /** property to define port of the SNMP agent */
-    public static final PropertyDescriptor PORT = new 
PropertyDescriptor.Builder()
+    public static final PropertyDescriptor AGENT_PORT = new 
PropertyDescriptor.Builder()
             .name("snmp-port")
-            .displayName("Port")
-            .description("Numeric value identifying Port of SNMP Agent (e.g., 
161)")
+            .displayName("SNMP Agent Port")
+            .description("Numeric value identifying the port of SNMP Agent.")
             .required(true)
             .defaultValue("161")
             .addValidator(StandardValidators.PORT_VALIDATOR)
             .build();
 
-    /** property to define SNMP version to use */
     public static final PropertyDescriptor SNMP_VERSION = new 
PropertyDescriptor.Builder()
             .name("snmp-version")
             .displayName("SNMP Version")
-            .description("SNMP Version to use")
+            .description("Three significant versions of SNMP have been 
developed and deployed. " +
+                    "SNMPv1 is the original version of the protocol. More 
recent versions, " +
+                    "SNMPv2c and SNMPv3, feature improvements in performance, 
flexibility and security.")
             .required(true)
-            .allowableValues("SNMPv1", "SNMPv2c", "SNMPv3")
-            .defaultValue("SNMPv1")
+            .allowableValues(SNMP_V1, SNMP_V2C, SNMP_V3)
+            .defaultValue(SNMP_V1.getValue())
             .build();
 
-    /** property to define SNMP community to use */
     public static final PropertyDescriptor SNMP_COMMUNITY = new 
PropertyDescriptor.Builder()
             .name("snmp-community")
-            .displayName("SNMP Community (v1 & v2c)")
-            .description("SNMP Community to use (e.g., public)")
-            .required(false)
+            .displayName("SNMP Community")
+            .description("SNMPv1 and SNMPv2 use communities to establish trust 
between managers and agents." +
+                    " Most agents support three community names, one each for 
read-only, read-write and trap." +
+                    " These three community strings control different types of 
activities. The read-only community" +
+                    " applies to get requests. The read-write community string 
applies to set requests. The trap" +
+                    " community string applies to receipt of traps.")
+            .required(true)
+            .sensitive(true)
             .defaultValue("public")
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V1, SNMP_V2C)
             .build();
 
-    /** property to define SNMP security level to use */
     public static final PropertyDescriptor SNMP_SECURITY_LEVEL = new 
PropertyDescriptor.Builder()
             .name("snmp-security-level")
             .displayName("SNMP Security Level")
-            .description("SNMP Security Level to use")
+            .description("SNMP version 3 provides extra security with User 
Based Security Model (USM). The three levels of security is " +
+                    "1. Communication without authentication and encryption 
(NoAuthNoPriv). " +
+                    "2. Communication with authentication and without 
encryption (AuthNoPriv). " +
+                    "3. Communication with authentication and encryption 
(AuthPriv). ")
             .required(true)
-            .allowableValues("noAuthNoPriv", "authNoPriv", "authPriv")
-            .defaultValue("authPriv")
+            .allowableValues(NO_AUTH_NO_PRIV, AUTH_NO_PRIV, AUTH_PRIV)
+            .defaultValue(NO_AUTH_NO_PRIV.getValue())
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP security name to use */
     public static final PropertyDescriptor SNMP_SECURITY_NAME = new 
PropertyDescriptor.Builder()
             .name("snmp-security-name")
-            .displayName("SNMP Security name / user name")
-            .description("Security name used for SNMP exchanges")
-            .required(false)
+            .displayName("SNMP Security Name / Username for SNMP v3 
Authentication")
+            .description("Security name / User name used for SNMP exchanges.")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP authentication protocol to use */
-    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-protocol")
-            .displayName("SNMP Authentication Protocol")
-            .description("SNMP Authentication Protocol to use")
+    public static final PropertyDescriptor SNMP_PRIVACY_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol")
+            .displayName("SNMP Privacy Protocol")
+            .description("Privacy allows for encryption of SNMP v3 messages to 
ensure confidentiality of data.")
             .required(true)
-            .allowableValues("MD5", "SHA", "")
+            .allowableValues(DES, DES3, AES128, AES192, AES256, NO_ENCRYPTION)

Review comment:
       `None` option seems to be obsolete because this property depends on 
Security Level and when the property is visible, it is mandatory.

##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/processors/AbstractSNMPProcessor.java
##########
@@ -16,413 +16,249 @@
  */
 package org.apache.nifi.snmp.processors;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
+import org.apache.nifi.annotation.lifecycle.OnScheduled;
 import org.apache.nifi.annotation.lifecycle.OnStopped;
+import org.apache.nifi.components.AllowableValue;
 import org.apache.nifi.components.PropertyDescriptor;
-import org.apache.nifi.components.ValidationContext;
-import org.apache.nifi.components.ValidationResult;
+import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.AbstractProcessor;
 import org.apache.nifi.processor.ProcessContext;
 import org.apache.nifi.processor.ProcessSession;
-import org.apache.nifi.processor.Processor;
-import org.apache.nifi.processor.exception.ProcessException;
 import org.apache.nifi.processor.util.StandardValidators;
-import org.snmp4j.AbstractTarget;
-import org.snmp4j.CommunityTarget;
-import org.snmp4j.Snmp;
-import org.snmp4j.TransportMapping;
-import org.snmp4j.UserTarget;
-import org.snmp4j.mp.MPv3;
-import org.snmp4j.mp.SnmpConstants;
-import org.snmp4j.security.SecurityModels;
-import org.snmp4j.security.SecurityProtocols;
-import org.snmp4j.security.USM;
-import org.snmp4j.security.UsmUser;
-import org.snmp4j.smi.OctetString;
-import org.snmp4j.smi.UdpAddress;
-import org.snmp4j.transport.DefaultUdpTransportMapping;
+import org.apache.nifi.reporting.InitializationException;
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.configuration.SNMPConfigurationBuilder;
+import org.apache.nifi.snmp.logging.SLF4JLogFactory;
+import org.apache.nifi.snmp.operations.SNMPRequestHandler;
+import org.apache.nifi.snmp.operations.SNMPRequestHandlerFactory;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.log.LogFactory;
+
+import java.util.HashMap;
+import java.util.Map;
 
 /**
- * Base processor that uses SNMP4J client API
+ * Base processor that uses SNMP4J client API.
  * (http://www.snmp4j.org/)
- *
- * @param <T> the type of {@link SNMPWorker}. Please see {@link SNMPSetter}
- *            and {@link SNMPGetter}
  */
-abstract class AbstractSNMPProcessor<T extends SNMPWorker> extends 
AbstractProcessor {
+abstract class AbstractSNMPProcessor extends AbstractProcessor {
+
+    static {
+        LogFactory.setLogFactory(new SLF4JLogFactory());
+    }
 
-    /** property to define host of the SNMP agent */
-    public static final PropertyDescriptor HOST = new 
PropertyDescriptor.Builder()
+    // SNMP versions
+    public static final AllowableValue SNMP_V1 = new AllowableValue("SNMPv1", 
"v1", "SNMP version 1");
+    public static final AllowableValue SNMP_V2C = new 
AllowableValue("SNMPv2c", "v2c", "SNMP version 2c");
+    public static final AllowableValue SNMP_V3 = new AllowableValue("SNMPv3", 
"v3", "SNMP version 3 with improved security");
+
+    // SNMPv3 privacy protocols
+    public static final AllowableValue NO_AUTH_NO_PRIV = new 
AllowableValue("noAuthNoPriv", "No authentication or encryption",
+            "No authentication or encryption.");
+    public static final AllowableValue AUTH_NO_PRIV = new 
AllowableValue("authNoPriv", "Authentication without encryption",
+            "Authentication without encryption.");
+    public static final AllowableValue AUTH_PRIV = new 
AllowableValue("authPriv", "Authentication and encryption",
+            "Authentication and encryption.");
+
+    // SNMPv3 authentication protocols
+    public static final AllowableValue MD5 = new AllowableValue("MD5", "MD5 
based authentication",
+            "Provides authentication based on the HMAC-MD5 algorithm.");
+    public static final AllowableValue SHA = new AllowableValue("SHA", "SHA 
based authentication",
+            "Provides authentication based on the HMAC-SHA algorithm.");
+    public static final AllowableValue NO_AUTHENTICATION = new 
AllowableValue("", "None",
+            "Sends SNMP requests without authentication.");
+
+    // SNMPv3 encryption
+    public static final AllowableValue DES = new AllowableValue("DES", "DES",
+            "Symmetric-key algorithm for the encryption of digital data.");
+    public static final AllowableValue DES3 = new AllowableValue("3DES", 
"3DES",
+            "Symmetric-key block cipher, which applies the DES cipher 
algorithm three times to each data block.");
+
+    private static final String AES_DESCRIPTION = "AES is a symmetric 
algorithm which uses the same 128, 192, or 256 bit" +
+            " key for both encryption and decryption (the security of an AES 
system increases exponentially with key length).";
+
+    public static final AllowableValue AES128 = new AllowableValue("AES128", 
"AES128", AES_DESCRIPTION);
+    public static final AllowableValue AES192 = new AllowableValue("AES192", 
"AES192", AES_DESCRIPTION);
+    public static final AllowableValue AES256 = new AllowableValue("AES256", 
"AES256", AES_DESCRIPTION);
+    public static final AllowableValue NO_ENCRYPTION = new AllowableValue("", 
"None",
+            "Sends SNMP requests without encryption.");
+
+
+    public static final PropertyDescriptor AGENT_HOST = new 
PropertyDescriptor.Builder()
             .name("snmp-hostname")
-            .displayName("Host Name")
-            .description("Network address of SNMP Agent (e.g., localhost)")
+            .displayName("SNMP Agent Hostname")
+            .description("Network address of the SNMP Agent.")
             .required(true)
             .defaultValue("localhost")
-            .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .addValidator(StandardValidators.NETWORK_ADDRESS_VALIDATOR)
             .build();
 
-    /** property to define port of the SNMP agent */
-    public static final PropertyDescriptor PORT = new 
PropertyDescriptor.Builder()
+    public static final PropertyDescriptor AGENT_PORT = new 
PropertyDescriptor.Builder()
             .name("snmp-port")
-            .displayName("Port")
-            .description("Numeric value identifying Port of SNMP Agent (e.g., 
161)")
+            .displayName("SNMP Agent Port")
+            .description("Numeric value identifying the port of SNMP Agent.")
             .required(true)
             .defaultValue("161")
             .addValidator(StandardValidators.PORT_VALIDATOR)
             .build();
 
-    /** property to define SNMP version to use */
     public static final PropertyDescriptor SNMP_VERSION = new 
PropertyDescriptor.Builder()
             .name("snmp-version")
             .displayName("SNMP Version")
-            .description("SNMP Version to use")
+            .description("Three significant versions of SNMP have been 
developed and deployed. " +
+                    "SNMPv1 is the original version of the protocol. More 
recent versions, " +
+                    "SNMPv2c and SNMPv3, feature improvements in performance, 
flexibility and security.")
             .required(true)
-            .allowableValues("SNMPv1", "SNMPv2c", "SNMPv3")
-            .defaultValue("SNMPv1")
+            .allowableValues(SNMP_V1, SNMP_V2C, SNMP_V3)
+            .defaultValue(SNMP_V1.getValue())
             .build();
 
-    /** property to define SNMP community to use */
     public static final PropertyDescriptor SNMP_COMMUNITY = new 
PropertyDescriptor.Builder()
             .name("snmp-community")
-            .displayName("SNMP Community (v1 & v2c)")
-            .description("SNMP Community to use (e.g., public)")
-            .required(false)
+            .displayName("SNMP Community")
+            .description("SNMPv1 and SNMPv2 use communities to establish trust 
between managers and agents." +
+                    " Most agents support three community names, one each for 
read-only, read-write and trap." +
+                    " These three community strings control different types of 
activities. The read-only community" +
+                    " applies to get requests. The read-write community string 
applies to set requests. The trap" +
+                    " community string applies to receipt of traps.")
+            .required(true)
+            .sensitive(true)
             .defaultValue("public")
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V1, SNMP_V2C)
             .build();
 
-    /** property to define SNMP security level to use */
     public static final PropertyDescriptor SNMP_SECURITY_LEVEL = new 
PropertyDescriptor.Builder()
             .name("snmp-security-level")
             .displayName("SNMP Security Level")
-            .description("SNMP Security Level to use")
+            .description("SNMP version 3 provides extra security with User 
Based Security Model (USM). The three levels of security is " +
+                    "1. Communication without authentication and encryption 
(NoAuthNoPriv). " +
+                    "2. Communication with authentication and without 
encryption (AuthNoPriv). " +
+                    "3. Communication with authentication and encryption 
(AuthPriv). ")
             .required(true)
-            .allowableValues("noAuthNoPriv", "authNoPriv", "authPriv")
-            .defaultValue("authPriv")
+            .allowableValues(NO_AUTH_NO_PRIV, AUTH_NO_PRIV, AUTH_PRIV)
+            .defaultValue(NO_AUTH_NO_PRIV.getValue())
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP security name to use */
     public static final PropertyDescriptor SNMP_SECURITY_NAME = new 
PropertyDescriptor.Builder()
             .name("snmp-security-name")
-            .displayName("SNMP Security name / user name")
-            .description("Security name used for SNMP exchanges")
-            .required(false)
+            .displayName("SNMP Security Name / Username for SNMP v3 
Authentication")
+            .description("Security name / User name used for SNMP exchanges.")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP authentication protocol to use */
-    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-protocol")
-            .displayName("SNMP Authentication Protocol")
-            .description("SNMP Authentication Protocol to use")
+    public static final PropertyDescriptor SNMP_PRIVACY_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol")
+            .displayName("SNMP Privacy Protocol")
+            .description("Privacy allows for encryption of SNMP v3 messages to 
ensure confidentiality of data.")
             .required(true)
-            .allowableValues("MD5", "SHA", "")
+            .allowableValues(DES, DES3, AES128, AES192, AES256, NO_ENCRYPTION)
             .defaultValue("")
+            .dependsOn(SNMP_SECURITY_LEVEL, AUTH_PRIV)
             .build();
 
-    /** property to define SNMP authentication password to use */
-    public static final PropertyDescriptor SNMP_AUTH_PASSWORD = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-passphrase")
-            .displayName("SNMP Authentication pass phrase")
-            .description("Pass phrase used for SNMP authentication protocol")
-            .required(false)
+    public static final PropertyDescriptor SNMP_PRIVACY_PASSWORD = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol-passphrase")
+            .displayName("SNMP Privacy Protocol Passphrase")
+            .description("Pass phrase used for SNMP privacy protocol")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
             .sensitive(true)
+            .dependsOn(SNMP_SECURITY_LEVEL, AUTH_PRIV)
             .build();
 
-    /** property to define SNMP private protocol to use */
-    public static final PropertyDescriptor SNMP_PRIV_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-private-protocol")
-            .displayName("SNMP Private Protocol")
-            .description("SNMP Private Protocol to use")
+    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-authentication-protocol")
+            .displayName("SNMP Authentication Protocol")
+            .description("Hash based auhentication protocols for secure 
authentication.")
             .required(true)
-            .allowableValues("DES", "3DES", "AES128", "AES192", "AES256", "")
+            .allowableValues(MD5, SHA, NO_AUTHENTICATION)

Review comment:
       SHA-2 based protocols are also available in SNMP4J (eg. 
`org.snmp4j.security.AuthHMAC192SHA256`) and we should support them too.

##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/processors/AbstractSNMPProcessor.java
##########
@@ -16,413 +16,249 @@
  */
 package org.apache.nifi.snmp.processors;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
+import org.apache.nifi.annotation.lifecycle.OnScheduled;
 import org.apache.nifi.annotation.lifecycle.OnStopped;
+import org.apache.nifi.components.AllowableValue;
 import org.apache.nifi.components.PropertyDescriptor;
-import org.apache.nifi.components.ValidationContext;
-import org.apache.nifi.components.ValidationResult;
+import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.AbstractProcessor;
 import org.apache.nifi.processor.ProcessContext;
 import org.apache.nifi.processor.ProcessSession;
-import org.apache.nifi.processor.Processor;
-import org.apache.nifi.processor.exception.ProcessException;
 import org.apache.nifi.processor.util.StandardValidators;
-import org.snmp4j.AbstractTarget;
-import org.snmp4j.CommunityTarget;
-import org.snmp4j.Snmp;
-import org.snmp4j.TransportMapping;
-import org.snmp4j.UserTarget;
-import org.snmp4j.mp.MPv3;
-import org.snmp4j.mp.SnmpConstants;
-import org.snmp4j.security.SecurityModels;
-import org.snmp4j.security.SecurityProtocols;
-import org.snmp4j.security.USM;
-import org.snmp4j.security.UsmUser;
-import org.snmp4j.smi.OctetString;
-import org.snmp4j.smi.UdpAddress;
-import org.snmp4j.transport.DefaultUdpTransportMapping;
+import org.apache.nifi.reporting.InitializationException;
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.configuration.SNMPConfigurationBuilder;
+import org.apache.nifi.snmp.logging.SLF4JLogFactory;
+import org.apache.nifi.snmp.operations.SNMPRequestHandler;
+import org.apache.nifi.snmp.operations.SNMPRequestHandlerFactory;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.log.LogFactory;
+
+import java.util.HashMap;
+import java.util.Map;
 
 /**
- * Base processor that uses SNMP4J client API
+ * Base processor that uses SNMP4J client API.
  * (http://www.snmp4j.org/)
- *
- * @param <T> the type of {@link SNMPWorker}. Please see {@link SNMPSetter}
- *            and {@link SNMPGetter}
  */
-abstract class AbstractSNMPProcessor<T extends SNMPWorker> extends 
AbstractProcessor {
+abstract class AbstractSNMPProcessor extends AbstractProcessor {
+
+    static {
+        LogFactory.setLogFactory(new SLF4JLogFactory());
+    }
 
-    /** property to define host of the SNMP agent */
-    public static final PropertyDescriptor HOST = new 
PropertyDescriptor.Builder()
+    // SNMP versions
+    public static final AllowableValue SNMP_V1 = new AllowableValue("SNMPv1", 
"v1", "SNMP version 1");
+    public static final AllowableValue SNMP_V2C = new 
AllowableValue("SNMPv2c", "v2c", "SNMP version 2c");
+    public static final AllowableValue SNMP_V3 = new AllowableValue("SNMPv3", 
"v3", "SNMP version 3 with improved security");
+
+    // SNMPv3 privacy protocols
+    public static final AllowableValue NO_AUTH_NO_PRIV = new 
AllowableValue("noAuthNoPriv", "No authentication or encryption",
+            "No authentication or encryption.");
+    public static final AllowableValue AUTH_NO_PRIV = new 
AllowableValue("authNoPriv", "Authentication without encryption",
+            "Authentication without encryption.");
+    public static final AllowableValue AUTH_PRIV = new 
AllowableValue("authPriv", "Authentication and encryption",
+            "Authentication and encryption.");
+
+    // SNMPv3 authentication protocols
+    public static final AllowableValue MD5 = new AllowableValue("MD5", "MD5 
based authentication",
+            "Provides authentication based on the HMAC-MD5 algorithm.");
+    public static final AllowableValue SHA = new AllowableValue("SHA", "SHA 
based authentication",
+            "Provides authentication based on the HMAC-SHA algorithm.");
+    public static final AllowableValue NO_AUTHENTICATION = new 
AllowableValue("", "None",
+            "Sends SNMP requests without authentication.");
+
+    // SNMPv3 encryption
+    public static final AllowableValue DES = new AllowableValue("DES", "DES",
+            "Symmetric-key algorithm for the encryption of digital data.");
+    public static final AllowableValue DES3 = new AllowableValue("3DES", 
"3DES",
+            "Symmetric-key block cipher, which applies the DES cipher 
algorithm three times to each data block.");
+
+    private static final String AES_DESCRIPTION = "AES is a symmetric 
algorithm which uses the same 128, 192, or 256 bit" +
+            " key for both encryption and decryption (the security of an AES 
system increases exponentially with key length).";
+
+    public static final AllowableValue AES128 = new AllowableValue("AES128", 
"AES128", AES_DESCRIPTION);
+    public static final AllowableValue AES192 = new AllowableValue("AES192", 
"AES192", AES_DESCRIPTION);
+    public static final AllowableValue AES256 = new AllowableValue("AES256", 
"AES256", AES_DESCRIPTION);
+    public static final AllowableValue NO_ENCRYPTION = new AllowableValue("", 
"None",
+            "Sends SNMP requests without encryption.");
+
+
+    public static final PropertyDescriptor AGENT_HOST = new 
PropertyDescriptor.Builder()
             .name("snmp-hostname")
-            .displayName("Host Name")
-            .description("Network address of SNMP Agent (e.g., localhost)")
+            .displayName("SNMP Agent Hostname")
+            .description("Network address of the SNMP Agent.")
             .required(true)
             .defaultValue("localhost")
-            .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .addValidator(StandardValidators.NETWORK_ADDRESS_VALIDATOR)
             .build();
 
-    /** property to define port of the SNMP agent */
-    public static final PropertyDescriptor PORT = new 
PropertyDescriptor.Builder()
+    public static final PropertyDescriptor AGENT_PORT = new 
PropertyDescriptor.Builder()
             .name("snmp-port")
-            .displayName("Port")
-            .description("Numeric value identifying Port of SNMP Agent (e.g., 
161)")
+            .displayName("SNMP Agent Port")
+            .description("Numeric value identifying the port of SNMP Agent.")
             .required(true)
             .defaultValue("161")
             .addValidator(StandardValidators.PORT_VALIDATOR)
             .build();
 
-    /** property to define SNMP version to use */
     public static final PropertyDescriptor SNMP_VERSION = new 
PropertyDescriptor.Builder()
             .name("snmp-version")
             .displayName("SNMP Version")
-            .description("SNMP Version to use")
+            .description("Three significant versions of SNMP have been 
developed and deployed. " +
+                    "SNMPv1 is the original version of the protocol. More 
recent versions, " +
+                    "SNMPv2c and SNMPv3, feature improvements in performance, 
flexibility and security.")
             .required(true)
-            .allowableValues("SNMPv1", "SNMPv2c", "SNMPv3")
-            .defaultValue("SNMPv1")
+            .allowableValues(SNMP_V1, SNMP_V2C, SNMP_V3)
+            .defaultValue(SNMP_V1.getValue())
             .build();
 
-    /** property to define SNMP community to use */
     public static final PropertyDescriptor SNMP_COMMUNITY = new 
PropertyDescriptor.Builder()
             .name("snmp-community")
-            .displayName("SNMP Community (v1 & v2c)")
-            .description("SNMP Community to use (e.g., public)")
-            .required(false)
+            .displayName("SNMP Community")
+            .description("SNMPv1 and SNMPv2 use communities to establish trust 
between managers and agents." +
+                    " Most agents support three community names, one each for 
read-only, read-write and trap." +
+                    " These three community strings control different types of 
activities. The read-only community" +
+                    " applies to get requests. The read-write community string 
applies to set requests. The trap" +
+                    " community string applies to receipt of traps.")
+            .required(true)
+            .sensitive(true)
             .defaultValue("public")
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V1, SNMP_V2C)
             .build();
 
-    /** property to define SNMP security level to use */
     public static final PropertyDescriptor SNMP_SECURITY_LEVEL = new 
PropertyDescriptor.Builder()
             .name("snmp-security-level")
             .displayName("SNMP Security Level")
-            .description("SNMP Security Level to use")
+            .description("SNMP version 3 provides extra security with User 
Based Security Model (USM). The three levels of security is " +
+                    "1. Communication without authentication and encryption 
(NoAuthNoPriv). " +
+                    "2. Communication with authentication and without 
encryption (AuthNoPriv). " +
+                    "3. Communication with authentication and encryption 
(AuthPriv). ")
             .required(true)
-            .allowableValues("noAuthNoPriv", "authNoPriv", "authPriv")
-            .defaultValue("authPriv")
+            .allowableValues(NO_AUTH_NO_PRIV, AUTH_NO_PRIV, AUTH_PRIV)
+            .defaultValue(NO_AUTH_NO_PRIV.getValue())
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP security name to use */
     public static final PropertyDescriptor SNMP_SECURITY_NAME = new 
PropertyDescriptor.Builder()
             .name("snmp-security-name")
-            .displayName("SNMP Security name / user name")
-            .description("Security name used for SNMP exchanges")
-            .required(false)
+            .displayName("SNMP Security Name / Username for SNMP v3 
Authentication")
+            .description("Security name / User name used for SNMP exchanges.")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP authentication protocol to use */
-    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-protocol")
-            .displayName("SNMP Authentication Protocol")
-            .description("SNMP Authentication Protocol to use")
+    public static final PropertyDescriptor SNMP_PRIVACY_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol")
+            .displayName("SNMP Privacy Protocol")
+            .description("Privacy allows for encryption of SNMP v3 messages to 
ensure confidentiality of data.")
             .required(true)
-            .allowableValues("MD5", "SHA", "")
+            .allowableValues(DES, DES3, AES128, AES192, AES256, NO_ENCRYPTION)
             .defaultValue("")
+            .dependsOn(SNMP_SECURITY_LEVEL, AUTH_PRIV)
             .build();
 
-    /** property to define SNMP authentication password to use */
-    public static final PropertyDescriptor SNMP_AUTH_PASSWORD = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-passphrase")
-            .displayName("SNMP Authentication pass phrase")
-            .description("Pass phrase used for SNMP authentication protocol")
-            .required(false)
+    public static final PropertyDescriptor SNMP_PRIVACY_PASSWORD = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol-passphrase")
+            .displayName("SNMP Privacy Protocol Passphrase")

Review comment:
       I would use `SNMP Privacy Passphrase`.
   (similar to `SNMP Authentication Passphrase`)

##########
File path: 
nifi-nar-bundles/nifi-snmp-bundle/nifi-snmp-processors/src/main/java/org/apache/nifi/snmp/processors/AbstractSNMPProcessor.java
##########
@@ -16,413 +16,249 @@
  */
 package org.apache.nifi.snmp.processors;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
+import org.apache.nifi.annotation.lifecycle.OnScheduled;
 import org.apache.nifi.annotation.lifecycle.OnStopped;
+import org.apache.nifi.components.AllowableValue;
 import org.apache.nifi.components.PropertyDescriptor;
-import org.apache.nifi.components.ValidationContext;
-import org.apache.nifi.components.ValidationResult;
+import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.AbstractProcessor;
 import org.apache.nifi.processor.ProcessContext;
 import org.apache.nifi.processor.ProcessSession;
-import org.apache.nifi.processor.Processor;
-import org.apache.nifi.processor.exception.ProcessException;
 import org.apache.nifi.processor.util.StandardValidators;
-import org.snmp4j.AbstractTarget;
-import org.snmp4j.CommunityTarget;
-import org.snmp4j.Snmp;
-import org.snmp4j.TransportMapping;
-import org.snmp4j.UserTarget;
-import org.snmp4j.mp.MPv3;
-import org.snmp4j.mp.SnmpConstants;
-import org.snmp4j.security.SecurityModels;
-import org.snmp4j.security.SecurityProtocols;
-import org.snmp4j.security.USM;
-import org.snmp4j.security.UsmUser;
-import org.snmp4j.smi.OctetString;
-import org.snmp4j.smi.UdpAddress;
-import org.snmp4j.transport.DefaultUdpTransportMapping;
+import org.apache.nifi.reporting.InitializationException;
+import org.apache.nifi.snmp.configuration.SNMPConfiguration;
+import org.apache.nifi.snmp.configuration.SNMPConfigurationBuilder;
+import org.apache.nifi.snmp.logging.SLF4JLogFactory;
+import org.apache.nifi.snmp.operations.SNMPRequestHandler;
+import org.apache.nifi.snmp.operations.SNMPRequestHandlerFactory;
+import org.apache.nifi.snmp.utils.SNMPUtils;
+import org.snmp4j.log.LogFactory;
+
+import java.util.HashMap;
+import java.util.Map;
 
 /**
- * Base processor that uses SNMP4J client API
+ * Base processor that uses SNMP4J client API.
  * (http://www.snmp4j.org/)
- *
- * @param <T> the type of {@link SNMPWorker}. Please see {@link SNMPSetter}
- *            and {@link SNMPGetter}
  */
-abstract class AbstractSNMPProcessor<T extends SNMPWorker> extends 
AbstractProcessor {
+abstract class AbstractSNMPProcessor extends AbstractProcessor {
+
+    static {
+        LogFactory.setLogFactory(new SLF4JLogFactory());
+    }
 
-    /** property to define host of the SNMP agent */
-    public static final PropertyDescriptor HOST = new 
PropertyDescriptor.Builder()
+    // SNMP versions
+    public static final AllowableValue SNMP_V1 = new AllowableValue("SNMPv1", 
"v1", "SNMP version 1");
+    public static final AllowableValue SNMP_V2C = new 
AllowableValue("SNMPv2c", "v2c", "SNMP version 2c");
+    public static final AllowableValue SNMP_V3 = new AllowableValue("SNMPv3", 
"v3", "SNMP version 3 with improved security");
+
+    // SNMPv3 privacy protocols
+    public static final AllowableValue NO_AUTH_NO_PRIV = new 
AllowableValue("noAuthNoPriv", "No authentication or encryption",
+            "No authentication or encryption.");
+    public static final AllowableValue AUTH_NO_PRIV = new 
AllowableValue("authNoPriv", "Authentication without encryption",
+            "Authentication without encryption.");
+    public static final AllowableValue AUTH_PRIV = new 
AllowableValue("authPriv", "Authentication and encryption",
+            "Authentication and encryption.");
+
+    // SNMPv3 authentication protocols
+    public static final AllowableValue MD5 = new AllowableValue("MD5", "MD5 
based authentication",
+            "Provides authentication based on the HMAC-MD5 algorithm.");
+    public static final AllowableValue SHA = new AllowableValue("SHA", "SHA 
based authentication",
+            "Provides authentication based on the HMAC-SHA algorithm.");
+    public static final AllowableValue NO_AUTHENTICATION = new 
AllowableValue("", "None",
+            "Sends SNMP requests without authentication.");
+
+    // SNMPv3 encryption
+    public static final AllowableValue DES = new AllowableValue("DES", "DES",
+            "Symmetric-key algorithm for the encryption of digital data.");
+    public static final AllowableValue DES3 = new AllowableValue("3DES", 
"3DES",
+            "Symmetric-key block cipher, which applies the DES cipher 
algorithm three times to each data block.");
+
+    private static final String AES_DESCRIPTION = "AES is a symmetric 
algorithm which uses the same 128, 192, or 256 bit" +
+            " key for both encryption and decryption (the security of an AES 
system increases exponentially with key length).";
+
+    public static final AllowableValue AES128 = new AllowableValue("AES128", 
"AES128", AES_DESCRIPTION);
+    public static final AllowableValue AES192 = new AllowableValue("AES192", 
"AES192", AES_DESCRIPTION);
+    public static final AllowableValue AES256 = new AllowableValue("AES256", 
"AES256", AES_DESCRIPTION);
+    public static final AllowableValue NO_ENCRYPTION = new AllowableValue("", 
"None",
+            "Sends SNMP requests without encryption.");
+
+
+    public static final PropertyDescriptor AGENT_HOST = new 
PropertyDescriptor.Builder()
             .name("snmp-hostname")
-            .displayName("Host Name")
-            .description("Network address of SNMP Agent (e.g., localhost)")
+            .displayName("SNMP Agent Hostname")
+            .description("Network address of the SNMP Agent.")
             .required(true)
             .defaultValue("localhost")
-            .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .addValidator(StandardValidators.NETWORK_ADDRESS_VALIDATOR)
             .build();
 
-    /** property to define port of the SNMP agent */
-    public static final PropertyDescriptor PORT = new 
PropertyDescriptor.Builder()
+    public static final PropertyDescriptor AGENT_PORT = new 
PropertyDescriptor.Builder()
             .name("snmp-port")
-            .displayName("Port")
-            .description("Numeric value identifying Port of SNMP Agent (e.g., 
161)")
+            .displayName("SNMP Agent Port")
+            .description("Numeric value identifying the port of SNMP Agent.")
             .required(true)
             .defaultValue("161")
             .addValidator(StandardValidators.PORT_VALIDATOR)
             .build();
 
-    /** property to define SNMP version to use */
     public static final PropertyDescriptor SNMP_VERSION = new 
PropertyDescriptor.Builder()
             .name("snmp-version")
             .displayName("SNMP Version")
-            .description("SNMP Version to use")
+            .description("Three significant versions of SNMP have been 
developed and deployed. " +
+                    "SNMPv1 is the original version of the protocol. More 
recent versions, " +
+                    "SNMPv2c and SNMPv3, feature improvements in performance, 
flexibility and security.")
             .required(true)
-            .allowableValues("SNMPv1", "SNMPv2c", "SNMPv3")
-            .defaultValue("SNMPv1")
+            .allowableValues(SNMP_V1, SNMP_V2C, SNMP_V3)
+            .defaultValue(SNMP_V1.getValue())
             .build();
 
-    /** property to define SNMP community to use */
     public static final PropertyDescriptor SNMP_COMMUNITY = new 
PropertyDescriptor.Builder()
             .name("snmp-community")
-            .displayName("SNMP Community (v1 & v2c)")
-            .description("SNMP Community to use (e.g., public)")
-            .required(false)
+            .displayName("SNMP Community")
+            .description("SNMPv1 and SNMPv2 use communities to establish trust 
between managers and agents." +
+                    " Most agents support three community names, one each for 
read-only, read-write and trap." +
+                    " These three community strings control different types of 
activities. The read-only community" +
+                    " applies to get requests. The read-write community string 
applies to set requests. The trap" +
+                    " community string applies to receipt of traps.")
+            .required(true)
+            .sensitive(true)
             .defaultValue("public")
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V1, SNMP_V2C)
             .build();
 
-    /** property to define SNMP security level to use */
     public static final PropertyDescriptor SNMP_SECURITY_LEVEL = new 
PropertyDescriptor.Builder()
             .name("snmp-security-level")
             .displayName("SNMP Security Level")
-            .description("SNMP Security Level to use")
+            .description("SNMP version 3 provides extra security with User 
Based Security Model (USM). The three levels of security is " +
+                    "1. Communication without authentication and encryption 
(NoAuthNoPriv). " +
+                    "2. Communication with authentication and without 
encryption (AuthNoPriv). " +
+                    "3. Communication with authentication and encryption 
(AuthPriv). ")
             .required(true)
-            .allowableValues("noAuthNoPriv", "authNoPriv", "authPriv")
-            .defaultValue("authPriv")
+            .allowableValues(NO_AUTH_NO_PRIV, AUTH_NO_PRIV, AUTH_PRIV)
+            .defaultValue(NO_AUTH_NO_PRIV.getValue())
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP security name to use */
     public static final PropertyDescriptor SNMP_SECURITY_NAME = new 
PropertyDescriptor.Builder()
             .name("snmp-security-name")
-            .displayName("SNMP Security name / user name")
-            .description("Security name used for SNMP exchanges")
-            .required(false)
+            .displayName("SNMP Security Name / Username for SNMP v3 
Authentication")
+            .description("Security name / User name used for SNMP exchanges.")
+            .required(true)
             .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+            .dependsOn(SNMP_VERSION, SNMP_V3)
             .build();
 
-    /** property to define SNMP authentication protocol to use */
-    public static final PropertyDescriptor SNMP_AUTH_PROTOCOL = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-protocol")
-            .displayName("SNMP Authentication Protocol")
-            .description("SNMP Authentication Protocol to use")
+    public static final PropertyDescriptor SNMP_PRIVACY_PROTOCOL = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol")
+            .displayName("SNMP Privacy Protocol")
+            .description("Privacy allows for encryption of SNMP v3 messages to 
ensure confidentiality of data.")
             .required(true)
-            .allowableValues("MD5", "SHA", "")
+            .allowableValues(DES, DES3, AES128, AES192, AES256, NO_ENCRYPTION)
             .defaultValue("")
+            .dependsOn(SNMP_SECURITY_LEVEL, AUTH_PRIV)
             .build();
 
-    /** property to define SNMP authentication password to use */
-    public static final PropertyDescriptor SNMP_AUTH_PASSWORD = new 
PropertyDescriptor.Builder()
-            .name("snmp-authentication-passphrase")
-            .displayName("SNMP Authentication pass phrase")
-            .description("Pass phrase used for SNMP authentication protocol")
-            .required(false)
+    public static final PropertyDescriptor SNMP_PRIVACY_PASSWORD = new 
PropertyDescriptor.Builder()
+            .name("snmp-private-protocol-passphrase")
+            .displayName("SNMP Privacy Protocol Passphrase")
+            .description("Pass phrase used for SNMP privacy protocol")

Review comment:
       Passphrase is written as a single word in other places nearby.
   (Minor: there should be a period at the end of the sentence.)




-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

For queries about this service, please contact Infrastructure at:
[email protected]


Reply via email to