我有一个wsdl文件,为同一个命名空间定义了两个模式,如下所示:
<wsdl:types>
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://example.com/payments"
attributeFormDefault="unqualified" elementFormDefault="qualified"
targetNamespace="http://example.com/payments">
<xsd:complexType name="TestType">
<xsd:sequence>
<xsd:element name="Version" type="xsd:string" />
</xsd:sequence>
</xsd:complexType>
</xsd:schema>
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://example.com/payments"
attributeFormDefault="unqualified" elementFormDefault="qualified"
targetNamespace="http://example.com/payments">
<xsd:element name="TestRequest">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="Header" type="TestType"/>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
</xsd:schema>
</wsdl:types>
无法从TestType
引用TestRequest
。我找到了几个answers,通过xsd:include
显示你是如何为不同的文件做的那样(因为我使用相同的targetNamespace
),但我很茫然如何给schemaLocation
包括?
请注意,这不是我应该做的事情不是问题。我知道如果我将元素定义移动到相同的模式定义中,问题就会消失。
答案 0 :(得分:2)
对于嵌入在WSDL中的XSD,考虑到您在问题中链接的答案,事情与您所看到的不同。
简答:
一个无法在嵌套在WSDL类型部分中的模式之间创建xsd:include references 。
xsd:大多数WSDL处理器都支持import。但是,您不提供schemaLocation属性。实际上,它创建了一个悬空模式引用,其中WSDL本身的行为类似于XML目录。
没有标准的方法指向任意XML文件中的模式(除了.XSD文件格式,其中整个文件仅用于一个模式)。当然,XPointer或类似的东西可能有用;但似乎没有人在XSD或WSDL处理器中实现此解决方案。
具有相同命名空间的模式不起作用的事实表明WSDL处理器的实现存在限制。应该没有理由解决悬挂导入,但不能解析具有目标命名空间的模式。后一个亮点的原因是可以包含和/或导入没有命名空间的模式,这会导致歧义。
答案 1 :(得分:1)
WSDL本身不是XSD Schema语言,所以要从XSD文件通过xs:include
引用它,你必须摆脱周围的wsdl:types
,你必须存储两个架构和#39 ; s在单独的文件中(或者,因为它们在同一个命名空间中,只需删除额外的xsd:schema
元素,但不删除其内容)。
你可以用一个简单的XSLT来做到这一点(为简洁起见,删除了根注释,确保声明相关的命名空间):
<xsl:template match="node() | @*">
<xsl:copy>
<xsl:apply-templates select="node() | @*" />
</xsl:copy>
</xsl:template>
<xsl:template match="wsdl:types">
<xsl:apply-templates select="xsd:schema[1]" />
</xsl:template>
<xsl:template match="xsd:schema">
<xsl:copy>
<xsl:copy-of select="@*" />
<xsl:apply-templates />
<xsl:apply-templates select="following-sibling::xsd:schema/*" />
</xsl:copy>
</xsl:template>
如果这是一次性任务,那么您只需针对WSDL运行一次,保存结果并通过相对文件URI引用它们。如果您需要更频繁地执行此操作,则应该自动执行此操作。