You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cxf.apache.org by dk...@apache.org on 2010/01/27 16:38:53 UTC
svn commit: r903690 - in /cxf/branches/2.2.x-fixes: ./
rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/
rt/ws/security/src/test/java/org/apache/cxf/ws/security/wss4j/
Author: dkulp
Date: Wed Jan 27 15:38:52 2010
New Revision: 903690
URL: http://svn.apache.org/viewvc?rev=903690&view=rev
Log:
Merged revisions 903445 via svnmerge from
https://svn.apache.org/repos/asf/cxf/trunk
........
r903445 | dkulp | 2010-01-26 16:56:52 -0500 (Tue, 26 Jan 2010) | 2 lines
Support for allowing users to configure custom Wss4J action implementations
in WSS4JOutInterceptor
........
Modified:
cxf/branches/2.2.x-fixes/ (props changed)
cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/Messages.properties
cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptor.java
cxf/branches/2.2.x-fixes/rt/ws/security/src/test/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptorTest.java
Propchange: cxf/branches/2.2.x-fixes/
------------------------------------------------------------------------------
Binary property 'svnmerge-integrated' - no diff available.
Modified: cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/Messages.properties
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/Messages.properties?rev=903690&r1=903689&r2=903690&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/Messages.properties (original)
+++ cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/Messages.properties Wed Jan 27 15:38:52 2010
@@ -22,5 +22,6 @@
# OutInterceptor error messages
NO_SAAJ_DOC: No SOAPMessage DOM was found. Please enable the SAAJInInterceptor.
NO_ACTION: No security action was defined.
+BAD_ACTION: An invalid action configuration was defined.
NO_USERNAME: Empty username for specified action.
SECURITY_FAILED: Security processing failed.
Modified: cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptor.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptor.java?rev=903690&r1=903689&r2=903690&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptor.java (original)
+++ cxf/branches/2.2.x-fixes/rt/ws/security/src/main/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptor.java Wed Jan 27 15:38:52 2010
@@ -35,16 +35,27 @@
import org.apache.cxf.binding.soap.saaj.SAAJOutInterceptor;
import org.apache.cxf.common.i18n.Message;
import org.apache.cxf.common.logging.LogUtils;
+import org.apache.cxf.helpers.CastUtils;
import org.apache.cxf.interceptor.Fault;
import org.apache.cxf.phase.Phase;
import org.apache.cxf.phase.PhaseInterceptor;
import org.apache.ws.security.WSConstants;
+import org.apache.ws.security.WSSConfig;
import org.apache.ws.security.WSSecurityException;
+import org.apache.ws.security.action.Action;
import org.apache.ws.security.handler.RequestData;
import org.apache.ws.security.handler.WSHandlerConstants;
import org.apache.ws.security.util.WSSecurityUtil;
public class WSS4JOutInterceptor extends AbstractWSS4JInterceptor {
+
+ /**
+ * Property name for a map of action IDs ({@link Integer}) to action
+ * class names. Values can be either {@link String}) or Objects
+ * implementing {@link Action}.
+ */
+ public static final String WSS4J_ACTION_MAP = "wss4j.action.map";
+
private static final Logger LOG = LogUtils
.getL7dLogger(WSS4JOutInterceptor.class);
@@ -52,6 +63,7 @@
.getL7dLogger(WSS4JOutInterceptor.class,
null,
WSS4JOutInterceptor.class.getName() + "-Time");
+
private WSS4JOutInterceptorInternal ending;
private SAAJOutInterceptor saajOut = new SAAJOutInterceptor();
private boolean mtomEnabled;
@@ -152,6 +164,15 @@
* housekeeping.
*/
try {
+ WSSConfig config = WSSConfig.getNewInstance();
+ reqData.setWssConfig(config);
+
+ /*
+ * Setup any custom actions first by processing the input properties
+ * and reconfiguring the WSSConfig with the user defined properties.
+ */
+ this.configureActions(mc, doDebug, version, config);
+
/*
* Get the action first.
*/
@@ -162,7 +183,7 @@
.getReceiver());
}
- int doAction = WSSecurityUtil.decodeAction(action, actions);
+ int doAction = WSSecurityUtil.decodeAction(action, actions, config);
if (doAction == WSConstants.NO_SECURITY) {
return;
}
@@ -275,5 +296,48 @@
public void handleFault(SoapMessage message) {
//nothing
}
+
+ private void configureActions(SoapMessage mc, boolean doDebug,
+ SoapVersion version, WSSConfig config) {
+
+ final Map<Integer, Object> actionMap = CastUtils.cast(
+ (Map<?, ?>)getProperty(mc, WSS4J_ACTION_MAP));
+ if (actionMap != null) {
+ for (Map.Entry<Integer, Object> entry : actionMap.entrySet()) {
+ String removedAction = null;
+
+ // Be defensive here since the cast above is slightly risky
+ // with the handler config options not being strongly typed.
+ try {
+ if (entry.getValue() instanceof String) {
+ removedAction = config.setAction(
+ entry.getKey().intValue(),
+ (String) entry.getValue());
+ } else if (entry.getValue() instanceof Action) {
+ removedAction = config.setAction(
+ entry.getKey().intValue(),
+ (Action) entry.getValue());
+ } else {
+ throw new SoapFault(new Message("BAD_ACTION", LOG), version
+ .getReceiver());
+ }
+ } catch (ClassCastException e) {
+ throw new SoapFault(new Message("BAD_ACTION", LOG), version
+ .getReceiver());
+ }
+
+ if (doDebug) {
+ if (removedAction != null) {
+ LOG.fine("Replaced Action: " + removedAction
+ + " with Action: " + entry.getValue()
+ + " for ID: " + entry.getKey());
+ } else {
+ LOG.fine("Added Action: " + entry.getValue()
+ + " with ID: " + entry.getKey());
+ }
+ }
+ }
+ }
+ }
}
}
Modified: cxf/branches/2.2.x-fixes/rt/ws/security/src/test/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptorTest.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/ws/security/src/test/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptorTest.java?rev=903690&r1=903689&r2=903690&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/ws/security/src/test/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptorTest.java (original)
+++ cxf/branches/2.2.x-fixes/rt/ws/security/src/test/java/org/apache/cxf/ws/security/wss4j/WSS4JOutInterceptorTest.java Wed Jan 27 15:38:52 2010
@@ -18,18 +18,29 @@
*/
package org.apache.cxf.ws.security.wss4j;
+import java.util.HashMap;
+import java.util.Map;
+
import javax.xml.soap.SOAPMessage;
import javax.xml.soap.SOAPPart;
+import org.w3c.dom.Document;
+
+import org.apache.cxf.binding.soap.SoapFault;
import org.apache.cxf.binding.soap.SoapMessage;
import org.apache.cxf.message.Exchange;
import org.apache.cxf.message.ExchangeImpl;
import org.apache.cxf.message.MessageImpl;
import org.apache.cxf.phase.PhaseInterceptor;
import org.apache.ws.security.WSConstants;
+import org.apache.ws.security.WSSecurityException;
+import org.apache.ws.security.action.UsernameTokenAction;
+import org.apache.ws.security.handler.RequestData;
+import org.apache.ws.security.handler.WSHandler;
import org.apache.ws.security.handler.WSHandlerConstants;
import org.junit.Test;
+
/**
* @author <a href="mailto:tsztelak@gmail.com">Tomasz Sztelak</a>
*/
@@ -62,7 +73,7 @@
// Test to see that the plaintext password is used in the header
assertValid("//wsse:Security/wsse:UsernameToken/wsse:Password[text()='myAliasPassword']", doc);
}
-
+
@Test
public void testUsernameTokenDigest() throws Exception {
SOAPMessage saaj = readSAAJDocument("wsse-request-clean.xml");
@@ -166,4 +177,69 @@
assertValid("//wsse:Security", doc);
assertValid("//wsse:Security/wsu:Timestamp", doc);
}
+
+ @Test
+ public void testCustomAction() throws Exception {
+ SOAPMessage saaj = readSAAJDocument("wsse-request-clean.xml");
+
+ WSS4JOutInterceptor ohandler = new WSS4JOutInterceptor();
+ PhaseInterceptor<SoapMessage> handler = ohandler.createEndingInterceptor();
+
+ SoapMessage msg = new SoapMessage(new MessageImpl());
+ Exchange ex = new ExchangeImpl();
+ ex.setInMessage(msg);
+
+ msg.setContent(SOAPMessage.class, saaj);
+
+ CountingUsernameTokenAction action = new CountingUsernameTokenAction();
+ Map<Object, Object> customActions = new HashMap<Object, Object>(1);
+ customActions.put(WSConstants.UT, action);
+
+ msg.put(WSHandlerConstants.ACTION, WSHandlerConstants.USERNAME_TOKEN);
+ msg.put(WSHandlerConstants.SIG_PROP_FILE, "META-INF/cxf/outsecurity.properties");
+ msg.put(WSHandlerConstants.USER, "username");
+ msg.put("password", "myAliasPassword");
+ msg.put(WSHandlerConstants.PASSWORD_TYPE, WSConstants.PW_TEXT);
+ msg.put(WSS4JOutInterceptor.WSS4J_ACTION_MAP, customActions);
+ handler.handleMessage(msg);
+
+ SOAPPart doc = saaj.getSOAPPart();
+ assertValid("//wsse:Security", doc);
+ assertValid("//wsse:Security/wsse:UsernameToken", doc);
+ assertValid("//wsse:Security/wsse:UsernameToken/wsse:Username[text()='username']", doc);
+ // Test to see that the plaintext password is used in the header
+ assertValid("//wsse:Security/wsse:UsernameToken/wsse:Password[text()='myAliasPassword']", doc);
+ assertEquals(1, action.getExecutions());
+
+ try {
+ customActions.put(WSConstants.UT, new Object());
+ handler.handleMessage(msg);
+ } catch (SoapFault e) {
+ assertEquals("An invalid action configuration was defined.", e.getMessage());
+ }
+
+ try {
+ customActions.put(new Object(), action);
+ handler.handleMessage(msg);
+ } catch (SoapFault e) {
+ assertEquals("An invalid action configuration was defined.", e.getMessage());
+ }
+ }
+
+ private static class CountingUsernameTokenAction extends UsernameTokenAction {
+
+ private int executions;
+
+ @Override
+ public void execute(WSHandler handler, int actionToDo, Document doc,
+ RequestData reqData) throws WSSecurityException {
+
+ this.executions++;
+ super.execute(handler, actionToDo, doc, reqData);
+ }
+
+ public int getExecutions() {
+ return this.executions;
+ }
+ }
}