gpt4 book ai didi

python - 如何为 Azure tts (mstts) 设置命名空间

转载 作者:行者123 更新时间:2023-12-02 16:51:51 26 4
gpt4 key购买 nike

我需要为 Azure TTS 创建这个 header :

 <speak version="1.0" 
xmlns="https://www.w3.org/2001/10/synthesis"
xmlns:mstts="https://www.w3.org/2001/mstts"
xml:lang="en-US">

这是用于创建 xml:lang 键的代码:

xml_body = ElementTree.Element('speak', version='1.0')
xml_body.set('{http://www.w3.org/XML/1998/namespace}lang', 'en-us')

我尝试创建 xmlns:mstts 但没有成功。这不起作用:

xml_body.set('{https://www.w3.org/2001/10/synthesis}mstts', 'https://www.w3.org/2001/mstts' )

因为这会产生以下输出:

<speak
xmlns:ns0="https://www.w3.org/2001/10/synthesis"
version="1.0"
xml:lang="en-us"
ns0:mstts="https://www.w3.org/2001/mstts" />

注意 xmlns:ns0ns0:mstts <speak> 上的属性问题元素。

有什么想法吗?

最佳答案

您需要提供 speak元素命名空间,以及它的version属性,这就是 xmlns="..."属性通常配置。使用 {<namespaceuri>}<tagname>限定名称格式,就像您对 xml:lang 所做的一样属性:

xml_body = ElementTree.Element('{https://www.w3.org/2001/10/synthesis}speak')
xml_body.set('{https://www.w3.org/2001/10/synthesis}version', '1.0')
xml_body.set('{http://www.w3.org/XML/1998/namespace}lang', 'en-us')

您还可以将属性添加为字典,作为第二个参数传入:

xml_body = ElementTree.Element(
'{https://www.w3.org/2001/10/synthesis}speak', {
'{https://www.w3.org/2001/10/synthesis}version': '1.0',
'{http://www.w3.org/XML/1998/namespace}lang': 'en-us'
})

不需要设置 xmlns:mstts属性不过! ElementTree 将根据需要根据您构建的 XML 树中使用的 namespace 自动添加此属性。

确实想要使用 register_namespace() function向ElementTree注册这个命名空间。 :

ElementTree.register_namespace('mstts', 'https://www.w3.org/2001/mstts')

这告诉 ElementTree,当您使用 {https://www.w3.org/2001/mstts}具有标记名称或属​​性的命名空间,将 XML 树序列化为文件或字符串时,该命名空间应使用 mstts作为前缀。如果您注册命名空间,将为您生成命名空间前缀(ns0:ns1: 等)。这将产生完全有效的 XML,命名空间前缀是文档本地的,前缀只是完整命名空间 URI 的简写名称。任何兼容的 XML 解析器都将处理 ns0作为 https://www.w3.org/2001/mstts 的前缀命名空间 URI 与使用 mstts 完全相同.

对于默认 命名空间(例如根 https://www.w3.org/2001/10/synthesis 元素的 <speak> 命名空间),使用 default_namespace ElementTree.write() method 的参数.

我发现 QName() objects 更容易处理命名空间属性和标签名称;连同特定命名空间的变量,使您不太可能打错字。这是一个更完整的例子 based on an example from the Azure SSML documentation

from xml.etree import ElementTree as ET
from functools import partial

ns = {
"synthesis": "https://www.w3.org/2001/10/synthesis",
"mstts": "https://www.w3.org/2001/mstts",
"xml": "http://www.w3.org/XML/1998/namespace",
}
ET.register_namespace('mstts', ns['mstts'])

synthesis = partial(ET.QName, ns["synthesis"])
mstts = partial(ET.QName, ns["mstts"])
xml_ = partial(ET.QName, ns["xml"])

xml_body = ET.Element(synthesis('speak'), {
synthesis('version'): '1.0',
xml_('lang'): 'en-us',
})
voice = ET.SubElement(xml_body, synthesis('voice'), {
synthesis('name'): 'en-US-JessaNeural'})
express_as = ET.SubElement(voice, mstts('express-as'), {
mstts('type'): 'cheerful'})
express_as.text = "That'd be just amazing!"

root = ET.ElementTree(xml_body)
root.write("filename.xml", encoding="UTF-8", default_namespace=ns["synthesis"])

上面的代码生成以下 XML(为了便于阅读而手动打印):

<speak
xmlns="https://www.w3.org/2001/10/synthesis"
xmlns:mstts="https://www.w3.org/2001/mstts"
version="1.0"
xml:lang="en-us">
<voice name="en-US-JessaNeural">
<mstts:express-as mstts:type="cheerful">
That'd be just amazing!
</mstts:express-as>
</voice>
</speak>

您可能想查看 external lxml library同样,因为它包含一个 lxml.builder.ElementMaker class这使得使用 namespace 更容易。

lxml 通常具有更好的命名空间支持,并且已经具有命名空间的元素的属性本身不需要显式限定命名空间。您可以使用前缀 None 将给定的命名空间映射标记为默认映射。在设置命名空间的字典中:

from lxml import etree as ET
from lxml.builder import ElementMaker

ns = {
None: "https://www.w3.org/2001/10/synthesis",
"mstts": "https://www.w3.org/2001/mstts",
}

E = ElementMaker(namespace=ns[None], nsmap=ns)
TTS = ElementMaker(namespace=ns['mstts'])

xml_body = E.speak(
{"version": "1.0",
"{http://www.w3.org/XML/1998/namespace}lang": "en-US"},
E.voice(
{"name": "en-US-JessaNeural"},
TTS.express_as(
"That'd be just amazing!",
type="cheerful",
)
)
)

在上面,使用 E.tagname(...)E('tagname', ...)将创建一个带有 https://www.w3.org/2001/10/synthesis 的元素命名空间 URI,而 MSTTS对象使用 https://www.w3.org/2001/mstts 创建标签命名空间 URI。因为我们给了E带有 None 的命名空间映射映射到 https://www.w3.org/2001/10/synthesis命名空间 URI,该 URI 将用作默认命名空间,该命名空间中的标记名和属性将不会添加前缀。

您可以将属性作为关键字参数 ( E.tagname(..., attributename="value") ) 或通过作为位置参数传入的字典传入。任何包含的元素都可以简单地添加为位置参数,包括文本。您还可以添加正常的 Element方法(例如 Element.append() 添加子元素,或 Element.text = ... 设置标记的文本内容)。

使用 lxml 的演示:

>>> from lxml import etree as ET
>>> from lxml.builder import ElementMaker
>>> ns = {
... None: "https://www.w3.org/2001/10/synthesis",
... "mstts": "https://www.w3.org/2001/mstts",
... }
>>> E = ElementMaker(namespace=ns[None], nsmap=ns)
>>> TTS = ElementMaker(namespace=ns['mstts'])
>>> xml_body = E.speak(
... {"version": "1.0",
... "{http://www.w3.org/XML/1998/namespace}lang": "en-US"},
... E.voice(
... {"name": "en-US-JessaNeural"},
... TTS.express_as(
... "That'd be just amazing!",
... type="cheerful",
... )
... )
... )
>>> print(ET.tostring(xml_body, encoding="unicode", pretty_print=True))
<speak xmlns="https://www.w3.org/2001/10/synthesis" xmlns:mstts="https://www.w3.org/2001/mstts" version="1.0" xml:lang="en-US">
<voice name="en-US-JessaNeural">
<mstts:express_as type="cheerful">That'd be just amazing!</mstts:express_as>
</voice>
</speak>

关于python - 如何为 Azure tts (mstts) 设置命名空间,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58339139/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com