You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@ode.apache.org by Tim Carpenter <ti...@permeance.com.au> on 2010/03/12 04:00:25 UTC

Memory usage of ODEAxisService$WSDL11ToAxisPatchedBuilder

Hi,

We have been having some problems with very high memory usage when deploying
processes in Apache ODE. The 48 processes we were deploying was taking up
1.9GB of memory.

Some profiling lead us to look at the
org.apache.ode.axis2.hooks.ODEAxisService$WSDL11ToAxisPatchedBuilder.getXMLSchemamethod.
Our schemas have a number of imports that subsequently import other
schemas and so on. We noticed that the XmlSchema objects were taking up a
lot of memory and some debugging showed that the same schemas were being
read repeatedly.

The class currently looks like this:

    // Axis2 monkey patching to force the usage of the read(element,baseUri)
method
    // of XmlSchema as the normal read is broken.
    public static class WSDL11ToAxisPatchedBuilder extends
WSDL11ToAxisServiceBuilder {
        // Constructors ommited.

        protected XmlSchema getXMLSchema(Element element, String baseUri) {
            XmlSchemaCollection schemaCollection = new
XmlSchemaCollection();
            if (baseUri != null) {
                schemaCollection.setBaseUri(baseUri);
            }
            return schemaCollection.read(element, baseUri);
        }
    }

I added some very simple caching to make it look like this

    // Axis2 monkey patching to force the usage of the read(element,baseUri)
method
    // of XmlSchema as the normal read is broken.
    public static class WSDL11ToAxisPatchedBuilder extends
WSDL11ToAxisServiceBuilder {
        // Constructors ommited

        protected XmlSchema getXMLSchema(Element element, String baseUri) {
            return findSchemaInCache(element, baseUri);
        }

        private static Map<String, XmlSchema> schemas = new HashMap<String,
XmlSchema>();
        public static XmlSchema findSchemaInCache(Element e, String baseUri)
{
            if (schemas.containsKey(baseUri)) {
                return schemas.get(baseUri);
            }
            XmlSchemaCollection schemaCollection = new
XmlSchemaCollection();
            if (baseUri != null) {
                schemaCollection.setBaseUri(baseUri);
            }
            XmlSchema s = schemaCollection.read(e, baseUri);
            schemas.put(baseUri, s);
            return s;
        }
    }

This reduced the memory usage for us from 1.9GB to 500MB.

A couple of questions

1. The comment at the top of the sub class is.... interesting. Is this
comment still true?
2. Is reuse of the XmlSchema objects like this OK? The
XmlSchemaCollection.read method seems to only read from the Element object
that is passed to it but the code that creates the Element (part of Axis'
org.apache.axis2.description.WSDL11ToAxisServiceBuilder.processServicemethod)
is more complex.
3. Is there another way to reduce the amount of memory being used for these
schema objects?

Many thanks.

Tim