쉘에서 XPath one-liners를 실행하는 방법은 무엇입니까? 적응이 필요없는 것을 찾고

Ubuntu 및 / 또는 CentOS 용 XPath one-liner를 실행 foo //element@attribute filename.xml하거나 foo //element@attribute < filename.xml한 줄씩 결과를 반환 할 수있는 명령 줄 도구가있는 패키지가 있습니까?

나는 단지 apt-get install foo또는 yum install foo즉시 사용할 수 있고 래퍼 또는 다른 적응이 필요없는 것을 찾고 있습니다.

다음은 가까이 오는 것들의 예입니다.

노코 기리. 이 래퍼를 작성하면 위에서 설명한 방식으로 래퍼를 호출 할 수 있습니다.

#!/usr/bin/ruby

require 'nokogiri'

Nokogiri::XML(STDIN).xpath(ARGV[0]).each do |row|
  puts row
end

XML :: XPath. 이 래퍼와 함께 작동합니다.

#!/usr/bin/perl

use strict;
use warnings;
use XML::XPath;

my $root = XML::XPath->new(ioref => 'STDIN');
for my $node ($root->find($ARGV[0])->get_nodelist) {
  print($node->getData, "\n");
}

xpathXML에서 :: XPath는 너무 많은 소음 반환 -- NODE --하고 attribute = "value".

xml_grep from XML :: Twig는 요소를 리턴하지 않는 표현식을 처리 할 수 ​​없으므로 추가 처리없이 속성 값을 추출하는 데 사용할 수 없습니다.

편집하다:

echo cat //element/@attribute | xmllint --shell filename.xml와 유사한 노이즈를 반환합니다 xpath.

xmllint --xpath //element/@attribute filename.xml을 반환합니다 attribute = "value".

xmllint --xpath 'string(//element/@attribute)' filename.xml 내가 원하는 것을 반환하지만 첫 번째 일치에 대해서만.

거의 모든 질문을 충족시키는 다른 솔루션을 위해 임의의 XPath 표현식을 평가하는 데 사용할 수있는 XSLT가 있습니다 (XSLT 프로세서에서 dyn : evaluate 지원 필요).

<?xml version="1.0"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0"
    xmlns:dyn="http://exslt.org/dynamic" extension-element-prefixes="dyn">
  <xsl:output omit-xml-declaration="yes" indent="no" method="text"/>
  <xsl:template match="/">
    <xsl:for-each select="dyn:evaluate($pattern)">
      <xsl:value-of select="dyn:evaluate($value)"/>
      <xsl:value-of select="'&#10;'"/>
    </xsl:for-each>
  </xsl:template>
</xsl:stylesheet>

로 실행하십시오 xsltproc --stringparam pattern //element/@attribute --stringparam value . arbitrary-xpath.xslt filename.xml.



답변

다음 도구를 사용해보십시오.

  • xmlstarlet : 편집, 선택, 변환 가능 … 기본적으로 설치되지 않음, xpath1
  • xmllint: 종종 libxml2-utilsxpath1을 사용 하여 기본적으로 설치됩니다 ( 래퍼--xpath매우 오래된 릴리스와 줄 바꿈으로 구분 된 출력 을 켜 려면 래퍼 를 확인하십시오 (v <2.9.9)
  • xpath: perl의 모듈 XML::XPathxpath1을 통해 설치
  • xml_grep: perl의 모듈 XML::Twigxpath1 (제한된 xpath 사용법)을 통해 설치
  • xidel: xpath3
  • saxon-lint : 내 자신의 프로젝트, @Michael Kay의 Saxon-HE Java 라이브러리 xpath3을 래퍼

xmllint함께 제공 libxml2-utils합니다 (대화 형 쉘로 사용할 수 있습니다 --shell스위치)

xmlstarlet입니다 xmlstarlet.

xpath 펄 모듈과 함께 제공 XML::Xpath

xml_grep 펄 모듈과 함께 제공 XML::Twig

xidel 이다 xidel

saxon-lint사용 SaxonHE 9.6 , XPath를 3.x를 (+ 역 호환성)

예 :

xmllint --xpath '//element/@attribute' file.xml
xmlstarlet sel -t -v "//element/@attribute" file.xml
xpath -q -e '//element/@attribute' file.xml
xidel -se '//element/@attribute' file.xml
saxon-lint --xpath '//element/@attribute' file.xml

.


답변

Xidel을 사용해 볼 수도 있습니다 . 저장소의 패키지에는 없지만 웹 페이지에서 다운로드 할 수 있습니다 (종속성이 없음).

이 작업에 대한 간단한 구문이 있습니다.

xidel filename.xml -e '//element/@attribute' 

그리고 XPath 2를 지원하는 것은 드문 도구 중 하나입니다.


답변

시스템에 이미 설치되어있을 가능성이 높은 패키지는 다음과 같습니다 python-lxml. 그렇다면 추가 패키지를 설치하지 않고도 가능합니다.

python -c "from lxml.etree import parse; from sys import stdin; print '\n'.join(parse(stdin).xpath('//element/@attribute'))"


답변

maven pom.xml 파일을 쿼리하는 검색 에서이 질문에 대해 실행했습니다. 그러나 나는 다음과 같은 한계가 있었다.

  • 크로스 플랫폼을 실행해야합니다.
  • 추가 모듈 설치없이 모든 주요 Linux 배포에 존재해야합니다.
  • maven pom.xml 파일과 같은 복잡한 xml 파일을 처리해야합니다.
  • 간단한 구문

나는 성공하지 않고 위의 많은 것들을 시도했다.

  • python lxml.etree는 표준 python 배포의 일부가 아닙니다
  • xml.etree는 복잡한 maven pom.xml 파일을 잘 처리하지 못하고 깊이 파고 들지 않았습니다.
  • python xml.etree가 알 수없는 이유로 maven pom.xml 파일을 처리하지 않습니다.
  • xmllint도 작동하지 않습니다. 우분투 12.04에서 종종 코어 덤프 “xmllint : using libxml version 20708”

내가 찾은 해결책은 안정적이고 짧으며 많은 플랫폼에서 작동하며 성숙한 솔루션은 루비에 내장 된 rexml lib입니다.

ruby -r rexml/document -e 'include REXML;
     puts XPath.first(Document.new($stdin), "/project/version/text()")' < pom.xml

이 기사를 찾게 된 계기는 다음과 같습니다.


답변

Saxon은 XPath 2.0뿐만 아니라 XQuery 1.0 및 (상업용 버전) 3.0에서도이 작업을 수행합니다. Linux 패키지가 아니라 jar 파일로 제공됩니다. 구문 (간단한 스크립트로 쉽게 랩핑 할 수 있음)은

java net.sf.saxon.Query -s:source.xml -qs://element/attribute

2020 업데이트

Saxon 10.0에는 명령 줄에서 대화식으로 또는 일괄 적으로 사용할 수있는 Gizmo 도구가 포함되어 있습니다. 예를 들어

java net.sf.saxon.Gizmo -s:source.xml
/>show //element/@attribute
/>quit


답변

xsh에 관심이있을 수도 있습니다 . 문서로 원하는 작업을 수행 할 수있는 대화식 모드가 있습니다.

open 1.xml ;
ls //element/@id ;
for //p[@class="first"] echo text() ;


답변

clacke의 대답 은 훌륭하지만 소스가 정상적인 HTML이 아닌 올바른 형식의 XML 인 경우에만 작동한다고 생각합니다.

따라서 정상적인 웹 컨텐트에 대해서도 동일하게 수행해야합니다. XML 형식이 아닌 HTML 문서는 다음과 같습니다.

echo "<p>foo<div>bar</div><p>baz" | python -c "from sys import stdin; \
from lxml import html; \
print '\n'.join(html.tostring(node) for node in html.parse(stdin).xpath('//p'))"

대신 html5lib를 사용하십시오 (브라우저 파서와 같이 웹 브라우저와 동일한 구문 분석 동작을 보장하기 위해 html5lib는 HTML 스펙의 구문 분석 요구 사항을 준수합니다).

echo "<p>foo<div>bar</div><p>baz" | python -c "from sys import stdin; \
import html5lib; from lxml import html; \
doc = html5lib.parse(stdin, treebuilder='lxml', namespaceHTMLElements=False); \
print '\n'.join(html.tostring(node) for node in doc.xpath('//p'))