2013-02-17 2 views
4

XML 파일을 가지고 있기 때문에 xmlstarlet을 사용하여 BASH 스크립트 등을 구문 분석하고 싶습니다.XML을 명령 줄을 통해 구문 분석

기본 구조는 다음이다 :

 <character> 
  <literal>恵</literal> 
    <misc> 
     <stroke_count>10</stroke_count> 
    </misc> 
    <reading_meaning> 
        <rmgroup> 
       <reading r_type="ja_on">ケイ</reading> 
       <reading r_type="ja_on">エ</reading> 
         <reading r_type="ja_kun">めぐ.む</reading> 
       <reading r_type="ja_kun">めぐ.み</reading> 
       <meaning>favor</meaning> 
       <meaning>blessing</meaning> 
       <meaning>grace</meaning> 
       <meaning>kindness</meaning> 
      </rmgroup> 
    </reading_meaning> 
    </character> 

번호 변경이 어떤 다른 필드와 의미 및 판독이있다. 기본적으로 모든 읽기, 의미, 획 수 등을 얻고 바스가있는 HTML 테이블을 생성하고 싶습니다.

이 파일은 조회가 필요한 많은 문자가 포함 된 큰 파일이기도합니다. 그래서 $ 1을 가져 와서 태그를 기반으로 값을 검색하는 스크립트로이 작업을하고 싶습니다. 이상적으로는 다음과 같습니다.

kanjilookup.sh 恵 

그런 다음 내용을 기반으로 HTML 테이블을 생성하십시오.

생각하십니까? (나는 또한 xpath 같은 다른 프로그램을 사용하고있을 것이다.)

+0

이것은 기본적으로 XSLT가 만들어진 것입니다. –

+0

예를 들어 주시겠습니까? @thatotherguy –

답변

2

@thatotherguy가 제안했듯이, 아마 Bash 대신 XSLT 같은 것을 사용하고 싶을 것이다. 너 can parse XML with Bash,하지만 아마 꽤 까다로워 질거야.

<characters> 
    <character> 
    <literal>恵</literal> 
    <misc> 
     <stroke_count>10</stroke_count> 
    </misc> 
    <reading_meaning> 
     <rmgroup> 
     <reading r_type="ja_on">ケイ</reading> 
     <reading r_type="ja_on">エ</reading> 
     <reading r_type="ja_kun">めぐ.む</reading> 
     <reading r_type="ja_kun">めぐ.み</reading> 
     <meaning>favor</meaning> 
     <meaning>blessing</meaning> 
     <meaning>grace</meaning> 
     <meaning>kindness</meaning> 
     </rmgroup> 
    </reading_meaning> 
    </character> 
</characters> 

당신은 그것을 kanjilookup.xsl를 실행할 수 있습니다 :

<!-- kanjilookup.xsl --> 

<?xml version="1.0" encoding="iso-8859-1"?> 

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:param name="character"/> 
    <xsl:output method="html" indent="yes"/> 
    <xsl:strip-space elements="*"/> 

    <!-- 
    From https://stackoverflow.com/questions/9611569/xsl-how-do-you-capitalize-first-letter 
    --> 

    <xsl:variable name="vLower" select="'abcdefghijklmnopqrstuvwxyz'"/> 
    <xsl:variable name="vUpper" select="'ABCDEFGHIJKLMNOPQRSTUVWXYZ'"/> 

    <xsl:template name="capitalize"> 
    <xsl:param name="string"/> 

    <xsl:value-of select= 
    "concat(translate(substring(
      $string, 1, 1), $vLower, $vUpper), 
      substring($string, 2) 
      ) 
    "/> 
    </xsl:template> 

    <xsl:template match="/"> 
    <xsl:if test="string-length($character) = 0 or not(//literal[. = $character])"> 
     <xsl:message terminate="yes">ERR: No input character given.</xsl:message> 
    </xsl:if> 
    <xsl:apply-templates select="characters/character[literal[. = $character]]"/> 
    </xsl:template> 

    <xsl:template match="character"> 
    <xsl:text disable-output-escaping='yes'>&lt;!DOCTYPE html> 
</xsl:text> 

    <html> 
     <head/> 
     <body> 
     <table> 
      <tbody> 
      <xsl:apply-templates/> 
      </tbody> 
     </table> 
     </body> 
    </html> 
    </xsl:template> 

    <xsl:template match="literal"> 
    <caption> 
     <xsl:value-of select="."/> 
    </caption> 
    </xsl:template> 

    <xsl:template match="stroke_count"> 
    <tr> 
     <td> 
     <xsl:call-template name="capitalize"> 
      <xsl:with-param name="string" select="translate(local-name(), '_', ' ')"/> 
     </xsl:call-template> 
     </td> 
     <td><xsl:value-of select="."/></td> 
    </tr> 
    </xsl:template> 

    <xsl:template match="misc | reading_meaning | rmgroup"> 
    <xsl:apply-templates/> 
    </xsl:template> 

    <xsl:template match="reading | meaning"> 
    <tr> 
     <td> 
     <xsl:call-template name="capitalize"> 
      <xsl:with-param name="string" select="local-name()"/> 
     </xsl:call-template> 
     <xsl:apply-templates select="@r_type"/> 
     </td> 
     <td> 
     <xsl:value-of select="."/> 
     </td> 
    </tr> 
    </xsl:template> 

    <xsl:template match="@r_type"> 
    <xsl:value-of select="concat(' ', '(', ., ')')"/> 
    </xsl:template> 
</xsl:stylesheet> 

하는의 당신이 characters.xml라는 파일이 있다고 가정 해 봅시다 : @의 thatotherguy의 제안에 따라

, 당신은 이런 식으로 뭔가를 보이는 XSLT 스타일 시트를 가질 수있다 XMLStarlet과 같이 다음과 같이 입력하십시오 :

xml tr kanjilookup.xsl -s character=恵 characters.xml 

즉 (꽤 - 인쇄 후)이처럼 보이는 HTML 테이블을 생성 할 수 있습니다 :

<!DOCTYPE html> 
<html> 
    <head> 
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 
    </head> 
    <body> 
    <table> 
     <tbody> 
     <caption>恵</caption> 
     <tr> 
      <td>Stroke count</td> 
      <td>10</td> 
     </tr> 
     <tr> 
      <td>Reading (ja_on)</td> 
      <td>ケイ</td> 
     </tr> 
     <tr> 
      <td>Reading (ja_on)</td> 
      <td>エ</td> 
     </tr> 
     <tr> 
      <td>Reading (ja_kun)</td> 
      <td>めぐ.む</td> 
     </tr> 
     <tr> 
      <td>Reading (ja_kun)</td> 
      <td>めぐ.み</td> 
     </tr> 
     <tr> 
      <td>Meaning</td> 
      <td>favor</td> 
     </tr> 
     <tr> 
      <td>Meaning</td> 
      <td>blessing</td> 
     </tr> 
     <tr> 
      <td>Meaning</td> 
      <td>grace</td> 
     </tr> 
     <tr> 
      <td>Meaning</td> 
      <td>kindness</td> 
     </tr> 
     </tbody> 
    </table> 
    </body> 
</html> 

당신은 물론, 사용자의 요구에 맞게 XSLT 스타일 시트를 수정해야 할 것입니다.

+0

와우! 모든 정보 주셔서 감사합니다! XSLT는 내가 처음으로 접하는 것이기 때문에 매우 유용하다! = D –

0

요즘에는 XQuery를 사용할 이유가 없으므로 XQuery는 훨씬 좋네요.

예. 내 XQuery interpreter와 함께, 당신은 다음과 같이 추가 파일없이 직접 실행할 수 있습니다

xidel --printed-node-format xml characters.xml -e "(character:='恵')[2]" -e - <<<'xquery version "1.0"; 
(<title>{$character}</title>, 
for $char in //character[literal eq $character] return 
    <table> 
    <tbody> 
     <caption>{$character}</caption> 
     <tr> 
     <td>Stroke count</td> 
     <td>{$char/misc/stroke_count/text()}</td> 
     </tr> 
     { for $reading in $char//rmgroup/reading return 
     <tr> 
      <td>Reading ({$reading/@r_type/data(.)})</td> 
      <td>{$reading/text()}</td> 
     </tr> } 
     { for $meaning in $char//rmgroup/meaning return 
     <tr> 
      <td>Meaning</td> 
      <td>{$meaning/text()}</td> 
     </tr> } 
    </tbody> 
    </table> 
) 
' 

는 XSLT의 응답으로 유사한 테이블을 작성합니다. (하지만 거기에 게시 된 characters.xml 앞에 <?xml version="1.0" encoding="utf-8"?>을 추가해야합니다.)