【问题标题】:How to parse HTML using XPath with Saxon-HE in command line?如何在命令行中使用 XPath 和 Saxon-HE 解析 HTML?
【发布时间】:2015-03-05 09:21:30
【问题描述】:

我使用的是 saxon HE 9.6,它非常适合在解析格式良好的 XML 文件时使用 XPath 3。

但我想知道如何将 expath-http-client(或任何其他工作解决方案)与 Saxon 结合起来,以解析 realLife©®™(可能已损坏)HTML。 (Java 不是我更好的技能)。

我在谷歌上搜索了很多小时,但没有任何可行的解决方案。我试过类似的东西:

xquery_file.xsl:

xquery version "1.0";

declare namespace http="http://expath.org/ns/http-client";

let $url := 'http://stackoverflow.com'
let $response := http:send-request(
   <http:request href="{$url}" method="get"/>
) return
    <echo-results>
        {$response}
    </echo-results>

Shell 命令取自 expath-http-client-saxon-0.10.0 的自述文件

saxon --repo /usr/share/java/expath/repo -xsl:sample/simple-get.xsl -it:main

saxon --repo /usr/share/java/expath/repo -xsl:xquery_file.xsl -it:main

没有成功。我得到:Transformation failed: Unknown configuration property http://saxon.sf.net/feature/repo

我最理想的做法是从命令行直接查询 URL,无需 XQuery 文件而是 XPath 表达式(如果可能)。我很确定一些 XML/那里的 Java/XPath 大师有我正在寻找的解决方案。

/usr/share/java/expath/repo 包含:

/usr/share/java/expath/repo
├── expath-http-client-saxon-0.10.0
│   ├── cxan.xml
│   ├── expath-http-client-saxon
│   │   ├── jar
│   │   │   ├── expath-http-client-java.jar
│   │   │   └── expath-http-client-saxon.jar
│   │   ├── lib
│   │   │   ├── apache-mime4j-0.6.jar
│   │   │   ├── commons-codec-1.4.jar
│   │   │   ├── commons-logging-1.1.1.jar
│   │   │   ├── httpclient-4.0.1.jar
│   │   │   ├── httpcore-4.0.1.jar
│   │   │   └── tagsoup-1.2.jar
│   │   ├── xq
│   │   │   └── expath-http-client-saxon.xq
│   │   └── xsl
│   │       └── expath-http-client-saxon.xsl
│   ├── expath-pkg.xml
│   └── saxon.xml
└── hello-1.1
    ├── expath-pkg.xml
    └── hello
        ├── hello.xq
        └── hello.xsl

编辑:

我的最佳尝试(基于 linux 的解决方案)

java -classpath "./tagsoup-1.2.jar:./saxon9he.jar" \
    net.sf.saxon.Query \
   -x:org.ccil.cowan.tagsoup.Parser \
   -s:myrealLife.html \
   -qs://*:body

这项工作,但现在我试图弄清楚如何设置default namespace能够通过示例//a直接查询

编辑 2

我根据这个帖子创建了一个完整的github项目,查看https://github.com/sputnick-dev/saxon-lint

【问题讨论】:

  • XML 解析器不适合解析 HTML,因为 HTML 不一定是有效的 XML。
  • 实际上,许多 XML 解析都包含或可以与 HTML tidier 耦合,这将产生 HTML 的有效 XML 表示。
  • “HTML 不需要是有效的 XML”——更糟糕的是,HTML 甚至不需要是格式正确的 XML。
  • 也许有命名空间?你试过-qs://*:body

标签: java xml xpath xquery saxon


【解决方案1】:

我认为您不需要任何 HTTP 客户端。您可以使用 doc() 函数读取文件,或者将其作为主要输入文档提供,前提是您将其配置为使用 HTML SAX 解析器而不是 XML 解析器进行解析。如果您将 John Cowan 的 TagSoup 放在类路径中,则使用

调用 Saxon
-x:org.ccil.cowan.tagsoup.Parser -s:myrealLife.html

应该可以解决问题。

我认为你也可以使用validator.nu,它使用HTML5 比TagSoup 更先进,但我自己没有尝试过。

【讨论】:

    【解决方案2】:

    如果您查看 EXPath HTTP 客户端的文档,您会发现如果您使用它检索 HTML,并且服务器以 HTML Internet 媒体类型进行响应,那么 HTML 将自动为您整理成有效的 XML ,请看这里http://expath.org/spec/http-client#d2e517

    因此,您无需编写任何 Java 代码即可实现您的目标。

    您的 XQuery 不正确,因为您尝试使用 eXist-db 的 HTTP 客户端,而您声明要使用 EXPath HTTP 客户端。所以你应该把你的 XQuery 改成这样:

    xquery version "1.0";
    
    declare namespace http="http://expath.org/ns/http-client";
    
    let $url := 'http://stackoverflow.com'
    let $response := http:send-request(
       <http:request href="{$url}" method="get"/>
    ) return
        <echo-results>
            {$response}
        </echo-results>
    

    但是,您还需要说服 Saxon 加载和使用 EXPath HTTP 客户端模块,默认情况下,Saxon 不支持 HTTP 客户端,请参阅http://saxonica.com/documentation/index.html#!functions

    您可以在此处找到 Saxon 的 EXPath HTTP 客户端实现:https://code.google.com/p/expath-http-client/downloads/list,如果您下载最新的 Zip 文件,里面有一个 README 文件,它告诉您如何在 Saxon 中使用它。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-06-11
      • 1970-01-01
      • 2021-08-04
      相关资源
      最近更新 更多