ws-commons-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From veit...@apache.org
Subject svn commit: r793405 - in /webservices/commons/trunk/modules/axiom/modules: axiom-api/src/main/java/org/apache/axiom/attachments/ axiom-api/src/main/java/org/apache/axiom/attachments/impl/ axiom-api/src/main/java/org/apache/axiom/util/activation/ axiom-...
Date Sun, 12 Jul 2009 20:52:40 GMT
Author: veithen
Date: Sun Jul 12 20:52:39 2009
New Revision: 793405

URL: http://svn.apache.org/viewvc?rev=793405&view=rev
Log:
Optimized DataHandler->base64(String) transformation:
* Use available information about the size of the content to accurately allocate the initial
capacity of the StringBuffer.
* Use DataHandler#writeTo because getInputStream will create a thread and a pipe if the DataHandler
was constructed using an object instead of a DataSource.

Added:
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/DataSourceUtils.java
  (with props)
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64StringBufferOutputStream.java
  (with props)
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64Utils.java
  (with props)
Modified:
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/SizeAwareDataSource.java
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/impl/BufferUtils.java
    webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/stax/xop/XOPDecodingStreamReader.java
    webservices/commons/trunk/modules/axiom/modules/axiom-dom/src/main/java/org/apache/axiom/om/impl/dom/TextNodeImpl.java
    webservices/commons/trunk/modules/axiom/modules/axiom-impl/src/main/java/org/apache/axiom/om/impl/llom/OMTextImpl.java

Modified: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/SizeAwareDataSource.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/SizeAwareDataSource.java?rev=793405&r1=793404&r2=793405&view=diff
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/SizeAwareDataSource.java
(original)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/SizeAwareDataSource.java
Sun Jul 12 20:52:39 2009
@@ -24,9 +24,10 @@
 /**
  * Optional extension interface that can be implemented by data sources that support a
  * getSize method.
- * Code working with data sources can use this interface to optimize certain operations.
- * An example is
- * {@link org.apache.axiom.attachments.impl.BufferUtils#doesDataHandlerExceedLimit(javax.activation.DataHandler,
int)}.
+ * Code working with data sources can use this this information to optimize certain operations.
+ * Note however that instead of checking of this interface directly, this kind of code
+ * should use {@link org.apache.axiom.util.activation.DataSourceUtils#getSize(DataSource)}
+ * because this method is able to determine the size of other types of data sources as well.
  * <p>
  * Code using this interface should be aware that some implementations may be unable to guarantee
  * 100% accuracy when determining the size of the data source. Situations where this can
occur

Modified: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/impl/BufferUtils.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/impl/BufferUtils.java?rev=793405&r1=793404&r2=793405&view=diff
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/impl/BufferUtils.java
(original)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/attachments/impl/BufferUtils.java
Sun Jul 12 20:52:39 2009
@@ -18,7 +18,6 @@
  */
 package org.apache.axiom.attachments.impl;
 
-import java.io.ByteArrayInputStream;
 import java.io.FileOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
@@ -28,11 +27,9 @@
 import java.nio.channels.FileLock;
 
 import javax.activation.DataHandler;
-import javax.activation.DataSource;
-import javax.activation.FileDataSource;
 
-import org.apache.axiom.attachments.SizeAwareDataSource;
 import org.apache.axiom.attachments.utils.BAAOutputStream;
+import org.apache.axiom.util.activation.DataSourceUtils;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 
@@ -277,28 +274,9 @@
         if(limit==0){
             return -1;
         }
-        DataSource ds = dh.getDataSource();
-        if (ds instanceof SizeAwareDataSource) {
-            long size = ((SizeAwareDataSource)ds).getSize();
-            if (size != -1) {
-                return size > limit ? 1 : 0;
-            }
-        }
-        if (ds instanceof javax.mail.util.ByteArrayDataSource) {
-            // Special optimization for JavaMail's ByteArrayDataSource (Axiom's ByteArrayDataSource
-            // already implements SizeAwareDataSource and doesn't need further optimization):
-            // we know that ByteArrayInputStream#available() directly returns the size of
the
-            // data source.
-            try {
-                return ((ByteArrayInputStream)ds.getInputStream()).available() > limit
? 1 : 0;
-            } catch (IOException ex) {
-                // We will never get here...
-                return -1;
-            }
-        } else if (ds instanceof FileDataSource) {
-            // Special optimization for FileDataSources: no need to open and read the file
-            // to know its size!
-            return ((FileDataSource)ds).getFile().length() > limit ? 1 : 0;
+        long size = DataSourceUtils.getSize(dh.getDataSource());
+        if (size != -1) {
+            return size > limit ? 1 : 0;
         } else {
             // In all other cases, we prefer DataHandler#writeTo over DataSource#getInputStream.
             // The reason is that if the DataHandler was constructed from an Object rather
than

Added: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/DataSourceUtils.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/DataSourceUtils.java?rev=793405&view=auto
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/DataSourceUtils.java
(added)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/DataSourceUtils.java
Sun Jul 12 20:52:39 2009
@@ -0,0 +1,71 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.axiom.util.activation;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+
+import javax.activation.DataSource;
+import javax.activation.FileDataSource;
+import javax.mail.util.ByteArrayDataSource;
+
+import org.apache.axiom.attachments.SizeAwareDataSource;
+
+/**
+ * Contains utility methods to work with {@link DataSource} objects.
+ */
+public class DataSourceUtils {
+    /**
+     * Determine the size of the data represented by a {@link DataSource} object.
+     * The method will try to determine the size without reading the data source.
+     * It will do so by looking for the {@link SizeAwareDataSource} interface. In addition,
it
+     * supports some other well known data source implementations for which it is possible
to
+     * get the size of the data without reading it.
+     * <p>
+     * As noted in the documentation of the {@link SizeAwareDataSource}, the returned value
+     * may be an estimation that is not 100% accurate, and code using this method must be
prepared
+     * to receive more or less data from the data source.
+     * 
+     * @param ds the data source
+     * @return (an estimation of) the size of the data or <code>-1</code> if
the size is unknown
+     */
+    public static long getSize(DataSource ds) {
+        if (ds instanceof SizeAwareDataSource) {
+            return ((SizeAwareDataSource)ds).getSize();
+        } else if (ds instanceof ByteArrayDataSource) {
+            // Special optimization for JavaMail's ByteArrayDataSource (Axiom's ByteArrayDataSource
+            // already implements SizeAwareDataSource and doesn't need further optimization):
+            // we know that ByteArrayInputStream#available() directly returns the size of
the
+            // data source.
+            try {
+                return ((ByteArrayInputStream)ds.getInputStream()).available();
+            } catch (IOException ex) {
+                // We will never get here...
+                return -1;
+            }
+        } else if (ds instanceof FileDataSource) {
+            // Special optimization for FileDataSources: no need to open and read the file
+            // to know its size!
+            return ((FileDataSource)ds).getFile().length();
+        } else {
+            return -1;
+        }
+    }
+}

Propchange: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/activation/DataSourceUtils.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64StringBufferOutputStream.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64StringBufferOutputStream.java?rev=793405&view=auto
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64StringBufferOutputStream.java
(added)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64StringBufferOutputStream.java
Sun Jul 12 20:52:39 2009
@@ -0,0 +1,57 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.axiom.util.base64;
+
+import java.io.IOException;
+import java.io.OutputStream;
+
+/**
+ * {@link OutputStream} implementation that writes base64 encoded data to a {@link StringBuffer}.
+ */
+public class Base64StringBufferOutputStream extends AbstractBase64OutputStream {
+    private final StringBuffer buffer;
+
+    /**
+     * Constructor.
+     * 
+     * @param buffer the buffer to append the encoded data to
+     */
+    public Base64StringBufferOutputStream(StringBuffer buffer) {
+        this.buffer = buffer;
+    }
+
+    protected void doWrite(byte[] b) throws IOException {
+        for (int i=0; i<4; i++) {
+            buffer.append((char)(b[i] & 0xFF));
+        }
+    }
+
+    protected void flushBuffer() throws IOException {
+        // Nothing to do
+    }
+    
+    protected void doClose() throws IOException {
+        // Nothing to do
+    }
+
+    protected void doFlush() throws IOException {
+        // Nothing to do
+    }
+}

Propchange: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64StringBufferOutputStream.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64Utils.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64Utils.java?rev=793405&view=auto
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64Utils.java
(added)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64Utils.java
Sun Jul 12 20:52:39 2009
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.axiom.util.base64;
+
+import java.io.IOException;
+
+import javax.activation.DataHandler;
+
+import org.apache.axiom.util.activation.DataSourceUtils;
+
+/**
+ * Contains utility methods to work with base64 encoded data.
+ */
+public class Base64Utils {
+    private static int getEncodedSize(int unencodedSize) {
+        return (unencodedSize+2) / 3 * 4;
+    }
+    
+    /**
+     * Get a base64 representation of the content of a given {@link DataHandler}.
+     * This method will try to carry out the encoding operation in the most efficient way.
+     * 
+     * @param dh the data handler with the content to encode
+     * @return the base64 encoded content
+     * @throws IOException if an I/O error occurs when reading the content of the data handler
+     */
+    public static String encode(DataHandler dh) throws IOException {
+        long size = DataSourceUtils.getSize(dh.getDataSource());
+        StringBuffer buffer;
+        if (size == -1) {
+            // Use a reasonable default capacity (better than the default of 16).
+            buffer = new StringBuffer(4096);
+        } else if (size > Integer.MAX_VALUE) {
+            throw new IllegalArgumentException("DataHandler is too large to encode to string");
+        } else {
+            buffer = new StringBuffer(getEncodedSize((int)size));
+        }
+        Base64StringBufferOutputStream out = new Base64StringBufferOutputStream(buffer);
+        // Always prefer writeTo, because getInputStream will create a thread and a pipe
if
+        // the DataHandler was constructed using an object instead of a DataSource
+        dh.writeTo(out);
+        out.complete();
+        return buffer.toString();
+    }
+}

Propchange: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/base64/Base64Utils.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/stax/xop/XOPDecodingStreamReader.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/stax/xop/XOPDecodingStreamReader.java?rev=793405&r1=793404&r2=793405&view=diff
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/stax/xop/XOPDecodingStreamReader.java
(original)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-api/src/main/java/org/apache/axiom/util/stax/xop/XOPDecodingStreamReader.java
Sun Jul 12 20:52:39 2009
@@ -20,7 +20,6 @@
 package org.apache.axiom.util.stax.xop;
 
 import java.io.IOException;
-import java.io.InputStream;
 import java.io.UnsupportedEncodingException;
 import java.net.URLDecoder;
 
@@ -34,7 +33,7 @@
 import org.apache.axiom.ext.stax.datahandler.DataHandlerProvider;
 import org.apache.axiom.ext.stax.datahandler.DataHandlerReader;
 import org.apache.axiom.om.util.StAXUtils;
-import org.apache.axiom.om.util.TextHelper;
+import org.apache.axiom.util.base64.Base64Utils;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 
@@ -390,13 +389,7 @@
 
     private static String toBase64(DataHandler dh) throws XMLStreamException {
         try {
-            InputStream in = dh.getInputStream();
-            try {
-                // TODO: we should also move the base64 stuff to org.apache.axiom.util
-                return TextHelper.toString(in);
-            } finally {
-                in.close();
-            }
+            return Base64Utils.encode(dh);
         } catch (IOException ex) {
             throw new XMLStreamException("Exception when encoding data handler as base64",
ex);
         }

Modified: webservices/commons/trunk/modules/axiom/modules/axiom-dom/src/main/java/org/apache/axiom/om/impl/dom/TextNodeImpl.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-dom/src/main/java/org/apache/axiom/om/impl/dom/TextNodeImpl.java?rev=793405&r1=793404&r2=793405&view=diff
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-dom/src/main/java/org/apache/axiom/om/impl/dom/TextNodeImpl.java
(original)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-dom/src/main/java/org/apache/axiom/om/impl/dom/TextNodeImpl.java
Sun Jul 12 20:52:39 2009
@@ -34,6 +34,7 @@
 import org.apache.axiom.om.impl.builder.XOPBuilder;
 import org.apache.axiom.om.util.TextHelper;
 import org.apache.axiom.om.util.UUIDGenerator;
+import org.apache.axiom.util.base64.Base64Utils;
 import org.apache.axiom.util.stax.XMLStreamWriterUtil;
 import org.w3c.dom.DOMException;
 import org.w3c.dom.Node;
@@ -363,7 +364,7 @@
             return getTextFromProperPlace();
         } else {
             try {
-                return TextHelper.toString(getInputStream());
+                return Base64Utils.encode((DataHandler)getDataHandler());
             } catch (Exception e) {
                 throw new OMException(e);
             }
@@ -413,7 +414,8 @@
             return new QName(getTextFromProperPlace());
         } else {
             try {
-                return new QName(TextHelper.toString(getInputStream()));
+                // TODO: do we really want to build a QName from base64 encoded data?!?
+                return new QName(Base64Utils.encode((DataHandler)getDataHandler()));
             } catch (Exception e) {
                 throw new OMException(e);
             }

Modified: webservices/commons/trunk/modules/axiom/modules/axiom-impl/src/main/java/org/apache/axiom/om/impl/llom/OMTextImpl.java
URL: http://svn.apache.org/viewvc/webservices/commons/trunk/modules/axiom/modules/axiom-impl/src/main/java/org/apache/axiom/om/impl/llom/OMTextImpl.java?rev=793405&r1=793404&r2=793405&view=diff
==============================================================================
--- webservices/commons/trunk/modules/axiom/modules/axiom-impl/src/main/java/org/apache/axiom/om/impl/llom/OMTextImpl.java
(original)
+++ webservices/commons/trunk/modules/axiom/modules/axiom-impl/src/main/java/org/apache/axiom/om/impl/llom/OMTextImpl.java
Sun Jul 12 20:52:39 2009
@@ -34,8 +34,8 @@
 import org.apache.axiom.om.impl.OMNamespaceImpl;
 import org.apache.axiom.om.impl.builder.XOPBuilder;
 import org.apache.axiom.om.impl.util.OMSerializerUtil;
-import org.apache.axiom.om.util.TextHelper;
 import org.apache.axiom.om.util.UUIDGenerator;
+import org.apache.axiom.util.base64.Base64Utils;
 import org.apache.axiom.util.stax.XMLStreamWriterUtil;
 
 import javax.activation.DataHandler;
@@ -285,7 +285,7 @@
             return getTextFromProperPlace();
         } else {
             try {
-                return TextHelper.toString(getInputStream());
+                return Base64Utils.encode((DataHandler)getDataHandler());
             } catch (Exception e) {
                 throw new OMException(e);
             }



Mime
View raw message