XSLTは、XMLファイルを変換して他のXMLの一部をメインXMLファイルに追加する特別な目的の言語です。 Pythonのサードパーティ製モジュールlxmlは、XSLT 1.0スクリプトを処理できます。 XSLTはdocument()
関数を維持し、同じディレクトリまたはサブディレクトリ内のドキュメント間でクエリを実行できます。ただし、このアプローチを実行するには、文書全体の処理を処理するために、小さなXMLストリングをディスクまたはファイルに保存し、XSLTスクリプトに保存する必要があります。
もう1つの重要な要件は、小さいXML文字列がルートタグ<wfs:Property xmlns:wfs="http://www.opengis.net/wfs">
に名前空間を定義して、ファイルに出力する前に連結する必要があることです。他のXML文字列をXSLTに追加するには、プロパティルーチンに従って、指定した親ノードに一致するxslテンプレートに<xsl:copy-of select="document('OtherXML.xml')">
という行を追加します。
import lxml.etree as et
# SAVE XML TO FILE
nmsp = 'xmlns:wfs="http://www.opengis.net/wfs"'
property_name = '''<wfs:Property {}>
<wfs:Name>Adm2_NAME</wfs:Name>
<wfs:Value>fff</wfs:Value>
</wfs:Property>'''
xmlfile = open('Property.xml','w')
xmlfile.write(property_name.format(nmsp))
xmlfile.close()
# SAVE XSL TO FILE
xslstr = '''<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0"
xmlns:ogc="http://www.opengis.net/ogc" xmlns:wfs="http://www.opengis.net/wfs">
<xsl:output version="1.0" encoding="UTF-8" indent="yes" />
<xsl:strip-space elements="*"/>
<xsl:template match="@*|node()">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="wfs:Update">
<xsl:copy>
<xsl:copy-of select="document('Property.xml')"/>
<xsl:apply-templates />
</xsl:copy>
</xsl:template>
</xsl:transform>'''
xslfile = open('XSLTScript.xsl','w')
xslfile.write(xslstr)
xslfile.close()
# PARSE MAIN XML STRING
xml = '''<wfs:Transaction service="WFS" version="1.0.0"
xmlns:ogc="http://www.opengis.net/ogc"
xmlns:wfs="http://www.opengis.net/wfs">
<wfs:Update typeName="geonode:tjk_nhr_shockriskscore">
<ogc:Filter>
<ogc:FeatureId fid="tjk_nhr_shockriskscore.2"/>
</ogc:Filter>
</wfs:Update>
</wfs:Transaction>'''
dom = et.fromstring(xml)
# TRANSFORM XML
xsl = et.parse('XSLTScript.xsl')
transform = et.XSLT(xsl)
newdom = transform(dom)
print(newdom)
# <?xml version="1.0"?>
# <wfs:Transaction xmlns:ogc="http://www.opengis.net/ogc"
# xmlns:wfs="http://www.opengis.net/wfs" service="WFS" version="1.0.0">
# <wfs:Update>
# <wfs:Property>
# <wfs:Name>Adm2_NAME</wfs:Name>
# <wfs:Value>fff</wfs:Value>
# </wfs:Property>
# <ogc:Filter>
# <ogc:FeatureId fid="tjk_nhr_shockriskscore.2"/>
# </ogc:Filter>
# </wfs:Update>
# </wfs:Transaction>
# OUTPUT FINAL XML
xmlfile = open('Final.xml','wb')
xmlfile.write(newdom)
xmlfile.close()
また、まだXSLTを使用して、あなたはdocument()
またはディスクに個々の文字列を保存するための任意の必要性を回避することができます。この方法では、小さなXMLストリングをXSLTのテンプレートマッチに連結するだけです。
import lxml.etree as et
# XML STRING
property_name = '''<wfs:Property>
<wfs:Name>Adm2_NAME</wfs:Name>
<wfs:Value>fff</wfs:Value>
</wfs:Property>'''
# XSL STRING
xslstr = '''<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0"
xmlns:ogc="http://www.opengis.net/ogc" xmlns:wfs="http://www.opengis.net/wfs">
<xsl:output version="1.0" encoding="UTF-8" indent="yes" />
<xsl:strip-space elements="*"/>
<xsl:template match="@*|node()">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="wfs:Update">
<xsl:copy>
{}
<xsl:apply-templates />
</xsl:copy>
</xsl:template>
</xsl:transform>'''.format(property_name)
# PARSE MAIN XML STRING
xmlstr = '''<wfs:Transaction service="WFS" version="1.0.0"
xmlns:ogc="http://www.opengis.net/ogc"
xmlns:wfs="http://www.opengis.net/wfs">
<wfs:Update typeName="geonode:tjk_nhr_shockriskscore">
<ogc:Filter>
<ogc:FeatureId fid="tjk_nhr_shockriskscore.2"/>
</ogc:Filter>
</wfs:Update>
</wfs:Transaction>'''
dom = et.fromstring(xmlstr)
# TRANSFORM XML
xsl = et.fromstring(xslstr)
transform = et.XSLT(xsl)
newdom = transform(dom)
print(newdom)
# <?xml version="1.0"?>
# <wfs:Transaction xmlns:ogc="http://www.opengis.net/ogc"
# xmlns:wfs="http://www.opengis.net/wfs" service="WFS" version="1.0.0">
# <wfs:Update>
# <wfs:Property>
# <wfs:Name>Adm2_NAME</wfs:Name>
# <wfs:Value>fff</wfs:Value>
# </wfs:Property>
# <ogc:Filter>
# <ogc:FeatureId fid="tjk_nhr_shockriskscore.2"/>
# </ogc:Filter>
# </wfs:Update>
# </wfs:Transaction>
# OUTPUT FINAL XML
xmlfile = open('Final.xml','wb')
xmlfile.write(newdom)
xmlfile.close()
'.format()'を使ってみましたか? –
あなたのサーバーの 'XML'データパターンとは何ですか?私の考えは、 'property'定義のcosを使っていません。 '更新セクション 'の下に' Adm2_NAME fff 'を使用してください。サーバーがあなたの 'property'を受け入れない、' invalid key error'を起こすかもしれません。コードにエラーはありませんが、サーバー側のパターンを宣言する必要があります。だから、おそらく '主キー'であり、 '不動産 'ではないかもしれない。 –
dsgdfg