Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Eclipse Projects » XML Schema Definition (XSD) » Parsing a WSDL with embedded xsd
Parsing a WSDL with embedded xsd [message #31929] Tue, 21 October 2003 11:37 Go to next message
Hayden Marchant is currently offline Hayden Marchant
Messages: 90
Registered: July 2009
Member
I have a WSDL file that contains embedded XSD. The approach that I've been
taking is to take the xsd part and parse it as a seperate blob using
Eclipse XSD. This approach works for simple cases, but with the WSDL
below, where the targetNamespace of the file has a prefix called typens,
there is a complication parsing the xsd since it cannot resolve the
typens: prefix for the complex types. In fact I also have a problem with
the wsdl:arrayType but I'm not sure if that can be overcome.

Is there a way that I can set the targetNamespace of the document such
that I can overcome this problem.

<wsdl:definitions xmlns:typens="http://soap.amazon.com"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns="http://schemas.xmlsoap.org/wsdl/"
targetNamespace="http://soap.amazon.com" name="AmazonSearch">
<wsdl:types>
<xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://soap.amazon.com">
<xsd:complexType name="ProductLineArray">
<xsd:complexContent>
<xsd:restriction base="soapenc:Array">
<xsd:attribute ref="soapenc:arrayType"
wsdl:arrayType="typens:ProductLine[]" />
</xsd:restriction>
</xsd:complexContent>
</xsd:complexType>
<xsd:complexType name="ProductLine">
<xsd:all>
<xsd:element name="Mode" type="xsd:string" minOccurs="0" />
<xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
/>
</xsd:all>
........................
Re: Parsing a WSDL with embedded xsd [message #31964 is a reply to message #31929] Tue, 21 October 2003 19:09 Go to previous messageGo to next message
Eclipse User
Originally posted by: merks.ca.ibm.com

This is a multi-part message in MIME format.
--------------5BE33EF585AFEC61B91DDA83
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit

Hayden,

I've been thinking about providing a convenience resource implementation for
handling WSDL. Attached are XSDWSDLResourceFactoryImpl and
XSDWSDLResourceImpl. If you register this factory against the "wsdl"
extension, it will create a resource that has all the WSDL contained schemas
in the getContents list. I've only test this a little bit...

Hayden Marchant wrote:

> I have a WSDL file that contains embedded XSD. The approach that I've been
> taking is to take the xsd part and parse it as a seperate blob using
> Eclipse XSD. This approach works for simple cases, but with the WSDL
> below, where the targetNamespace of the file has a prefix called typens,
> there is a complication parsing the xsd since it cannot resolve the
> typens: prefix for the complex types. In fact I also have a problem with
> the wsdl:arrayType but I'm not sure if that can be overcome.
>
> Is there a way that I can set the targetNamespace of the document such
> that I can overcome this problem.
>
> <wsdl:definitions xmlns:typens="http://soap.amazon.com"
> xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
> xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
> xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
> xmlns="http://schemas.xmlsoap.org/wsdl/"
> targetNamespace="http://soap.amazon.com" name="AmazonSearch">
> <wsdl:types>
> <xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> targetNamespace="http://soap.amazon.com">
> <xsd:complexType name="ProductLineArray">
> <xsd:complexContent>
> <xsd:restriction base="soapenc:Array">
> <xsd:attribute ref="soapenc:arrayType"
> wsdl:arrayType="typens:ProductLine[]" />
> </xsd:restriction>
> </xsd:complexContent>
> </xsd:complexType>
> <xsd:complexType name="ProductLine">
> <xsd:all>
> <xsd:element name="Mode" type="xsd:string" minOccurs="0" />
> <xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
> />
> </xsd:all>
> .......................

--------------5BE33EF585AFEC61B91DDA83
Content-Type: text/plain; charset=us-ascii;
name="XSDWSDLResourceFactoryImpl.java"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="XSDWSDLResourceFactoryImpl.java"

/**
* <copyright>
*
* Copyright (c) 2002 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Common Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/cpl-v10.html
*
* Contributors:
* IBM - Initial API and implementation
*
* </copyright>
*
* %W%
* @version %I% %H%
*/
package org.eclipse.xsd.util;


import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.resource.impl.ResourceFactoryImpl;


/**
* The <b>Resource Factory</b> implementation for as WSDL resource.
*/
public class XSDWSDLResourceFactoryImpl extends ResourceFactoryImpl
{
/**
* Creates an instance.
*/
public XSDWSDLResourceFactoryImpl()
{
super();
}

/**
* Creates an {@link XSDResourceImpl}.
* @param uri the URI of the new resource.
* @param extent the extent of the new resource.
* @return an XSDResourceImpl.
*/
public Resource createResource(URI uri)
{
return new XSDWSDLResourceImpl(uri);
}
}

--------------5BE33EF585AFEC61B91DDA83
Content-Type: text/plain; charset=us-ascii;
name="XSDWSDLResourceImpl.java"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="XSDWSDLResourceImpl.java"

/**
* <copyright>
*
* Copyright (c) 2002 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Common Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/cpl-v10.html
*
* Contributors:
* IBM - Initial API and implementation
*
* </copyright>
*
* %W%
* @version %I% %H%
*/
package org.eclipse.xsd.util;


import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import org.apache.xml.serialize.OutputFormat;
import org.apache.xml.serialize.XMLSerializer;

import org.eclipse.core.runtime.IProgressMonitor;

import org.eclipse.emf.common.notify.Notification;

import org.eclipse.emf.common.util.URI;

import org.eclipse.emf.ecore.EObject;

import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.resource.ResourceSet;

import org.eclipse.emf.ecore.resource.impl.ResourceFactoryImpl;
import org.eclipse.emf.ecore.resource.impl.ResourceImpl;

import org.eclipse.xsd.*;
import org.eclipse.xsd.XSDDiagnostic;
import org.eclipse.xsd.XSDFactory;
import org.eclipse.xsd.XSDPackage;
import org.eclipse.xsd.XSDPlugin;
import org.eclipse.xsd.XSDSchema;

import org.eclipse.xsd.impl.XSDSchemaImpl;

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;

import org.xml.sax.EntityResolver;
import org.xml.sax.ErrorHandler;
import org.xml.sax.InputSource;
import org.xml.sax.Locator;
import org.xml.sax.SAXException;
import org.xml.sax.SAXParseException;

import org.xml.sax.helpers.DefaultHandler;


/**
* The <b>Resource</b> implementation for a WSDL resource.
*/
public class XSDWSDLResourceImpl extends XSDResourceImpl
{
protected Document document;

public XSDWSDLResourceImpl()
{
super();
}

public XSDWSDLResourceImpl(URI uri)
{
super(uri);
}

protected void doSave(OutputStream os, Map options) throws IOException
{
if (document != null)
{
doSerialize(os, document, options == null ? null : (String)options.get(XSD_ENCODING));
}
}

/**
* Loads a new {@link XSDResourceImpl} into the resource set.
* @param resourceSet the resource set to hold the new resource.
* @param uri the URI of the new resource.
* @param inputStream the contents of the new resource.
* @param options any options to influence loading behavior.
* @return a new XSDResourceImpl.
*/
protected void doLoad(InputStream inputStream, Map options) throws IOException
{
// This pattern avoids loading the IProgressMonitor class when there is no progress monitor.
// This is important for stand-alone execution to work correctly.
//
IProgressMonitor progressMonitor = null;
Object monitor = options == null ? null : options.get("XSD_PROGRESS_MONITOR");
if (monitor != null)
{
progressMonitor = (IProgressMonitor)monitor;
progressMonitor.setTaskName(XSDPlugin.INSTANCE.getString("_UI_ResourceLoad_progress "));
progressMonitor.subTask(getURI().toString());
}

XSDParser xsdParser = new XSDParser();
try
{
if (options != null && Boolean.TRUE.equals(options.get("XSD_TRACK_LOCATION")))
{
xsdParser.parse(inputStream);
document = xsdParser.getDocument();
}
else
{
document = getDocument(inputStream, xsdParser);
}

if (xsdParser.getEncoding() != null)
{
getDefaultSaveOptions().put(XSD_ENCODING, xsdParser.getEncoding());
}

if (document != null && document.getDocumentElement() != null)
{
ResourceSet globalResourceSet = XSDSchemaImpl.getGlobalResourceSet();
Object oldMonitor = globalResourceSet.getLoadOptions().get("XSD_PROGRESS_MONITOR ");
try
{
XSDSchemaImpl.getGlobalResourceSet().getLoadOptions().put("XSD_PROGRESS_MONITOR ", progressMonitor);
findSchemas(document.getDocumentElement());
}
finally
{
XSDSchemaImpl.getGlobalResourceSet().getLoadOptions().put("XSD_PROGRESS_MONITOR ", oldMonitor);
}
}
}
catch (Exception exception)
{
XSDPlugin.INSTANCE.log(exception);
}

for (Iterator i = getContents().iterator(); i.hasNext(); )
{
XSDSchema xsdSchema = (XSDSchema)i.next();
assignDiagnostics(xsdSchema, xsdParser.getDiagnostics());

for (Iterator diagnostics = xsdParser.getDiagnostics().iterator(); diagnostics.hasNext(); )
{
XSDDiagnostic xsdDiagnostic = (XSDDiagnostic)diagnostics.next();
switch (xsdDiagnostic.getSeverity().getValue())
{
case XSDDiagnosticSeverity.FATAL:
case XSDDiagnosticSeverity.ERROR:
{
getErrors().add(xsdDiagnostic);
break;
}
case XSDDiagnosticSeverity.WARNING:
case XSDDiagnosticSeverity.INFORMATION:
{
getWarnings().add(xsdDiagnostic);
break;
}
}
}
}


if (progressMonitor != null)
{
progressMonitor.worked(1);
}
}

protected void findSchemas(Element element)
{
if (XSDConstants.nodeType(element) == XSDConstants.SCHEMA_ELEMENT)
{
XSDSchema xsdSchema = XSDSchemaImpl.createSchema(element);
getContents().add(xsdSchema);
}
else
{
for (Node child = element.getFirstChild(); child != null; child = child.getNextSibling())
{
if (child instanceof Element)
{
findSchemas((Element)child);
}
}
}
}

public void attached(EObject eObject)
{
super.attached(eObject);

if (eObject instanceof XSDSchema)
{
((XSDSchema)eObject).setSchemaLocation(getURI().toString());
}
}
}

--------------5BE33EF585AFEC61B91DDA83--
Re: Parsing a WSDL with embedded xsd [message #32777 is a reply to message #31964] Sun, 09 November 2003 17:44 Go to previous messageGo to next message
Hayden Marchant is currently offline Hayden Marchant
Messages: 90
Registered: July 2009
Member
Ed,

Thanks for this utility - nice to know how resource factories can be used.
This doesn't really solve our problem since there are lines in the xsd,
like:

<xsd:restriction base="soapenc:Array">

Now, we don't have any explicit import statement for that namespace. All
there is, is the XML Namespace declaration at the head of the WSDL. I
could hack in, and simulate an import statement in the xsd body and then
parse but I was wondering if there was a nicer way.

Thanks

Ed Merks wrote:

> Hayden,

> I've been thinking about providing a convenience resource implementation for
> handling WSDL. Attached are XSDWSDLResourceFactoryImpl and
> XSDWSDLResourceImpl. If you register this factory against the "wsdl"
> extension, it will create a resource that has all the WSDL contained schemas
> in the getContents list. I've only test this a little bit...

> Hayden Marchant wrote:

> > I have a WSDL file that contains embedded XSD. The approach that I've been
> > taking is to take the xsd part and parse it as a seperate blob using
> > Eclipse XSD. This approach works for simple cases, but with the WSDL
> > below, where the targetNamespace of the file has a prefix called typens,
> > there is a complication parsing the xsd since it cannot resolve the
> > typens: prefix for the complex types. In fact I also have a problem with
> > the wsdl:arrayType but I'm not sure if that can be overcome.
> >
> > Is there a way that I can set the targetNamespace of the document such
> > that I can overcome this problem.
> >
> > <wsdl:definitions xmlns:typens="http://soap.amazon.com"
> > xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
> > xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
> > xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
> > xmlns="http://schemas.xmlsoap.org/wsdl/"
> > targetNamespace="http://soap.amazon.com" name="AmazonSearch">
> > <wsdl:types>
> > <xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > targetNamespace="http://soap.amazon.com">
> > <xsd:complexType name="ProductLineArray">
> > <xsd:complexContent>
> > <xsd:restriction base="soapenc:Array">
> > <xsd:attribute ref="soapenc:arrayType"
> > wsdl:arrayType="typens:ProductLine[]" />
> > </xsd:restriction>
> > </xsd:complexContent>
> > </xsd:complexType>
> > <xsd:complexType name="ProductLine">
> > <xsd:all>
> > <xsd:element name="Mode" type="xsd:string" minOccurs="0" />
> > <xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
> > />
> > </xsd:all>
> > .......................
Re: Parsing a WSDL with embedded xsd [message #32868 is a reply to message #32777] Mon, 10 November 2003 11:51 Go to previous message
Eclipse User
Originally posted by: merks.ca.ibm.com

Hayden,

Soap encoding arrays are bit of a hack. It's most certainly invalid to reference
a name in a namespace that isn't explicitly imported, so to make a valid model,
you'll have to do something. You could build the model first, and then use the
model to add the import...


Hayden Marchant wrote:

> Ed,
>
> Thanks for this utility - nice to know how resource factories can be used.
> This doesn't really solve our problem since there are lines in the xsd,
> like:
>
> <xsd:restriction base="soapenc:Array">
>
> Now, we don't have any explicit import statement for that namespace. All
> there is, is the XML Namespace declaration at the head of the WSDL. I
> could hack in, and simulate an import statement in the xsd body and then
> parse but I was wondering if there was a nicer way.
>
> Thanks
>
> Ed Merks wrote:
>
> > Hayden,
>
> > I've been thinking about providing a convenience resource implementation for
> > handling WSDL. Attached are XSDWSDLResourceFactoryImpl and
> > XSDWSDLResourceImpl. If you register this factory against the "wsdl"
> > extension, it will create a resource that has all the WSDL contained schemas
> > in the getContents list. I've only test this a little bit...
>
> > Hayden Marchant wrote:
>
> > > I have a WSDL file that contains embedded XSD. The approach that I've been
> > > taking is to take the xsd part and parse it as a seperate blob using
> > > Eclipse XSD. This approach works for simple cases, but with the WSDL
> > > below, where the targetNamespace of the file has a prefix called typens,
> > > there is a complication parsing the xsd since it cannot resolve the
> > > typens: prefix for the complex types. In fact I also have a problem with
> > > the wsdl:arrayType but I'm not sure if that can be overcome.
> > >
> > > Is there a way that I can set the targetNamespace of the document such
> > > that I can overcome this problem.
> > >
> > > <wsdl:definitions xmlns:typens="http://soap.amazon.com"
> > > xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > > xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
> > > xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
> > > xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
> > > xmlns="http://schemas.xmlsoap.org/wsdl/"
> > > targetNamespace="http://soap.amazon.com" name="AmazonSearch">
> > > <wsdl:types>
> > > <xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > > targetNamespace="http://soap.amazon.com">
> > > <xsd:complexType name="ProductLineArray">
> > > <xsd:complexContent>
> > > <xsd:restriction base="soapenc:Array">
> > > <xsd:attribute ref="soapenc:arrayType"
> > > wsdl:arrayType="typens:ProductLine[]" />
> > > </xsd:restriction>
> > > </xsd:complexContent>
> > > </xsd:complexType>
> > > <xsd:complexType name="ProductLine">
> > > <xsd:all>
> > > <xsd:element name="Mode" type="xsd:string" minOccurs="0" />
> > > <xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
> > > />
> > > </xsd:all>
> > > .......................
Re: Parsing a WSDL with embedded xsd [message #579939 is a reply to message #31929] Tue, 21 October 2003 19:09 Go to previous message
Ed Merks is currently offline Ed Merks
Messages: 26141
Registered: July 2009
Senior Member
This is a multi-part message in MIME format.
--------------5BE33EF585AFEC61B91DDA83
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit

Hayden,

I've been thinking about providing a convenience resource implementation for
handling WSDL. Attached are XSDWSDLResourceFactoryImpl and
XSDWSDLResourceImpl. If you register this factory against the "wsdl"
extension, it will create a resource that has all the WSDL contained schemas
in the getContents list. I've only test this a little bit...

Hayden Marchant wrote:

> I have a WSDL file that contains embedded XSD. The approach that I've been
> taking is to take the xsd part and parse it as a seperate blob using
> Eclipse XSD. This approach works for simple cases, but with the WSDL
> below, where the targetNamespace of the file has a prefix called typens,
> there is a complication parsing the xsd since it cannot resolve the
> typens: prefix for the complex types. In fact I also have a problem with
> the wsdl:arrayType but I'm not sure if that can be overcome.
>
> Is there a way that I can set the targetNamespace of the document such
> that I can overcome this problem.
>
> <wsdl:definitions xmlns:typens="http://soap.amazon.com"
> xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
> xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
> xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
> xmlns="http://schemas.xmlsoap.org/wsdl/"
> targetNamespace="http://soap.amazon.com" name="AmazonSearch">
> <wsdl:types>
> <xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> targetNamespace="http://soap.amazon.com">
> <xsd:complexType name="ProductLineArray">
> <xsd:complexContent>
> <xsd:restriction base="soapenc:Array">
> <xsd:attribute ref="soapenc:arrayType"
> wsdl:arrayType="typens:ProductLine[]" />
> </xsd:restriction>
> </xsd:complexContent>
> </xsd:complexType>
> <xsd:complexType name="ProductLine">
> <xsd:all>
> <xsd:element name="Mode" type="xsd:string" minOccurs="0" />
> <xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
> />
> </xsd:all>
> .......................

--------------5BE33EF585AFEC61B91DDA83
Content-Type: text/plain; charset=us-ascii;
name="XSDWSDLResourceFactoryImpl.java"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="XSDWSDLResourceFactoryImpl.java"

/**
* <copyright>
*
* Copyright (c) 2002 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Common Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/cpl-v10.html
*
* Contributors:
* IBM - Initial API and implementation
*
* </copyright>
*
* %W%
* @version %I% %H%
*/
package org.eclipse.xsd.util;


import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.resource.impl.ResourceFactoryImpl;


/**
* The <b>Resource Factory</b> implementation for as WSDL resource.
*/
public class XSDWSDLResourceFactoryImpl extends ResourceFactoryImpl
{
/**
* Creates an instance.
*/
public XSDWSDLResourceFactoryImpl()
{
super();
}

/**
* Creates an {@link XSDResourceImpl}.
* @param uri the URI of the new resource.
* @param extent the extent of the new resource.
* @return an XSDResourceImpl.
*/
public Resource createResource(URI uri)
{
return new XSDWSDLResourceImpl(uri);
}
}

--------------5BE33EF585AFEC61B91DDA83
Content-Type: text/plain; charset=us-ascii;
name="XSDWSDLResourceImpl.java"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="XSDWSDLResourceImpl.java"

/**
* <copyright>
*
* Copyright (c) 2002 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Common Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/cpl-v10.html
*
* Contributors:
* IBM - Initial API and implementation
*
* </copyright>
*
* %W%
* @version %I% %H%
*/
package org.eclipse.xsd.util;


import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import org.apache.xml.serialize.OutputFormat;
import org.apache.xml.serialize.XMLSerializer;

import org.eclipse.core.runtime.IProgressMonitor;

import org.eclipse.emf.common.notify.Notification;

import org.eclipse.emf.common.util.URI;

import org.eclipse.emf.ecore.EObject;

import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.resource.ResourceSet;

import org.eclipse.emf.ecore.resource.impl.ResourceFactoryImpl;
import org.eclipse.emf.ecore.resource.impl.ResourceImpl;

import org.eclipse.xsd.*;
import org.eclipse.xsd.XSDDiagnostic;
import org.eclipse.xsd.XSDFactory;
import org.eclipse.xsd.XSDPackage;
import org.eclipse.xsd.XSDPlugin;
import org.eclipse.xsd.XSDSchema;

import org.eclipse.xsd.impl.XSDSchemaImpl;

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;

import org.xml.sax.EntityResolver;
import org.xml.sax.ErrorHandler;
import org.xml.sax.InputSource;
import org.xml.sax.Locator;
import org.xml.sax.SAXException;
import org.xml.sax.SAXParseException;

import org.xml.sax.helpers.DefaultHandler;


/**
* The <b>Resource</b> implementation for a WSDL resource.
*/
public class XSDWSDLResourceImpl extends XSDResourceImpl
{
protected Document document;

public XSDWSDLResourceImpl()
{
super();
}

public XSDWSDLResourceImpl(URI uri)
{
super(uri);
}

protected void doSave(OutputStream os, Map options) throws IOException
{
if (document != null)
{
doSerialize(os, document, options == null ? null : (String)options.get(XSD_ENCODING));
}
}

/**
* Loads a new {@link XSDResourceImpl} into the resource set.
* @param resourceSet the resource set to hold the new resource.
* @param uri the URI of the new resource.
* @param inputStream the contents of the new resource.
* @param options any options to influence loading behavior.
* @return a new XSDResourceImpl.
*/
protected void doLoad(InputStream inputStream, Map options) throws IOException
{
// This pattern avoids loading the IProgressMonitor class when there is no progress monitor.
// This is important for stand-alone execution to work correctly.
//
IProgressMonitor progressMonitor = null;
Object monitor = options == null ? null : options.get("XSD_PROGRESS_MONITOR");
if (monitor != null)
{
progressMonitor = (IProgressMonitor)monitor;
progressMonitor.setTaskName(XSDPlugin.INSTANCE.getString("_UI_ResourceLoad_progress "));
progressMonitor.subTask(getURI().toString());
}

XSDParser xsdParser = new XSDParser();
try
{
if (options != null && Boolean.TRUE.equals(options.get("XSD_TRACK_LOCATION")))
{
xsdParser.parse(inputStream);
document = xsdParser.getDocument();
}
else
{
document = getDocument(inputStream, xsdParser);
}

if (xsdParser.getEncoding() != null)
{
getDefaultSaveOptions().put(XSD_ENCODING, xsdParser.getEncoding());
}

if (document != null && document.getDocumentElement() != null)
{
ResourceSet globalResourceSet = XSDSchemaImpl.getGlobalResourceSet();
Object oldMonitor = globalResourceSet.getLoadOptions().get("XSD_PROGRESS_MONITOR ");
try
{
XSDSchemaImpl.getGlobalResourceSet().getLoadOptions().put("XSD_PROGRESS_MONITOR ", progressMonitor);
findSchemas(document.getDocumentElement());
}
finally
{
XSDSchemaImpl.getGlobalResourceSet().getLoadOptions().put("XSD_PROGRESS_MONITOR ", oldMonitor);
}
}
}
catch (Exception exception)
{
XSDPlugin.INSTANCE.log(exception);
}

for (Iterator i = getContents().iterator(); i.hasNext(); )
{
XSDSchema xsdSchema = (XSDSchema)i.next();
assignDiagnostics(xsdSchema, xsdParser.getDiagnostics());

for (Iterator diagnostics = xsdParser.getDiagnostics().iterator(); diagnostics.hasNext(); )
{
XSDDiagnostic xsdDiagnostic = (XSDDiagnostic)diagnostics.next();
switch (xsdDiagnostic.getSeverity().getValue())
{
case XSDDiagnosticSeverity.FATAL:
case XSDDiagnosticSeverity.ERROR:
{
getErrors().add(xsdDiagnostic);
break;
}
case XSDDiagnosticSeverity.WARNING:
case XSDDiagnosticSeverity.INFORMATION:
{
getWarnings().add(xsdDiagnostic);
break;
}
}
}
}


if (progressMonitor != null)
{
progressMonitor.worked(1);
}
}

protected void findSchemas(Element element)
{
if (XSDConstants.nodeType(element) == XSDConstants.SCHEMA_ELEMENT)
{
XSDSchema xsdSchema = XSDSchemaImpl.createSchema(element);
getContents().add(xsdSchema);
}
else
{
for (Node child = element.getFirstChild(); child != null; child = child.getNextSibling())
{
if (child instanceof Element)
{
findSchemas((Element)child);
}
}
}
}

public void attached(EObject eObject)
{
super.attached(eObject);

if (eObject instanceof XSDSchema)
{
((XSDSchema)eObject).setSchemaLocation(getURI().toString());
}
}
}

--------------5BE33EF585AFEC61B91DDA83--
Re: Parsing a WSDL with embedded xsd [message #580550 is a reply to message #31964] Sun, 09 November 2003 17:44 Go to previous message
Hayden Marchant is currently offline Hayden Marchant
Messages: 90
Registered: July 2009
Member
Ed,

Thanks for this utility - nice to know how resource factories can be used.
This doesn't really solve our problem since there are lines in the xsd,
like:

<xsd:restriction base="soapenc:Array">

Now, we don't have any explicit import statement for that namespace. All
there is, is the XML Namespace declaration at the head of the WSDL. I
could hack in, and simulate an import statement in the xsd body and then
parse but I was wondering if there was a nicer way.

Thanks

Ed Merks wrote:

> Hayden,

> I've been thinking about providing a convenience resource implementation for
> handling WSDL. Attached are XSDWSDLResourceFactoryImpl and
> XSDWSDLResourceImpl. If you register this factory against the "wsdl"
> extension, it will create a resource that has all the WSDL contained schemas
> in the getContents list. I've only test this a little bit...

> Hayden Marchant wrote:

> > I have a WSDL file that contains embedded XSD. The approach that I've been
> > taking is to take the xsd part and parse it as a seperate blob using
> > Eclipse XSD. This approach works for simple cases, but with the WSDL
> > below, where the targetNamespace of the file has a prefix called typens,
> > there is a complication parsing the xsd since it cannot resolve the
> > typens: prefix for the complex types. In fact I also have a problem with
> > the wsdl:arrayType but I'm not sure if that can be overcome.
> >
> > Is there a way that I can set the targetNamespace of the document such
> > that I can overcome this problem.
> >
> > <wsdl:definitions xmlns:typens="http://soap.amazon.com"
> > xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
> > xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
> > xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
> > xmlns="http://schemas.xmlsoap.org/wsdl/"
> > targetNamespace="http://soap.amazon.com" name="AmazonSearch">
> > <wsdl:types>
> > <xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > targetNamespace="http://soap.amazon.com">
> > <xsd:complexType name="ProductLineArray">
> > <xsd:complexContent>
> > <xsd:restriction base="soapenc:Array">
> > <xsd:attribute ref="soapenc:arrayType"
> > wsdl:arrayType="typens:ProductLine[]" />
> > </xsd:restriction>
> > </xsd:complexContent>
> > </xsd:complexType>
> > <xsd:complexType name="ProductLine">
> > <xsd:all>
> > <xsd:element name="Mode" type="xsd:string" minOccurs="0" />
> > <xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
> > />
> > </xsd:all>
> > .......................
Re: Parsing a WSDL with embedded xsd [message #580597 is a reply to message #32777] Mon, 10 November 2003 11:51 Go to previous message
Ed Merks is currently offline Ed Merks
Messages: 26141
Registered: July 2009
Senior Member
Hayden,

Soap encoding arrays are bit of a hack. It's most certainly invalid to reference
a name in a namespace that isn't explicitly imported, so to make a valid model,
you'll have to do something. You could build the model first, and then use the
model to add the import...


Hayden Marchant wrote:

> Ed,
>
> Thanks for this utility - nice to know how resource factories can be used.
> This doesn't really solve our problem since there are lines in the xsd,
> like:
>
> <xsd:restriction base="soapenc:Array">
>
> Now, we don't have any explicit import statement for that namespace. All
> there is, is the XML Namespace declaration at the head of the WSDL. I
> could hack in, and simulate an import statement in the xsd body and then
> parse but I was wondering if there was a nicer way.
>
> Thanks
>
> Ed Merks wrote:
>
> > Hayden,
>
> > I've been thinking about providing a convenience resource implementation for
> > handling WSDL. Attached are XSDWSDLResourceFactoryImpl and
> > XSDWSDLResourceImpl. If you register this factory against the "wsdl"
> > extension, it will create a resource that has all the WSDL contained schemas
> > in the getContents list. I've only test this a little bit...
>
> > Hayden Marchant wrote:
>
> > > I have a WSDL file that contains embedded XSD. The approach that I've been
> > > taking is to take the xsd part and parse it as a seperate blob using
> > > Eclipse XSD. This approach works for simple cases, but with the WSDL
> > > below, where the targetNamespace of the file has a prefix called typens,
> > > there is a complication parsing the xsd since it cannot resolve the
> > > typens: prefix for the complex types. In fact I also have a problem with
> > > the wsdl:arrayType but I'm not sure if that can be overcome.
> > >
> > > Is there a way that I can set the targetNamespace of the document such
> > > that I can overcome this problem.
> > >
> > > <wsdl:definitions xmlns:typens="http://soap.amazon.com"
> > > xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > > xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
> > > xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
> > > xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
> > > xmlns="http://schemas.xmlsoap.org/wsdl/"
> > > targetNamespace="http://soap.amazon.com" name="AmazonSearch">
> > > <wsdl:types>
> > > <xsd:schema xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
> > > targetNamespace="http://soap.amazon.com">
> > > <xsd:complexType name="ProductLineArray">
> > > <xsd:complexContent>
> > > <xsd:restriction base="soapenc:Array">
> > > <xsd:attribute ref="soapenc:arrayType"
> > > wsdl:arrayType="typens:ProductLine[]" />
> > > </xsd:restriction>
> > > </xsd:complexContent>
> > > </xsd:complexType>
> > > <xsd:complexType name="ProductLine">
> > > <xsd:all>
> > > <xsd:element name="Mode" type="xsd:string" minOccurs="0" />
> > > <xsd:element name="ProductInfo" type="typens:ProductInfo" minOccurs="0"
> > > />
> > > </xsd:all>
> > > .......................
Previous Topic:Maximum content for <all> ??
Next Topic:Initializing XSDSimpleTypeDefinition instances
Goto Forum:
  


Current Time: Sun Oct 26 08:51:25 GMT 2014

Powered by FUDForum. Page generated in 0.02693 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software