1

我通过 dbms_xmlschema.registerschema() 包子程序将模式注册到 Oracle XMLDB。

然后我从 user_xml_schemas 中选择注册的模式。

模式返回正常,但 Oracle 已将各种 Oracle 相关信息插入到模式中。这是一个示例插入(这只是其中之一):

xmlns:oraxdb="http://xmlns.oracle.com/xdb" oraxdb:storeVarrayAsTable="true" oraxdb:flags="2105633" oraxdb:schemaURL="mySchema.xsd" oraxdb:schemaOwner="bob" oraxdb:numProps ="22"

这与我在数据库中的使用无关,但是我需要向数据库外部的消费者提供架构,而 Oracle 注释只是让我的目标外部消费者感到困惑。

我想要的是能够使用我的“发明”dbms_xmlschema_annotate 来实现类似以下代码的功能。stripAllOracleAnnotations子程序:

begin
  select dbms_xmlschema_annotate.stripAllOracleAnnotations(schema)
  into vMyOriginalPreRegisteredSchema
  from user_xml_schemas;
  ...
end;

所以我可以向外部消费者提供vMyOriginalPreRegisteredSchema 。

我已经搜索过,但找不到任何可以从 xml db 返回“原始、干净”模式的东西。

任何帮助将不胜感激。

注意:我尝试使用 XSL 转换来去除 Oracle 注释,但是虽然我创建的 XSL 文件在 XMLSpy 中完美运行,但 Oracle (18c) 完成了转换而没有错误,但返回的结果完全不正确。我通过 xmltransform() 和 xmltype.transform() 进行了测试。我只能假设这是因为 Oracle 在内部解释 oraxdb: 节点并“做自己的事情”。

4

1 回答 1

0

虽然这不是我的首选方法,因为通过正则表达式捕获所有情况可能容易出错,但以下似乎可行,并且是我目前能找到的实现我需要的唯一方法:

select regexp_replace(s.schema.getClobVal()
                     ,'( oraxdb:.*?= *".*?"| xmlns:oraxdb="http://xmlns.oracle.com/xdb")',''
                     )
from user_xml_schemas s
where s.schema_url = 'my schema XDB URL';

注意:正如我在问题编辑中所解释的,虽然以下 XSL 转换在 XMLspy 中完美运行,并且在正常情况下是我的首选,但它通过 Oracle xmltransform() 或 xmltype.transform() 产生不正确的输出,因为 Oracle 似乎污染了输出在带有内部注释的转换中:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:xml="http://www.w3.org/XML/1998/namespace"
xmlns:oraxdb="http://xmlns.oracle.com/xdb"
exclude-result-prefixes="oraxdb"
>
    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

    <!-- copy all elements -->
    <xsl:template match="*" priority="-1">
        <xsl:element name="{name()}">
            <xsl:copy-of select="@*[substring(name(),1,7) != 'oraxdb:']"/>
            <xsl:apply-templates/>
        </xsl:element>
    </xsl:template>

    <!-- Copy all other nodes -->
    <xsl:template match="node()|@*" priority="-2">
        <xsl:copy />
    </xsl:template>

</xsl:stylesheet>

上面的 XSL 方法使用了从 XSLT 样式表中删除命名空间声明和 XSLT(因为 <xsl:copy> 不适用于exclude-result-prefixes删除 xmlns:oraxdb 命名空间声明本身)。

于 2019-07-22T10:17:00.340 回答