================================= XML对于SQL的限制和符合性/XML ================================= .. container:: sect1 :name: XML-LIMITS-CONFORMANCE .. container:: titlepage .. container:: .. container:: .. rubric:: XML对于SQL的限制和符合性/XML :name: xml对于sql的限制和符合性xml :class: title .. container:: toc ISO/IEC 9075-14中与XML相关的规范进行了重大修订 (SQL/XML)与SQL:2006一起被引入. OushuDB's 的XML数据类型和相关函数的实现基本上沿用了2003年的早期版本。有一些借鉴了后来的版本。 特别是: .. container:: itemizedlist - 现行标准提供了一系列可扩展标记语言数据类型,其中将“文档”或“内容”保存在非类型或XML Schema类型的变体,以及类型\ ``XML(SEQUENCE)``\ 用于保存任意的XML内容片段。 OushuDB提供了一个单一的\ ``xml``\ 类型,可以容纳“文档”或“内容”。 没有相应的标准的“序列”类型。 - OushuDB提供了两个函数在SQL:2006中引入的,但是在变体中,使用的是XPath 1.0语言,而不是在标准中为其指定的XML查询。 本节介绍了一些你可能会遇到的差异。 .. container:: sect2 :name: FUNCTIONS-XML-LIMITS-XPATH1 .. container:: titlepage .. container:: .. container:: .. rubric:: 查询只限于XPath 1.0 :name: 查询只限于xpath-1.0 :class: title OushuDB-指定的函数 ``xpath()`` 和 ``xpath_exists()``\ 使用XPath语言查询XML文档。 OushuDB也提供了标准函数中的XPath-only变体\ ``XMLEXISTS``\ 和 ``XMLTABLE``, 其中正式采用XQuery语言。所有这些函数 OushuDB都依赖于libxml2 库,而这个库仅在XPath 1.0中提供。 在XQuery语言和XPath 2.0及以后的版本之间有很强的联系:任何语法上有效的表达式,在这两个版本中都能成功地执行,都会产生相同的结果(对于包含数字字符引用或预定义的实体引用的表达式会略有不同, XQuery会用相应的字符替换,而 XPath则不会。) 但这些语言和XPath 1.0之间没有这种联系,它是一种较早的语言,在很多方面都有区别。 有两类限制需要记住:一是对SQL标准中指定的函数从XQuery到XPath的限制,二是对标准和OushuDB特定函数XPath的限制是1.0版本 。 .. container:: sect3 :name: id-1.11.5.13.5.5 .. container:: titlepage .. container:: .. container:: .. rubric:: XQuery到XPath的限制 :name: xquery到xpath的限制 :class: title 除了XPath的特性之外,XQuery的特性还包括: .. container:: itemizedlist - 除了所有可能的XPath值之外,XQuery表达式还可以构造和返回新的XML节点。 XPath 可以创建和返回原子类型(数字、字符串等)的值,但只能返回作为表达式输入的文档中已经存在的XML节点。 - XQuery有用于迭代、排序和分组的控制结构。 - XQuery允许声明和使用局部函数。 最近的 XPath 版本开始提供与这些功能重叠的功能(例如函数式的 ``for-each``\ 和\ ``sort``\ ,匿名函数,以及 ``parse-xml``\ 从字符串中创建节点的\ ``parse-xml``\ ),但这些功能在 XPath 3.0 之前是不具备的。 .. container:: sect3 :name: XML-XPATH-1-SPECIFICS .. container:: titlepage .. container:: .. container:: .. rubric:: 对XPath的限制为1.0 :name: 对xpath的限制为1.0 :class: title 对于熟悉XQuery和XPath 2.0或更高版本的开发人员来说,XPath 1.0带来了许多不同的地方,需要解决的是: .. container:: itemizedlist - 一个XQuery/XPath表达式的基本类型,即 ``sequence``\ ,它可以包含XML节点、原子值或两者,在XPath 1.0中不存在。一个1.0表达式只能产生一个节点集(包含0个或更多的XML节点),或者一个原子值。 - 与XQuery/XPath序列不同的是,XPath 1.0节点集没有保证顺序,和任何集一样,不允许同一个项目多次出现。 .. note:: .. rubric:: 注意 :name: 注意 :class: title libxml2库似乎总是将节点集返回到OushuDB的节点集,其成员在输入文档中的相对顺序是一样的。 它的文档并没有承诺这种行为,而且XPath 1.0表达式不能控制它。 - 虽然XQuery/XPath提供了XML Schema中定义的所有类型和许多操作符和函数,但XPath 1.0只有节点集和三种原子类型\ ``boolean``\ 、\ ``double``\ 和\ ``string``\ 。 - XPath 1.0没有条件运算符。一个XQuery/XPath表达式,如\ ``if ( hat ) then hat/@size else "no hat"``\ 没有XPath 1.0的等价物。 - XPath 1.0没有对字符串进行排序比较运算符。\ ``"cat" < "dog"``\ 和\ ``"cat" > "dog"``\ 都是假的,因为每一个都是两个\ ``NaN``\ 的数值比较。相比之下,\ ``=``\ 和\ ``!!=``\ 确实将字符串作为字符串进行比较。 - XPath 1.0模糊了XQuery/XPath定义的\ *值比较*\ 和\ *一般比较*\ 之间的区别。 ``sale/@hatsize = 7``\ 和\ ``sale/@customer = "alice"``\ 都是存在的量化比较,如果有任何\ ``sale``\ 属性的给定值,则为真。但\ ``sale/@taxable = false()``\ 是与整个节点集的\ *有效布尔值*\ 的值比较。只有当没有\ ``sale``\ 有一个\ ``taxable``\ 属性时,它才是真值。 - 在XQuery/XPath数据模型中,一个\ *文档节点*\ 既可以有文档形式(即正好有一个顶层元素,只有注释和处理指令以外的注释和处理指令),也可以有内容形式(放宽了这些限制)。在XPath 1.0中,它的等价物是\ *根节点*\ ,只能是文档形式。这也是\ ``xml``\ 的值被作为 上下文项到任何 OushuDB的上下文项 基于XPath的函数必须是以文档形式出现。 这里强调的区别并不是全部。在XQuery和XPath的2.0及以后的版本中,有一个XPath 1.0的兼容性模式,W3C列出的 `函数库变化 `__\ 和\ `语言变化 `__\ 在该模式下应用的列表提供了一个更完整(但仍然不是详尽的)的差异说明。 兼容性模式不能使后来的语言与XPath 1.0完全等同。 .. container:: sect3 :name: FUNCTIONS-XML-LIMITS-CASTS .. container:: titlepage .. container:: .. container:: .. rubric:: SQL和XML数据类型和值之间的映射 :name: sql和xml数据类型和值之间的映射 :class: title 在SQL:2006及以后的版本中,标准SQL数据类型和XML Schema类型之间的转换方向都被精确地指定了。但是,这些规则都是用XQuery/XPath的类型和语义来表示的,对于XPath 1.0的不同数据模型没有直接应用。 当OushuDB将SQL数据值映射到XML(如\ ``xmlelement``\ ),或XML映射到SQL(如输出 ``xmltable``\ 的列),除了少数情况下的 特殊处理,OushuDB只需假定 XML 数据类型的 XPath 1.0 字符串形式将被视为有效的文本输入形式的SQL数据类型,反之。 该规则的优点是简单,同时对许多数据类型来说,产生的结果与标准中规定的映射类似。 如果与其他系统的互操作性是一个问题,对于某些数据类型,可能需要使用数据类型格式化函数(如\ `数据类型格式化函数 `__\ 中的函数)来生成标准映射。 .. container:: sect2 :name: FUNCTIONS-XML-LIMITS-POSTGRESQL .. container:: titlepage .. container:: .. container:: .. rubric:: 实现中的偶然限制 :name: 实现中的偶然限制 :class: title 本节涉及的限制并不是libxml2库所固有的,而是适用于OushuDB中的当前实现。 .. container:: sect3 :name: id-1.11.5.13.6.3 .. container:: titlepage .. container:: .. container:: .. rubric:: 仅支持\ ``by VALUE``\ 传递机制 :name: 仅支持by-value传递机制 :class: title SQL标准定义了两种\ *传递机制*\ ,适用于从SQL向XML函数传递XML参数或接收结果时。\ ``BY REF``\ ,其中一个特定的XML 值保留其节点身份,以及\ ``BY VALUE``\ ,其中传递XML的内容,但不保留节点身份。可以在参数列表之前指定,作为所有参数的默认机制,也可以在任何参数之后指定,以覆盖默认机制。 为了说明区别,如果\ *``x``*\ 是一个XML值,那么在SQL:2006环境下的这两个查询将分别产生true和false。 .. code:: programlisting SELECT XMLQUERY('$a is $b' PASSING BY REF x AS a, x AS b NULL ON EMPTY); SELECT XMLQUERY('$a is $b' PASSING BY VALUE x AS a, x AS b NULL ON EMPTY); OushuDB将在\ ``XMLEXISTS``\ 或\ ``XMLTABLE``\ 构造中接受\ ``BY VALUE``\ 或\ ``BY REF``\ ,但它会忽略它们。 ``xml``\ 数据类型持有一个字符串的序列化表示,因此没有节点标识需要保留,并且传递总是有效的\ ``BY VALUE``\ 。 .. container:: sect3 :name: id-1.11.5.13.6.4 .. container:: titlepage .. container:: .. container:: .. rubric:: 不能将命名的参数传递到查询中 :name: 不能将命名的参数传递到查询中 :class: title 基于 XPath 的函数支持传递一个参数作为 XPath 表达式的上下文项,但不支持传递额外的值作为命名参数提供给表达式。 .. container:: sect3 :name: id-1.11.5.13.6.5 .. container:: titlepage .. container:: .. container:: .. rubric:: 无 ``XML(SEQUENCE)``\ 类型 :name: 无-xmlsequence类型 :class: title OushuDB ``xml``\ 数据类型只能保存一个值,在\ ``DOCUMENT``\ 或 ``CONTENT``\ 形式。 一个XQuery/XPath表达式上下文项必须是一个单一的XML节点或原子值,但XPath 1.0进一步限制它只能是一个XML节点,并且没有允许\ ``CONTENT``\ 的节点类型。 最终的结果是,一个完善的\ ``DOCUMENT``\ 是OushuDB可以作为XPath上下文项提供的唯一形式的XML值。