2008-11-03 18:27:16 +00:00
# -*- encoding: utf-8 -*-
2006-12-07 13:41:40 +00:00
##############################################################################
#
2008-12-16 10:14:22 +00:00
# OpenERP, Open Source Management Solution
2009-01-04 22:13:29 +00:00
# Copyright (C) 2004-2009 Tiny SPRL (<http://tiny.be>). All Rights Reserved
2008-11-03 18:27:16 +00:00
# $Id$
2008-06-16 11:00:21 +00:00
#
2008-11-03 18:27:16 +00:00
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
2006-12-07 13:41:40 +00:00
#
2008-11-03 18:27:16 +00:00
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
2006-12-07 13:41:40 +00:00
#
2008-11-03 18:27:16 +00:00
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
2006-12-07 13:41:40 +00:00
#
##############################################################################
from osv import fields , osv
2008-06-19 15:42:15 +00:00
import ir , re
2006-12-07 13:41:40 +00:00
import netsvc
2008-10-08 14:13:18 +00:00
from osv . orm import except_orm , browse_record
2006-12-07 13:41:40 +00:00
import time
import tools
2008-11-25 15:19:14 +00:00
from tools import config
2006-12-07 13:41:40 +00:00
import pooler
2008-03-26 13:15:13 +00:00
def _get_fields_type ( self , cr , uid , context = None ) :
2008-07-22 14:24:36 +00:00
cr . execute ( ' select distinct ttype,ttype from ir_model_fields ' )
return cr . fetchall ( )
2008-03-26 13:15:13 +00:00
2006-12-07 13:41:40 +00:00
class ir_model ( osv . osv ) :
2008-07-22 14:24:36 +00:00
_name = ' ir.model '
_description = " Objects "
_rec_name = ' name '
_columns = {
2008-08-21 13:49:55 +00:00
' name ' : fields . char ( ' Object Name ' , size = 64 , translate = True , required = True ) ,
2008-07-22 14:24:36 +00:00
' model ' : fields . char ( ' Object Name ' , size = 64 , required = True , search = 1 ) ,
' info ' : fields . text ( ' Information ' ) ,
' field_id ' : fields . one2many ( ' ir.model.fields ' , ' model_id ' , ' Fields ' , required = True ) ,
2008-09-02 21:31:44 +00:00
' state ' : fields . selection ( [ ( ' manual ' , ' Custom Object ' ) , ( ' base ' , ' Base Object ' ) ] , ' Manualy Created ' , readonly = 1 ) ,
2008-09-04 16:14:13 +00:00
' access_ids ' : fields . one2many ( ' ir.model.access ' , ' model_id ' , ' Access ' ) ,
2008-07-22 14:24:36 +00:00
}
_defaults = {
' model ' : lambda * a : ' x_ ' ,
' state ' : lambda self , cr , uid , ctx = { } : ( ctx and ctx . get ( ' manual ' , False ) ) and ' manual ' or ' base ' ,
}
def _check_model_name ( self , cr , uid , ids ) :
for model in self . browse ( cr , uid , ids ) :
if model . state == ' manual ' :
if not model . model . startswith ( ' x_ ' ) :
return False
2008-12-16 09:45:49 +00:00
if not re . match ( ' ^[a-z_A-Z0-9.]+$ ' , model . model ) :
2008-07-22 14:24:36 +00:00
return False
return True
2008-06-19 15:42:15 +00:00
2008-07-22 14:24:36 +00:00
_constraints = [
2008-08-21 13:49:55 +00:00
( _check_model_name , ' The Object name must start with x_ and not contain any special character ! ' , [ ' model ' ] ) ,
2008-07-22 14:24:36 +00:00
]
def unlink ( self , cr , user , ids , context = None ) :
for model in self . browse ( cr , user , ids , context ) :
if model . state < > ' manual ' :
2008-10-23 13:28:28 +00:00
raise except_orm ( _ ( ' Error ' ) , _ ( " You can not remove the model ' %s ' ! " ) % ( model . name , ) )
2008-07-22 14:24:36 +00:00
res = super ( ir_model , self ) . unlink ( cr , user , ids , context )
pooler . restart_pool ( cr . dbname )
return res
2008-04-13 06:54:08 +00:00
2008-07-22 14:24:36 +00:00
def create ( self , cr , user , vals , context = None ) :
if context and context . get ( ' manual ' , False ) :
vals [ ' state ' ] = ' manual '
res = super ( ir_model , self ) . create ( cr , user , vals , context )
if vals . get ( ' state ' , ' base ' ) == ' manual ' :
2008-11-25 23:33:17 +00:00
self . instanciate ( cr , user , vals [ ' model ' ] , context )
self . pool . get ( vals [ ' model ' ] ) . __init__ ( self . pool , cr )
self . pool . get ( vals [ ' model ' ] ) . _auto_init ( cr , { } )
#pooler.restart_pool(cr.dbname)
2008-07-22 14:24:36 +00:00
return res
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def instanciate ( self , cr , user , model , context = { } ) :
class x_custom_model ( osv . osv ) :
pass
x_custom_model . _name = model
x_custom_model . _module = False
x_custom_model . createInstance ( self . pool , ' ' , cr )
2008-11-25 23:33:17 +00:00
x_custom_model . _rec_name = ' x_name '
2008-04-13 06:54:08 +00:00
ir_model ( )
2008-03-26 21:46:53 +00:00
2008-06-19 15:42:15 +00:00
2008-09-02 21:31:44 +00:00
class ir_model_grid ( osv . osv ) :
_name = ' ir.model.grid '
_table = ' ir_model '
_description = " Objects Security Grid "
_rec_name = ' name '
_columns = {
' name ' : fields . char ( ' Object ' , size = 64 ) ,
' model ' : fields . char ( ' Object Name ' , size = 64 ) ,
}
def create ( self , cr , uid , vals , context = None ) :
raise osv . except_osv ( ' Error ! ' , ' You cannot add an entry to this view ! ' )
def unlink ( self , * args , * * argv ) :
raise osv . except_osv ( ' Error ! ' , ' You cannot add an entry to this view ! ' )
2008-09-03 18:11:03 +00:00
2008-09-02 21:31:44 +00:00
def read ( self , cr , uid , ids , fields = None , context = None , load = ' _classic_read ' ) :
2008-09-03 18:11:03 +00:00
result = super ( osv . osv , self ) . read ( cr , uid , ids , fields , context , load )
2008-09-02 21:31:44 +00:00
allgr = self . pool . get ( ' res.groups ' ) . search ( cr , uid , [ ] , context = context )
acc_obj = self . pool . get ( ' ir.model.access ' )
2008-12-30 13:34:30 +00:00
if not isinstance ( result , list ) :
result = [ result ]
2008-09-02 21:31:44 +00:00
for res in result :
rules = acc_obj . search ( cr , uid , [ ( ' model_id ' , ' = ' , res [ ' id ' ] ) ] )
rules_br = acc_obj . browse ( cr , uid , rules , context = context )
for g in allgr :
res [ ' group_ ' + str ( g ) ] = ' '
for rule in rules_br :
perm_list = [ ]
if rule . perm_read :
perm_list . append ( ' r ' )
if rule . perm_write :
perm_list . append ( ' w ' )
if rule . perm_create :
perm_list . append ( ' c ' )
if rule . perm_unlink :
perm_list . append ( ' u ' )
perms = " , " . join ( perm_list )
2008-09-03 18:11:03 +00:00
if rule . group_id :
res [ ' group_ %d ' % rule . group_id . id ] = perms
else :
res [ ' group_0 ' ] = perms
2008-07-18 15:53:12 +00:00
return result
2008-04-13 06:54:08 +00:00
2008-09-02 21:31:44 +00:00
#
# This function do not write fields from ir.model because
# access rights may be different for managing models and
# access rights
#
def write ( self , cr , uid , ids , vals , context = None ) :
2008-07-30 12:42:48 +00:00
vals_new = vals . copy ( )
2008-09-02 21:31:44 +00:00
acc_obj = self . pool . get ( ' ir.model.access ' )
for grid in self . browse ( cr , uid , ids , context = context ) :
model_id = grid . id
2008-07-30 12:42:48 +00:00
perms_rel = [ ' read ' , ' write ' , ' create ' , ' unlink ' ]
2008-07-18 15:53:12 +00:00
for val in vals :
2008-09-02 21:31:44 +00:00
if not val [ : 6 ] == ' group_ ' :
continue
2008-09-03 18:11:03 +00:00
group_id = int ( val [ 6 : ] ) or False
2008-09-02 21:31:44 +00:00
rules = acc_obj . search ( cr , uid , [ ( ' model_id ' , ' = ' , model_id ) , ( ' group_id ' , ' = ' , group_id ) ] )
if not rules :
rules = [ acc_obj . create ( cr , uid , {
' name ' : grid . name ,
' model_id ' : model_id ,
' group_id ' : group_id
} ) ]
2008-10-31 16:40:14 +00:00
vals2 = dict ( map ( lambda x : ( ' perm_ ' + x , x [ 0 ] in ( vals [ val ] or ' ' ) ) , perms_rel ) )
acc_obj . write ( cr , uid , rules , vals2 , context = context )
2008-09-02 21:31:44 +00:00
return True
def fields_get ( self , cr , uid , fields = None , context = None , read_access = True ) :
result = super ( ir_model_grid , self ) . fields_get ( cr , uid , fields , context )
groups = self . pool . get ( ' res.groups ' ) . search ( cr , uid , [ ] )
groups_br = self . pool . get ( ' res.groups ' ) . browse ( cr , uid , groups )
2008-09-03 18:11:03 +00:00
result [ ' group_0 ' ] = { ' string ' : ' All Users ' , ' type ' : ' char ' , ' size ' : 7 }
2008-09-02 21:31:44 +00:00
for group in groups_br :
2008-09-03 18:11:03 +00:00
result [ ' group_ %d ' % group . id ] = { ' string ' : ' %s ' % group . name , ' type ' : ' char ' , ' size ' : 7 }
2008-07-18 15:53:12 +00:00
return result
2008-09-02 21:31:44 +00:00
2008-07-18 15:53:12 +00:00
def fields_view_get ( self , cr , uid , view_id = None , view_type = ' form ' , context = { } , toolbar = False ) :
2008-09-02 21:31:44 +00:00
result = super ( ir_model_grid , self ) . fields_view_get ( cr , uid , view_id , view_type , context = context , toolbar = toolbar )
groups = self . pool . get ( ' res.groups ' ) . search ( cr , uid , [ ] )
groups_br = self . pool . get ( ' res.groups ' ) . browse ( cr , uid , groups )
cols = [ ' model ' , ' name ' ]
xml = ''' <?xml version= " 1.0 " ?>
< % s editable = " bottom " >
2008-10-31 20:44:01 +00:00
< field name = " name " select = " 1 " readonly = " 1 " required = " 1 " / >
< field name = " model " select = " 1 " readonly = " 1 " required = " 1 " / >
2008-09-03 18:11:03 +00:00
< field name = " group_0 " / >
''' % (view_type,)
2008-09-02 21:31:44 +00:00
for group in groups_br :
2008-09-03 18:11:03 +00:00
xml + = ''' <field name= " group_ %d " /> ''' % ( group . id , )
2008-09-02 21:31:44 +00:00
xml + = ''' </ %s > ''' % ( view_type , )
result [ ' arch ' ] = xml
result [ ' fields ' ] = self . fields_get ( cr , uid , cols , context )
2008-07-18 15:53:12 +00:00
return result
2008-09-02 21:31:44 +00:00
ir_model_grid ( )
2008-03-26 21:46:53 +00:00
2006-12-07 13:41:40 +00:00
class ir_model_fields ( osv . osv ) :
2008-07-22 14:24:36 +00:00
_name = ' ir.model.fields '
_description = " Fields "
_columns = {
' name ' : fields . char ( ' Name ' , required = True , size = 64 , select = 1 ) ,
' model ' : fields . char ( ' Object Name ' , size = 64 , required = True ) ,
2008-08-21 13:49:55 +00:00
' relation ' : fields . char ( ' Object Relation ' , size = 64 ) ,
2008-10-23 13:28:28 +00:00
' relation_field ' : fields . char ( ' Relation Field ' , size = 64 ) ,
2008-08-21 13:49:55 +00:00
' model_id ' : fields . many2one ( ' ir.model ' , ' Object id ' , required = True , select = True , ondelete = ' cascade ' ) ,
2008-07-22 14:24:36 +00:00
' field_description ' : fields . char ( ' Field Label ' , required = True , size = 256 ) ,
' ttype ' : fields . selection ( _get_fields_type , ' Field Type ' , size = 64 , required = True ) ,
' selection ' : fields . char ( ' Field Selection ' , size = 128 ) ,
' required ' : fields . boolean ( ' Required ' ) ,
' readonly ' : fields . boolean ( ' Readonly ' ) ,
' select_level ' : fields . selection ( [ ( ' 0 ' , ' Not Searchable ' ) , ( ' 1 ' , ' Always Searchable ' ) , ( ' 2 ' , ' Advanced Search ' ) ] , ' Searchable ' , required = True ) ,
' translate ' : fields . boolean ( ' Translate ' ) ,
' size ' : fields . integer ( ' Size ' ) ,
2008-11-27 10:51:34 +00:00
' state ' : fields . selection ( [ ( ' manual ' , ' Custom Field ' ) , ( ' base ' , ' Base Field ' ) ] , ' Manualy Created ' , required = True , readonly = True ) ,
2008-07-22 14:24:36 +00:00
' on_delete ' : fields . selection ( [ ( ' cascade ' , ' Cascade ' ) , ( ' set null ' , ' Set NULL ' ) ] , ' On delete ' , help = ' On delete property for many2one fields ' ) ,
' domain ' : fields . char ( ' Domain ' , size = 256 ) ,
' groups ' : fields . many2many ( ' res.groups ' , ' ir_model_fields_group_rel ' , ' field_id ' , ' group_id ' , ' Groups ' ) ,
' view_load ' : fields . boolean ( ' View Auto-Load ' ) ,
}
2008-10-28 23:15:42 +00:00
_rec_name = ' field_description '
2008-07-22 14:24:36 +00:00
_defaults = {
' view_load ' : lambda * a : 0 ,
' selection ' : lambda * a : " [] " ,
' domain ' : lambda * a : " [] " ,
' name ' : lambda * a : ' x_ ' ,
' state ' : lambda self , cr , uid , ctx = { } : ( ctx and ctx . get ( ' manual ' , False ) ) and ' manual ' or ' base ' ,
' on_delete ' : lambda * a : ' set null ' ,
' select_level ' : lambda * a : ' 0 ' ,
' size ' : lambda * a : 64 ,
' field_description ' : lambda * a : ' ' ,
}
_order = " id "
def unlink ( self , cr , user , ids , context = None ) :
for field in self . browse ( cr , user , ids , context ) :
if field . state < > ' manual ' :
raise except_orm ( _ ( ' Error ' ) , _ ( " You can not remove the field ' %s ' ! " ) % ( field . name , ) )
#
# MAY BE ADD A ALTER TABLE DROP ?
#
return super ( ir_model_fields , self ) . unlink ( cr , user , ids , context )
2008-12-16 10:14:22 +00:00
2008-07-22 14:24:36 +00:00
def create ( self , cr , user , vals , context = None ) :
if ' model_id ' in vals :
2008-12-16 10:14:22 +00:00
model_data = self . pool . get ( ' ir.model ' ) . browse ( cr , user , vals [ ' model_id ' ] )
vals [ ' model ' ] = model_data . model
2008-07-22 14:24:36 +00:00
if context and context . get ( ' manual ' , False ) :
2008-12-16 10:14:22 +00:00
vals [ ' state ' ] = ' manual '
2008-07-22 14:24:36 +00:00
res = super ( ir_model_fields , self ) . create ( cr , user , vals , context )
2008-12-16 10:14:22 +00:00
if vals . get ( ' state ' , ' base ' ) == ' manual ' :
2008-07-22 14:24:36 +00:00
if not vals [ ' name ' ] . startswith ( ' x_ ' ) :
raise except_orm ( _ ( ' Error ' ) , _ ( " Custom fields must have a name that starts with ' x_ ' ! " ) )
if self . pool . get ( vals [ ' model ' ] ) :
self . pool . get ( vals [ ' model ' ] ) . __init__ ( self . pool , cr )
2008-12-16 10:14:22 +00:00
self . pool . get ( vals [ ' model ' ] ) . _auto_init ( cr , { } )
2008-07-22 14:24:36 +00:00
return res
2006-12-07 13:41:40 +00:00
ir_model_fields ( )
class ir_model_access ( osv . osv ) :
2008-07-22 14:24:36 +00:00
_name = ' ir.model.access '
_columns = {
' name ' : fields . char ( ' Name ' , size = 64 , required = True ) ,
2008-08-21 13:49:55 +00:00
' model_id ' : fields . many2one ( ' ir.model ' , ' Object ' , required = True ) ,
2008-07-22 14:24:36 +00:00
' group_id ' : fields . many2one ( ' res.groups ' , ' Group ' ) ,
' perm_read ' : fields . boolean ( ' Read Access ' ) ,
' perm_write ' : fields . boolean ( ' Write Access ' ) ,
' perm_create ' : fields . boolean ( ' Create Access ' ) ,
' perm_unlink ' : fields . boolean ( ' Delete Permission ' ) ,
}
2008-09-22 06:48:49 +00:00
2008-07-22 14:24:36 +00:00
def check_groups ( self , cr , uid , group ) :
res = False
grouparr = group . split ( ' . ' )
2008-09-22 11:13:18 +00:00
if not grouparr :
return False
2008-12-09 12:37:22 +00:00
cr . execute ( " select 1 from res_groups_users_rel where uid= %s and gid in(select res_id from ir_model_data where module= %s and name= %s ) " , ( uid , grouparr [ 0 ] , grouparr [ 1 ] , ) )
2008-09-22 11:13:18 +00:00
return bool ( cr . fetchone ( ) )
2008-09-22 06:48:49 +00:00
2008-10-17 16:15:53 +00:00
def check_group ( self , cr , uid , model , mode , group_ids ) :
2008-10-17 09:23:18 +00:00
""" Check if a specific group has the access mode to the specified model """
assert mode in [ ' read ' , ' write ' , ' create ' , ' unlink ' ] , ' Invalid access mode '
if isinstance ( model , browse_record ) :
assert model . _table_name == ' ir.model ' , ' Invalid model object '
model_name = model . name
else :
model_name = model
2008-12-16 10:14:22 +00:00
2008-10-17 16:15:53 +00:00
if isinstance ( group_ids , ( int , long ) ) :
group_ids = [ group_ids ]
for group_id in group_ids :
cr . execute ( " SELECT perm_ " + mode + " "
2008-10-17 09:23:18 +00:00
" FROM ir_model_access a "
" JOIN ir_model m ON (m.id = a.model_id) "
2008-12-09 12:37:22 +00:00
" WHERE m.model = %s AND a.group_id = %s " , ( model_name , group_id )
2008-10-17 09:23:18 +00:00
)
2008-10-17 16:15:53 +00:00
r = cr . fetchone ( )
if r is None :
cr . execute ( " SELECT perm_ " + mode + " "
2008-10-17 10:05:50 +00:00
" FROM ir_model_access a "
" JOIN ir_model m ON (m.id = a.model_id) "
" WHERE m.model = %s AND a.group_id IS NULL " , ( model_name , )
)
2008-10-17 16:15:53 +00:00
r = cr . fetchone ( )
2008-10-17 10:05:50 +00:00
2008-10-17 16:15:53 +00:00
access = bool ( r and r [ 0 ] )
if access :
return True
# pass no groups -> no access
return False
2008-09-22 06:48:49 +00:00
2008-10-08 14:13:18 +00:00
def check ( self , cr , uid , model , mode = ' read ' , raise_exception = True ) :
2008-07-18 16:40:51 +00:00
if uid == 1 :
2008-12-16 10:14:22 +00:00
# User root have all accesses
2008-10-17 09:23:18 +00:00
# TODO: exclude xml-rpc requests
2008-08-24 15:03:23 +00:00
return True
2008-09-22 06:48:49 +00:00
2008-08-04 09:31:37 +00:00
assert mode in [ ' read ' , ' write ' , ' create ' , ' unlink ' ] , ' Invalid access mode '
2008-09-22 06:48:49 +00:00
2008-10-08 14:13:18 +00:00
if isinstance ( model , browse_record ) :
assert model . _table_name == ' ir.model ' , ' Invalid model object '
model_name = model . name
else :
model_name = model
2008-12-16 10:14:22 +00:00
2008-07-18 15:53:12 +00:00
# We check if a specific rule exists
2008-09-22 11:13:18 +00:00
cr . execute ( ' SELECT MAX(CASE WHEN perm_ ' + mode + ' THEN 1 ELSE 0 END) '
' FROM ir_model_access a '
' JOIN ir_model m ON (m.id = a.model_id) '
' JOIN res_groups_users_rel gu ON (gu.gid = a.group_id) '
' WHERE m.model = %s '
' AND gu.uid = %s '
, ( model_name , uid , )
)
r = cr . fetchone ( ) [ 0 ]
if r is None :
# there is no specific rule. We check the generic rule
cr . execute ( ' SELECT MAX(CASE WHEN perm_ ' + mode + ' THEN 1 ELSE 0 END) '
' FROM ir_model_access a '
' JOIN ir_model m ON (m.id = a.model_id) '
' WHERE a.group_id IS NULL '
' AND m.model = %s '
, ( model_name , )
)
r = cr . fetchone ( ) [ 0 ]
2008-09-22 06:48:49 +00:00
2008-09-22 11:13:18 +00:00
if not r and raise_exception :
msgs = {
' read ' : _ ( ' You can not read this document! ( %s ) ' ) ,
' write ' : _ ( ' You can not write in this document! ( %s ) ' ) ,
' create ' : _ ( ' You can not create this kind of document! ( %s ) ' ) ,
' unlink ' : _ ( ' You can not delete this document! ( %s ) ' ) ,
}
raise except_orm ( _ ( ' AccessError ' ) , msgs [ mode ] % model_name )
return r
2007-09-26 05:17:28 +00:00
2008-07-22 14:24:36 +00:00
check = tools . cache ( ) ( check )
2006-12-07 13:41:40 +00:00
2008-10-16 18:28:16 +00:00
__cache_clearing_methods = [ ]
def register_cache_clearing_method ( self , model , method ) :
self . __cache_clearing_methods . append ( ( model , method ) )
def unregister_cache_clearing_method ( self , model , method ) :
try :
i = self . __cache_clearing_methods . index ( ( model , method ) )
del self . __cache_clearing_methods [ i ]
except ValueError :
pass
def call_cache_clearing_methods ( self ) :
for model , method in self . __cache_clearing_methods :
getattr ( self . pool . get ( model ) , method ) ( )
2008-07-22 14:24:36 +00:00
#
2008-07-14 13:53:01 +00:00
# Check rights on actions
2008-07-22 14:24:36 +00:00
#
def write ( self , cr , uid , * args , * * argv ) :
2008-10-16 18:28:16 +00:00
self . call_cache_clearing_methods ( )
2008-07-22 14:24:36 +00:00
res = super ( ir_model_access , self ) . write ( cr , uid , * args , * * argv )
2009-01-05 21:17:46 +00:00
self . check . clear_cache ( cr . dbname ) # clear the cache of check function
2008-07-22 14:24:36 +00:00
return res
2008-12-16 10:14:22 +00:00
2008-07-22 14:24:36 +00:00
def create ( self , cr , uid , * args , * * argv ) :
res = super ( ir_model_access , self ) . create ( cr , uid , * args , * * argv )
2009-01-05 21:17:46 +00:00
self . check . clear_cache ( cr . dbname ) # clear the cache of check function
2008-07-22 14:24:36 +00:00
return res
2008-10-16 18:28:16 +00:00
2008-07-22 14:24:36 +00:00
def unlink ( self , cr , uid , * args , * * argv ) :
2008-10-16 18:28:16 +00:00
self . call_cache_clearing_methods ( )
2008-07-22 14:24:36 +00:00
res = super ( ir_model_access , self ) . unlink ( cr , uid , * args , * * argv )
2009-01-05 21:17:46 +00:00
self . check . clear_cache ( cr . dbname ) # clear the cache of check function
2008-07-22 14:24:36 +00:00
return res
2008-10-16 18:28:16 +00:00
2006-12-07 13:41:40 +00:00
ir_model_access ( )
class ir_model_data ( osv . osv ) :
2008-07-22 14:24:36 +00:00
_name = ' ir.model.data '
_columns = {
' name ' : fields . char ( ' XML Identifier ' , required = True , size = 64 ) ,
2008-08-21 13:49:55 +00:00
' model ' : fields . char ( ' Object ' , required = True , size = 64 ) ,
2008-07-22 14:24:36 +00:00
' module ' : fields . char ( ' Module ' , required = True , size = 64 ) ,
' res_id ' : fields . integer ( ' Resource ID ' ) ,
' noupdate ' : fields . boolean ( ' Non Updatable ' ) ,
' date_update ' : fields . datetime ( ' Update Date ' ) ,
' date_init ' : fields . datetime ( ' Init Date ' )
}
_defaults = {
' date_init ' : lambda * a : time . strftime ( ' % Y- % m- %d % H: % M: % S ' ) ,
' date_update ' : lambda * a : time . strftime ( ' % Y- % m- %d % H: % M: % S ' ) ,
' noupdate ' : lambda * a : False
}
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def __init__ ( self , pool , cr ) :
osv . osv . __init__ ( self , pool , cr )
self . loads = { }
self . doinit = True
self . unlink_mark = { }
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def _get_id ( self , cr , uid , module , xml_id ) :
ids = self . search ( cr , uid , [ ( ' module ' , ' = ' , module ) , ( ' name ' , ' = ' , xml_id ) ] )
2008-09-30 13:17:54 +00:00
assert len ( ids ) == 1 , ' %d reference(s) to %s . %s . You should have one and only one ! ' % ( len ( ids ) , module , xml_id )
2008-07-22 14:24:36 +00:00
return ids [ 0 ]
2008-12-13 06:15:46 +00:00
_get_id = tools . cache ( skiparg = 2 ) ( _get_id )
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def _update_dummy ( self , cr , uid , model , module , xml_id = False , store = True ) :
if not xml_id :
return False
try :
id = self . read ( cr , uid , [ self . _get_id ( cr , uid , module , xml_id ) ] , [ ' res_id ' ] ) [ 0 ] [ ' res_id ' ]
self . loads [ ( module , xml_id ) ] = ( model , id )
except :
id = False
return id
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def _update ( self , cr , uid , model , module , values , xml_id = False , store = True , noupdate = False , mode = ' init ' , res_id = False ) :
warning = True
model_obj = self . pool . get ( model )
2008-09-22 06:48:49 +00:00
context = { }
2008-07-22 14:24:36 +00:00
if xml_id and ( ' . ' in xml_id ) :
assert len ( xml_id . split ( ' . ' ) ) == 2 , _ ( ' " %s " contains too many dots. XML ids should not contain dots ! These are used to refer to other modules data, as in module.reference_id ' ) % ( xml_id )
warning = False
module , xml_id = xml_id . split ( ' . ' )
if ( not xml_id ) and ( not self . doinit ) :
return False
action_id = False
if xml_id :
cr . execute ( ' select id,res_id from ir_model_data where module= %s and name= %s ' , ( module , xml_id ) )
results = cr . fetchall ( )
for action_id2 , res_id2 in results :
2008-12-09 12:37:22 +00:00
cr . execute ( ' select id from ' + self . pool . get ( model ) . _table + ' where id= %s ' , ( res_id2 , ) )
2008-07-22 14:24:36 +00:00
result3 = cr . fetchone ( )
if not result3 :
2008-12-09 12:37:22 +00:00
cr . execute ( ' delete from ir_model_data where id= %s ' , ( action_id2 , ) )
2008-07-22 14:24:36 +00:00
else :
res_id , action_id = res_id2 , action_id2
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
if action_id and res_id :
model_obj . write ( cr , uid , [ res_id ] , values )
self . write ( cr , uid , [ action_id ] , {
' date_update ' : time . strftime ( ' % Y- % m- %d % H: % M: % S ' ) ,
} )
elif res_id :
model_obj . write ( cr , uid , [ res_id ] , values )
if xml_id :
self . create ( cr , uid , {
' name ' : xml_id ,
' model ' : model ,
' module ' : module ,
' res_id ' : res_id ,
' noupdate ' : noupdate ,
} )
if model_obj . _inherits :
for table in model_obj . _inherits :
inherit_id = model_obj . browse ( cr , uid ,
res_id ) [ model_obj . _inherits [ table ] ]
self . create ( cr , uid , {
' name ' : xml_id + ' _ ' + table . replace ( ' . ' , ' _ ' ) ,
' model ' : table ,
' module ' : module ,
' res_id ' : inherit_id ,
' noupdate ' : noupdate ,
} )
else :
if mode == ' init ' or ( mode == ' update ' and xml_id ) :
res_id = model_obj . create ( cr , uid , values )
if xml_id :
self . create ( cr , uid , {
' name ' : xml_id ,
' model ' : model ,
' module ' : module ,
' res_id ' : res_id ,
' noupdate ' : noupdate
} )
if model_obj . _inherits :
for table in model_obj . _inherits :
inherit_id = model_obj . browse ( cr , uid ,
res_id ) [ model_obj . _inherits [ table ] ]
self . create ( cr , uid , {
' name ' : xml_id + ' _ ' + table . replace ( ' . ' , ' _ ' ) ,
' model ' : table ,
' module ' : module ,
' res_id ' : inherit_id ,
' noupdate ' : noupdate ,
} )
if xml_id :
if res_id :
self . loads [ ( module , xml_id ) ] = ( model , res_id )
if model_obj . _inherits :
for table in model_obj . _inherits :
inherit_field = model_obj . _inherits [ table ]
inherit_id = model_obj . read ( cr , uid , res_id ,
[ inherit_field ] ) [ inherit_field ]
self . loads [ ( module , xml_id + ' _ ' + \
table . replace ( ' . ' , ' _ ' ) ) ] = ( table , inherit_id )
return res_id
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def _unlink ( self , cr , uid , model , ids , direct = False ) :
#self.pool.get(model).unlink(cr, uid, ids)
for id in ids :
self . unlink_mark [ ( model , id ) ] = False
2008-12-09 12:37:22 +00:00
cr . execute ( ' delete from ir_model_data where res_id= %s and model= \' %s \' ' , ( id , model ) )
2008-07-22 14:24:36 +00:00
return True
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def ir_set ( self , cr , uid , key , key2 , name , models , value , replace = True , isobject = False , meta = None , xml_id = False ) :
obj = self . pool . get ( ' ir.values ' )
if type ( models [ 0 ] ) == type ( [ ] ) or type ( models [ 0 ] ) == type ( ( ) ) :
model , res_id = models [ 0 ]
else :
res_id = None
model = models [ 0 ]
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
if res_id :
2008-12-09 12:37:22 +00:00
where = ' and res_id= %s ' % ( res_id , )
2008-07-22 14:24:36 +00:00
else :
where = ' and (res_id is null) '
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
if key2 :
where + = ' and key2= \' %s \' ' % ( key2 , )
else :
where + = ' and (key2 is null) '
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
cr . execute ( ' select * from ir_values where model= %s and key= %s and name= %s ' + where , ( model , key , name ) )
res = cr . fetchone ( )
if not res :
res = ir . ir_set ( cr , uid , key , key2 , name , models , value , replace , isobject , meta )
elif xml_id :
cr . execute ( ' UPDATE ir_values set value= %s WHERE model= %s and key= %s and name= %s ' + where , ( value , model , key , name ) )
return True
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
def _process_end ( self , cr , uid , modules ) :
if not modules :
return True
2008-12-30 13:08:29 +00:00
modules = list ( modules )
2008-12-30 21:35:12 +00:00
module_in = " , " . join ( [ " %s " ] * len ( modules ) )
2008-12-30 13:08:29 +00:00
cr . execute ( ' select id,name,model,res_id,module from ir_model_data where module in ( ' + module_in + ' ) and noupdate= %s ' , modules + [ False ] )
2008-07-22 14:24:36 +00:00
wkf_todo = [ ]
for ( id , name , model , res_id , module ) in cr . fetchall ( ) :
if ( module , name ) not in self . loads :
self . unlink_mark [ ( model , res_id ) ] = id
if model == ' workflow.activity ' :
2008-12-09 12:37:22 +00:00
cr . execute ( ' select res_type,res_id from wkf_instance where id in (select inst_id from wkf_workitem where act_id= %s ) ' , ( res_id , ) )
2008-07-22 14:24:36 +00:00
wkf_todo . extend ( cr . fetchall ( ) )
2008-12-09 12:37:22 +00:00
cr . execute ( " update wkf_transition set condition= ' True ' , role_id=NULL, signal=NULL,act_to=act_from,act_from= %s where act_to= %s " , ( res_id , res_id ) )
cr . execute ( " delete from wkf_transition where act_to= %s " , ( res_id , ) )
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
for model , id in wkf_todo :
wf_service = netsvc . LocalService ( " workflow " )
wf_service . trg_write ( uid , model , id , cr )
2006-12-07 13:41:40 +00:00
2008-07-22 14:24:36 +00:00
cr . commit ( )
2008-11-25 15:19:14 +00:00
if not config . get ( ' import_partial ' , False ) :
for ( model , id ) in self . unlink_mark . keys ( ) :
if self . pool . get ( model ) :
logger = netsvc . Logger ( )
logger . notifyChannel ( ' init ' , netsvc . LOG_INFO , ' Deleting %s @ %s ' % ( id , model ) )
try :
self . pool . get ( model ) . unlink ( cr , uid , [ id ] )
if self . unlink_mark [ ( model , id ) ] :
self . unlink ( cr , uid , [ self . unlink_mark [ ( model , id ) ] ] )
cr . execute ( ' DELETE FROM ir_values WHERE value= %s ' , ( model + ' , ' + str ( id ) , ) )
cr . commit ( )
except :
logger . notifyChannel ( ' init ' , netsvc . LOG_ERROR , ' Could not delete id: %d of model %s \t There should be some relation that points to this resource \t You should manually fix this and restart --update=module ' % ( id , model ) )
2008-07-22 14:24:36 +00:00
return True
2006-12-07 13:41:40 +00:00
ir_model_data ( )
2008-07-23 14:27:04 +00:00
class ir_model_config ( osv . osv ) :
_name = ' ir.model.config '
2008-07-23 10:25:20 +00:00
_columns = {
2008-07-28 15:43:35 +00:00
' password ' : fields . char ( ' Password ' , size = 64 ) ,
' password_check ' : fields . char ( ' confirmation ' , size = 64 ) ,
2008-07-23 10:25:20 +00:00
}
def action_cancel ( self , cr , uid , ids , context = { } ) :
return {
' view_type ' : ' form ' ,
" view_mode " : ' form ' ,
2008-09-29 08:49:06 +00:00
' res_model ' : ' ir.actions.configuration.wizard ' ,
2008-07-23 10:25:20 +00:00
' type ' : ' ir.actions.act_window ' ,
' target ' : ' new ' ,
}
2008-09-22 06:48:49 +00:00
2008-07-23 10:25:20 +00:00
def action_update_pw ( self , cr , uid , ids , context = { } ) :
res = self . read ( cr , uid , ids ) [ 0 ]
root = self . pool . get ( ' res.users ' ) . browse ( cr , uid , [ 1 ] ) [ 0 ]
self . unlink ( cr , uid , [ res [ ' id ' ] ] )
2008-07-28 15:43:35 +00:00
if res [ ' password ' ] != res [ ' password_check ' ] :
2008-07-24 16:19:44 +00:00
raise except_orm ( _ ( ' Error ' ) , _ ( " Password mismatch ! " ) )
2008-07-28 15:43:35 +00:00
elif not res [ ' password ' ] :
raise except_orm ( _ ( ' Error ' ) , _ ( " Password empty ! " ) )
self . pool . get ( ' res.users ' ) . write ( cr , uid , [ root . id ] , { ' password ' : res [ ' password ' ] } )
return {
' view_type ' : ' form ' ,
" view_mode " : ' form ' ,
2008-09-29 08:49:06 +00:00
' res_model ' : ' ir.actions.configuration.wizard ' ,
2008-07-28 15:43:35 +00:00
' type ' : ' ir.actions.act_window ' ,
' target ' : ' new ' ,
}
2008-07-23 14:27:04 +00:00
ir_model_config ( )
2008-07-23 15:01:27 +00:00
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: