在exist-db 中编写一个支持多种输出格式的XQuery 脚本
Posted
技术标签:
【中文标题】在exist-db 中编写一个支持多种输出格式的XQuery 脚本【英文标题】:Writing one XQuery script in exist-db with support for multiple output formats 【发布时间】:2014-08-22 22:25:40 【问题描述】:这是
的后续问题Getting hold of tag content in XQuery 3.0 (exist-db)
假设这样的 xquery 脚本应该能够根据类似的查询参数以 XML、JSON 或 html 格式返回结果
http://host/exist/rest/db/myscript.xql?mode=xml|html|json
我知道如何从 XML 更改序列化程序 -> JSON 以及如何应用 使用 transform:transform() 进行 XSLT 转换。
为结果封装 XML 生成然后根据请求参数将其转换为一种输出格式的最佳方法是什么?
xquery version "3.0";
module namespace services = "http://my/services";
import module namespace transform = "http://exist-db.org/xquery/transform";
declare namespace rest = "http://exquery.org/ns/restxq";
declare namespace output = "http://www.w3.org/2010/xslt-xquery-serialization";
declare
%rest:GET
%rest:path("/data.html")
%output:media-type("text/html")
%output:method("html5")
function services:home()
transform:transform(services:example1(), doc("/db/my-xml-to-html.xslt"), ())
;
declare
%rest:GET
%rest:path("/data.json")
%rest:produces("application/json")
%output:method("json")
function services:home-json()
services:example1()
;
declare
%rest:GET
%rest:path("/data.xml")
%rest:produces("application/xml")
function services:home-xml()
services:example1()
;
declare
%private
function services:example1()
<some>
<data>hello world</data>
</some>
;
【问题讨论】:
【参考方案1】:我建议看一下 eXist 中的 RESTXQ,因为这使您可以根据内容协商或任何其他 HTTP 参数或标头轻松控制结果格式。例如使用内容协商来生成 XML、JSON 和 HTML 表现形式:
xquery version "3.0";
module namespace services = "http://my/services";
import module namespace transform = "http://exist-db.org/xquery/transform";
declare namespace rest = "http://exquery.org/ns/restxq";
declare namespace output = "http://www.w3.org/2010/xslt-xquery-serialization";
declare
%rest:GET
%rest:path("/data")
%rest:produces("text/html")
%output:method("html5")
function services:home()
transform:transform(services:example1(), doc("/db/my-xml-to-html.xslt"), ())
;
declare
%rest:GET
%rest:path("/data")
%rest:produces("application/json")
%output:method("json")
function services:home-json()
services:example1()
;
declare
%rest:GET
%rest:path("/data")
%rest:produces("application/xml")
function services:home-xml()
services:example1()
;
declare
%private
function services:example1()
<some>
<data>here</data>
</some>
;
【讨论】:
如果您想基于 URI 进行内容协商,而不是像上面那样使用Accept
HTTP 标头,您可以改为执行类似的操作 - 声明 %rest:GET %rest:path(" /data.html") %output:method("html5") %output:media-type("text/html") function services:home() (: etc... :)
我从配置中得出,上面脚本的位置无关紧要。在这种情况下,对host:port//exist/rest/db/data.html(或原始代码的 /data)的 HTTP GET 应该返回 exist/restxq
,所以你的 URL 看起来像 http://host:port/exist/restxq/data
不直接..查看我上面的 RESTXQ 代码的更新。调用host.port/exist/restxq/data.html 给我:HTTP ERROR 405 访问/exist/restxq/data.html 时出现问题。原因:此 URL 不支持 HTTP 方法 GET
@AndreasJung 我认为理想情况下您应该为此提出一个新问题,因为现在您的问题没有多大意义。但是,您应该查阅 restxq 日志文件以了解您的查询是否被添加到注册表中。以上是关于在exist-db 中编写一个支持多种输出格式的XQuery 脚本的主要内容,如果未能解决你的问题,请参考以下文章