Update AAF Version 1.0.0
[aaf/cadi.git] / aaf / src / main / java / com / att / cadi / cm / CmAgent.java
1 /*******************************************************************************\r
2  * ============LICENSE_START====================================================\r
3  * * org.onap.aaf\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 package com.att.cadi.cm;\r
24 \r
25 import java.io.File;\r
26 import java.io.FileInputStream;\r
27 import java.io.FileOutputStream;\r
28 import java.net.InetAddress;\r
29 import java.net.UnknownHostException;\r
30 import java.security.KeyStore;\r
31 import java.security.cert.X509Certificate;\r
32 import java.util.ArrayDeque;\r
33 import java.util.Deque;\r
34 import java.util.GregorianCalendar;\r
35 import java.util.HashMap;\r
36 import java.util.Iterator;\r
37 import java.util.Map;\r
38 import java.util.Map.Entry;\r
39 import java.util.Properties;\r
40 \r
41 import com.att.cadi.PropAccess;\r
42 import com.att.cadi.Symm;\r
43 import com.att.cadi.aaf.client.ErrMessage;\r
44 import com.att.cadi.aaf.v2_0.AAFCon;\r
45 import com.att.cadi.aaf.v2_0.AAFConHttp;\r
46 import com.att.cadi.client.Future;\r
47 import com.att.cadi.config.Config;\r
48 import com.att.cadi.http.HBasicAuthSS;\r
49 import com.att.cadi.sso.AAFSSO;\r
50 import com.att.inno.env.Data.TYPE;\r
51 import com.att.inno.env.Env;\r
52 import com.att.inno.env.TimeTaken;\r
53 import com.att.inno.env.Trans;\r
54 import com.att.inno.env.util.Chrono;\r
55 import com.att.inno.env.util.Split;\r
56 import com.att.rosetta.env.RosettaDF;\r
57 import com.att.rosetta.env.RosettaEnv;\r
58 \r
59 import certman.v1_0.Artifacts;\r
60 import certman.v1_0.Artifacts.Artifact;\r
61 import certman.v1_0.CertInfo;\r
62 import certman.v1_0.CertificateRequest;\r
63 \r
64 public class CmAgent {\r
65         private static final String PRINT = "print";\r
66         private static final String FILE = "file";\r
67         private static final String PKCS12 = "pkcs12";\r
68         private static final String JKS = "jks";\r
69         private static final String SCRIPT="script";\r
70         \r
71         private static final String CM_VER = "1.0";\r
72         public static final int PASS_SIZE = 24;\r
73         private static int TIMEOUT;\r
74         \r
75         private static RosettaDF<CertificateRequest> reqDF;\r
76         private static RosettaDF<CertInfo> certDF;\r
77         private static RosettaDF<Artifacts> artifactsDF;\r
78         private static ErrMessage errMsg;\r
79         private static Map<String,PlaceArtifact> placeArtifact;\r
80         private static RosettaEnv env;\r
81 \r
82         public static void main(String[] args) {\r
83                 int exitCode = 0;\r
84                 try {\r
85                         AAFSSO aafsso = new AAFSSO(args);\r
86                         if(aafsso.loginOnly()) {\r
87                                 aafsso.setLogDefault();\r
88                                 aafsso.writeFiles();\r
89                                 System.out.println("AAF SSO information created in ~/.aaf");\r
90                         } else {\r
91                                 PropAccess access = aafsso.access();\r
92                                 env = new RosettaEnv(access.getProperties());\r
93                                 Deque<String> cmds = new ArrayDeque<String>();\r
94                                 for(String p : args) {\r
95                                         if(p.indexOf('=')<0) {\r
96                                                 cmds.add(p);\r
97                                         }\r
98                                 }\r
99                                 \r
100                                 if(cmds.size()==0) {\r
101                                         aafsso.setLogDefault();\r
102                                         System.out.println("Usage: java -jar <cadi-aaf-*-full.jar> cmd [<tag=value>]*");\r
103                                         System.out.println("   create   <mechID> [<machine>]");\r
104                                         System.out.println("   read     <mechID> [<machine>]");\r
105                                         System.out.println("   update   <mechID> [<machine>]");\r
106                                         System.out.println("   delete   <mechID> [<machine>]");\r
107                                         System.out.println("   copy     <mechID> <machine> <newmachine>[,<newmachine>]*");\r
108                                         System.out.println("   place    <mechID> [<machine>]");\r
109                                         System.out.println("   showpass <mechID> [<machine>]");\r
110                                         System.out.println("   check    <mechID> [<machine>]");\r
111                                         System.exit(1);\r
112                                 }\r
113                                 \r
114                                 TIMEOUT = Integer.parseInt(env.getProperty(Config.AAF_CONN_TIMEOUT, "5000"));\r
115                         \r
116                                 reqDF = env.newDataFactory(CertificateRequest.class);\r
117                                 artifactsDF = env.newDataFactory(Artifacts.class);\r
118                                 certDF = env.newDataFactory(CertInfo.class);\r
119                                 errMsg = new ErrMessage(env);\r
120         \r
121                                 placeArtifact = new HashMap<String,PlaceArtifact>();\r
122                                 placeArtifact.put(JKS, new PlaceArtifactInKeystore(JKS));\r
123                                 placeArtifact.put(PKCS12, new PlaceArtifactInKeystore(PKCS12));\r
124                                 placeArtifact.put(FILE, new PlaceArtifactInFiles());\r
125                                 placeArtifact.put(PRINT, new PlaceArtifactOnStream(System.out));\r
126                                 placeArtifact.put(SCRIPT, new PlaceArtifactScripts());\r
127                                 \r
128                                 Trans trans = env.newTrans();\r
129                                 try {\r
130                                         // show Std out again\r
131                                         aafsso.setLogDefault();\r
132                                         aafsso.setStdErrDefault();\r
133                                         \r
134                                         // if CM_URL can be obtained, add to sso.props, if written\r
135                                         String cm_url = getProperty(access,env,false, Config.CM_URL,Config.CM_URL+": ");\r
136                                         if(cm_url!=null) {\r
137                                                 aafsso.addProp(Config.CM_URL, cm_url);\r
138                                         }\r
139                                         aafsso.writeFiles();\r
140 \r
141                                         AAFCon<?> aafcon = new AAFConHttp(access,Config.CM_URL);\r
142 \r
143                                         String cmd = cmds.removeFirst();\r
144                                         if("place".equals(cmd)) {\r
145                                                 placeCerts(trans,aafcon,cmds);\r
146                                         } else if("create".equals(cmd)) {\r
147                                                 createArtifact(trans, aafcon,cmds);\r
148                                         } else if("read".equals(cmd)) {\r
149                                                 readArtifact(trans, aafcon, cmds);\r
150                                         } else if("copy".equals(cmd)) {\r
151                                                 copyArtifact(trans, aafcon, cmds);\r
152                                         } else if("update".equals(cmd)) {\r
153                                                 updateArtifact(trans, aafcon, cmds);\r
154                                         } else if("delete".equals(cmd)) {\r
155                                                 deleteArtifact(trans, aafcon, cmds);\r
156                                         } else if("showpass".equals(cmd)) {\r
157                                                 showPass(trans,aafcon,cmds);\r
158                                         } else if("check".equals(cmd)) {\r
159                                                 try {\r
160                                                         exitCode = check(trans,aafcon,cmds);\r
161                                                 } catch (Exception e) {\r
162                                                         exitCode = 1;\r
163                                                         throw e;\r
164                                                 }\r
165                                         } else {\r
166                                                 AAFSSO.cons.printf("Unknown command \"%s\"\n", cmd);\r
167                                         }\r
168                                 } finally {\r
169                                         StringBuilder sb = new StringBuilder();\r
170                         trans.auditTrail(4, sb, Trans.REMOTE);\r
171                         if(sb.length()>0) {\r
172                                 trans.info().log("Trans Info\n",sb);\r
173                         }\r
174                                 }\r
175                                 aafsso.close();\r
176                         }\r
177                 } catch (Exception e) {\r
178                         e.printStackTrace();\r
179                 }\r
180                 if(exitCode!=0) {\r
181                         System.exit(exitCode);\r
182                 }\r
183         }\r
184 \r
185         private static String getProperty(PropAccess pa, Env env, boolean secure, String tag, String prompt, Object ... def) {\r
186                 String value;\r
187                 if((value=pa.getProperty(tag))==null) {\r
188                         if(secure) {\r
189                                 value = new String(AAFSSO.cons.readPassword(prompt, def));\r
190                         } else {\r
191                                 value = AAFSSO.cons.readLine(prompt,def).trim();\r
192                         }\r
193                         if(value!=null) {\r
194                                 if(value.length()>0) {\r
195                                         pa.setProperty(tag,value);\r
196                                         env.setProperty(tag,value);\r
197                                 } else if(def.length==1) {\r
198                                         value=def[0].toString();\r
199                                         pa.setProperty(tag,value);\r
200                                         env.setProperty(tag,value);\r
201                                 }\r
202                         }\r
203                 }\r
204                 return value;\r
205         }\r
206 \r
207         private static String mechID(Deque<String> cmds) {\r
208                 if(cmds.size()<1) {\r
209                         String alias = env.getProperty(Config.CADI_ALIAS);\r
210                         return alias!=null?alias:AAFSSO.cons.readLine("MechID: ");\r
211                 }\r
212                 return cmds.removeFirst();      \r
213         }\r
214 \r
215         private static String machine(Deque<String> cmds) throws UnknownHostException {\r
216                 if(cmds.size()>0) {\r
217                         return cmds.removeFirst();\r
218                 } else {\r
219                         String mach = env.getProperty(Config.HOSTNAME);\r
220                         return mach!=null?mach:InetAddress.getLocalHost().getHostName();\r
221                 }\r
222         }\r
223 \r
224         private static String[] machines(Deque<String> cmds)  {\r
225                 String machines;\r
226                 if(cmds.size()>0) {\r
227                         machines = cmds.removeFirst();\r
228                 } else {\r
229                         machines = AAFSSO.cons.readLine("Machines (sep by ','): ");\r
230                 }\r
231                 return Split.split(',', machines);\r
232         }\r
233 \r
234         private static void createArtifact(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
235                 String mechID = mechID(cmds);\r
236                 String machine = machine(cmds);\r
237 \r
238                 Artifacts artifacts = new Artifacts();\r
239                 Artifact arti = new Artifact();\r
240                 artifacts.getArtifact().add(arti);\r
241                 arti.setMechid(mechID!=null?mechID:AAFSSO.cons.readLine("MechID: "));\r
242                 arti.setMachine(machine!=null?machine:AAFSSO.cons.readLine("Machine (%s): ",InetAddress.getLocalHost().getHostName()));\r
243                 arti.setCa(AAFSSO.cons.readLine("CA: (%s): ","aaf"));\r
244                 \r
245                 String resp = AAFSSO.cons.readLine("Types [file,jks,script] (%s): ", "jks");\r
246                 for(String s : Split.splitTrim(',', resp)) {\r
247                         arti.getType().add(s);\r
248                 }\r
249                 // Always do Script\r
250                 if(!resp.contains(SCRIPT)) {\r
251                         arti.getType().add(SCRIPT);\r
252                 }\r
253 \r
254                 // Note: Sponsor is set on Creation by CM\r
255                 String configRootName = AAFCon.reverseDomain(arti.getMechid());\r
256                 arti.setAppName(AAFSSO.cons.readLine("Namespace (%s): ",configRootName));\r
257                 arti.setDir(AAFSSO.cons.readLine("Directory (%s): ", System.getProperty("user.dir")));\r
258                 arti.setOsUser(AAFSSO.cons.readLine("OS User (%s): ", System.getProperty("user.name")));\r
259                 arti.setRenewDays(Integer.parseInt(AAFSSO.cons.readLine("Renewal Days (%s):", "30")));\r
260                 arti.setNotification(toNotification(AAFSSO.cons.readLine("Notification (mailto owner):", "")));\r
261                 \r
262                 TimeTaken tt = trans.start("Create Artifact", Env.REMOTE);\r
263                 try {\r
264                         Future<Artifacts> future = aafcon.client(CM_VER).create("/cert/artifacts", artifactsDF, artifacts);\r
265                         if(future.get(TIMEOUT)) {\r
266                                 trans.info().printf("Call to AAF Certman successful %s, %s",arti.getMechid(), arti.getMachine());\r
267                         } else {\r
268                                 trans.error().printf("Call to AAF Certman failed, %s",\r
269                                         errMsg.toMsg(future));\r
270                         }\r
271                 } finally {\r
272                         tt.done();\r
273                 }\r
274         }\r
275 \r
276         private static String toNotification(String notification) {\r
277                 if(notification==null) {\r
278                         notification="";\r
279                 } else if(notification.length()>0) {\r
280                         if(notification.indexOf(':')<0) {\r
281                                 notification = "mailto:" + notification;\r
282                         }\r
283                 }\r
284                 return notification;\r
285         }\r
286         \r
287 \r
288         private static void readArtifact(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
289                 String mechID = mechID(cmds);\r
290                 String machine = machine(cmds);\r
291 \r
292                 TimeTaken tt = trans.start("Read Artifact", Env.SUB);\r
293                 try {\r
294                         Future<Artifacts> future = aafcon.client(CM_VER)\r
295                                         .read("/cert/artifacts/"+mechID+'/'+machine, artifactsDF);\r
296         \r
297                         if(future.get(TIMEOUT)) {\r
298                                 boolean printed = false;\r
299                                 for(Artifact a : future.value.getArtifact()) {\r
300                                         AAFSSO.cons.printf("MechID:          %s\n",a.getMechid()); \r
301                                         AAFSSO.cons.printf("  Sponsor:       %s\n",a.getSponsor()); \r
302                                         AAFSSO.cons.printf("Machine:         %s\n",a.getMachine()); \r
303                                         AAFSSO.cons.printf("CA:              %s\n",a.getCa()); \r
304                                         StringBuilder sb = new StringBuilder();\r
305                                         boolean first = true;\r
306                                         for(String t : a.getType()) {\r
307                                                 if(first) {first=false;}\r
308                                                 else{sb.append(',');}\r
309                                                 sb.append(t);\r
310                                         }\r
311                                         AAFSSO.cons.printf("Types:           %s\n",sb);\r
312                                         AAFSSO.cons.printf("Namespace:       %s\n",a.getAppName()); \r
313                                         AAFSSO.cons.printf("Directory:       %s\n",a.getDir());\r
314                                         AAFSSO.cons.printf("O/S User:        %s\n",a.getOsUser());\r
315                                         AAFSSO.cons.printf("Renew Days:      %d\n",a.getRenewDays());\r
316                                         AAFSSO.cons.printf("Notification     %s\n",a.getNotification());\r
317                                         printed = true;\r
318                                 }\r
319                                 if(!printed) {\r
320                                         AAFSSO.cons.printf("Artifact for %s %s does not exist", mechID, machine);\r
321                                 }\r
322                         } else {\r
323                                 trans.error().log(errMsg.toMsg(future));\r
324                         }\r
325                 } finally {\r
326                         tt.done();\r
327                 }\r
328         }\r
329         \r
330         private static void copyArtifact(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
331                 String mechID = mechID(cmds);\r
332                 String machine = machine(cmds);\r
333                 String[] newmachs = machines(cmds);\r
334                 if(newmachs==null || newmachs == null) {\r
335                         trans.error().log("No machines listed to copy to");\r
336                 } else {\r
337                         TimeTaken tt = trans.start("Copy Artifact", Env.REMOTE);\r
338                         try {\r
339                                 Future<Artifacts> future = aafcon.client(CM_VER)\r
340                                                 .read("/cert/artifacts/"+mechID+'/'+machine, artifactsDF);\r
341                         \r
342                                 if(future.get(TIMEOUT)) {\r
343                                         boolean printed = false;\r
344                                         for(Artifact a : future.value.getArtifact()) {\r
345                                                 for(String m : newmachs) {\r
346                                                         a.setMachine(m);\r
347                                                         Future<Artifacts> fup = aafcon.client(CM_VER).update("/cert/artifacts", artifactsDF, future.value);\r
348                                                         if(fup.get(TIMEOUT)) {\r
349                                                                 trans.info().printf("Copy of %s %s successful to %s",mechID,machine,m);\r
350                                                         } else {\r
351                                                                 trans.error().printf("Call to AAF Certman failed, %s",\r
352                                                                         errMsg.toMsg(fup));\r
353                                                         }\r
354         \r
355                                                         printed = true;\r
356                                                 }\r
357                                         }\r
358                                         if(!printed) {\r
359                                                 AAFSSO.cons.printf("Artifact for %s %s does not exist", mechID, machine);\r
360                                         }\r
361                                 } else {\r
362                                         trans.error().log(errMsg.toMsg(future));\r
363                                 }\r
364                         } finally {\r
365                                 tt.done();\r
366                         }\r
367                 }\r
368         }\r
369 \r
370         private static void updateArtifact(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
371                 String mechID = mechID(cmds);\r
372                 String machine = machine(cmds);\r
373 \r
374                 TimeTaken tt = trans.start("Update Artifact", Env.REMOTE);\r
375                 try {\r
376                         Future<Artifacts> fread = aafcon.client(CM_VER)\r
377                                         .read("/cert/artifacts/"+mechID+'/'+machine, artifactsDF);\r
378         \r
379                         if(fread.get(TIMEOUT)) {\r
380                                 Artifacts artifacts = new Artifacts();\r
381                                 for(Artifact a : fread.value.getArtifact()) {\r
382                                         Artifact arti = new Artifact();\r
383                                         artifacts.getArtifact().add(arti);\r
384                                         \r
385                                         AAFSSO.cons.printf("For %s on %s\n", a.getMechid(),a.getMachine());\r
386                                         arti.setMechid(a.getMechid());\r
387                                         arti.setMachine(a.getMachine());\r
388                                         arti.setCa(AAFSSO.cons.readLine("CA: (%s): ",a.getCa()));\r
389                                         StringBuilder sb = new StringBuilder();\r
390                                         boolean first = true;\r
391                                         for(String t : a.getType()) {\r
392                                                 if(first) {first=false;}\r
393                                                 else{sb.append(',');}\r
394                                                 sb.append(t);\r
395                                         }\r
396         \r
397                                         String resp = AAFSSO.cons.readLine("Types [file,jks,pkcs12] (%s): ", sb);\r
398                                         for(String s : Split.splitTrim(',', resp)) {\r
399                                                 arti.getType().add(s);\r
400                                         }\r
401                                         // Always do Script\r
402                                         if(!resp.contains(SCRIPT)) {\r
403                                                 arti.getType().add(SCRIPT);\r
404                                         }\r
405 \r
406                                         // Note: Sponsor is set on Creation by CM\r
407                                         arti.setAppName(AAFSSO.cons.readLine("Namespace (%s): ",a.getAppName()));\r
408                                         arti.setDir(AAFSSO.cons.readLine("Directory (%s): ", a.getDir()));\r
409                                         arti.setOsUser(AAFSSO.cons.readLine("OS User (%s): ", a.getOsUser()));\r
410                                         arti.setRenewDays(Integer.parseInt(AAFSSO.cons.readLine("Renew Days (%s):", a.getRenewDays())));\r
411                                         arti.setNotification(toNotification(AAFSSO.cons.readLine("Notification (%s):", a.getNotification())));\r
412         \r
413                                 }\r
414                                 if(artifacts.getArtifact().size()==0) {\r
415                                         AAFSSO.cons.printf("Artifact for %s %s does not exist", mechID, machine);\r
416                                 } else {\r
417                                         Future<Artifacts> fup = aafcon.client(CM_VER).update("/cert/artifacts", artifactsDF, artifacts);\r
418                                         if(fup.get(TIMEOUT)) {\r
419                                                 trans.info().printf("Call to AAF Certman successful %s, %s",mechID,machine);\r
420                                         } else {\r
421                                                 trans.error().printf("Call to AAF Certman failed, %s",\r
422                                                         errMsg.toMsg(fup));\r
423                                         }\r
424                                 }\r
425                         } else {\r
426                                 trans.error().printf("Call to AAF Certman failed, %s %s, %s",\r
427                                                 errMsg.toMsg(fread),mechID,machine);\r
428                         }\r
429                 } finally {\r
430                         tt.done();\r
431                 }\r
432         }\r
433         \r
434         private static void deleteArtifact(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
435                 String mechid = mechID(cmds);\r
436                 String machine = machine(cmds);\r
437                 \r
438                 TimeTaken tt = trans.start("Delete Artifact", Env.REMOTE);\r
439                 try {\r
440                         Future<Void> future = aafcon.client(CM_VER)\r
441                                         .delete("/cert/artifacts/"+mechid+"/"+machine,"application/json" );\r
442         \r
443                         if(future.get(TIMEOUT)) {\r
444                                 trans.info().printf("Call to AAF Certman successful %s, %s",mechid,machine);\r
445                         } else {\r
446                                 trans.error().printf("Call to AAF Certman failed, %s %s, %s",\r
447                                         errMsg.toMsg(future),mechid,machine);\r
448                         }\r
449                 } finally {\r
450                         tt.done();\r
451                 }\r
452         }\r
453 \r
454         \r
455 \r
456         private static boolean placeCerts(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
457                 boolean rv = false;\r
458                 String mechID = mechID(cmds);\r
459                 String machine = machine(cmds);\r
460                 \r
461                 TimeTaken tt = trans.start("Place Artifact", Env.REMOTE);\r
462                 try {\r
463                         Future<Artifacts> acf = aafcon.client(CM_VER)\r
464                                         .read("/cert/artifacts/"+mechID+'/'+machine, artifactsDF);\r
465                         if(acf.get(TIMEOUT)) {\r
466                                 // Have to wait for JDK 1.7 source...\r
467                                 //switch(artifact.getType()) {\r
468                                 if(acf.value.getArtifact()==null || acf.value.getArtifact().isEmpty()) {\r
469                                         AAFSSO.cons.printf("===> There are no artifacts for %s %s", mechID, machine);\r
470                                 } else {\r
471                                         for(Artifact a : acf.value.getArtifact()) {\r
472                                                 String osID = System.getProperty("user.name");\r
473                                                 if(a.getOsUser().equals(osID)) {\r
474                                                         CertificateRequest cr = new CertificateRequest();\r
475                                                         cr.setMechid(a.getMechid());\r
476                                                         cr.setSponsor(a.getSponsor());\r
477                                                         cr.getFqdns().add(a.getMachine());\r
478                                                         Future<String> f = aafcon.client(CM_VER)\r
479                                                                         .setQueryParams("withTrust")\r
480                                                                         .updateRespondString("/cert/" + a.getCa(),reqDF, cr);\r
481                                                         if(f.get(TIMEOUT)) {\r
482                                                                 CertInfo capi = certDF.newData().in(TYPE.JSON).load(f.body()).asObject();\r
483                                                                 for(String type : a.getType()) {\r
484                                                                         PlaceArtifact pa = placeArtifact.get(type);\r
485                                                                         if(pa!=null) {\r
486                                                                                 if(rv = pa.place(trans, capi, a)) {\r
487                                                                                         notifyPlaced(a,rv);\r
488                                                                                 }\r
489                                                                         }\r
490                                                                 }\r
491                                                                 // Cover for the above multiple pass possibilities with some static Data, then clear per Artifact\r
492                                                         } else {\r
493                                                                 trans.error().log(errMsg.toMsg(f));\r
494                                                         }\r
495                                                 } else {\r
496                                                         trans.error().log("You must be OS User \"" + a.getOsUser() +"\" to place Certificates on this box");\r
497                                                 }\r
498                                         }\r
499                                 }\r
500                         } else {\r
501                                 trans.error().log(errMsg.toMsg(acf));\r
502                         }\r
503                 } finally {\r
504                         tt.done();\r
505                 }\r
506                 return rv;\r
507         }\r
508         \r
509         private static void notifyPlaced(Artifact a, boolean rv) {\r
510                 \r
511                 \r
512         }\r
513 \r
514         private static void showPass(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
515                 String mechID = mechID(cmds);\r
516                 String machine = machine(cmds);\r
517 \r
518                 TimeTaken tt = trans.start("Show Password", Env.REMOTE);\r
519                 try {\r
520                         Future<Artifacts> acf = aafcon.client(CM_VER)\r
521                                         .read("/cert/artifacts/"+mechID+'/'+machine, artifactsDF);\r
522                         if(acf.get(TIMEOUT)) {\r
523                                 // Have to wait for JDK 1.7 source...\r
524                                 //switch(artifact.getType()) {\r
525                                 if(acf.value.getArtifact()==null || acf.value.getArtifact().isEmpty()) {\r
526                                         AAFSSO.cons.printf("No Artifacts found for %s on %s", mechID, machine);\r
527                                 } else {\r
528                                         String id = aafcon.defID();\r
529                                         boolean allowed;\r
530                                         for(Artifact a : acf.value.getArtifact()) {\r
531                                                 allowed = id!=null && (id.equals(a.getSponsor()) ||\r
532                                                                 (id.equals(a.getMechid()) \r
533                                                                                 && aafcon.securityInfo().defSS.getClass().isAssignableFrom(HBasicAuthSS.class)));\r
534                                                 if(!allowed) {\r
535                                                         Future<String> pf = aafcon.client(CM_VER).read("/cert/may/" + \r
536                                                                         a.getAppName() + ".certman|"+a.getCa()+"|showpass","*/*");\r
537                                                         if(pf.get(TIMEOUT)) {\r
538                                                                 allowed = true;\r
539                                                         } else {\r
540                                                                 trans.error().log(errMsg.toMsg(pf));\r
541                                                         }\r
542                                                 }\r
543                                                 if(allowed) {\r
544                                                         File dir = new File(a.getDir());\r
545                                                         Properties props = new Properties();\r
546                                                         FileInputStream fis = new FileInputStream(new File(dir,a.getAppName()+".props"));\r
547                                                         try {\r
548                                                                 props.load(fis);\r
549                                                                 fis.close();\r
550                                                                 fis = new FileInputStream(new File(dir,a.getAppName()+".chal"));\r
551                                                                 props.load(fis);\r
552                                                         } finally {\r
553                                                                 fis.close();\r
554                                                         }\r
555                                                         \r
556                                                         File f = new File(dir,a.getAppName()+".keyfile");\r
557                                                         if(f.exists()) {\r
558                                                                 Symm symm = Symm.obtain(f);\r
559                                                                 \r
560                                                                 for(Iterator<Entry<Object,Object>> iter = props.entrySet().iterator(); iter.hasNext();) {\r
561                                                                         Entry<Object,Object> en = iter.next();\r
562                                                                         if(en.getValue().toString().startsWith("enc:???")) {\r
563                                                                                 System.out.printf("%s=%s\n", en.getKey(), symm.depass(en.getValue().toString()));\r
564                                                                         }\r
565                                                                 }\r
566                                                         } else {\r
567                                                                 trans.error().printf("%s.keyfile must exist to read passwords for %s on %s",\r
568                                                                                 f.getAbsolutePath(),a.getMechid(), a.getMachine());\r
569                                                         }\r
570                                                 }\r
571                                         }\r
572                                 }\r
573                         } else {\r
574                                 trans.error().log(errMsg.toMsg(acf));\r
575                         }\r
576                 } finally {\r
577                         tt.done();\r
578                 }\r
579 \r
580         }\r
581         \r
582 \r
583         /**\r
584          * Check returns Error Codes, so that Scripts can know what to do\r
585          * \r
586          *   0 - Check Complete, nothing to do\r
587          *   1 - General Error\r
588          *   2 - Error for specific Artifact - read check.msg\r
589          *   10 - Certificate Updated - check.msg is email content\r
590          *   \r
591          * @param trans\r
592          * @param aafcon\r
593          * @param cmds\r
594          * @return\r
595          * @throws Exception\r
596          */\r
597         private static int check(Trans trans, AAFCon<?> aafcon, Deque<String> cmds) throws Exception {\r
598                 int exitCode=1;\r
599                 String mechID = mechID(cmds);\r
600                 String machine = machine(cmds);\r
601                 \r
602                 TimeTaken tt = trans.start("Check Certificate", Env.REMOTE);\r
603                 try {\r
604                 \r
605                         Future<Artifacts> acf = aafcon.client(CM_VER)\r
606                                         .read("/cert/artifacts/"+mechID+'/'+machine, artifactsDF);\r
607                         if(acf.get(TIMEOUT)) {\r
608                                 // Have to wait for JDK 1.7 source...\r
609                                 //switch(artifact.getType()) {\r
610                                 if(acf.value.getArtifact()==null || acf.value.getArtifact().isEmpty()) {\r
611                                         AAFSSO.cons.printf("No Artifacts found for %s on %s", mechID, machine);\r
612                                 } else {\r
613                                         String id = aafcon.defID();\r
614                                         GregorianCalendar now = new GregorianCalendar();\r
615                                         for(Artifact a : acf.value.getArtifact()) {\r
616                                                 if(id.equals(a.getMechid())) {\r
617                                                         File dir = new File(a.getDir());\r
618                                                         Properties props = new Properties();\r
619                                                         FileInputStream fis = new FileInputStream(new File(dir,a.getAppName()+".props"));\r
620                                                         try {\r
621                                                                 props.load(fis);\r
622                                                         } finally {\r
623                                                                 fis.close();\r
624                                                         }\r
625                                                         \r
626                                                         String prop;                                            \r
627                                                         File f;\r
628         \r
629                                                         if((prop=props.getProperty(Config.CADI_KEYFILE))==null ||\r
630                                                                 !(f=new File(prop)).exists()) {\r
631                                                                         trans.error().printf("Keyfile must exist to check Certificates for %s on %s",\r
632                                                                                 a.getMechid(), a.getMachine());\r
633                                                         } else {\r
634                                                                 String ksf = props.getProperty(Config.CADI_KEYSTORE);\r
635                                                                 String ksps = props.getProperty(Config.CADI_KEYSTORE_PASSWORD);\r
636                                                                 if(ksf==null || ksps == null) {\r
637                                                                         trans.error().printf("Properties %s and %s must exist to check Certificates for %s on %s",\r
638                                                                                         Config.CADI_KEYSTORE, Config.CADI_KEYSTORE_PASSWORD,a.getMechid(), a.getMachine());\r
639                                                                 } else {\r
640                                                                         KeyStore ks = KeyStore.getInstance("JKS");\r
641                                                                         Symm symm = Symm.obtain(f);\r
642                                                                         \r
643                                                                         fis = new FileInputStream(ksf);\r
644                                                                         try {\r
645                                                                                 ks.load(fis,symm.depass(ksps).toCharArray());\r
646                                                                         } finally {\r
647                                                                                 fis.close();\r
648                                                                         }\r
649                                                                         X509Certificate cert = (X509Certificate)ks.getCertificate(mechID);\r
650                                                                         String msg = null;\r
651 \r
652                                                                         if(cert==null) {\r
653                                                                                 msg = String.format("X509Certificate does not exist for %s on %s in %s",\r
654                                                                                                 a.getMechid(), a.getMachine(), ksf);\r
655                                                                                 trans.error().log(msg);\r
656                                                                                 exitCode = 2;\r
657                                                                         } else {\r
658                                                                                 GregorianCalendar renew = new GregorianCalendar();\r
659                                                                                 renew.setTime(cert.getNotAfter());\r
660                                                                                 renew.add(GregorianCalendar.DAY_OF_MONTH,-1*a.getRenewDays());\r
661                                                                                 if(renew.after(now)) {\r
662                                                                                         msg = String.format("X509Certificate for %s on %s has been checked on %s. It expires on %s; it will not be renewed until %s.\n", \r
663                                                                                                         a.getMechid(), a.getMachine(),Chrono.dateOnlyStamp(now),cert.getNotAfter(),Chrono.dateOnlyStamp(renew));\r
664                                                                                         trans.info().log(msg);\r
665                                                                                         exitCode = 0; // OK\r
666                                                                                 } else {\r
667                                                                                         trans.info().printf("X509Certificate for %s on %s expiration, %s, needs Renewal.\n", \r
668                                                                                                         a.getMechid(), a.getMachine(),cert.getNotAfter());\r
669                                                                                         cmds.offerLast(mechID);\r
670                                                                                         cmds.offerLast(machine);\r
671                                                                                         if(placeCerts(trans,aafcon,cmds)) {\r
672                                                                                                 msg = String.format("X509Certificate for %s on %s has been renewed. Ensure services using are refreshed.\n", \r
673                                                                                                                 a.getMechid(), a.getMachine());\r
674                                                                                                 exitCode = 10; // Refreshed\r
675                                                                                         } else {\r
676                                                                                                 msg = String.format("X509Certificate for %s on %s attempted renewal, but failed. Immediate Investigation is required!\n", \r
677                                                                                                                 a.getMechid(), a.getMachine());\r
678                                                                                                 exitCode = 1; // Error Renewing\r
679                                                                                         }\r
680                                                                                 }\r
681                                                                         }\r
682                                                                         if(msg!=null) {\r
683                                                                                 FileOutputStream fos = new FileOutputStream(a.getDir()+'/'+a.getAppName()+".msg");\r
684                                                                                 try {\r
685                                                                                         fos.write(msg.getBytes());\r
686                                                                                 } finally {\r
687                                                                                         fos.close();\r
688                                                                                 }\r
689                                                                         }\r
690                                                                 }\r
691                                                                 \r
692                                                         }\r
693                                                 }\r
694                                         }\r
695                                 }\r
696                         } else {\r
697                                 trans.error().log(errMsg.toMsg(acf));\r
698                                 exitCode=1;\r
699                         }\r
700                 } finally {\r
701                         tt.done();\r
702                 }\r
703                 return exitCode;\r
704         }\r
705 \r
706 }\r
707                         \r
708                 \r
709 \r
710 \r