4

我有一个内置在 OpenERP 中的模块,可以为现有模型添加一些字段。

定义大致如下:

class res_partner(osv.osv):
    _name = _inherit = 'res.partner'
    _columns = {
        'my_special_id': fields.integer('Special ID', required=False, readonly=True),
    }
    _defaults = {
        'my_special_id': lambda *a: None
    }

    _sql_constraints = [
        ('special_id_uniq', 'UNIQUE (my_special_id)', 'Must be unique.'),
    }

    _sql = """CREATE UNIQUE INDEX special_id_limited_uniq
            ON res_partner (my_special_id)
            WHERE my_special_id != 0
    """
res_partner()

我的目标是有一个字段(special_id_uniq):

  1. 默认为 NULL
  2. 是整数
  3. 在所有值中是唯一的,但 NULL 除外

我的第一直觉是创建上面的 _sql_constraint 定义,但这引起了问题:显然 OpenERP 没有可为空的整数字段,因此“无”被视为 0。这打破了 SQL 约束,因为现在必须允许多个 0 值.

为了解决这个问题,我删除了模型上的 _sql_constraints 选项并添加了创建 PostgreSQL 部分索引的 _sql 代码。为了验证它是否有效,我自己在 PostgreSQL 上运行了 SQL,它达到了我想要的效果。但是,当我通过 OpenERP 创建一个新数据库并安装我的自定义模块时,此 SQL 不会运行。那是因为没有创建模型:

def _auto_init(self, cr, context=None):
    #...
    create = not self._table_exist(cr)
    #...
    #Line 3046 of openerp/osv/orm.py version 6.1 function _auto_init
    if create:
        self._execute_sql(cr)
    #...

那么,如何在模块安装时运行一些自定义 SQL?

4

2 回答 2

4

实际上,我可能刚刚回答了我自己的问题:覆盖 _auto_init。

编辑:

是的,在安装/升级期间运行 SQL 的方法如下:

def _auto_init(self, cr, context=None):
    ret = super(res_partner, self)._auto_init(cr, context)
    self._execute_sql(cr)
    return ret
于 2012-05-29T20:38:50.390 回答
3

function您可以通过在模块的数据 xml 文件中添加一个条目来实现此目的。

<openerp>
  <data>
    <!-- ... your init data records ...-->
    <function model="res.partner" name="_my_init_mehod"/>
  </data>
</openerp>

您可以在标准模块中看到一个工作示例documentdocument_data.xml 声明调用函数_attach_parent_id以在安装结束时将所有附件迁移到新的 DMS 结构。

于 2012-05-30T08:29:46.557 回答