import static com.att.eelf.configuration.Configuration.MDC_SERVER_IP_ADDRESS;
import static com.att.eelf.configuration.Configuration.MDC_SERVICE_NAME;
+import static com.att.eelf.configuration.Configuration.MDC_KEY_REQUEST_ID;
+
+
import java.io.IOException;
import java.io.InputStream;
import java.security.cert.X509Certificate;
import java.sql.Connection;
import java.sql.SQLException;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Set;
-import java.util.List;
-import java.util.ArrayList;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
-import org.apache.log4j.Logger;
+import com.att.eelf.configuration.EELFLogger;
+import com.att.eelf.configuration.EELFManager;
+import org.apache.commons.lang3.StringUtils;
+import org.json.JSONArray;
+import org.json.JSONException;
import org.json.JSONObject;
import org.json.JSONTokener;
import org.onap.dmaap.datarouter.authz.Authorizer;
import org.onap.dmaap.datarouter.authz.impl.ProvAuthorizer;
import org.onap.dmaap.datarouter.authz.impl.ProvDataProvider;
-import org.onap.dmaap.datarouter.provisioning.beans.Deleteable;
-import org.onap.dmaap.datarouter.provisioning.beans.Feed;
-import org.onap.dmaap.datarouter.provisioning.beans.Group;
-import org.onap.dmaap.datarouter.provisioning.beans.Insertable;
-import org.onap.dmaap.datarouter.provisioning.beans.NodeClass;
-import org.onap.dmaap.datarouter.provisioning.beans.Parameters;
-import org.onap.dmaap.datarouter.provisioning.beans.Subscription;
-import org.onap.dmaap.datarouter.provisioning.beans.Updateable;
+import org.onap.dmaap.datarouter.provisioning.beans.*;
import org.onap.dmaap.datarouter.provisioning.utils.DB;
+import org.onap.dmaap.datarouter.provisioning.utils.PasswordProcessor;
import org.onap.dmaap.datarouter.provisioning.utils.ThrottleFilter;
-import org.json.JSONException;
import org.slf4j.MDC;
-import java.util.Properties;
-import java.util.regex.Pattern;
-import javax.mail.Message;
-import javax.mail.MessagingException;
-import javax.mail.Multipart;
-import javax.mail.Session;
-import javax.mail.Transport;
-import javax.mail.internet.AddressException;
+import javax.mail.*;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeBodyPart;
import javax.mail.internet.MimeMessage;
import javax.mail.internet.MimeMultipart;
+import java.security.GeneralSecurityException;
+import java.util.*;
+import java.util.regex.Pattern;
+
/**
* This is the base class for all Servlets in the provisioning code. It provides standard constants and some common
@SuppressWarnings("serial")
public class BaseServlet extends HttpServlet implements ProvDataProvider {
- public static final String BEHALF_HEADER = "X-ATT-DR-ON-BEHALF-OF";
- static final String FEED_BASECONTENT_TYPE = "application/vnd.att-dr.feed";
- public static final String FEED_CONTENT_TYPE = "application/vnd.att-dr.feed; version=2.0";
- public static final String FEEDFULL_CONTENT_TYPE = "application/vnd.att-dr.feed-full; version=2.0";
- public static final String FEEDLIST_CONTENT_TYPE = "application/vnd.att-dr.feed-list; version=1.0";
- static final String SUB_BASECONTENT_TYPE = "application/vnd.att-dr.subscription";
- public static final String SUB_CONTENT_TYPE = "application/vnd.att-dr.subscription; version=2.0";
- public static final String SUBFULL_CONTENT_TYPE = "application/vnd.att-dr.subscription-full; version=2.0";
- static final String SUBLIST_CONTENT_TYPE = "application/vnd.att-dr.subscription-list; version=1.0";
+ public static final String BEHALF_HEADER = "X-DMAAP-DR-ON-BEHALF-OF";
+
+ public static final String EXCLUDE_AAF_HEADER = "X-EXCLUDE-AAF";
+
+ private static final String AAF_CADI_FEED_TYPE = "org.onap.dmaap.datarouter.provserver.aaf.feed.type";
+ private static final String AAF_CADI_SUB_TYPE = "org.onap.dmaap.datarouter.provserver.aaf.sub.type";
+ private static final String AAF_INSTANCE = "org.onap.dmaap.datarouter.provserver.aaf.instance";
+ private static final String AAF_CADI_FEED = "org.onap.dmaap-dr.feed";
+ private static final String AAF_CADI_SUB = "org.onap.dmaap-dr.sub";
+
+ static final String CREATE_PERMISSION = "create";
+ static final String EDIT_PERMISSION = "edit";
+ static final String DELETE_PERMISSION = "delete";
+ static final String PUBLISH_PERMISSION = "publish";
+ static final String SUSPEND_PERMISSION = "suspend";
+ static final String RESTORE_PERMISSION = "restore";
+ static final String SUBSCRIBE_PERMISSION = "subscribe";
+ static final String APPROVE_SUB_PERMISSION = "approveSub";
+
+ static final String FEED_BASECONTENT_TYPE = "application/vnd.dmaap-dr.feed";
+ public static final String FEED_CONTENT_TYPE = "application/vnd.dmaap-dr.feed; version=2.0";
+ public static final String FEEDFULL_CONTENT_TYPE = "application/vnd.dmaap-dr.feed-full; version=2.0";
+ public static final String FEEDLIST_CONTENT_TYPE = "application/vnd.dmaap-dr.feed-list; version=1.0";
+ static final String SUB_BASECONTENT_TYPE = "application/vnd.dmaap-dr.subscription";
+ public static final String SUB_CONTENT_TYPE = "application/vnd.dmaap-dr.subscription; version=2.0";
+ public static final String SUBFULL_CONTENT_TYPE = "application/vnd.dmaap-dr.subscription-full; version=2.0";
+ static final String SUBLIST_CONTENT_TYPE = "application/vnd.dmaap-dr.subscription-list; version=1.0";
//Adding groups functionality, ...1610
- static final String GROUP_BASECONTENT_TYPE = "application/vnd.att-dr.group";
- public static final String GROUP_CONTENT_TYPE = "application/vnd.att-dr.group; version=2.0";
- static final String GROUPFULL_CONTENT_TYPE = "application/vnd.att-dr.group-full; version=2.0";
- public static final String GROUPLIST_CONTENT_TYPE = "application/vnd.att-dr.fegrouped-list; version=1.0";
+ static final String GROUP_BASECONTENT_TYPE = "application/vnd.dmaap-dr.group";
+ static final String GROUP_CONTENT_TYPE = "application/vnd.dmaap-dr.group; version=2.0";
+ public static final String GROUPFULL_CONTENT_TYPE = "application/vnd.dmaap-dr.group-full; version=2.0";
+ public static final String GROUPLIST_CONTENT_TYPE = "application/vnd.dmaap-dr.fegrouped-list; version=1.0";
- public static final String LOGLIST_CONTENT_TYPE = "application/vnd.att-dr.log-list; version=1.0";
- public static final String PROVFULL_CONTENT_TYPE1 = "application/vnd.att-dr.provfeed-full; version=1.0";
- public static final String PROVFULL_CONTENT_TYPE2 = "application/vnd.att-dr.provfeed-full; version=2.0";
+ public static final String LOGLIST_CONTENT_TYPE = "application/vnd.dmaap-dr.log-list; version=1.0";
+ public static final String PROVFULL_CONTENT_TYPE1 = "application/vnd.dmaap-dr.provfeed-full; version=1.0";
+ public static final String PROVFULL_CONTENT_TYPE2 = "application/vnd.dmaap-dr.provfeed-full; version=2.0";
public static final String CERT_ATTRIBUTE = "javax.servlet.request.X509Certificate";
static final String DB_PROBLEM_MSG = "There has been a problem with the DB. It is suggested you try the operation again.";
* Array of nodes names and/or FQDNs
*/
private static String[] nodes = new String[0];
+ /**
+ * [DATARTR-27] Poke all the DR nodes : Array of nodes names and/or FQDNs
+ */
+ private static String[] drnodes = new String[0];
/**
* Array of node IP addresses
*/
* The current number of subscriptions in the system
*/
static int activeSubs = 0;
+
/**
* The domain used to generate a FQDN from the "bare" node names
*/
private static String provDomain = "web.att.com";
+
/**
* The standard FQDN of the provisioning server in this Data Router ecosystem
*/
*/
private static String activeProvName = "feeds-drtr.web.att.com";
- private static String staticRoutingNodes = STATIC_ROUTING_NODES; //Adding new param for static Routing - Rally:US664862-1610
+ //Adding new param for static Routing - Rally:US664862-1610
+ private static String staticRoutingNodes = STATIC_ROUTING_NODES;
/**
* This logger is used to log provisioning events
*/
- protected static Logger eventlogger;
+ protected static EELFLogger eventlogger;
/**
* This logger is used to log internal events (errors, etc.)
*/
- protected static Logger intlogger;
+ protected static EELFLogger intlogger;
/**
* Authorizer - interface to the Policy Engine
*/
//DMAAP-597 (Tech Dept) REST request source IP auth relaxation to accommodate OOM kubernetes deploy
private static String isAddressAuthEnabled = (new DB()).getProperties()
- .getProperty("org.onap.dmaap.datarouter.provserver.isaddressauthenabled", "false");
+ .getProperty("org.onap.dmaap.datarouter.provserver.isaddressauthenabled", "false");
+
+ static String isCadiEnabled = (new DB()).getProperties()
+ .getProperty("org.onap.dmaap.datarouter.provserver.cadi.enabled", "false");
/**
* Initialize data common to all the provisioning server servlets.
*/
protected BaseServlet() {
- if (eventlogger == null) {
- eventlogger = Logger.getLogger("org.onap.dmaap.datarouter.provisioning.events");
+ if(eventlogger == null) {
+ this.eventlogger = EELFManager.getInstance().getLogger("EventLog");
}
- if (intlogger == null) {
- intlogger = Logger.getLogger("org.onap.dmaap.datarouter.provisioning.internal");
+ if(intlogger == null) {
+ this.intlogger = EELFManager.getInstance().getLogger("InternalLog");
}
if (authz == null) {
authz = new ProvAuthorizer(this);
}
}
- int getIdFromPath(HttpServletRequest req) {
+ public static int getIdFromPath(HttpServletRequest req) {
String path = req.getPathInfo();
if (path == null || path.length() < 2) {
return -1;
return jo;
}
+ /**
+ * This method encrypt/decrypt the key in the JSON passed by user request inside the authorisation header object in request before logging the JSON.
+ *
+ * @param jo- the JSON passed in http request.
+ * @param maskKey- the key to be masked in the JSON passed.
+ * @param action- whether to mask the key or unmask it in a JSON passed.
+ * @return the JSONObject, or null if the stream cannot be parsed.
+ */
+ public static JSONObject maskJSON(JSONObject jo, String maskKey, boolean action) {
+ if (!jo.isNull("authorization")) {
+ JSONObject j2 = jo.getJSONObject("authorization");
+ JSONArray ja = j2.getJSONArray("endpoint_ids");
+ for (int i = 0; i < ja.length(); i++) {
+ if ((!ja.getJSONObject(i).isNull(maskKey))) {
+ String password = ja.getJSONObject(i).get(maskKey).toString();
+ try {
+ if (action) {
+ ja.getJSONObject(i).put(maskKey, PasswordProcessor.encrypt(password));
+ } else {
+ ja.getJSONObject(i).put(maskKey, PasswordProcessor.decrypt(password));
+ }
+ } catch (JSONException | GeneralSecurityException e) {
+ intlogger.info("Error reading JSON while masking: " + e);
+ }
+ }
+ }
+ }
+ return jo;
+ }
+
/**
* Check if the remote host is authorized to perform provisioning. Is the request secure? Is it coming from an
* authorized IP address or network (configured via PROV_AUTH_ADDRESSES)? Does it have a valid client certificate
if (requireSecure && !request.isSecure()) {
return "Request must be made over an HTTPS connection.";
}
-
// Is remote IP authorized?
String remote = request.getRemoteAddr();
try {
return "Unauthorized address: " + remote;
}
} catch (UnknownHostException e) {
+ intlogger.error("PROV0051 BaseServlet.isAuthorizedForProvisioning: ", e.getMessage());
return "Unauthorized address: " + remote;
}
-
// Does remote have a valid certificate?
if (requireCert) {
- X509Certificate certs[] = (X509Certificate[]) request.getAttribute(CERT_ATTRIBUTE);
+ X509Certificate[] certs = (X509Certificate[]) request.getAttribute(CERT_ATTRIBUTE);
if (certs == null || certs.length == 0) {
return "Client certificate is missing.";
}
return "No authorized certificate found.";
}
}
-
// No problems!
return null;
}
* @return true iff authorized
*/
boolean isAuthorizedForInternal(HttpServletRequest request) {
-
try {
if (!Boolean.parseBoolean(isAddressAuthEnabled)) {
return true;
return true;
}
} catch (UnknownHostException e) {
- // ignore
+ intlogger.error("PROV0052 BaseServlet.isAuthorizedForInternal: ", e.getMessage());
}
return false;
}
* Check if an IP address matches a network address.
*
* @param ip the IP address
- * @param s the network address; a bare IP address may be matched also
+ * @param s the network address; a bare IP address may be matched also
* @return true if they intersect
*/
private static boolean addressMatchesNetwork(InetAddress ip, String s) {
}
if (mlen > 0) {
byte[] masks = {
- (byte) 0x00, (byte) 0x80, (byte) 0xC0, (byte) 0xE0,
- (byte) 0xF0, (byte) 0xF8, (byte) 0xFC, (byte) 0xFE
+ (byte) 0x00, (byte) 0x80, (byte) 0xC0, (byte) 0xE0,
+ (byte) 0xF0, (byte) 0xF8, (byte) 0xFC, (byte) 0xFE
};
byte mask = masks[mlen % 8];
for (n = mlen / 8; n < b1.length; n++) {
}
}
} catch (UnknownHostException e) {
+ intlogger.error("PROV0053 BaseServlet.addressMatchesNetwork: ", e.getMessage());
return false;
}
return true;
* Something has changed in the provisioning data. Start the timers that will cause the pre-packaged JSON string to
* be regenerated, and cause nodes and the other provisioning server to be notified.
*/
- public static void provisioningDataChanged() {
+ static void provisioningDataChanged() {
long now = System.currentTimeMillis();
Poker p = Poker.getPoker();
p.setTimers(now + (pokeTimer1 * 1000L), now + (pokeTimer2 * 1000L));
/**
* Something in the parameters has changed, reload all parameters from the DB.
*/
- public static void provisioningParametersChanged() {
+ static void provisioningParametersChanged() {
Map<String, String> map = Parameters.getParameters();
requireSecure = getBoolean(map, Parameters.PROV_REQUIRE_SECURE);
requireCert = getBoolean(map, Parameters.PROV_REQUIRE_CERT);
maxSubs = getInt(map, Parameters.PROV_MAXSUB_COUNT, DEFAULT_MAX_SUBS);
pokeTimer1 = getInt(map, Parameters.PROV_POKETIMER1, DEFAULT_POKETIMER1);
pokeTimer2 = getInt(map, Parameters.PROV_POKETIMER2, DEFAULT_POKETIMER2);
+ /**
+ * The domain used to generate a FQDN from the "bare" node names
+ */
provDomain = getString(map, Parameters.PROV_DOMAIN, DEFAULT_DOMAIN);
provName = getString(map, Parameters.PROV_NAME, DEFAULT_PROVSRVR_NAME);
activeProvName = getString(map, Parameters.PROV_ACTIVE_NAME, provName);
- staticRoutingNodes = getString(map, Parameters.STATIC_ROUTING_NODES,
- ""); //Adding new param for static Routing - Rally:US664862-1610
initialActivePod = getString(map, Parameters.ACTIVE_POD, "");
initialStandbyPod = getString(map, Parameters.STANDBY_POD, "");
staticRoutingNodes = getString(map, Parameters.STATIC_ROUTING_NODES,
- ""); //Adding new param for static Routing - Rally:US664862-1610
+ ""); //Adding new param for static Routing - Rally:US664862-1610
activeFeeds = Feed.countActiveFeeds();
activeSubs = Subscription.countActiveSubscriptions();
try {
intlogger.debug("PROV0003 DNS lookup: " + nodes[i] + " => " + na[i].toString());
} catch (UnknownHostException e) {
na[i] = null;
- intlogger.warn("PROV0004 Cannot lookup " + nodes[i] + ": " + e);
+ intlogger.warn("PROV0004 Cannot lookup " + nodes[i] + ": " + e.getMessage());
}
}
+ //[DATARTR-27] Poke all the DR nodes: assigning DR Nodes
+ drnodes = nodes.clone();
+
//Reset Nodes arr after - removing static routing Nodes, Rally Userstory - US664862 .
List<String> filterNodes = new ArrayList<>();
for (String node : nodes) {
filterNodes.add(node);
}
}
- nodes = filterNodes.toArray(new String[filterNodes.size()]);
+ nodes = filterNodes.toArray(new String[0]);
nodeAddresses = na;
NodeClass.setNodes(nodes); // update NODES table
intlogger.debug("PROV0003 DNS lookup: " + pods[i] + " => " + na[i].toString());
} catch (UnknownHostException e) {
na[i] = null;
- intlogger.warn("PROV0004 Cannot lookup " + pods[i] + ": " + e);
+ intlogger.warn("PROV0004 Cannot lookup " + pods[i] + ": " + e.getMessage());
}
}
podAddresses = na;
private void loadMailProperties() {
if (mailprops == null) {
mailprops = new Properties();
- InputStream inStream = getClass().getClassLoader().getResourceAsStream(MAILCONFIG_FILE);
- try {
+ try (InputStream inStream = getClass().getClassLoader().getResourceAsStream(MAILCONFIG_FILE)) {
mailprops.load(inStream);
} catch (IOException e) {
- intlogger.fatal("PROV9003 Opening properties: " + e.getMessage());
+ intlogger.error("PROV9003 Opening properties: " + e.getMessage());
System.exit(1);
- } finally {
- try {
- inStream.close();
- } catch (IOException e) {
- }
}
}
}
msg.addRecipients(Message.RecipientType.TO, addressTo);
msg.setSubject(mailprops.get("com.att.dmaap.datarouter.mail.subject").toString());
htmlPart.setContent(mailprops.get("com.att.dmaap.datarouter.mail.body").toString()
- .replace("[SERVER]", InetAddress.getLocalHost().getHostName()), "text/html");
+ .replace("[SERVER]", InetAddress.getLocalHost().getHostName()), "text/html");
mp.addBodyPart(htmlPart);
msg.setContent(mp);
System.out.println(mailprops.get("com.att.dmaap.datarouter.mail.body").toString()
- .replace("[SERVER]", InetAddress.getLocalHost().getHostName()));
+ .replace("[SERVER]", InetAddress.getLocalHost().getHostName()));
Transport.send(msg);
intlogger.info("HTTPS relaxation mail is sent to - : " + email);
- } catch (AddressException e) {
- intlogger.error("Invalid email address, unable to send https relaxation mail to - : " + email);
} catch (MessagingException e) {
intlogger.error("Invalid email address, unable to send https relaxation mail to - : " + email);
}
return nodes;
}
+ /**
+ * [DATARTR-27] Poke all the DR nodes
+ * Get an array of all node names in the DR network.
+ *
+ * @return an array of Strings
+ */
+ public static String[] getDRNodes() {
+ return drnodes;
+ }
+
/**
* Get an array of all node InetAddresses in the DR network.
*
}
/*
- * @Method - setIpAndFqdnForEelf - Rally:US664892
+ * @Method - setIpFqdnRequestIDandInvocationIDForEelf
+ * @Params - method, prints method name in EELF log.
+ * @Params- Req, Request used to get RequestId and InvocationId
+ */
+ void setIpFqdnRequestIDandInvocationIDForEelf(String method, HttpServletRequest req) {
+ setIpFqdnForEelf(method);
+ setMDC(req, "X-ONAP-RequestID", MDC_KEY_REQUEST_ID);
+ setMDC(req, "X-InvocationID", "InvocationId");
+ }
+
+ private void setMDC(HttpServletRequest req, String headerName, String keyName) {
+ String mdcId = req.getHeader(headerName);
+ if (StringUtils.isBlank(mdcId)) {
+ mdcId = UUID.randomUUID().toString();
+ }
+ MDC.put(keyName, mdcId);
+ }
+
+ /*
+ * @Method - setIpFqdnRequestIdForEelf - Rally:US664892
* @Params - method, prints method name in EELF log.
*/
- void setIpAndFqdnForEelf(String method) {
+ void setIpFqdnForEelf(String method) {
MDC.clear();
MDC.put(MDC_SERVICE_NAME, method);
try {
}
}
+
+ /*
+ * AAF changes: TDP EPIC US# 307413
+ * @Method - getFeedPermission - Forming permission string for feed part to check AAF access in CADI Framework
+ * @Params - aafInstance Passing aafInstance as it's used in permission string
+ * @Params - userAction Passing CONST values to set different actions in permission string
+ */
+ String getFeedPermission(String aafInstance, String userAction) {
+ try {
+ Properties props = (new DB()).getProperties();
+ String type = props.getProperty(AAF_CADI_FEED_TYPE, AAF_CADI_FEED);
+ String action;
+ switch (userAction) {
+ case CREATE_PERMISSION:
+ action = CREATE_PERMISSION;
+ break;
+ case EDIT_PERMISSION:
+ action = EDIT_PERMISSION;
+ break;
+ case DELETE_PERMISSION:
+ action = DELETE_PERMISSION;
+ break;
+ case PUBLISH_PERMISSION:
+ action = PUBLISH_PERMISSION;
+ break;
+ case SUSPEND_PERMISSION:
+ action = SUSPEND_PERMISSION;
+ break;
+ case RESTORE_PERMISSION:
+ action = RESTORE_PERMISSION;
+ break;
+ default:
+ action = "*";
+ }
+ if (aafInstance == null || aafInstance.equals("")) {
+ aafInstance = props.getProperty(AAF_INSTANCE, "org.onap.dmaap-dr.NoInstanceDefined");
+ }
+ return type + "|" + aafInstance + "|" + action;
+ } catch (Exception e) {
+ intlogger.error("PROV7005 BaseServlet.getFeedPermission: ", e.getMessage());
+ }
+ return null;
+ }
+
+ /*
+ * AAF changes: TDP EPIC US# 307413
+ * @Method - getSubscriberPermission - Forming permission string for subscription part to check AAF access in CADI Framework
+ * @Params - aafInstance Passing aafInstance as it's used in permission string
+ * @Params - userAction Passing CONST values to set different actions in permission string
+ */
+ String getSubscriberPermission(String aafInstance, String userAction) {
+ try {
+ Properties props = (new DB()).getProperties();
+ String type = props.getProperty(AAF_CADI_SUB_TYPE, AAF_CADI_SUB);
+ String action;
+ switch (userAction) {
+ case SUBSCRIBE_PERMISSION:
+ action = SUBSCRIBE_PERMISSION;
+ type = props.getProperty(AAF_CADI_FEED_TYPE, AAF_CADI_FEED);
+ break;
+ case EDIT_PERMISSION:
+ action = EDIT_PERMISSION;
+ break;
+ case DELETE_PERMISSION:
+ action = DELETE_PERMISSION;
+ break;
+ case RESTORE_PERMISSION:
+ action = RESTORE_PERMISSION;
+ break;
+ case SUSPEND_PERMISSION:
+ action = SUSPEND_PERMISSION;
+ break;
+ case PUBLISH_PERMISSION:
+ action = PUBLISH_PERMISSION;
+ break;
+ case APPROVE_SUB_PERMISSION:
+ action = APPROVE_SUB_PERMISSION;
+ type = props.getProperty(AAF_CADI_FEED_TYPE, AAF_CADI_FEED);
+ break;
+ default:
+ action = "*";
+ }
+ if (aafInstance == null || aafInstance.equals("")) {
+ aafInstance = props.getProperty(AAF_INSTANCE, "org.onap.dmaap-dr.NoInstanceDefined");
+ }
+ return type + "|" + aafInstance + "|" + action;
+ } catch (Exception e) {
+ intlogger.error("PROV7005 BaseServlet.getSubscriberPermission: ", e.getMessage());
+ }
+ return null;
+ }
}