52621e5429ecc934b1e3b82eaed47470d1bf7eb6
[aaf/authz.git] / authz-certman / src / main / java / com / att / authz / cm / cert / BCFactory.java
1 /*******************************************************************************\r
2  * ============LICENSE_START====================================================\r
3  * * org.onap.aai\r
4  * * ===========================================================================\r
5  * * Copyright © 2017 AT&T Intellectual Property. All rights reserved.\r
6  * * Copyright © 2017 Amdocs\r
7  * * ===========================================================================\r
8  * * Licensed under the Apache License, Version 2.0 (the "License");\r
9  * * you may not use this file except in compliance with the License.\r
10  * * You may obtain a copy of the License at\r
11  * * \r
12  *  *      http://www.apache.org/licenses/LICENSE-2.0\r
13  * * \r
14  *  * Unless required by applicable law or agreed to in writing, software\r
15  * * distributed under the License is distributed on an "AS IS" BASIS,\r
16  * * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
17  * * See the License for the specific language governing permissions and\r
18  * * limitations under the License.\r
19  * * ============LICENSE_END====================================================\r
20  * *\r
21  * * ECOMP is a trademark and service mark of AT&T Intellectual Property.\r
22  * *\r
23  ******************************************************************************/\r
24 package com.att.authz.cm.cert;\r
25 \r
26 import java.io.File;\r
27 import java.io.FileReader;\r
28 import java.io.IOException;\r
29 import java.lang.reflect.Field;\r
30 import java.security.InvalidKeyException;\r
31 import java.security.NoSuchAlgorithmException;\r
32 import java.security.PrivateKey;\r
33 import java.security.SignatureException;\r
34 import java.util.List;\r
35 \r
36 import org.bouncycastle.asn1.ASN1Object;\r
37 import org.bouncycastle.operator.ContentSigner;\r
38 import org.bouncycastle.operator.OperatorCreationException;\r
39 import org.bouncycastle.operator.jcajce.JcaContentSignerBuilder;\r
40 import org.bouncycastle.pkcs.PKCS10CertificationRequest;\r
41 \r
42 import com.att.authz.cm.ca.CA;\r
43 import com.att.authz.cm.validation.Validator;\r
44 import com.att.cadi.Symm;\r
45 import com.att.cadi.cm.CertException;\r
46 import com.att.cadi.cm.Factory;\r
47 import com.att.inno.env.Env;\r
48 import com.att.inno.env.TimeTaken;\r
49 import com.att.inno.env.Trans;\r
50 \r
51 \r
52 /**\r
53  * Additional Factory mechanisms for CSRs, and BouncyCastle.  The main Factory\r
54  * utilizes only Java abstractions, and is useful in Client code.\r
55  * \r
56 \r
57  *\r
58  */\r
59 public class BCFactory extends Factory {\r
60         private static final JcaContentSignerBuilder jcsb;\r
61 \r
62 \r
63         static {\r
64                 // Bouncy\r
65                 jcsb = new JcaContentSignerBuilder(Factory.SIG_ALGO);\r
66         }\r
67         \r
68         public static ContentSigner contentSigner(PrivateKey pk) throws OperatorCreationException {\r
69                 return jcsb.build(pk);\r
70         }\r
71         \r
72         public static String toString(Trans trans, PKCS10CertificationRequest csr) throws IOException, CertException {\r
73                 TimeTaken tt = trans.start("CSR to String", Env.SUB);\r
74                 try {\r
75                         if(csr==null) {\r
76                                 throw new CertException("x509 Certificate Request not built");\r
77                         }\r
78                         return textBuilder("CERTIFICATE REQUEST",csr.getEncoded());\r
79                 }finally {\r
80                         tt.done();\r
81                 }\r
82         }\r
83 \r
84         public static PKCS10CertificationRequest toCSR(Trans trans, File file) throws IOException {\r
85                 TimeTaken tt = trans.start("Reconstitute CSR", Env.SUB);\r
86                 try {\r
87                         FileReader fr = new FileReader(file);\r
88                         return new PKCS10CertificationRequest(decode(strip(fr)));\r
89                 } finally {\r
90                         tt.done();\r
91                 }\r
92         }\r
93 \r
94         public static byte[] sign(Trans trans, ASN1Object toSign, PrivateKey pk) throws IOException, InvalidKeyException, SignatureException, NoSuchAlgorithmException {\r
95                 TimeTaken tt = trans.start("Encode Security Object", Env.SUB);\r
96                 try {\r
97                         return sign(trans,toSign.getEncoded(),pk);\r
98                 } finally {\r
99                         tt.done();\r
100                 }\r
101         }\r
102 \r
103         public static CSRMeta createCSRMeta(CA ca,final String args[]) throws IllegalArgumentException, IllegalAccessException, CertException {\r
104                 CSRMeta csr = new CSRMeta();\r
105                 ca.stdFields().set(csr);\r
106                 //TODO should we checkDigest?\r
107 //              digest = ca.messageDigest();\r
108 \r
109                 Field[] fld = CSRMeta.class.getDeclaredFields();\r
110                 for(int i=0;i+1<args.length;++i) {\r
111                         if(args[i].charAt(0)=='-') {\r
112                                 for(int j=0;j<fld.length;++j) {\r
113                                         if(fld[j].getType().equals(String.class) && args[i].substring(1).equals(fld[j].getName())) {\r
114                                                 fld[j].set(csr,args[++i]);\r
115                                                 break;\r
116                                         }\r
117                                 }\r
118                         }\r
119                 }\r
120                 String errs = validate(csr);\r
121                 if(errs!=null) {\r
122                         throw new CertException(errs);\r
123                 }\r
124                 return csr;\r
125         }\r
126         \r
127         \r
128         public static CSRMeta createCSRMeta(CA ca, String mechid, String sponsorEmail, List<String> fqdns) throws CertException {\r
129                 CSRMeta csr = new CSRMeta();\r
130                 boolean first = true;\r
131                 // Set CN (and SAN)\r
132                 for(String fqdn : fqdns) {\r
133                         if(first) {\r
134                                 first = false;\r
135                                 csr.cn(fqdn);\r
136                         } else {\r
137                                 csr.san(fqdn);\r
138                         }\r
139                 }\r
140                 \r
141                 csr.challenge(new String(Symm.randomGen(24)));\r
142                 ca.stdFields().set(csr);\r
143                 csr.mechID(mechid);\r
144                 csr.email(sponsorEmail);\r
145                 String errs = validate(csr);\r
146                 if(errs!=null) {\r
147                         throw new CertException(errs);\r
148                 }\r
149                 return csr;\r
150         }\r
151 \r
152         private static String validate(CSRMeta csr) {\r
153                 Validator v = new Validator();\r
154                 if(v.nullOrBlank("cn", csr.cn())\r
155                         .nullOrBlank("mechID", csr.mechID())\r
156                         .nullOrBlank("email", csr.email())\r
157                         .nullOrBlank("o",csr.o())\r
158                         .nullOrBlank("l",csr.l())\r
159                         .nullOrBlank("st",csr.st())\r
160                         .nullOrBlank("c",csr.c())\r
161                         .err()) {\r
162                         return v.errs();\r
163                 } else {\r
164                         return null;\r
165                 }\r
166         }\r
167         \r
168 \r
169 }\r