View Javadoc

    1   package org.codehaus.xfire.jaxb;
    2
    3   import org.codehaus.xfire.XFireRuntimeException;
    4   import org.codehaus.xfire.aegis.type.Type;
    5   import org.codehaus.xfire.soap.SoapConstants;
    6   import org.codehaus.yom.Document;
    7   import org.codehaus.yom.Element;
    8   import org.codehaus.yom.stax.StaxBuilder;
    9   import org.codehaus.yom.xpath.YOMXPath;
    10  import org.jaxen.JaxenException;
    11  import org.jaxen.XPath;
    12
    13  import javax.xml.stream.XMLStreamException;
    14  import java.io.FileInputStream;
    15  import java.io.FileNotFoundException;
    16  import java.io.InputStream;
    17  import java.util.*;
    18
    19  /***
    20   * User: chris
    21   * Date: Aug 21, 2005
    22   * Time: 1:41:05 PM
    23   */
    24  public class JaxbSchemaProvider
    25  {
    26      private Document[] schemas;
    27      private Map schemaCache;
    28
    29      public JaxbSchemaProvider(List schemaLocations)
    30      {
    31          schemaCache = new HashMap();
    32          List schemaList = new ArrayList();
    33
    34          StaxBuilder builder = new StaxBuilder();
    35          for (Iterator iterator = schemaLocations.iterator(); iterator.hasNext();)
    36          {
    37              String s = (String) iterator.next();
    38              InputStream fileInputStream = null;
    39              try
    40              {
    41                  fileInputStream = new FileInputStream(s);
    42              } catch (FileNotFoundException e)
    43              {
    44                  fileInputStream = Thread.currentThread().getContextClassLoader().getResourceAsStream(s);
    45              }
    46              if (fileInputStream == null)
    47                  throw new XFireRuntimeException("couldnt load schema file:" + s);
    48              Document schema = null;
    49              try
    50              {
    51                  schema = builder.build(fileInputStream);
    52              } catch (XMLStreamException e)
    53              {
    54                  throw new XFireRuntimeException("error parsing schema file:" + s, e);
    55              }
    56              schemaList.add(schema);
    57
    58          }
    59          schemas = (Document[]) schemaList.toArray(new Document[schemaList.size()]);
    60
    61      }
    62
    63
    64      public Element getSchema(Type jaxbType, JaxbWsdlBuilder jaxbWsdlBuilder)
    65      {
    66          Element schema = null;
    67
    68
    69          List nodes = null;
    70          String ns = jaxbType.getSchemaType().getNamespaceURI();
    71          Element o = (Element) schemaCache.get(ns);
    72          if (o != null)
    73              return o;
    74          boolean found = false;
    75          for (int i = 0; i < schemas.length; i++)
    76          {
    77
    78              Document document = schemas[i];
    79              schema = document.getRootElement();
    80              String expr = "//xsd:schema[@targetNamespace='" + ns + "']";
    81
    82              nodes = getMatches(schema, expr);
    83              if (nodes.size() != 0)
    84              {
    85
    86                  found = true;
    87                  break;
    88              }
    89          }
    90
    91          if (!found)
    92              throw new XFireRuntimeException("couldnt find namespace " + ns);
    93          Element node = (Element) nodes.get(0);
    94
    95          nodes = getMatches(schema, "//xsd:import");
    96          for (int i = 0; i < nodes.size(); i++)
    97          {
    98              Element imp = (Element) nodes.get(i);
    99
    100             String importedNs = imp.getAttributeValue("namespace");
    101
    102             // TODO: How do we make sure this is imported???
    103
    104             imp.detach();
    105         }
    106         schemaCache.put(ns, node);
    107         return node;
    108     }
    109
    110     private List getMatches(Object doc, String xpath)
    111     {
    112         try
    113         {
    114             XPath path = new YOMXPath(xpath);
    115             path.addNamespace("xsd", SoapConstants.XSD);
    116             path.addNamespace("s", SoapConstants.XSD);
    117             List result = path.selectNodes(doc);
    118             return result;
    119         }
    120         catch (JaxenException e)
    121         {
    122             throw new XFireRuntimeException("Error evaluating xpath " + xpath, e);
    123         }
    124     }
    125 }