Refactor Prov DB handling
[dmaap/datarouter.git] / datarouter-prov / src / main / java / org / onap / dmaap / datarouter / provisioning / ProxyServlet.java
old mode 100644 (file)
new mode 100755 (executable)
index 6564e17..d84e492
@@ -24,6 +24,8 @@
 
 package org.onap.dmaap.datarouter.provisioning;
 
+import static org.onap.dmaap.datarouter.provisioning.utils.HttpServletUtils.sendResponseError;
+
 import java.io.File;
 import java.io.FileInputStream;
 import java.io.FileNotFoundException;
@@ -34,13 +36,10 @@ import java.security.KeyStore;
 import java.security.KeyStoreException;
 import java.util.Collections;
 import java.util.List;
-import java.util.Properties;
-
 import javax.servlet.ServletConfig;
 import javax.servlet.ServletException;
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
-
 import org.apache.commons.io.IOUtils;
 import org.apache.http.Header;
 import org.apache.http.HttpEntity;
@@ -53,20 +52,22 @@ import org.apache.http.conn.ssl.SSLSocketFactory;
 import org.apache.http.entity.BasicHttpEntity;
 import org.apache.http.impl.client.AbstractHttpClient;
 import org.apache.http.impl.client.DefaultHttpClient;
-import org.onap.dmaap.datarouter.provisioning.utils.DB;
+import org.onap.dmaap.datarouter.provisioning.utils.AafPropsUtils;
+import org.onap.dmaap.datarouter.provisioning.utils.SynchronizerTask;
 import org.onap.dmaap.datarouter.provisioning.utils.URLUtilities;
 
 /**
- * This class is the base class for those servlets that need to proxy their requests from the
- * standby to active server.  Its methods perform the proxy function to the active server. If the
- * active server is not reachable, a 503 (SC_SERVICE_UNAVAILABLE) is returned.  Only
- * DELETE/GET/PUT/POST are supported.
+ * This class is the base class for those servlets that need to proxy their requests from the standby to active server.
+ * Its methods perform the proxy function to the active server. If the active server is not reachable, a 503
+ * (SC_SERVICE_UNAVAILABLE) is returned.  Only DELETE/GET/PUT/POST are supported.
  *
  * @author Robert Eby
  * @version $Id: ProxyServlet.java,v 1.3 2014/03/24 18:47:10 eby Exp $
  */
 @SuppressWarnings("serial")
+
 public class ProxyServlet extends BaseServlet {
+
     private boolean inited = false;
     private Scheme sch;
 
@@ -79,222 +80,245 @@ public class ProxyServlet extends BaseServlet {
         super.init(config);
         try {
             // Set up keystore
-            Properties props = (new DB()).getProperties();
-            String type  = props.getProperty(Main.KEYSTORE_TYPE_PROPERTY, "jks");
-            String store = props.getProperty(Main.KEYSTORE_PATH_PROPERTY);
-            String pass  = props.getProperty(Main.KEYSTORE_PASSWORD_PROPERTY);
+            String type = AafPropsUtils.KEYSTORE_TYPE_PROPERTY;
+            String store = ProvRunner.getAafPropsUtils().getKeystorePathProperty();
+            String pass = ProvRunner.getAafPropsUtils().getKeystorePassProperty();
             KeyStore keyStore = readStore(store, pass, type);
-
-            store = props.getProperty(Main.TRUSTSTORE_PATH_PROPERTY);
-            pass  = props.getProperty(Main.TRUSTSTORE_PASSWORD_PROPERTY);
+            // Set up truststore
+            store = ProvRunner.getAafPropsUtils().getTruststorePathProperty();
+            pass = ProvRunner.getAafPropsUtils().getTruststorePassProperty();
             if (store == null || store.length() == 0) {
-                store = Main.DEFAULT_TRUSTSTORE;
+                store = AafPropsUtils.DEFAULT_TRUSTSTORE;
                 pass = "changeit";
             }
-            KeyStore trustStore = readStore(store, pass, KeyStore.getDefaultType());
+            KeyStore trustStore = readStore(store, pass, AafPropsUtils.TRUESTSTORE_TYPE_PROPERTY);
 
             // We are connecting with the node name, but the certificate will have the CNAME
             // So we need to accept a non-matching certificate name
-            SSLSocketFactory socketFactory = new SSLSocketFactory(keyStore, "changeit", trustStore);
+            SSLSocketFactory socketFactory = new SSLSocketFactory(keyStore,
+                    ProvRunner.getAafPropsUtils().getKeystorePassProperty(), trustStore);
             socketFactory.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
             sch = new Scheme("https", 443, socketFactory);
             inited = true;
         } catch (Exception e) {
-            e.printStackTrace();
+            intlogger.error("ProxyServlet.init: " + e.getMessage(), e);
         }
-        intlogger.info("ProxyServlet: inited = "+inited);
+        intlogger.info("ProxyServlet: inited = " + inited);
     }
-    private KeyStore readStore(String store, String pass, String type) throws KeyStoreException, FileNotFoundException {
+
+    private KeyStore readStore(String store, String pass, String type) throws KeyStoreException {
         KeyStore ks = KeyStore.getInstance(type);
-        FileInputStream instream = new FileInputStream(new File(store));
-        try {
+        try (FileInputStream instream = new FileInputStream(new File(store))) {
             ks.load(instream, pass.toCharArray());
+        } catch (FileNotFoundException fileNotFoundException) {
+            intlogger.error("ProxyServlet.readStore: " + fileNotFoundException.getMessage(), fileNotFoundException);
         } catch (Exception x) {
-            System.err.println("READING TRUSTSTORE: "+x);
-        } finally {
-            try { instream.close(); } catch (Exception ignore) {}
+            intlogger.error("READING TRUSTSTORE: " + x);
         }
         return ks;
     }
+
     /**
-     * Return <i>true</i> if the requester has NOT set the <i>noproxy</i> CGI variable.
-     * If they have, this indicates they want to forcibly turn the proxy off.
+     * Return <i>true</i> if the requester has NOT set the <i>noproxy</i> CGI variable. If they have, this indicates
+     * they want to forcibly turn the proxy off.
+     *
      * @param req the HTTP request
      * @return true or false
      */
-    protected boolean isProxyOK(final HttpServletRequest req) {
-        String t = req.getQueryString();
-        if (t != null) {
-            t = t.replaceAll("&amp;", "&");
-            for (String s : t.split("&")) {
-                if (s.equals("noproxy") || s.startsWith("noproxy="))
+    boolean isProxyOK(final HttpServletRequest req) {
+        String str = req.getQueryString();
+        if (str != null) {
+            str = str.replaceAll("&amp;", "&");
+            for (String s : str.split("&")) {
+                if ("noproxy".equals(s) || s.startsWith("noproxy=")) {
                     return false;
+                }
             }
         }
         return true;
     }
+
     /**
-     * Is this the standby server?  If it is, the proxy functions can be used.
-     * If not, the proxy functions should not be called, and will send a response of 500
-     * (Internal Server Error).
+     * Is this the standby server?  If it is, the proxy functions can be used. If not, the proxy functions should not be
+     * called, and will send a response of 500 (Internal Server Error).
+     *
      * @return true if this server is the standby (and hence a proxy server).
      */
-    public boolean isProxyServer() {
+    boolean isProxyServer() {
         SynchronizerTask st = SynchronizerTask.getSynchronizer();
-        return st.getState() == SynchronizerTask.STANDBY;
+        return st.getPodState() == SynchronizerTask.STANDBY_POD;
     }
+
     /**
      * Issue a proxy DELETE to the active provisioning server.
      */
     @Override
-    public void doDelete(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+    public void doDelete(HttpServletRequest req, HttpServletResponse resp) {
         doProxy(req, resp, "DELETE");
     }
+
     /**
      * Issue a proxy GET to the active provisioning server.
      */
     @Override
-    public void doGet(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+    public void doGet(HttpServletRequest req, HttpServletResponse resp) {
         doProxy(req, resp, "GET");
     }
+
     /**
      * Issue a proxy PUT to the active provisioning server.
      */
     @Override
-    public void doPut(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+    public void doPut(HttpServletRequest req, HttpServletResponse resp) {
         doProxy(req, resp, "PUT");
     }
+
     /**
      * Issue a proxy POST to the active provisioning server.
      */
     @Override
-    public void doPost(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+    public void doPost(HttpServletRequest req, HttpServletResponse resp) {
         doProxy(req, resp, "POST");
     }
+
     /**
-     * Issue a proxy GET to the active provisioning server.  Unlike doGet() above,
-     * this method will allow the caller to fall back to other code if the remote server is unreachable.
+     * Issue a proxy GET to the active provisioning server.  Unlike doGet() above, this method will allow the caller to
+     * fall back to other code if the remote server is unreachable.
+     *
      * @return true if the proxy succeeded
      */
-    public boolean doGetWithFallback(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+    boolean doGetWithFallback(HttpServletRequest req, HttpServletResponse resp) {
         boolean rv = false;
         if (inited) {
             String url = buildUrl(req);
-            intlogger.info("ProxyServlet: proxying with fallback GET "+url);
-            AbstractHttpClient httpclient = new DefaultHttpClient();
-            HttpRequestBase proxy = new HttpGet(url);
-            try {
-                httpclient.getConnectionManager().getSchemeRegistry().register(sch);
-
-                // Copy request headers and request body
-                copyRequestHeaders(req, proxy);
-
-                // Execute the request
-                HttpResponse pxy_response = httpclient.execute(proxy);
-
-                // Get response headers and body
-                int code = pxy_response.getStatusLine().getStatusCode();
-                resp.setStatus(code);
-                copyResponseHeaders(pxy_response, resp);
-
-                HttpEntity entity = pxy_response.getEntity();
-                if (entity != null) {
-                    InputStream in = entity.getContent();
-                    IOUtils.copy(in, resp.getOutputStream());
-                    in.close();
+            intlogger.info("ProxyServlet: proxying with fallback GET " + url);
+            try (AbstractHttpClient httpclient = new DefaultHttpClient()) {
+                HttpRequestBase proxy = new HttpGet(url);
+                try {
+                    httpclient.getConnectionManager().getSchemeRegistry().register(sch);
+
+                    // Copy request headers and request body
+                    copyRequestHeaders(req, proxy);
+
+                    // Execute the request
+                    HttpResponse pxyResponse = httpclient.execute(proxy);
+
+                    // Get response headers and body
+                    int code = pxyResponse.getStatusLine().getStatusCode();
+                    resp.setStatus(code);
+                    copyResponseHeaders(pxyResponse, resp);
+                    copyEntityContent(pxyResponse, resp);
+                    rv = true;
+
+                } catch (IOException e) {
+                    intlogger.error("ProxyServlet.doGetWithFallback: " + e.getMessage(), e);
+                } finally {
+                    proxy.releaseConnection();
+                    httpclient.getConnectionManager().shutdown();
                 }
-                rv = true;
-            } catch (IOException e) {
-                System.err.println("ProxyServlet: "+e);
-                e.printStackTrace();
-            } finally {
-                proxy.releaseConnection();
-                httpclient.getConnectionManager().shutdown();
             }
         } else {
             intlogger.warn("ProxyServlet: proxy disabled");
         }
         return rv;
     }
-    private void doProxy(HttpServletRequest req, HttpServletResponse resp, final String method) throws IOException {
+
+    private void doProxy(HttpServletRequest req, HttpServletResponse resp, final String method) {
         if (inited && isProxyServer()) {
             String url = buildUrl(req);
-            intlogger.info("ProxyServlet: proxying "+method + " "+url);
-            AbstractHttpClient httpclient = new DefaultHttpClient();
-            ProxyHttpRequest proxy = new ProxyHttpRequest(method, url);
-            try {
-                httpclient.getConnectionManager().getSchemeRegistry().register(sch);
-
-                // Copy request headers and request body
-                copyRequestHeaders(req, proxy);
-                if (method.equals("POST") || method.equals("PUT")){
-                    BasicHttpEntity body = new BasicHttpEntity();
-                    body.setContent(req.getInputStream());
-                    body.setContentLength(-1);    // -1 = unknown
-                    proxy.setEntity(body);
-                }
+            intlogger.info("ProxyServlet: proxying " + method + " " + url);
+            try (AbstractHttpClient httpclient = new DefaultHttpClient()) {
+                ProxyHttpRequest proxy = new ProxyHttpRequest(method, url);
+                try {
+                    httpclient.getConnectionManager().getSchemeRegistry().register(sch);
 
-                // Execute the request
-                HttpResponse pxy_response = httpclient.execute(proxy);
+                    // Copy request headers and request body
+                    copyRequestHeaders(req, proxy);
 
-                // Get response headers and body
-                int code = pxy_response.getStatusLine().getStatusCode();
-                resp.setStatus(code);
-                copyResponseHeaders(pxy_response, resp);
+                    handlePutOrPost(req, method, proxy);
 
-                HttpEntity entity = pxy_response.getEntity();
-                if (entity != null) {
-                    InputStream in = entity.getContent();
-                    IOUtils.copy(in, resp.getOutputStream());
-                    in.close();
+                    // Execute the request
+                    HttpResponse pxyResponse = httpclient.execute(proxy);
+
+                    // Get response headers and body
+                    int code = pxyResponse.getStatusLine().getStatusCode();
+                    resp.setStatus(code);
+                    copyResponseHeaders(pxyResponse, resp);
+                    copyEntityContent(pxyResponse, resp);
+                } catch (IOException e) {
+                    intlogger.warn("ProxyServlet.doProxy: " + e.getMessage(), e);
+                    sendResponseError(resp, HttpServletResponse.SC_SERVICE_UNAVAILABLE, "", intlogger);
+                } finally {
+                    proxy.releaseConnection();
+                    httpclient.getConnectionManager().shutdown();
                 }
-            } catch (IOException e) {
-                intlogger.warn("ProxyServlet: "+e);
-                resp.sendError(HttpServletResponse.SC_SERVICE_UNAVAILABLE);
-                e.printStackTrace();
-            } finally {
-                proxy.releaseConnection();
-                httpclient.getConnectionManager().shutdown();
             }
         } else {
             intlogger.warn("ProxyServlet: proxy disabled");
-            resp.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
+            sendResponseError(resp, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, DB_PROBLEM_MSG, intlogger);
+        }
+    }
+
+    private void handlePutOrPost(HttpServletRequest req, String method, ProxyHttpRequest proxy) throws IOException {
+        if ("POST".equals(method) || "PUT".equals(method)) {
+            BasicHttpEntity body = new BasicHttpEntity();
+            body.setContent(req.getInputStream());
+            body.setContentLength(-1);    // -1 = unknown
+            proxy.setEntity(body);
         }
     }
+
     private String buildUrl(HttpServletRequest req) {
         StringBuilder sb = new StringBuilder("https://");
         sb.append(URLUtilities.getPeerPodName());
         sb.append(req.getRequestURI());
-        String q = req.getQueryString();
-        if (q != null)
-            sb.append("?").append(q);
+        String query = req.getQueryString();
+        if (query != null) {
+            sb.append("?").append(query);
+        }
         return sb.toString();
     }
+
     private void copyRequestHeaders(HttpServletRequest from, HttpRequestBase to) {
-        @SuppressWarnings("unchecked")
         List<String> list = Collections.list(from.getHeaderNames());
         for (String name : list) {
             // Proxy code will add this one
-            if (!name.equalsIgnoreCase("Content-Length"))
+            if (!"Content-Length".equalsIgnoreCase(name)) {
                 to.addHeader(name, from.getHeader(name));
+            }
         }
     }
-    private void copyResponseHeaders(HttpResponse from, HttpServletResponse to) {
+
+    void copyResponseHeaders(HttpResponse from, HttpServletResponse to) {
         for (Header hdr : from.getAllHeaders()) {
             // Don't copy Date: our Jetty will add another Date header
-            if (!hdr.getName().equals("Date"))
+            if (!"Date".equals(hdr.getName())) {
                 to.addHeader(hdr.getName(), hdr.getValue());
+            }
         }
     }
 
-    public class ProxyHttpRequest extends HttpEntityEnclosingRequestBase {
+    void copyEntityContent(HttpResponse pxyResponse, HttpServletResponse resp) {
+        HttpEntity entity = pxyResponse.getEntity();
+        if (entity != null) {
+            try (InputStream in = entity.getContent()) {
+                IOUtils.copy(in, resp.getOutputStream());
+            } catch (Exception e) {
+                intlogger.error("ProxyServlet.copyEntityContent: " + e.getMessage(), e);
+            }
+        }
+    }
+
+    public static class ProxyHttpRequest extends HttpEntityEnclosingRequestBase {
+
         private final String method;
 
-        public ProxyHttpRequest(final String method, final String uri) {
+        ProxyHttpRequest(final String method, final String uri) {
             super();
             this.method = method;
             setURI(URI.create(uri));
         }
+
         @Override
         public String getMethod() {
             return method;