1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.wss4j.dom.message;
21
22 import org.apache.wss4j.common.util.SOAPUtil;
23 import org.apache.wss4j.dom.WSConstants;
24 import org.apache.wss4j.dom.common.CustomHandler;
25
26 import org.apache.wss4j.dom.engine.WSSConfig;
27 import org.apache.wss4j.dom.engine.WSSecurityEngine;
28 import org.apache.wss4j.dom.engine.WSSecurityEngineResult;
29 import org.apache.wss4j.common.crypto.Crypto;
30 import org.apache.wss4j.common.crypto.CryptoFactory;
31 import org.apache.wss4j.common.crypto.Merlin;
32 import org.apache.wss4j.common.ext.WSSecurityException;
33 import org.apache.wss4j.common.util.XMLUtils;
34 import org.apache.wss4j.dom.handler.HandlerAction;
35 import org.apache.wss4j.dom.handler.RequestData;
36 import org.apache.wss4j.dom.handler.WSHandlerConstants;
37 import org.apache.wss4j.dom.handler.WSHandlerResult;
38
39 import org.junit.jupiter.api.Test;
40 import org.w3c.dom.Document;
41
42 import java.security.cert.X509Certificate;
43 import java.util.Collections;
44 import java.util.Properties;
45
46 import static org.junit.jupiter.api.Assertions.assertNotNull;
47 import static org.junit.jupiter.api.Assertions.assertTrue;
48 import static org.junit.jupiter.api.Assertions.fail;
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78 public class SignatureCertTest {
79 private static final org.slf4j.Logger LOG =
80 org.slf4j.LoggerFactory.getLogger(SignatureCertTest.class);
81 private WSSecurityEngine secEngine = new WSSecurityEngine();
82 private Crypto crypto;
83 private Crypto cryptoCA;
84
85 public SignatureCertTest() throws Exception {
86 WSSConfig.init();
87 crypto = CryptoFactory.getInstance("wss40.properties");
88 cryptoCA = CryptoFactory.getInstance("wss40CA.properties");
89 }
90
91
92
93
94 @Test
95 public void testSignatureDirectReference() throws Exception {
96 Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
97 WSSecHeader secHeader = new WSSecHeader(doc);
98 secHeader.insertSecurityHeader();
99
100 WSSecSignature sign = new WSSecSignature(secHeader);
101 sign.setUserInfo("wss40", "security");
102 sign.setKeyIdentifierType(WSConstants.BST_DIRECT_REFERENCE);
103
104 Document signedDoc = sign.build(crypto);
105
106 if (LOG.isDebugEnabled()) {
107 String outputString =
108 XMLUtils.prettyDocumentToString(signedDoc);
109 LOG.debug(outputString);
110 }
111
112
113
114 WSHandlerResult results = verify(signedDoc, cryptoCA);
115 WSSecurityEngineResult result =
116 results.getActionResults().get(WSConstants.SIGN).get(0);
117 X509Certificate cert =
118 (X509Certificate)result.get(WSSecurityEngineResult.TAG_X509_CERTIFICATE);
119 assertNotNull(cert);
120 }
121
122
123
124
125
126 @Test
127 public void testSignatureDirectReferenceCACert() throws Exception {
128 Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
129 WSSecHeader secHeader = new WSSecHeader(doc);
130 secHeader.insertSecurityHeader();
131
132 WSSecSignature sign = new WSSecSignature(secHeader);
133 sign.setUserInfo("wss40", "security");
134 sign.setKeyIdentifierType(WSConstants.BST_DIRECT_REFERENCE);
135 sign.setUseSingleCertificate(false);
136
137 Document signedDoc = sign.build(crypto);
138
139 if (LOG.isDebugEnabled()) {
140 String outputString =
141 XMLUtils.prettyDocumentToString(signedDoc);
142 LOG.debug("BST CA Cert");
143 LOG.debug(outputString);
144 }
145
146
147
148 WSHandlerResult results = verify(signedDoc, cryptoCA);
149 WSSecurityEngineResult result =
150 results.getActionResults().get(WSConstants.SIGN).get(0);
151 X509Certificate cert =
152 (X509Certificate)result.get(WSSecurityEngineResult.TAG_X509_CERTIFICATE);
153 assertNotNull(cert);
154 X509Certificate[] certs =
155 (X509Certificate[])result.get(WSSecurityEngineResult.TAG_X509_CERTIFICATES);
156 assertTrue(certs != null && certs.length == 2);
157 }
158
159
160
161
162
163
164
165 @Test
166 public void testSignatureIssuerSerial() throws Exception {
167 Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
168 WSSecHeader secHeader = new WSSecHeader(doc);
169 secHeader.insertSecurityHeader();
170
171 WSSecSignature sign = new WSSecSignature(secHeader);
172 sign.setUserInfo("wss40", "security");
173 sign.setKeyIdentifierType(WSConstants.ISSUER_SERIAL);
174
175 Document signedDoc = sign.build(crypto);
176
177 if (LOG.isDebugEnabled()) {
178 String outputString =
179 XMLUtils.prettyDocumentToString(signedDoc);
180 LOG.debug(outputString);
181 }
182
183 try {
184 verify(signedDoc, cryptoCA);
185 fail("Failure expected on issuer serial");
186 } catch (WSSecurityException ex) {
187 assertTrue(ex.getErrorCode() == WSSecurityException.ErrorCode.FAILED_CHECK);
188 }
189 }
190
191
192
193
194
195
196 @Test
197 public void testSignatureBadCACert() throws Exception {
198 Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
199 WSSecHeader secHeader = new WSSecHeader(doc);
200 secHeader.insertSecurityHeader();
201
202 WSSecSignature sign = new WSSecSignature(secHeader);
203 sign.setUserInfo("wss40expca", "security");
204 sign.setKeyIdentifierType(WSConstants.BST_DIRECT_REFERENCE);
205
206 Document signedDoc =
207 sign.build(CryptoFactory.getInstance("wss40badca.properties"));
208
209 if (LOG.isDebugEnabled()) {
210 String outputString =
211 XMLUtils.prettyDocumentToString(signedDoc);
212 LOG.debug(outputString);
213 }
214
215
216
217 try {
218 verify(signedDoc, CryptoFactory.getInstance("wss40badcatrust.properties"));
219 fail("Failure expected on bad CA cert!");
220 } catch (WSSecurityException ex) {
221 assertTrue(ex.getErrorCode() == WSSecurityException.ErrorCode.FAILURE);
222 }
223 }
224
225
226
227
228 @Test
229 public void testMultipleCertsWSHandler() throws Exception {
230 final WSSConfig cfg = WSSConfig.getNewInstance();
231 final RequestData reqData = new RequestData();
232 reqData.setWssConfig(cfg);
233 reqData.setUsername("wss40");
234 java.util.Map<String, String> config = new java.util.TreeMap<>();
235 config.put(WSHandlerConstants.SIG_PROP_FILE, "wss40.properties");
236 config.put("password", "security");
237 config.put(WSHandlerConstants.SIG_KEY_ID, "DirectReference");
238 config.put(WSHandlerConstants.USE_SINGLE_CERTIFICATE, "false");
239 reqData.setMsgContext(config);
240
241 final Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
242 CustomHandler handler = new CustomHandler();
243 HandlerAction action = new HandlerAction(WSConstants.SIGN);
244 handler.send(
245 doc,
246 reqData,
247 Collections.singletonList(action),
248 true
249 );
250
251
252
253
254 WSHandlerResult results = verify(doc, cryptoCA);
255 WSSecurityEngineResult result =
256 results.getActionResults().get(WSConstants.SIGN).get(0);
257 X509Certificate cert =
258 (X509Certificate)result.get(WSSecurityEngineResult.TAG_X509_CERTIFICATE);
259 assertNotNull(cert);
260 X509Certificate[] certs =
261 (X509Certificate[])result.get(WSSecurityEngineResult.TAG_X509_CERTIFICATES);
262 assertTrue(certs != null && certs.length == 2);
263 }
264
265 @Test
266 public void testExpiredCert() throws Exception {
267 Properties clientProperties = new Properties();
268 clientProperties.put("org.apache.wss4j.crypto.provider",
269 "org.apache.wss4j.common.crypto.Merlin");
270 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.type", "jks");
271 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.password", "security");
272 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.alias", "wss40exp");
273 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.file", "keys/wss40exp.jks");
274
275 Crypto clientCrypto = new Merlin(clientProperties, this.getClass().getClassLoader(), null);
276
277 Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
278 WSSecHeader secHeader = new WSSecHeader(doc);
279 secHeader.insertSecurityHeader();
280
281 WSSecSignature sign = new WSSecSignature(secHeader);
282 sign.setUserInfo("wss40exp", "security");
283 sign.setKeyIdentifierType(WSConstants.BST_DIRECT_REFERENCE);
284
285 Document signedDoc = sign.build(clientCrypto);
286
287 if (LOG.isDebugEnabled()) {
288 String outputString =
289 XMLUtils.prettyDocumentToString(signedDoc);
290 LOG.debug(outputString);
291 }
292
293
294
295 WSSecurityEngine newEngine = new WSSecurityEngine();
296 try {
297 newEngine.processSecurityHeader(doc, null, null, cryptoCA);
298 fail("Failure expected on an expired cert");
299 } catch (WSSecurityException ex) {
300 assertTrue(ex.getErrorCode() == WSSecurityException.ErrorCode.FAILURE);
301 }
302 }
303
304 @Test
305 public void testExpiredCertInKeystore() throws Exception {
306 Properties clientProperties = new Properties();
307 clientProperties.put("org.apache.wss4j.crypto.provider",
308 "org.apache.wss4j.common.crypto.Merlin");
309 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.type", "jks");
310 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.password", "security");
311 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.alias", "wss40exp");
312 clientProperties.put("org.apache.wss4j.crypto.merlin.keystore.file", "keys/wss40exp.jks");
313
314 Crypto clientCrypto = new Merlin(clientProperties, this.getClass().getClassLoader(), null);
315
316 Document doc = SOAPUtil.toSOAPPart(SOAPUtil.SAMPLE_SOAP_MSG);
317 WSSecHeader secHeader = new WSSecHeader(doc);
318 secHeader.insertSecurityHeader();
319
320 WSSecSignature sign = new WSSecSignature(secHeader);
321 sign.setUserInfo("wss40exp", "security");
322 sign.setKeyIdentifierType(WSConstants.BST_DIRECT_REFERENCE);
323
324 Document signedDoc = sign.build(clientCrypto);
325
326 if (LOG.isDebugEnabled()) {
327 String outputString =
328 XMLUtils.prettyDocumentToString(signedDoc);
329 LOG.debug(outputString);
330 }
331
332
333
334 WSSecurityEngine newEngine = new WSSecurityEngine();
335 try {
336 newEngine.processSecurityHeader(doc, null, null, clientCrypto);
337 fail("Failure expected on an expired cert");
338 } catch (WSSecurityException ex) {
339 assertTrue(ex.getErrorCode() == WSSecurityException.ErrorCode.FAILED_CHECK);
340 }
341 }
342
343
344
345
346
347
348
349
350 private WSHandlerResult verify(Document doc, Crypto crypto) throws Exception {
351 WSHandlerResult results = secEngine.processSecurityHeader(
352 doc, null, null, crypto
353 );
354 if (LOG.isDebugEnabled()) {
355 LOG.debug("Verfied and decrypted message:");
356 String outputString =
357 XMLUtils.prettyDocumentToString(doc);
358 LOG.debug(outputString);
359 }
360 return results;
361 }
362
363
364 }