2014-09-29 3 views
1

Я использую lxml для создания xml-файла.Как заставить все объявления пространства имен присоединяться к корневому элементу?

from lxml import etree as ET 

зарегистрировать пространство имен, используя эту строку

ET.register_namespace("exp", "http://www.example.com/exp/") 

Если добавить элемент с

root_exp = ET.Element("{http://www.example.com/exp/}root_exp") 

или подэлементом с

foo_hdr = ET.SubElement(root_exp, "{http://www.example.com/exp/}fooHdr") 

пространства имен определяются каждый время, когда пространство имен ars, например.

<exp:bar xmlns:exp="http://www.example.com/exp/"> 
    <exp:fooHdr CREATEDATE="2013-03-22T10:28:27.137531"> 

Это хорошо сформированный XML AFAIK, но я думаю, что это не нужно, и это выглядит очень многословным. Как это поведение может быть подавлено? Для каждого пространства имен в корневом элементе xml-файла должно быть одно определение.

Заранее благодарен!

UPDATE

Пример минимального

#!/usr/bin/env python2 
from lxml import etree as ET 

ET.register_namespace("exa", "http://www.example.com/test") 

root = ET.Element("{http://www.example.com/test}root") 

tree = ET.ElementTree(root) 
tree.write("example.xml", encoding="UTF-8", pretty_print=True, xml_declaration=True) 

UPDATE 2

Обновлено сниппет

#!/usr/bin/env python2 
from lxml import etree as ET 

ET.register_namespace("exa", "http://www.example.com/test") 
ET.register_namespace("axx", "http://www.example.com/foo") 

root = ET.Element("{http://www.example.com/test}root") 
sub_element = ET.SubElement(root, "{http://www.example.com/test}sub_element") 
foo_element = ET.SubElement(sub_element, "{http://www.example.com/foo}foo") 
bar_element = ET.SubElement(sub_element, "{http://www.example.com/foo}bar") 

tree = ET.ElementTree(root) 
tree.write("example.xml", encoding="UTF-8", pretty_print=True, xml_declaration=True) 

Ожидаемое:

<?xml version="1.0" encoding="UTF-8"?> 
<exa:root xmlns:exa="http://www.example.com/test"/ xmlns:axx="http://www.example.com/foo"> 
    <exa:sub_element> 
    <axx:foo /> 
    <axx:bar /> 
    </exa:sub_element> 
</exa:root> 

Is:

<?xml version="1.0" encoding="UTF-8"?> 
<exa:root xmlns:exa="http://www.example.com/test"> 
    <exa:sub_element> 
    <axx:foo xmlns:axx="http://www.example.com/foo"/> 
    <axx:bar xmlns:axx="http://www.example.com/foo"/> 
    </exa:sub_element> 
</exa:root> 
+0

Я добавил фрагмент. – Steffen

ответ

1

Используйте карту пространства имен:

NSMAP = { 'exa': 'http://www.example.com/test', 
      'axx': 'http://www.example.com/foo' } 

root = ET.Element('{http://www.example.com/test}root', nsmap=NSMAP) 
sub_element = ET.SubElement(root, '{http://www.example.com/test}sub_element') 
foo_element = ET.SubElement(sub_element, '{http://www.example.com/foo}foo') 
bar_element = ET.SubElement(sub_element, '{http://www.example.com/foo}bar') 

tree = ET.ElementTree(root) 

print(ET.tostring(tree,encoding='UTF-8',pretty_print=True,xml_declaration=True)) 

результаты в:

<?xml version='1.0' encoding='UTF-8'?> 
<exa:root xmlns:axx="http://www.example.com/foo" xmlns:exa="http://www.examplom/test"> 
    <exa:sub_element> 
    <axx:foo/> 
    <axx:bar/> 
    </exa:sub_element> 
</exa:root> 

Какой именно желаемый результат.

+0

Спасибо! Оно работает! Я предполагал, что 'register_namespace' делает это (в некотором роде). – Steffen

Смежные вопросы