XML几乎总是被错误地使用


XML语言是1996年发明的。 在应用的可能性开始被误解之前,他几乎没有出现过,对于他们试图适应他的那些目的,他不是最佳选择。

毫不夸张地说,我所看到的绝大多数XML模式都是不适当的或滥用XML。 而且,对XML的这种使用证明了对XML的根本误解。

XML是一种标记语言。 这不是数据格式 。 在大多数XML方案中,没有明确考虑这种区别,这使XML与数据格式混淆,这最终意味着选择XML本身是错误的,因为实际上需要数据格式。

无需赘述,XML最适合使用结构和元数据来注释文本块。 如果您的主要任务不是处理文本块,那么选择XML不太可能。

从这个角度来看,有一种简单的方法可以检查XML模式的制作情况。 以提议的模式中的文档为例,并从中删除所有标签和属性。 如果剩下的东西没有意义(或者剩余的字符串为空),则说明您的架构未正确构建,或者根本不应该使用XML。

下面,我将给出一些错误构造电路的最常见示例。

<rot> <item name="name" value="John" /> <item name="city" value="London" /> </rot> 

在这里,我们看到了一个不合理且奇怪(尽管非常普遍)尝试以XML表示简单键值字典的示例。 如果删除所有标签和属性,将保留一个空行。 本质上,无论听起来多么荒谬,该文档都是空行的语义注释。

 <root name="John" city="London" /> 

更糟糕的是,这里我们所得到的不只是空字符串的语义注释,它是表达字典的一种奢侈方式-这次,“字典”被直接编码为根元素的属性。 因此,元素上给定的一组属性名称变得不确定且动态。 而且,从这里可以清楚地看出,作者真正想表达的全部只是一种简单的键值语法,但是他做出了使用XML的绝对奇怪的决定,迫使使用单个空元素作为要使用的前缀属性语法。 这样的计划经常出现在我身上。

 <rot> <item key="name">John</item> <item key="city">London</item> </rot> 

这已经更好了,但是由于某些原因,键现在是元数据,但值却不是。 字典非常奇怪。 如果删除所有标签和属性,则一半的信息将丢失。

XML中正确的字典表达式将如下所示:

 <rot> <item> <key>Name</key> <value>John</value> </item> <item> <key>City</key> <value>London</value> </item> </rot> 

但是,如果人们做出了一个奇怪的决定,那就是使用XML作为数据格式,然后使用它来组织字典,那么他们应该了解他们正在做的事情是不合适的,而且不方便。 通常,设计人员会错误地选择XML来构建其应用程序。 但是,更常见的是,它们通过以上述一种形式对XML的无意义使用而加剧了这种情况,而忽略了XML根本不适合这种情况的事实。

最糟糕的XML模式? 顺便说一句, 我所见过的最糟糕的XML模式的奖品是Polycom IP电话电话的自动资源分配配置文件的格式。 此类文件需要通过TFTP加载XML请求文件,通常...这是此类文件的摘录:

 <softkey softkey.feature.directories="0" softkey.feature.buddies="0" softkey.feature.forward="0" softkey.feature.meetnow="0" softkey.feature.redial="1" softkey.feature.search="1" softkey.1.enable="1" softkey.1.use.idle="1" softkey.1.label="Foo" softkey.1.insert="1" softkey.1.action="..." softkey.2.enable="1" softkey.2.use.idle="1" softkey.2.label="Bar" softkey.2.insert="2" softkey.2.action="..." /> 

这不是一个坏笑话。 这不是我的发明:

  • 元素只是用作附加属性的前缀,而属性本身具有层次名称。
  • 如果要为某个类型的记录的多个实例分配值,则需要使用其中包含索引的属性的名称。
  • 此外,属性以softkey.开头softkey. ,您需要在<softkey/>元素上放置以feature.开头的属性feature. 应该放在<feature/>元素等上,尽管它看起来完全多余并且乍看之下毫无意义。
  • 最后,如果您希望属性名称的第一部分始终与元素名称匹配-就是这样! 例如,属性up. 必须附加到<userpreferences/> 。 将属性名称附加到元素的顺序是任意的,几乎是完全相同的。

文件或数据 。 有时,有人会做一些绝对奇怪的事情,试图将XML和JSON进行比较-从而表明他不理解彼此。 XML是一种文档标记语言。 JSON是一种结构化的数据格式,因此相互比较就像尝试比较暖和软。

要理解这一点, 文档和数据之间的区别的概念将有所帮助。 作为XML的类似物,您可以随意获取机器可读的文档。 尽管它打算由机器读取,但它隐喻地与文档相关,并且从这个角度来看,它实际上可与PDF文档相媲美,而PDF文档通常不是机器可读的。

例如,在XML中,元素的顺序很重要。 在JSON中,对象内部的键值对的顺序没有意义,也没有定义。 如果要从键值对中获取无序字典,则此文件中各项的实际顺序无关紧要。 但是您可以根据此数据形成许多不同的文档 ,因为文档具有特定的顺序。 隐喻上,这是纸上文件的类似物,尽管它没有物理尺寸,与打印输出或PDF文件不同。

在我用XML正确表示字典的示例中,显示了字典中元素的顺序,与JSON语言中的表示相反。 我不能忽略这个顺序:这种线性是文档模型和XML格式固有的。 在解释此XML文档时,可能会有人决定忽略该顺序,但是对此争论毫无意义,因为这个问题超出了讨论格式本身的范围。 此外,如果通过在文档中附加级联样式表使文档在浏览器中可见,则可以看到字典中的元素以某种顺序存在,而没有其他方式。

换句话说,字典(结构化数据的片段)可以转换为n个不同的可能文档(XML,PDF,纸上等),其中n是字典中元素的可能组合数,而我们尚未考虑其他元素可能的变量。

但是,由此得出的结论是,如果您想单独传输数据,那么使用机器可读的文档将无效。 它使用一个模型,在这种情况下是多余的,它只会产生干扰。 另外,为了提取源数据,有必要编写程序。 将XML用于某些在某个阶段不会被格式化为文档的内容(例如,使用CSS或XSLT或两者都使用)几乎没有意义,因为这是这样做的主要原因(如果不是唯一的话)坚持文档模型。

此外,由于XML没有数字(或布尔表达式或其他数据类型)的概念,因此以这种格式表示的所有数字仅被视为附加文本。 要提取数据,必须知道方案及其与相应表示数据的关系。 还需要根据上下文知道何时文本的一个或另一个元素是数字,并且应该将其转换为数字,等等。

因此,从XML文档提取数据的过程与识别包含例如形成许多数值数据页的表格的扫描文档的过程没有太大的不同。 是的,原则上可以这样做,但这不是最佳的方法,除非在极端情况下根本没有其他选择。 一个明智的决定是简单地找到未嵌入文档模型中的原始数据的数字副本,其中将数据与其特定的文本表示形式组合在一起。

但是,XML在商业中很流行也不足为奇。 这样做的原因恰恰是因为文档的格式(纸上)对于业务是可以理解和熟悉的,并且他们希望在那里继续使用熟悉和可理解的模型。 出于同样的原因,在商业中也经常使用PDF格式的文档,而不是更方便地使用机器处理格式-因为它们仍然与具有特定物理尺寸的打印页面的概念联系在一起。 这甚至适用于不可能打印的文档(例如,8,000页的注册表文档的PDF文件)。 从这个角度来看,在业务中使用XML本质上是拟态的一种体现。 人们了解有限尺寸的打印页面的隐喻概念,并且他们了解如何基于打印文档创建业务流程。 如果这是您的指导原则,那么机器可读的,物理尺寸不受限制的文档-XML文档-是一种创新,同时又是文档的熟悉且舒适的类比。 这并不能阻止它们保持不正确且过度类化的数据呈现方式。

到目前为止,我知道可以真正调用这种格式的正确用法的唯一XML模式是XHTML和DocBook。

Source: https://habr.com/ru/post/zh-CN475474/


All Articles