【问题标题】:How we can add xpath information in schematron error message output我们如何在 schematron 错误消息输出中添加 xpath 信息
【发布时间】:2018-08-27 13:11:07
【问题描述】:

我在 MarkLogic 中使用 schematron API 来验证 XML 文档。下面是sn-p的代码供参考。

xquery version "1.0-ml";

import module namespace sch = "http://marklogic.com/validate" at 
"/MarkLogic/appservices/utils/validate.xqy";

import module namespace transform = "http://marklogic.com/transform" at "/MarkLogic/appservices/utils/transform.xqy";

declare namespace xsl = "http://www.w3.org/1999/XSL/not-Transform";

declare namespace iso = "http://purl.oclc.org/dsdl/schematron";


let $document :=
      document{
        <book xmlns="http://docbook.org/ns/docbook">
              <title>Some Title</title>
              <chapter>
              <para>...</para>
              </chapter>
        </book>
      }

let $schema := 
    <s:schema xmlns:s="http://purl.oclc.org/dsdl/schematron"
              xmlns:db="http://docbook.org/ns/docbook">
       <s:ns prefix="db" uri="http://docbook.org/ns/docbook"/>
       <s:pattern name="Glossary 'firstterm' type constraint">
          <s:rule context="db:chapter">
             <s:assert test="db:title">Chapter should contain title</s:assert>
          </s:rule>
       </s:pattern>
     </s:schema>
return
 sch:schematron($document, $schema)

谁能帮我获取上下文节点的 XPath 信息以及 schematron 错误消息输出。

【问题讨论】:

  • 您可以尝试基于 XSLT 的 schematron 验证,而不是使用 ML schematron 验证 API,通过它您可以轻松获得 XPATH。看看 SVRL

标签: xquery xslt-2.0 marklogic schematron


【解决方案1】:

这是我认为您所要求的代码。

如果你想要一个项目的 xpath,你可以使用xdmp:path。为了获得整个文档的 xpath,您只需要遍历树,这就是递归函数 local:getXpathDeep 正在做的事情。您可以更改我使用的string-join 的输出格式,它只是让我更容易阅读。我创建了一个 XML 输出来将 schematron 结果和 XPath 放入其中,但您可以根据需要返回一个序列或将其放入映射中。

xquery version "1.0-ml";

import module namespace sch = "http://marklogic.com/validate" at 
"/MarkLogic/appservices/utils/validate.xqy";

import module namespace transform = "http://marklogic.com/transform" at "/MarkLogic/appservices/utils/transform.xqy";

declare namespace xsl = "http://www.w3.org/1999/XSL/not-Transform";

declare namespace iso = "http://purl.oclc.org/dsdl/schematron";

declare function local:getXpathDeep($node){
  (
    xdmp:path($node), 
    if (fn:exists($node/*)) then (
      local:getXpathDeep($node/*)
    ) else ()
  )
};

let $document :=
      document{
        <book xmlns="http://docbook.org/ns/docbook">
              <title>Some Title</title>
              <chapter>
              <para>...</para>
              </chapter>
        </book>
      }

let $schema := 
    <s:schema xmlns:s="http://purl.oclc.org/dsdl/schematron"
              xmlns:db="http://docbook.org/ns/docbook">
       <s:ns prefix="db" uri="http://docbook.org/ns/docbook"/>
       <s:pattern name="Glossary 'firstterm' type constraint">
          <s:rule context="db:chapter">
             <s:assert test="db:title">Chapter should contain title</s:assert>
          </s:rule>
       </s:pattern>
     </s:schema>
return
  <result>
    <contextNodeXpath>{fn:string-join(local:getXpathDeep($document), " 
    " )}</contextNodeXpath>
    <schematronOutPut>{sch:schematron($document, $schema)}</schematronOutPut>
  </result>

【讨论】:

    【解决方案2】:

    该特定 Schematron 模块相当有限,并且不提供从报告或失败断言返回上下文节点的 XPath 的方法。

    标准 Schematron SVRL 输出确实包含触发失败断言或报告的项目的 XPath。

    Norm Walsh 发布了ML-Schematron module,它使用 Schematron 样式表将 Schematron 模式的编译包装到 XSLT 中,并随后执行编译后的 XSLT 以生成 SVRL 报告。

    您可以调整您的模块以使用它(在安装它和模块数据库中的standard Schematron XSLT files 之后):

    xquery version "1.0-ml";
    declare namespace svrl="http://purl.oclc.org/dsdl/svrl";
    import module namespace sch="http://marklogic.com/schematron" at "/schematron.xqy";
    
    let $document :=
          document{
            <book xmlns="http://docbook.org/ns/docbook">
                  <title>Some Title</title>
                  <chapter>
                  <para>...</para>
                  </chapter>
            </book>
          }
    
    let $schema := 
        <s:schema xmlns:s="http://purl.oclc.org/dsdl/schematron"
                  xmlns:db="http://docbook.org/ns/docbook">
           <s:ns prefix="db" uri="http://docbook.org/ns/docbook"/>
           <s:pattern name="Glossary 'firstterm' type constraint">
              <s:rule context="db:chapter">
                 <s:assert test="db:title">Chapter should contain title</s:assert>
              </s:rule>
           </s:pattern>
         </s:schema>
    
    return
      sch:validate-document($document, $schema)
    

    它会生成以下 SVRL 报告,其中包括位置属性 /*[local-name()='book']/*[local-name()='chapter'] 中的 XPath:

    <svrl:schematron-output title="" schemaVersion="" xmlns:schold="http://www.ascc.net/xml/schematron" 
    xmlns:iso="http://purl.oclc.org/dsdl/schematron" xmlns:xhtml="http://www.w3.org/1999/xhtml" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns:db="http://docbook.org/ns/docbook" xmlns:axsl="http://www.w3.org/1999/XSL/TransformAlias" 
    xmlns:svrl="http://purl.oclc.org/dsdl/svrl">
      <!---->
      <svrl:ns-prefix-in-attribute-values uri="http://docbook.org/ns/docbook" prefix="db"/>
      <svrl:active-pattern document=""/>
      <svrl:fired-rule context="db:chapter"/>
      <svrl:failed-assert test="db:title" location="/*[local-name()='book']/*[local-name()='chapter']">
        <svrl:text>Chapter should contain title</svrl:text>
      </svrl:failed-assert>
    </svrl:schematron-output>
    

    【讨论】:

      猜你喜欢
      • 2016-03-30
      • 1970-01-01
      • 2021-10-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-01-19
      • 1970-01-01
      • 2011-02-18
      相关资源
      最近更新 更多