[DMAAP-48] Initial code import
[dmaap/datarouter.git] / datarouter-node / src / main / java / com / att / research / datarouter / node / NodeUtils.java
1 /*******************************************************************************\r
2  * ============LICENSE_START==================================================\r
3  * * org.onap.dmaap\r
4  * * ===========================================================================\r
5  * * Copyright © 2017 AT&T Intellectual Property. All rights reserved.\r
6  * * ===========================================================================\r
7  * * Licensed under the Apache License, Version 2.0 (the "License");\r
8  * * you may not use this file except in compliance with the License.\r
9  * * You may obtain a copy of the License at\r
10  * * \r
11  *  *      http://www.apache.org/licenses/LICENSE-2.0\r
12  * * \r
13  *  * Unless required by applicable law or agreed to in writing, software\r
14  * * distributed under the License is distributed on an "AS IS" BASIS,\r
15  * * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
16  * * See the License for the specific language governing permissions and\r
17  * * limitations under the License.\r
18  * * ============LICENSE_END====================================================\r
19  * *\r
20  * * ECOMP is a trademark and service mark of AT&T Intellectual Property.\r
21  * *\r
22  ******************************************************************************/\r
23 \r
24 \r
25 package com.att.research.datarouter.node;\r
26 \r
27 import static com.att.eelf.configuration.Configuration.MDC_SERVER_FQDN;\r
28 import static com.att.eelf.configuration.Configuration.MDC_SERVER_IP_ADDRESS;\r
29 import static com.att.eelf.configuration.Configuration.MDC_SERVICE_NAME;\r
30 \r
31 import java.security.*;\r
32 import java.io.*;\r
33 import java.util.*;\r
34 import java.security.cert.*;\r
35 import java.net.*;\r
36 import java.text.*;\r
37 import org.apache.commons.codec.binary.Base64;\r
38 import org.apache.log4j.Logger;\r
39 import org.slf4j.MDC;\r
40 \r
41 import com.att.eelf.configuration.EELFLogger;\r
42 import com.att.eelf.configuration.EELFManager;\r
43 import com.att.research.datarouter.node.eelf.EelfMsgs;\r
44 \r
45 /**\r
46  *      Utility functions for the data router node\r
47  */\r
48 public class NodeUtils  {\r
49     private static EELFLogger eelflogger = EELFManager.getInstance().getLogger("com.att.research.datarouter.node.NodeUtils");\r
50         private static Logger logger = Logger.getLogger("com.att.research.datarouter.node.NodeUtils");\r
51         private static SimpleDateFormat logdate;\r
52         static {\r
53                 logdate = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");\r
54                 logdate.setTimeZone(TimeZone.getTimeZone("GMT"));\r
55         }\r
56         private NodeUtils() {}\r
57         /**\r
58          *      Base64 encode a byte array\r
59          *      @param raw      The bytes to be encoded\r
60          *      @return The encoded string\r
61          */\r
62         public static String base64Encode(byte[] raw) {\r
63                 return(Base64.encodeBase64String(raw));\r
64         }\r
65         /**\r
66          *      Given a user and password, generate the credentials\r
67          *      @param user     User name\r
68          *      @param password User password\r
69          *      @return Authorization header value\r
70          */\r
71         public static String getAuthHdr(String user, String password) {\r
72                 if (user == null || password == null) {\r
73                         return(null);\r
74                 }\r
75                 return("Basic " + base64Encode((user + ":" + password).getBytes()));\r
76         }\r
77         /**\r
78          *      Given a node name, generate the credentials\r
79          *      @param node     Node name\r
80          */\r
81         public static String    getNodeAuthHdr(String node, String key) {\r
82                 try {\r
83                         MessageDigest md = MessageDigest.getInstance("SHA");\r
84                         md.update(key.getBytes());\r
85                         md.update(node.getBytes());\r
86                         md.update(key.getBytes());\r
87                         return(getAuthHdr(node, base64Encode(md.digest())));\r
88                 } catch (Exception e) {\r
89                         return(null);\r
90                 }\r
91         }\r
92         /**\r
93          *      Given a keystore file and its password, return the value of the CN of the first private key entry with a certificate.\r
94          *      @param kstype   The type of keystore\r
95          *      @param ksfile   The file name of the keystore\r
96          *      @param kspass   The password of the keystore\r
97          *      @return CN of the certificate subject or null\r
98          */\r
99         public static String getCanonicalName(String kstype, String ksfile, String kspass) {\r
100                 try {\r
101                         KeyStore ks = KeyStore.getInstance(kstype);\r
102                         ks.load(new FileInputStream(ksfile), kspass.toCharArray());\r
103                         return(getCanonicalName(ks));\r
104                 } catch (Exception e) {\r
105                         setIpAndFqdnForEelf("getCanonicalName");\r
106                         eelflogger.error(EelfMsgs.MESSAGE_KEYSTORE_LOAD_ERROR, ksfile, e.toString());\r
107                         logger.error("NODE0401 Error loading my keystore file + " + ksfile + " " + e.toString(), e);\r
108                         return(null);\r
109                 }\r
110         }\r
111         /**\r
112          *      Given a keystore, return the value of the CN of the first private key entry with a certificate.\r
113          *      @param ks       The KeyStore\r
114          *      @return CN of the certificate subject or null\r
115          */\r
116         public static String getCanonicalName(KeyStore ks) {\r
117                 try {\r
118                         Enumeration<String> aliases = ks.aliases();\r
119                         while (aliases.hasMoreElements()) {\r
120                                 String s = aliases.nextElement();\r
121                                 if (ks.entryInstanceOf(s, KeyStore.PrivateKeyEntry.class)) {\r
122                                         X509Certificate c = (X509Certificate)ks.getCertificate(s);\r
123                                         if (c != null) {\r
124                                                 String subject = c.getSubjectX500Principal().getName();\r
125                                                 String[] parts = subject.split(",");\r
126                                                 if (parts.length < 1) {\r
127                                                         return(null);\r
128                                                 }\r
129                                                 subject = parts[0].trim();\r
130                                                 if (!subject.startsWith("CN=")) {\r
131                                                         return(null);\r
132 \r
133                                                 }\r
134                                                 return(subject.substring(3));\r
135                                         }\r
136                                 }\r
137                         }\r
138                 } catch (Exception e) {\r
139                         logger.error("NODE0402 Error extracting my name from my keystore file " + e.toString(), e);\r
140                 }\r
141                 return(null);\r
142         }\r
143         /**\r
144          *      Given a string representation of an IP address, get the corresponding byte array\r
145          *      @param ip       The IP address as a string\r
146          *      @return The IP address as a byte array or null if the address is invalid\r
147          */\r
148         public static byte[] getInetAddress(String ip) {\r
149                 try {\r
150                         return(InetAddress.getByName(ip).getAddress());\r
151                 } catch (Exception e) {\r
152                 }\r
153                 return(null);\r
154         }\r
155         /**\r
156          *      Given a uri with parameters, split out the feed ID and file ID\r
157          */\r
158         public static String[] getFeedAndFileID(String uriandparams) {\r
159                 int end = uriandparams.length();\r
160                 int i = uriandparams.indexOf('#');\r
161                 if (i != -1 && i < end) {\r
162                         end = i;\r
163                 }\r
164                 i = uriandparams.indexOf('?');\r
165                 if (i != -1 && i < end) {\r
166                         end = i;\r
167                 }\r
168                 end = uriandparams.lastIndexOf('/', end);\r
169                 if (end < 2) {\r
170                         return(null);\r
171                 }\r
172                 i = uriandparams.lastIndexOf('/', end - 1);\r
173                 if (i == -1) {\r
174                         return(null);\r
175                 }\r
176                 return(new String[] { uriandparams.substring(i + 1, end - 1), uriandparams.substring(end + 1) });\r
177         }\r
178         /**\r
179          *      Escape fields that might contain vertical bar, backslash, or newline by replacing them with backslash p, backslash e and backslash n.\r
180          */\r
181         public static String loge(String s) {\r
182                 if (s == null) {\r
183                         return(s);\r
184                 }\r
185                 return(s.replaceAll("\\\\", "\\\\e").replaceAll("\\|", "\\\\p").replaceAll("\n", "\\\\n"));\r
186         }\r
187         /**\r
188          *      Undo what loge does.\r
189          */\r
190         public static String unloge(String s) {\r
191                 if (s == null) {\r
192                         return(s);\r
193                 }\r
194                 return(s.replaceAll("\\\\p", "\\|").replaceAll("\\\\n", "\n").replaceAll("\\\\e", "\\\\"));\r
195         }\r
196         /**\r
197          *      Format a logging timestamp as yyyy-mm-ddThh:mm:ss.mmmZ\r
198          */\r
199         public static String logts(long when) {\r
200                 return(logts(new Date(when)));\r
201         }\r
202         /**\r
203          *      Format a logging timestamp as yyyy-mm-ddThh:mm:ss.mmmZ\r
204          */\r
205         public static synchronized String logts(Date when) {\r
206                 return(logdate.format(when));\r
207         }\r
208         \r
209         /* Method prints method name, server FQDN and IP Address of the machine in EELF logs\r
210          * @Method - setIpAndFqdnForEelf - Rally:US664892  \r
211          * @Params - method, prints method name in EELF log.\r
212          */     \r
213         public static void setIpAndFqdnForEelf(String method) {\r
214                 MDC.clear();\r
215         MDC.put(MDC_SERVICE_NAME, method);\r
216         try {\r
217             MDC.put(MDC_SERVER_FQDN, InetAddress.getLocalHost().getHostName());\r
218             MDC.put(MDC_SERVER_IP_ADDRESS, InetAddress.getLocalHost().getHostAddress());\r
219         } catch (Exception e) {\r
220             e.printStackTrace();\r
221         }\r
222 \r
223         }\r
224         \r
225 \r
226 }\r