如何在 xmlstarlet 中声明 XPath 命名空间? [英] How to declare XPath namespaces in xmlstarlet?

查看:27
本文介绍了如何在 xmlstarlet 中声明 XPath 命名空间?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是 xmlstarlet 的新手,所以希望这个答案很简单.

I am new to xmlstarlet so hoping this answer is a simple one.

我正在编写一个脚本来从命令行修改 Inkscape SVG 文件.我选择了工具xmlstarlet.

I am writing a script to modify Inkscape SVG files from the command line. I chose the tool xmlstarlet.

在测试文件上测试命令语法后,我在真正的 SVG 文件上遇到了问题.我认为命名空间的使用让我失望.

After testing the command syntax on test files, I am having trouble on the real SVG files. I think the use of namespaces is throwing me off.

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->    
<svg
   xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
   xmlns:dc="http://purl.org/dc/elements/1.1/"
   xmlns:cc="http://creativecommons.org/ns#"
   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
   xmlns:svg="http://www.w3.org/2000/svg"
   xmlns="http://www.w3.org/2000/svg"
   xmlns:xlink="http://www.w3.org/1999/xlink"
   xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
   xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
   width="603"
   height="1000"
   viewBox="0 0 159.54375 264.58334"
   version="1.1"
   id="svg8"
   inkscape:version="0.92.1 r"
   sodipodi:docname="test.svg"
   inkscape:export-filename="/home/user/dev/inkscape/test/1.png"
   inkscape:export-xdpi="96"
   inkscape:export-ydpi="96">
  <defs
     id="defs2">
    <linearGradient
       inkscape:collect="always"
       id="linearGradient6204">
      <stop
         style="stop-color:#8f1a22;stop-opacity:1;"
         offset="0"
         id="stop6200" />
      <stop
         style="stop-color:#8f1a22;stop-opacity:0;"
         offset="1"
         id="stop6202" />
    </linearGradient>
  </defs>
</svg>

我想把Gradient6204改成Gradient9999.

I want to change Gradient6204 to Gradient9999.

我写了这个命令,它不起作用(只返回原始文件).

I wrote this command, which does not work (just returns the original file).

xmlstarlet ed -u "/svg/defs/linearGradient[@id='linearGradient6204']/@id" -v 'linearGradient9999' text.txt

我也再次尝试,使用 -N 添加命名空间,但没有成功.我发现如果我删除该行:

I also tried again, adding the namespaces with -N but no luck. I found that if I delete the line:

xmlns="http://www.w3.org/2000/svg"

从文件然后我上面写的命令有效.

from the file then the command I wrote above works.

按照我描述的方式更新上述 SVG 文件的正确语法是什么?

What is the proper syntax for updating the SVG file above in the way I described?

推荐答案

显式命名空间声明

添加 -N s=http://www.w3.org/2000/svg 然后使用 s: 命名空间前缀有效:

Explicit Namespace Declaration

Adding -N s=http://www.w3.org/2000/svg and then using the s: namespace prefix works:

xmlstarlet ed  -N s=http://www.w3.org/2000/svg -u "/s:svg/s:defs/s:linearGradient[@id='linearGradient6204']/@id" -v 'linearGradient9999' text.txt

<小时>

默认命名空间的隐式声明

XMLStarlet v1.2.1 开始,可以通过使用 的自动绑定来避免默认命名空间的显式命令行定义(例如 OP 的 SVG 文件的情况)_ 到默认命名空间:


Implicit Declaration of Default Namespace

Starting with XMLStarlet v1.2.1, an explicit command line definition for the default namespace (such as is the case with OP's SVG file) can be avoided via use of an automated binding of _ to the default namespace:

1.3.更方便的解决方案

XML 文档也可以使用不同的命名空间前缀,在任何文档中的元素.为了处理更大的命名空间轻松,XMLStarlet(版本 1.2.1+)将使用命名空间前缀在输入文档的根元素上声明.默认的命名空间将绑定到前缀 _DEFAULT(在版本中1.5.0+).

XML documents can also use different namespace prefixes, on any element in the document. In order to handle namespaces with greater ease, XMLStarlet (versions 1.2.1+) will use the namespace prefixes declared on the root element of the input document. The default namespace will be bound to the prefixes _ and DEFAULT (in versions 1.5.0+).

所以,上面的命令行可以改写为:

So, the above command line could be re-written as:

xmlstarlet ed -u "/_:svg/_:defs/_:linearGradient[@id='linearGradient6204']/@id" -v 'linearGradient9999' text.txt

这篇关于如何在 xmlstarlet 中声明 XPath 命名空间?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆