2010-01-21 218 views
6

我负责定义两个Web应用程序之间的通信。我决定为此使用JSON。在JSON中有一个根节点有多常见?JSON中的根节点

比方说,我们有一个汽车对象。这是“汽车”作为根节点的JSON:

{"Car": { 
    "Make":"Mustang", 
    "YearBuilt":"1999"}} 

所以,现在让我们说我有一个轮胎对象,因为我们规范在具有根节点,这其中也有拥有它。

{"Tire": {"Make": "Brirdgestone", "Size":"15"}} 

将轮胎对象JSON集成到原始Car对象中显示它可能有多笨拙。

{"Car": { "Make":"Mustang", 
"YearBuilt":"1999", 
"Tires": "[{"Tire": {"Make": "Brirdgestone", "Size":"15"}}, 
{"Tire": {"Make": "Brirdgestone", "Size":"15"}}, 
{"Tire": {"Make": "Bridgestone", "Size":"15"}}, 
{"Tire": {"Make": "Brirdgestone", "Size":"15"}} 
]}} 

所以在PHP连载,第一轮胎的品牌将是$object->Car->Tires[0]->Tire->Make。由于根节点,在那里有额外的轮胎等级。

如果Tire没有根节点,代码可能会变得很苗条。

{"Car": { "Make":"Mustang", 
"YearBuilt":"1999", 
"Tires": "[{ {"Make": "Bridgestone", "Size":"15"}}, 
{"Make": "Brirdgestone", "Size":"15"}}, 
{"Make": "Brirdgestone", "Size":"15"}}, 
{"Make": "Brirdgestone", "Size":"15"}}]}} 

在PHP中,有较少的混乱,因为有较少的冗余:第一轮胎的品牌是由$object->Car->Tires[0]->Make

叫有什么不好的没有一个根节点?我喜欢拥有根节点,因为它的行为类似于类名,但不必要的级别会让我感到困惑,并且会使遍历变得更加复杂。

回答

4

我会省略两个根节点,轮胎汽车

请记住,JSON的主要用途是以紧凑格式通过网络传输对象。除此之外,没有其他用法。您希望使用JSON编码的数据并通过添加根节点来创建没有真实身份和用途的空容器对象。当omiting根节点,你

$car->tires[0]->make 

和JS你会得到

car.tires[0].make 

这是更清晰,表示对象要好得多。请记住,这是你将不得不合作。当然,你可以使用某种类型的JSON映射器来映射对象应该如何被序列化,并导致上述对象,但这是很多额外的努力,不值得它imho。

如果您想在JSON中使用类名称,请将其作为属性,例如,

{ 'klass': 'Car', 'make': 'Mustang', 'year':1999 } 
+0

我同意。根节点只会使消费应用代码不必要地变得冗长。 – Steve 2010-01-21 16:33:36

+0

很酷,非常感谢。我想到了一个重要的领域。如果JSON镜像和XML文档,您至少应该在主对象上添加一个,因为在XML中,您需要一个根元素。 一位同事也指出,这对于JSONP回调很重要,如果我创建一个API,结果会更好。例如,Yahoo和eBay API将所有内容都包裹在ResultSet节点周围。这允许关心类型的解析器将ResultSet绑定到对象类型。 – 2010-01-21 16:54:08

+0

那么,我确信你可以想到UseCases在哪里可以派上用场,但是再次,当我在我的应用程序中使用JSON时,我有回调知道如何处理他们收到的数据,例如, example.com/cars/find/id/123会返回汽车数据,我的回调会创建它们。 – Gordon 2010-01-21 17:04:57

0

@Gordon说得很好。不过,我喜欢使用带有AJAX消息的AOP来拦截进出服务器的消息。这些拦截器为每条消息添加一个时间戳和从服务器发送的状态标志(失败,异常,成功,无论...)的消息。正如您猜测的那样,我为有效负载,状态和时间戳使用了一个根JSON节点。

从服务器发送的状态标志可以在前端的一个功能(方面)中检查,所有异常都在一个地方处理。当服务器由于异常以外的原因而失败时,aspect/advice允许将数据传递给AJAX启动器。