Hi Florent,

Other pieces of OpenCMIS also depend on JAX-WS RI, the classes PortProvider and Converter for example. So it shouldn't make a difference.

The problem is that if we want to make use of the streaming capabilities of JAX-WS RI, we have to use some non-standard interfaces. If we restrict ourselves to the standard interfaces we will end up with poor performance and OutOfMemory exceptions when large content is transferred.

I guess it we would be similar with CXF.


- Florian


On 29/11/2010 14:08, Florent Guillaume wrote:
Hi,

This checkin makes the auth implementation depend on the Sun JAX-WS RI
stack (Metro).
Is it not possible to keep independence from the actual implementation
(I haven't looked, not knowing JAX-WS in great detail)?

Thanks,
Florent


On Mon, Nov 29, 2010 at 1:09 PM,<[email protected]>  wrote:
Author: fmui
Date: Mon Nov 29 12:09:34 2010
New Revision: 1040081

URL: http://svn.apache.org/viewvc?rev=1040081&view=rev
Log:
- reimplemented Web Services server authentication handler - content upload is 
now drastically faster

Modified:
    
incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-bindings/src/main/java/org/apache/chemistry/opencmis/server/impl/webservices/AuthHandler.java
    
incubator/chemistry/opencmis/trunk/chemistry-opencmis-test/chemistry-opencmis-test-fit/src/test/java/org/apache/chemistry/opencmis/fit/runtime/AbstractWriteObjectIT.java

Modified: 
incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-bindings/src/main/java/org/apache/chemistry/opencmis/server/impl/webservices/AuthHandler.java
URL: 
http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-bindings/src/main/java/org/apache/chemistry/opencmis/server/impl/webservices/AuthHandler.java?rev=1040081&r1=1040080&r2=1040081&view=diff
==============================================================================
--- 
incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-bindings/src/main/java/org/apache/chemistry/opencmis/server/impl/webservices/AuthHandler.java
 (original)
+++ 
incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-bindings/src/main/java/org/apache/chemistry/opencmis/server/impl/webservices/AuthHandler.java
 Mon Nov 29 12:09:34 2010
@@ -18,36 +18,64 @@
  */
  package org.apache.chemistry.opencmis.server.impl.webservices;

+import java.util.ArrayList;
  import java.util.HashMap;
  import java.util.HashSet;
+import java.util.List;
  import java.util.Map;
  import java.util.Set;

+import javax.xml.bind.JAXBContext;
+import javax.xml.bind.JAXBElement;
+import javax.xml.bind.JAXBException;
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlAnyAttribute;
+import javax.xml.bind.annotation.XmlAnyElement;
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlElementDecl;
+import javax.xml.bind.annotation.XmlID;
+import javax.xml.bind.annotation.XmlRegistry;
+import javax.xml.bind.annotation.XmlSchemaType;
+import javax.xml.bind.annotation.XmlSeeAlso;
+import javax.xml.bind.annotation.XmlType;
+import javax.xml.bind.annotation.XmlValue;
+import javax.xml.bind.annotation.adapters.CollapsedStringAdapter;
+import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;
  import javax.xml.namespace.QName;
-import javax.xml.soap.SOAPElement;
-import javax.xml.soap.SOAPHeader;
-import javax.xml.soap.SOAPMessage;
  import javax.xml.ws.handler.MessageContext;
  import javax.xml.ws.handler.MessageContext.Scope;
-import javax.xml.ws.handler.soap.SOAPHandler;
-import javax.xml.ws.handler.soap.SOAPMessageContext;

  import org.apache.chemistry.opencmis.commons.server.CallContext;

+import com.sun.xml.ws.api.handler.MessageHandler;
+import com.sun.xml.ws.api.handler.MessageHandlerContext;
+import com.sun.xml.ws.api.message.Header;
+import com.sun.xml.ws.api.message.HeaderList;
+import com.sun.xml.ws.api.message.Message;
+
  /**
  * This class tries to extract a user name and a password from a UsernameToken.
- *
- * @author<a href="mailto:[email protected]";>Florian M&uuml;ller</a>
- *
  */
-public class AuthHandler implements SOAPHandler<SOAPMessageContext>  {
+public class AuthHandler implements MessageHandler<MessageHandlerContext>  {

     private static final String WSSE_NS = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd";;
     private static final QName WSSE_SECURITY = new QName(WSSE_NS, "Security");
     private static final QName WSSE_USERNAME_TOKEN = new QName(WSSE_NS, 
"UsernameToken");
-    private static final QName WSSE_USERNAME = new QName(WSSE_NS, "Username");
     private static final QName WSSE_PASSWORD = new QName(WSSE_NS, "Password");

+    private static final JAXBContext WSSE_CONTEXT;
+    static {
+        JAXBContext jc = null;
+        try {
+            jc = JAXBContext.newInstance(ObjectFactory.class);
+        } catch (JAXBException e) {
+            e.printStackTrace();
+        }
+        WSSE_CONTEXT = jc;
+    }
+
     private static final Set<QName>  HEADERS = new HashSet<QName>();
     static {
         HEADERS.add(WSSE_SECURITY);
@@ -60,38 +88,216 @@ public class AuthHandler implements SOAP
     public void close(MessageContext context) {
     }

-    public boolean handleFault(SOAPMessageContext context) {
+    public boolean handleFault(MessageHandlerContext context) {
         return true;
     }

-    public boolean handleMessage(SOAPMessageContext context) {
+    @SuppressWarnings("unchecked")
+    public boolean handleMessage(MessageHandlerContext context) {
         Boolean outboundProperty = (Boolean) 
context.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY);
         if (outboundProperty.booleanValue()) {
             // we are only looking at inbound messages
             return true;
         }

+        String username = null;
+        String password = null;
+
         try {
             // read the header
-            SOAPMessage msg = context.getMessage();
-            SOAPHeader sh = msg.getSOAPHeader();
-            SOAPElement securityElement = (SOAPElement) 
sh.getChildElements(WSSE_SECURITY).next();
-            SOAPElement tokenElement = (SOAPElement) 
securityElement.getChildElements(WSSE_USERNAME_TOKEN).next();
-            SOAPElement userElement = (SOAPElement) 
tokenElement.getChildElements(WSSE_USERNAME).next();
-            SOAPElement passwordElement = (SOAPElement) 
tokenElement.getChildElements(WSSE_PASSWORD).next();
-
-            // add user and password to context
-            Map<String, String>  callContextMap = new HashMap<String, 
String>();
-            callContextMap.put(CallContext.USERNAME, userElement.getValue());
-            callContextMap.put(CallContext.PASSWORD, 
passwordElement.getValue());
-
-            context.put(AbstractService.CALL_CONTEXT_MAP, callContextMap);
-            context.setScope(AbstractService.CALL_CONTEXT_MAP, 
Scope.APPLICATION);
+            Message msg = context.getMessage();
+            HeaderList hl = msg.getHeaders();
+            Header securityHeader = hl.get(WSSE_SECURITY, true);
+
+            JAXBElement<SecurityHeaderType>  sht = 
securityHeader.readAsJAXB(WSSE_CONTEXT.createUnmarshaller());
+
+            for (Object uno : sht.getValue().getAny()) {
+                if ((uno instanceof JAXBElement)&&  ((JAXBElement<?>) 
uno).getValue() instanceof UsernameTokenType) {
+                    UsernameTokenType utt = (UsernameTokenType) 
((JAXBElement<UsernameTokenType>) uno).getValue();
+                    username = utt.getUsername().getValue();
+
+                    for (Object po : utt.getAny()) {
+                        if ((po instanceof JAXBElement)&&  ((JAXBElement<?>) 
po).getValue() instanceof PasswordString) {
+                            password = ((JAXBElement<PasswordString>) 
po).getValue().getValue();
+                            break;
+                        }
+                    }
+
+                    break;
+                }
+            }
         } catch (Exception e) {
             // something went wrong, e.g. a part of the SOAP header wasn't set
-            throw new RuntimeException("UsernameToken not set!", e);
         }

+        // add user and password to context
+        Map<String, String>  callContextMap = new HashMap<String, String>();
+        callContextMap.put(CallContext.USERNAME, username);
+        callContextMap.put(CallContext.PASSWORD, password);
+
+        context.put(AbstractService.CALL_CONTEXT_MAP, callContextMap);
+        context.setScope(AbstractService.CALL_CONTEXT_MAP, Scope.APPLICATION);
+
         return true;
     }
+
+    // --- JAXB classes ---
+
+    @XmlRegistry
+    public static class ObjectFactory {
+
+        public ObjectFactory() {
+        }
+
+        public SecurityHeaderType createSecurityHeaderType() {
+            return new SecurityHeaderType();
+        }
+
+        public UsernameTokenType createUsernameTokenType() {
+            return new UsernameTokenType();
+        }
+
+        public PasswordString createPasswordString() {
+            return new PasswordString();
+        }
+
+        public AttributedString createAttributedString() {
+            return new AttributedString();
+        }
+
+        @XmlElementDecl(namespace = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd";, name 
= "Security")
+        public JAXBElement<SecurityHeaderType>  
createSecurity(SecurityHeaderType value) {
+            return new JAXBElement<SecurityHeaderType>(WSSE_SECURITY, 
SecurityHeaderType.class, null, value);
+        }
+
+        @XmlElementDecl(namespace = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd";, name 
= "UsernameToken")
+        public JAXBElement<UsernameTokenType>  
createUsernameToken(UsernameTokenType value) {
+            return new JAXBElement<UsernameTokenType>(WSSE_USERNAME_TOKEN, 
UsernameTokenType.class, null, value);
+        }
+
+        @XmlElementDecl(namespace = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd";, name 
= "Password")
+        public JAXBElement<PasswordString>  createPassword(PasswordString 
value) {
+            return new JAXBElement<PasswordString>(WSSE_PASSWORD, 
PasswordString.class, null, value);
+        }
+
+    }
+
+    @XmlAccessorType(XmlAccessType.FIELD)
+    @XmlType(name = "SecurityHeaderType", propOrder = { "any" })
+    public static class SecurityHeaderType {
+
+        @XmlAnyElement(lax = true)
+        protected List<Object>  any;
+        @XmlAnyAttribute
+        private Map<QName, String>  otherAttributes = new HashMap<QName, 
String>();
+
+        public List<Object>  getAny() {
+            if (any == null) {
+                any = new ArrayList<Object>();
+            }
+            return this.any;
+        }
+
+        public Map<QName, String>  getOtherAttributes() {
+            return otherAttributes;
+        }
+
+    }
+
+    @XmlAccessorType(XmlAccessType.FIELD)
+    @XmlType(name = "UsernameTokenType", propOrder = { "username", "any" })
+    public static class UsernameTokenType {
+
+        @XmlElement(name = "Username", namespace = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd";, 
required = true)
+        protected AttributedString username;
+        @XmlAnyElement(lax = true)
+        protected List<Object>  any;
+        @XmlAttribute(name = "Id", namespace = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd";)
+        @XmlJavaTypeAdapter(CollapsedStringAdapter.class)
+        @XmlID
+        @XmlSchemaType(name = "ID")
+        protected String id;
+        @XmlAnyAttribute
+        private Map<QName, String>  otherAttributes = new HashMap<QName, 
String>();
+
+        public AttributedString getUsername() {
+            return username;
+        }
+
+        public void setUsername(AttributedString value) {
+            this.username = value;
+        }
+
+        public List<Object>  getAny() {
+            if (any == null) {
+                any = new ArrayList<Object>();
+            }
+            return this.any;
+        }
+
+        public String getId() {
+            return id;
+        }
+
+        public void setId(String value) {
+            this.id = value;
+        }
+
+        public Map<QName, String>  getOtherAttributes() {
+            return otherAttributes;
+        }
+    }
+
+    @XmlAccessorType(XmlAccessType.FIELD)
+    @XmlType(name = "PasswordString")
+    public static class PasswordString extends AttributedString {
+
+        @XmlAttribute(name = "Type")
+        @XmlSchemaType(name = "anyURI")
+        protected String type;
+
+        public String getType() {
+            return type;
+        }
+
+        public void setType(String value) {
+            this.type = value;
+        }
+    }
+
+    @XmlAccessorType(XmlAccessType.FIELD)
+    @XmlType(name = "AttributedString", propOrder = { "value" })
+    @XmlSeeAlso({ PasswordString.class })
+    public static class AttributedString {
+
+        @XmlValue
+        protected String value;
+        @XmlAttribute(name = "Id", namespace = 
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd";)
+        @XmlJavaTypeAdapter(CollapsedStringAdapter.class)
+        @XmlID
+        @XmlSchemaType(name = "ID")
+        protected String id;
+        @XmlAnyAttribute
+        private Map<QName, String>  otherAttributes = new HashMap<QName, 
String>();
+
+        public String getValue() {
+            return value;
+        }
+
+        public void setValue(String value) {
+            this.value = value;
+        }
+
+        public String getId() {
+            return id;
+        }
+
+        public void setId(String value) {
+            this.id = value;
+        }
+
+        public Map<QName, String>  getOtherAttributes() {
+            return otherAttributes;
+        }
+    }
  }

Modified: 
incubator/chemistry/opencmis/trunk/chemistry-opencmis-test/chemistry-opencmis-test-fit/src/test/java/org/apache/chemistry/opencmis/fit/runtime/AbstractWriteObjectIT.java
URL: 
http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-test/chemistry-opencmis-test-fit/src/test/java/org/apache/chemistry/opencmis/fit/runtime/AbstractWriteObjectIT.java?rev=1040081&r1=1040080&r2=1040081&view=diff
==============================================================================
--- 
incubator/chemistry/opencmis/trunk/chemistry-opencmis-test/chemistry-opencmis-test-fit/src/test/java/org/apache/chemistry/opencmis/fit/runtime/AbstractWriteObjectIT.java
 (original)
+++ 
incubator/chemistry/opencmis/trunk/chemistry-opencmis-test/chemistry-opencmis-test-fit/src/test/java/org/apache/chemistry/opencmis/fit/runtime/AbstractWriteObjectIT.java
 Mon Nov 29 12:09:34 2010
@@ -135,7 +135,11 @@ public abstract class AbstractWriteObjec
         ContentStream contentStream = 
this.session.getObjectFactory().createContentStream(filename, size, mimetype, 
in);
         assertNotNull(contentStream);

+        long start = System.currentTimeMillis();
         doc.setContentStream(contentStream, true);
+        long end = System.currentTimeMillis();
+
+        log.info("setContentStream of " + size + " bytes:" + (end - start) + 
"ms");
     }

     @Test
@@ -523,24 +527,23 @@ public abstract class AbstractWriteObjec

         ContentStream cs5 = tdoc4.getContentStream();
         assertNull(cs5);
-
+
         assertEquals(false, tdoc5.isMarkedForDelete());
-
+
         tdoc5.delete(true);

-        assertEquals(true, tdoc5.isMarkedForDelete());
+        assertEquals(true, tdoc5.isMarkedForDelete());

         ObjectId id5 = tdoc5.save();
         assertNull(id5);
-
+
         // check
         try {
             this.session.getObject(id4, oc);
             fail("CmisObjectNotFoundException expected!");
-        }
-        catch (CmisObjectNotFoundException e) {
+        } catch (CmisObjectNotFoundException e) {
             // expected
-        }
+        }
     }

     private byte[] readContent(ContentStream contentStream) throws Exception {







Reply via email to