如何引用同一 WSDL 文件中定义的架构?
How do I reference a schema defined in the same WSDL file?
我得到了一个 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
包括?
请注意,这不是我应该做的事情不是问题。我知道如果我将元素定义移动到相同的架构定义中,问题就会消失。
WSDL 本身不是 XSD 模式语言,因此要通过 xs:include
从 XSD 文件中引用它,您必须摆脱周围的 wsdl:types
并且您必须将两个模式存储在单独的文件中(或者,因为它们无论如何都在同一个命名空间中,只需删除额外的 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 引用它们。如果您需要更频繁地执行此操作,您应该将其自动化。
对于嵌入在 WSDL 中的 XSD,考虑到您在问题中链接的答案,情况与您所看到的有所不同。
简答:
一个 无法在嵌套在 WSDL 类型部分中的模式之间创建 xsd:include 引用。
xsd:大多数 WSDL 处理器都支持导入。但是,您不 提供 schemaLocation 属性。实际上,它创建了一个悬空模式引用,WSDL 本身的行为类似于 XML 目录。
没有标准方法可以指向任意 XML 文件中的模式(除了 .XSD 文件格式,其中整个文件仅用于一个模式)。当然,XPointer 或类似的东西可能有用;但似乎没有人在 XSD 或 WSDL 处理器中为此实施解决方案。
具有相同命名空间的架构无法正常工作这一事实表明 WSDL 处理器的实现存在局限性。应该没有理由解决悬空导入问题,但没有理由解决带有目标命名空间 的模式。后一个亮点的原因是可以包含没有命名空间的模式and/or导入,这会导致歧义。
我得到了一个 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
包括?
请注意,这不是我应该做的事情不是问题。我知道如果我将元素定义移动到相同的架构定义中,问题就会消失。
WSDL 本身不是 XSD 模式语言,因此要通过 xs:include
从 XSD 文件中引用它,您必须摆脱周围的 wsdl:types
并且您必须将两个模式存储在单独的文件中(或者,因为它们无论如何都在同一个命名空间中,只需删除额外的 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 引用它们。如果您需要更频繁地执行此操作,您应该将其自动化。
对于嵌入在 WSDL 中的 XSD,考虑到您在问题中链接的答案,情况与您所看到的有所不同。
简答:
一个 无法在嵌套在 WSDL 类型部分中的模式之间创建 xsd:include 引用。
xsd:大多数 WSDL 处理器都支持导入。但是,您不 提供 schemaLocation 属性。实际上,它创建了一个悬空模式引用,WSDL 本身的行为类似于 XML 目录。
没有标准方法可以指向任意 XML 文件中的模式(除了 .XSD 文件格式,其中整个文件仅用于一个模式)。当然,XPointer 或类似的东西可能有用;但似乎没有人在 XSD 或 WSDL 处理器中为此实施解决方案。
具有相同命名空间的架构无法正常工作这一事实表明 WSDL 处理器的实现存在局限性。应该没有理由解决悬空导入问题,但没有理由解决带有目标命名空间 的模式。后一个亮点的原因是可以包含没有命名空间的模式and/or导入,这会导致歧义。