Rainfall’s CodeLife

C/C++/C#/VB/JavaScript/Python/XML

 

Python对象转换REST、Json(下) December 22, 2006

Filed under: Python — Rainfall @ 11:47 pm

★ REST格式

 REST格式采用XML标准,这里我们采用xml.dom.minidom来构建REST数据。这里采用递归函数在父节点下转换当前数据:

def simple2rest(self, instance, pnode, force_child=False):
if isinstance(instance[1], (DictType)):

elif isinstance(instance[1], ListType):

elif instance[0][:-1].lower() == ’s’:

else:

instance是当前数据对象二元组(名称,值),其中pnode是上级数据结构对应的DomNode,force_child是标识强制在父节点下建立,这主要是满足list类型的需要,下面会逐个介绍。

A)字典类型:
建立字典节点,并遍历字典所有数据:

node = pnode.appendChild(pnode.ownerDocument.createElement(instance[0]))
for name in list(instance[1]):
  self.simple2rest((name, instance[1][name]), node)

B)列表类型:

过程和字典类型处理方式类似,但如果一个类中有下列情况:

class mybook:
   chapters[] = …

他对应的REST应该是:

<mybook>
  <chapters>
    <chapter … >…</chapter>
    <chapter … >…</chapter>
    …
  </chapters>
</mybook>

这样就需要根据字段名称生成REST中的集合名和集合项目名:

itemname, itemsname = instance[0], instance[0] + ’s’
if instance[0][-2:].lower() == ‘es’:
  itemname, itemsname = instance[0][:-2], instance[0]
elif instance[0][:-1].lower() == ’s’:
  itemname, itemsname = instance[0][:-1], instance[0]

其他基本和字典一样

C)值类型:

首先对于列表元素数据,将列表内容作为列表集合标签的属性处理,由于tag属性不能重名,因此必须先建立单独的节点:

if force_child:
  pnode = pnode.appendChild(pnode.ownerDocument.createElement(instance[0]))

同一个值可以有两种形式存在,如:

<tag some=”…” value=”…”>或
<tag some=”…”>…</tag>

一个Tag最多只可能有一个作为TextNode内容,因此这里的处理方式是将字段名为“value”的数据处理为textnode。

if force_child or instance[0].lower() == ‘value’:
  pnode.appendChild(pnode.ownerDocument.createTextNode(str(instance[1])))
else:
  pnode.setAttribute(instance[0], str(instance[1])

★ 值类型过滤

在Json中,布尔表示为“true”和“false”,而在REST中通常会表示“1”和“0”,另外枚举的处理也需要转换为字串,比如“read”比“1”要好的多。上面都是默认用Python的str函数转换值类型,为了满足上述要求,必须做针对类型的过滤器:

ins_value = self.fmtfilters.type2str(instance[1])

class ValueFilters:
  trans_filters = None

  def type2str(self, instance):
    if self.trans_filters and self.trans_filters.has_key(type(instance)):
      return self.trans_filters[type(instance)](instance)
  return str(instance)

在简单类型转换过程中,会先查找某个类成员是否有对应的转换函数,如果有则不调用默认的obj2simple:

fmtname = ‘format_’ + name + ‘_field’
if hasattr(instance, fmtname):
  clsdict[name] = getattr(instance, fmtname)()
else:
  clsdict[name] = obj2simple(field)

 

WordPress database error: [Table 'duanyuluocode.wp_comments' doesn't exist]
SELECT * FROM wp_comments WHERE comment_post_ID = '15' AND comment_approved = '1' ORDER BY comment_date

Leave a Reply