Odoo中文网|Odoo实施培训

 找回密码
 立即注册
搜索
热搜: Odoo OpenERP 实施
查看: 7011|回复: 0

OpenERP中get_name()的不同表现

[复制链接]

1

主题

3

帖子

11

积分

新手上路

Rank: 1

积分
11
发表于 2015-8-31 20:36:48 | 显示全部楼层 |阅读模式
openerp中get_name()的不同表现
openerp中每个类都有一个get_name()方法,或者在类内用代码实现这个方法, 或者默认继承父类中的这个方法。 它的签名为
def name_get(self, cr, uid, ids, context=None)

其中ids为要查询记录的id号, 其数据类型为list。
【1】 继承父类get_name时的, 具有很好的容错性
其ids中的记录号可以是不存在的号码, 如果只有一个号码, ids的类型可以不使用列表,而直接使用整数
例如 res.user 没有实现自己的name_get, 而是继承了父类的name_get, 如下是其测试代码
import xmlrpclib
sock=xmlrpclib.ServerProxy("http://127.0.0.1:8069/xmlrpc/object"
print sock.execute("demo", 1,"admin", "res.users","name_get", [1] )
print sock.execute("demo", 1,"admin", "res.users","name_get",  1)
print sock.execute("demo", 1,"admin", "res.users","name_get", [1, 0, -1]  )

上例中,使用了三种不同的ids来调用name_get的方法,其结果都是一样的, 为[[1, 'Administrator']], 因为记录号 0和-1 不存在, 因此不返回他们的查询结果, 也不抛出异常。
【2】模块内部完美地实现了get_name方法, 像父类方法一样,具有很好的兼容性,比如 product_category
    def name_get(self, cr, uid, ids,context=None):
        if isinstance(ids, (list, tuple)) andnot len(ids):
            return[]                          
        if isinstance(ids, (long, int)):   
            ids = [ids]
        reads = self.read(cr, uid, ids,['name','parent_id'], context=context)
        res = []
        for record in reads:
            name = record['name']
            if record['parent_id']:
                name = record['parent_id'][1]+'/ '+name
            res.append((record['id'], name))
        return res                                

这段代码使用instance判断ids的类型,如果是整数或浮点数, 则转换为列表。对于ids中不存在的记录号,self.read具有兼容性,因此, 本模块的name_get就具备了响应的兼容性。


【3】模块内实现get_name方法时, ids是整数而不是列表, 会抛出异常。 例如类account.tax:
    def name_get(self, cr, uid, ids,context=None):
        if not ids:
            return []                          
        res = []
        for record in self.read(cr, uid, ids,['description','name'], context=context)
            name = record['description']and record['description] or record['name']
            res.append((record['id'], name))
        return res                                

这段代码没有判断ids的数据类型,当ids的数据类型不是列表, 它没有进行适当的转换。因此会导致错误发生
【4】模块内实现get_name方法时, ids中出现不存在的记录号时, 会抛出异常, 例如类 event.event
    def name_get(self, cr, uid, ids,context=None):
        if not ids:
            return[]                          
        if isinstance(ids, (long, int)):   
            ids = [ids]
        res = []
        for record in self.browse(cr, uid, ids,context=context):
            date =record.date_begin.split(" ")[0]
            date_end =record.date_end.split(" ")[0]
            if date != date_end:
                date += ' - ' + date_end
            display_name = record.name + ' (' + date +')'
            res.append((record['id'],display_name))
        return res                             

这段代码内调用了自己的browse方法, 如果ids中的id号不存在,browse_record会抛出异常, 因此会导致其name_get方法也抛出异常


【5】最后,我们看一个奇葩,类product_pricelist中的name_get
    def name_get(self, cr, uid, ids,context=None):
       result= []
        if notall(ids):
            returnresult
        for pl inself.browse(cr, uid, ids, context=context):
            name =pl.name + ' ('+ pl.currency_id.name + ')'
           result.append((pl.id,name))
        returnres                             

---- 它没有对ids的类型进行判断, 因此当ids为整数时,会抛出异常
---- 它调用的函数是self.browse,而不是self.read, 因此,如果ids中出现了不存在的记录号,也会抛出异常
---- 更糟糕的是,如果ids中出现了数字零, 那么all(ids)就为假, 这个函数会直接返回一个空的列表。虽然没有抛出异常,但是它并不按我们期望的那样工作。 这个样子最惹人恨了。


erp中文社区的许多朋友在摇摇欲试,要自己在平板电脑上开发oe模块。 这就免不了要用xml-rpc调用openerp的各种模块。 因此需要关注其行为的差异, 以免掉到坑里。

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|手机版|小黑屋|技术支持|开发手册|Odoo中文网-远鼎旗下odoo培训网站 ( 苏ICP备15039516号 )

GMT+8, 2024-4-16 19:12 , Processed in 0.014718 second(s), 14 queries , Xcache On.

Powered by Discuz! X3.2

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表