2017-11-09 11 views
0

XMLからフィールドを抽出するスクリプトを作成していますが、これを取得して動作させる必要があります.2とgrepsを試していました。少し助けが必要です。カスタムXMLからフィールドを抽出する

#! /bin/bash 

function charge_files() { 
XML="Prueba.xml"; 
if [ -f "$XML" ]; then 
echo "============================="; 
echo "| XML CHARGED |"; 
echo "============================="; 
else 
echo "============================="; 
echo "| XML NOT CHARGED |"; 
echo "============================="; 
fi 
} 

function extract() { 
#extract all from the file (not curr working) 
x=`grep "Host"` 
for $x in "$XML" 
do 
for LINEA in `cat $XML | grep "<Telegram" ` #LINEA guarda el resultado del fichero datos.txt 
do 
TIMESTAMP=`echo $LINEA | grep [Timestamp="*"] ` #Extracts TIMESTAMP 
FRAMEFORMAT=`echo $LINEA | grep [FrameFormat="*"]` #Extracts FRAMEFORMAT 
RAWDATA=`echo $LINEA | grep [RawData="*"]` #Extracts RAWDATA 

echo "$x $HOST $TIMESTAMP $FRAMEFORMAT $RAWDATA" >> output.logs #Shows result 
done 
done 
} 

charge_files 
extract 

私は、これは

<CommunicationLog xmlns="http://knx.org/xml/telegrams/01"> 
    <RecordStart Timestamp="" Mode="" Host="PC1" ConnectionName="" ConnectionOptions="" ConnectorType="" MediumType="" /> 
    <Telegram Timestamp="" Service="" FrameFormat="" RawData="" /> 
    <Telegram Timestamp="" Service="" FrameFormat="" RawData="" /> 

    <RecordStart Timestamp="" Mode="" Host="PC2" ConnectionName="" ConnectionOptions="" ConnectorType="" MediumType="" /> 
    <Telegram Timestamp="" Service="" FrameFormat="" RawData="" /> 
    <Telegram Timestamp="" Service="" FrameFormat="" RawData="" /> 
    <RecordStop Timestamp="" /> 
</CommunicationLog> 

をフィールドと私はより多くのcomparationsを作るために、このような出力をしたい、このXML withsを得た:

HOST="PC1" ConnectorType="" Timestamp="" FrameFormat="" RawData="" 
HOST="PC1" ConnectorType="" Timestamp="" FrameFormat="" RawData="" 

HOST="PC2" ConnectorType="" Timestamp="" FrameFormat="" RawData="" 
HOST="PC2" ConnectorType="" Timestamp="" FrameFormat="" RawData="" 

答えて

0

コードには多くの問題があります。

  • 一般:あなたと他の人がコードをデバッグし、サポートする
    • インデントあなたのコード、それは非常に簡単になります。
    • スクリプトを書くときは、ほとんどの行を行ごとに行い、すべての行をテストします。あなたの変数のエコーを追加してください...
    • 一束の線を書いておき、それがなぜ機能しないのか理解しようとしないでください。
    • Ex。 extract()の最初の行は機能しません。その1行だけでextract()を試してみると、先に進まずに最初にデバッグしてください。
  • Prueba.xml:
    • あなたはRecordStopよりRecordStart、その後、別のRecordStartを、持っています。最初のRecordStartのRecordStopを忘れましたか?
    • 空のフィールドでデバッグするのが難しいため、テストデータを追加しました。
  • charge_files:
    • がないファイルが存在する場合は、チェックよりも何もありません。しかし、大丈夫です。
    • ';'は不要です。エコーコマンド、またはXMLの割り当てについて説明します。削除されました。
    • XMLファイルが存在しない場合、スクリプトは関係なく実行されます。スクリプトの残りの部分にファイルが存在する必要があるため、exitを追加しました。
  • エキス:

    • あなたはあなたがしようとしたようなラインに反復するために使用することはできません。すべての言葉を繰り返します。私のコードを書いているようにしばらく使ってください。
    • すべての行をループする必要があります。自分のコードを見てください。グレープテレグラムを使ったあなたの方法は、PC1のテレグラムラインとPC2のテレグラムラインを区別しません。
    • grepコマンドは、行全体を返します。したがって、行の中の単語をgrepすると、行の一部が返されず、行全体が返されます。
    • 行の一部を抽出するには、cut(あなたの要件が単純なので、やったように)、awk、sedを使用することができます。
  • 仮定:

    • 行が常に同じ順序で、同じ情報が含まれています。だからここ

は、私は私のテストのために使用されるXMLファイルです:

<CommunicationLog xmlns="http://knx.org/xml/telegrams/01"> 
    <RecordStart Timestamp="" Mode="" Host="PC1" ConnectionName="name1" ConnectionOptions="option1" ConnectorType="type1" MediumType="med1" /> 
    <Telegram Timestamp="t1a" Service="s1a" FrameFormat="ff1a" RawData="rd1a" /> 
    <Telegram Timestamp="t1b" Service="s1b" FrameFormat="ff1b" RawData="rd1b" /> 

    <RecordStart Timestamp="" Mode="" Host="PC2" ConnectionName="name2" ConnectionOptions="option2" ConnectorType="type2" MediumType="med2" /> 
    <Telegram Timestamp="t2a" Service="s2a" FrameFormat="ff2a" RawData="rd2a" /> 
    <Telegram Timestamp="t2b" Service="s2b" FrameFormat="ff2b" RawData="rd2b" /> 
    <RecordStop Timestamp="stoptimestamp" /> 
</CommunicationLog> 

そして、ここでのスクリプト:この出力を生成

#! /bin/bash 

function charge_files() 
{ 
    XML="Prueba.xml" 
    if [ -f "$XML" ]; then 
     echo "=============================" 
     echo "| XML CHARGED |" 
     echo "=============================" 
    else 
     echo "=============================" 
     echo "| XML NOT CHARGED |" 
     echo "=============================" 
     exit 1 
    fi 
} 

function extract() 
{ 
    host='' 

    while IFS= read -r line; do 
     # Find if it is a RecordtStart line 
     if [ $(echo $line | grep -c "RecordStart") -eq 1 ] 
     then 
      # If host == '', then it is the first host we see. 
      # Otherwise, we are changing host, so print an empty line 
      if [ "$host" != '' ] 
      then 
       echo "" 
      fi 

      # Collect the host information 
      host=$(echo $line | awk '{print $4}' | cut -d'"' -f2) 

      # Collect the ConnectorType information 
      connectortype=$(echo $line | awk '{print $7}') 

      # Done with this loop in the while, move on to the next 
      continue 
     fi 

     # Find if it is a Telegram line 
     if [ $(echo $line | grep -c "Telegram") -eq 1 ] 
     then 
      # Collect the Timestamp information 
      timestamp=$(echo $line | awk '{print $2}') 

      # Collect the FrameFormat information 
      frameformat=$(echo $line | awk '{print $4}') 

      # Collect the RawData information 
      rawdata=$(echo $line | awk '{print $5}') 

      # Print the information 
      echo "HOST=\"$host\" $connectortype $timestamp $frameformat $rawdata" 

      # Done with this loop in the while, move on to the next 
      continue 
     fi 

    done <$XML 
} 

charge_files 
extract 

============================= 
| XML CHARGED | 
============================= 
HOST="PC1" ConnectorType="type1" Timestamp="t1a" FrameFormat="ff1a" RawData="rd1a" 
HOST="PC1" ConnectorType="type1" Timestamp="t1b" FrameFormat="ff1b" RawData="rd1b" 

HOST="PC2" ConnectorType="type2" Timestamp="t2a" FrameFormat="ff2a" RawData="rd2a" 
HOST="PC2" ConnectorType="type2" Timestamp="t2b" FrameFormat="ff2b" RawData="rd2b" 
関連する問題