生成xml的最佳方法是什么?

Jos*_*unz 66 python xml api

我正在创建一个web api,需要一个很好的方法来快速生成一些格式良好的xml.我在python中找不到任何好的方法.

注意:有些库看起来很有前途,但要么缺少文档,要么只输出到文件.

ars*_*ars 91

使用lxml:

from lxml import etree

# create XML 
root = etree.Element('root')
root.append(etree.Element('child'))
# another child with text
child = etree.Element('child')
child.text = 'some text'
root.append(child)

# pretty string
s = etree.tostring(root, pretty_print=True)
print s
Run Code Online (Sandbox Code Playgroud)

输出:

<root>
  <child/>
  <child>some text</child>
</root>
Run Code Online (Sandbox Code Playgroud)

有关更多信息,请参阅教程.


Anu*_*yal 88

ElementTree是一个很好的模块,用于读取xml和编写例如

from xml.etree.ElementTree import Element, SubElement, tostring

root = Element('root')
child = SubElement(root, "child")
child.text = "I am a child"

print tostring(root)
Run Code Online (Sandbox Code Playgroud)

输出:

<root><child>I am a child</child></root>
Run Code Online (Sandbox Code Playgroud)

有关详细信息以及如何打印,请参阅本教程.

或者,如果您的XML很简单,请不要低估字符串格式的强大功能:)

xmlTemplate = """<root>
    <person>
        <name>%(name)s</name>
        <address>%(address)s</address>
     </person>
</root>"""

data = {'name':'anurag', 'address':'Pune, india'}
print xmlTemplate%data
Run Code Online (Sandbox Code Playgroud)

输出:

<root>
    <person>
        <name>anurag</name>
        <address>Pune, india</address>
     </person>
</root>
Run Code Online (Sandbox Code Playgroud)

您也可以使用string.Template或某些模板引擎进行复杂的格式化.

  • 小心第二种方法,因为它不引用特殊字符,所以如果你的数据包含诸如"<>&"之类的字符,你最终可能会出现格式错误的xml. (6认同)

Joh*_*nal 17

我会使用yattag库.我认为这是最蟒蛇的方式:

from yattag import Doc

doc, tag, text = Doc().tagtext()

with tag('food'):
    with tag('name'):
        text('French Breakfast')
    with tag('price', currency='USD'):
        text('6.95')
    with tag('ingredients'):
        for ingredient in ('baguettes', 'jam', 'butter', 'croissants'):
            with tag('ingredient'):
                text(ingredient)


print(doc.getvalue())
Run Code Online (Sandbox Code Playgroud)

  • 我不确定,如果我认为它实际上是美丽的还是丑陋的。到目前为止,我已经使用 `with` 语句打开文件,我认为它有助于“清理”或“关闭”我在 `with` 语句之后直接写入的任何内容。所以在这种情况下,它会关闭标签?或者它会在打开文件时像文件句柄一样扔掉它们?如果它扔掉它,那为什么它仍然在最终输出中?一定是因为那个 `text()` 函数。但这不是绕过`with`语句的特性吗? (2认同)
  • yattag.org 的官方文档对其工作原理有很好的解释“标记方法返回一个上下文管理器。在 Python 中,上下文管理器是一个可以在 with 语句中使用的对象。上下文管理器有 __enter__ 和 __exit__ 方法。 __enter__ 方法在 with 块的开头调用,而 __exit__ 方法在离开块时调用。现在我想你可以明白为什么这对于生成 xml 或 html 很有用了。with tag('h1') 创建一个 &lt;h1&gt;标签。它将在 with 块的末尾关闭。这样你就不必担心关闭标签。” (2认同)

Lar*_*din 15

使用lxml.builder类,来自:http://lxml.de/tutorial.html#the-efactory

import lxml.builder as lb
from lxml import etree

nstext = "new story"
story = lb.E.Asset(
  lb.E.Attribute(nstext, name="Name", act="set"),
  lb.E.Relation(lb.E.Asset(idref="Scope:767"),
            name="Scope", act="set")
  )

print 'story:\n', etree.tostring(story, pretty_print=True)
Run Code Online (Sandbox Code Playgroud)

输出:

story:
<Asset>
  <Attribute name="Name" act="set">new story</Attribute>
  <Relation name="Scope" act="set">
    <Asset idref="Scope:767"/>
  </Relation>
</Asset>
Run Code Online (Sandbox Code Playgroud)


Ser*_*rgO 10

如果要使用纯Python,可选方式:

ElementTree适用于大多数情况,但它不能 CData漂亮的打印.

所以,如果你需要CData漂亮的打印,你应该使用minidom:

minidom_example.py:

from xml.dom import minidom

doc = minidom.Document()

root = doc.createElement('root')
doc.appendChild(root)

leaf = doc.createElement('leaf')
text = doc.createTextNode('Text element with attributes')
leaf.appendChild(text)
leaf.setAttribute('color', 'white')
root.appendChild(leaf)

leaf_cdata = doc.createElement('leaf_cdata')
cdata = doc.createCDATASection('<em>CData</em> can contain <strong>HTML tags</strong> without encoding')
leaf_cdata.appendChild(cdata)
root.appendChild(leaf_cdata)

branch = doc.createElement('branch')
branch.appendChild(leaf.cloneNode(True))
root.appendChild(branch)

mixed = doc.createElement('mixed')
mixed_leaf = leaf.cloneNode(True)
mixed_leaf.setAttribute('color', 'black')
mixed_leaf.setAttribute('state', 'modified')
mixed.appendChild(mixed_leaf)
mixed_text = doc.createTextNode('Do not use mixed elements if it possible.')
mixed.appendChild(mixed_text)
root.appendChild(mixed)

xml_str = doc.toprettyxml(indent="  ")
with open("minidom_example.xml", "w") as f:
    f.write(xml_str)
Run Code Online (Sandbox Code Playgroud)

minidom_example.xml:

<?xml version="1.0" ?>
<root>
  <leaf color="white">Text element with attributes</leaf>
  <leaf_cdata>
<![CDATA[<em>CData</em> can contain <strong>HTML tags</strong> without encoding]]>  </leaf_cdata>
  <branch>
    <leaf color="white">Text element with attributes</leaf>
  </branch>
  <mixed>
    <leaf color="black" state="modified">Text element with attributes</leaf>
    Do not use mixed elements if it possible.
  </mixed>
</root>
Run Code Online (Sandbox Code Playgroud)