Max (OpenERP) has proposed merging lp:~openerp-dev/openerp-int/mck_audit_mmu 
into lp:~openerp-dev/openerp-int/mck_audit_tfr.

Requested reviews:
  tfr (Openerp) (tfr)

For more details, see:
https://code.launchpad.net/~openerp-dev/openerp-int/mck_audit_mmu/+merge/133895

[IMP] Replaced model level field access permissions with abstracted orm level 
read override to control which users can see which fields
-- 
https://code.launchpad.net/~openerp-dev/openerp-int/mck_audit_mmu/+merge/133895
Your team OpenERP R&D Team is subscribed to branch 
lp:~openerp-dev/openerp-int/mck_audit_tfr.
=== modified file 'mck_common/event.py'
--- mck_common/event.py	2012-10-23 08:09:42 +0000
+++ mck_common/event.py	2012-11-12 11:47:27 +0000
@@ -327,11 +327,7 @@
             args.append(('date','>=',today))
         return super(mck_invitee, self).search(cr, uid, args,offset, limit, order, context, count)
     
-    def filter_email(self, cr, uid, ids, res, context=None):
-        user_level = self.pool.get('res.users').get_level(cr, uid, context)
-        if user_level > 2:
-            return res
-        
+    def _filter_records(self, cr, uid, res, context=None):
         user_practice_id = self.pool.get('res.users').browse(cr, uid, uid, context=context).context_practice_id.id
         
         contact_ids = []
@@ -356,16 +352,34 @@
                     contact_id = contact_id[0]
                 if not (practice_link_ids_per_contact[contact_id] and
                     user_practice_id in practice_link_ids_per_contact[contact_id]):
-                        result['email'] = "<Access denied>"
+                        result = self._filter_record(result)
         
         return res
 
+    # define fields that should be hidden from users who do not have enough permissions
+    _access_denied_fields = ['email']
+
+    def _filter_read(self, cr, uid, all_records, context=None):
+        """
+            override this field from the BaseModel class to check user access and, if needed, hide some fields
+            using the _filter_records function
+        """
+
+        # if user level is above 2, return full data
+        user_level = self.pool.get('res.users').get_level(cr, uid, context)
+        if user_level > 2:
+            return all_records
+        
+        # otherwise, apply _filter_records function to data and return it
+        all_records = self._filter_records(cr, uid, all_records, context=context)
+        return all_records
+
     def read(self, cr, uid, ids, fields=None, context=None, load='_classic_read'):
         if fields and not 'executive_id' in fields:
             fields.append('executive_id')
         res = super(mck_invitee, self).read(cr, uid, ids, fields, context, load)
-        if not fields or 'email' in fields:
-            res = self.filter_email(cr, uid, ids, res, context)
+        #if not fields or 'email' in fields:
+        #    res = self._filter_records(cr, uid, ids, res, context)
         return res
         
 

=== modified file 'mck_contact/__init__.py'
--- mck_contact/__init__.py	2012-05-22 14:33:56 +0000
+++ mck_contact/__init__.py	2012-11-12 11:47:27 +0000
@@ -1,3 +1,4 @@
+import orm
 import role_type
 import company
 import industry

=== added file 'mck_contact/orm.py'
--- mck_contact/orm.py	1970-01-01 00:00:00 +0000
+++ mck_contact/orm.py	2012-11-12 11:47:27 +0000
@@ -0,0 +1,34 @@
+from openerp.osv.orm import BaseModel
+
+# list of field names that should be shown as "<Access Denied>" to users without high enough permissions
+BaseModel._access_denied_fields = []
+# function to be overridden by function that checks users access and calls _filter_record if data should be hidden from them
+BaseModel._filter_read = lambda self, cr, uid, all_records, context=None: all_records
+
+# get reference to the old read function for emulating super call outside of class context
+super_read = BaseModel.read
+
+# define new read function to override basemodel read
+def read(self, cr, uid, ids, fields=None, context=None, load='_classic_read'):
+
+	# get objects from the database
+	all_records = super_read(self, cr, uid, ids, fields=fields, context=context, load=load)
+
+	# if the _access_denied_fields attribute of the model has any fields defined, 
+	# run the all_records set through the overridden filter_read function.
+	# Otherwise return the full data set
+	if len(self._access_denied_fields) > 0:
+		all_records = self._filter_read(cr, uid, all_records, context)
+		return all_records
+	else:
+		return all_records
+
+def _filter_record(self, record):
+	"Method used for replacing dictionary items whose keys are in the _access_denied_fields list with <Access Denied>"
+	filtered_values = dict.fromkeys(self._access_denied_fields, "<Access denied>")
+	record.update(filtered_values)
+	return record
+
+# Replace read with our custom read function and attach the _filter_record function
+BaseModel.read = read
+BaseModel._filter_record = _filter_record
\ No newline at end of file

=== modified file 'mck_contact/role.py'
--- mck_contact/role.py	2012-11-09 09:58:54 +0000
+++ mck_contact/role.py	2012-11-12 11:47:27 +0000
@@ -190,43 +190,65 @@
                 contact_ids.append(contact_id)
         return contact_ids
     
-    def filter_email(self, cr, uid, ids, res, context=None):
-        user_level = self.pool.get('res.users').get_level(cr, uid, context)
-        if user_level > 2:
-            return res
+    def _filter_records(self, cr, uid, data, context=None):
+        """
+            Take in a list of data, check the user has access to read this data
+            and call the _filter_record function to filter access denied fields
+            if they do not have permission
+        """
         
+        # get the user's practice id and extract all contacts from each record
         user_practice_id = self.pool.get('res.users').browse(cr, uid, uid, context=context).context_practice_id.id
-        #user_region = self.pool.get('res.users').browse(cr, uid, uid, context=context).context_region
+
         contact_ids = []
-        for result in res:
-            if result.get('contact_id'):
-                contact_id = result.get('contact_id')
+        for record in data:
+            if record.get('contact_id'):
+                contact_id = record.get('contact_id')
                 if isinstance(contact_id, tuple):
                     contact_id = contact_id[0]
                 contact_ids.append(contact_id)
-                
+             
+        # get contact records from contact ids   
         contacts = self.pool.get('res.partner.contact').browse(cr, uid, contact_ids, context=context)
         practice_link_ids_per_contact = {}
+
+        # for each contact, extract all their executive practice link ids and the cell id that created the executive
         for contact in contacts:
             practice_link_ids_per_contact[contact.id] = [p.practice_id.id for p in contact.exec_practice_link_ids]
             if contact.cell_id: #Add the cell that create the exec
                 practice_link_ids_per_contact[contact.id].append(contact.cell_id.id)
-                    
-        for result in res:
-            if result.get('contact_id'):
-                contact_id = result.get('contact_id')
+  
+        # for each record, extract the contact_id and look for it in the list of result practice ids. Filter data if
+        # it is not found                  
+        for record in data:
+            if record.get('contact_id'):
+                contact_id = record.get('contact_id')
                 if isinstance(contact_id, tuple):
                     contact_id = contact_id[0]
-                if not (practice_link_ids_per_contact[contact_id] and
-                    user_practice_id in practice_link_ids_per_contact[contact_id]): 
+                if not (practice_link_ids_per_contact[contact_id] and user_practice_id in practice_link_ids_per_contact[contact_id]): 
                     #or (user_region != REGION_GLOBAL and user_region != result.get('region'))
-                        deny_values = dict.fromkeys(self._FIELD_DENY, "<Access denied>")
-                        result.update(deny_values)
-        return res
-
-    _FIELD_DENY = ['email', 'fax', 'phone', 'mobile', 'assistant_email', 'assistant_mobile', 'assistant_phone']
-    
-    
+                        record = self._filter_record(record)
+
+        return data
+
+    # define fields that should be hidden from users who do not have enough permissions
+    _access_denied_fields = ['email', 'fax', 'phone', 'mobile', 'assistant_email', 'assistant_mobile', 'assistant_phone']
+
+    def _filter_read(self, cr, uid, all_records, context=None):
+        """
+            override this field from the BaseModel class to check user access and, if needed, hide some fields
+            using the _filter_records function
+        """
+
+        # if user level is above 2, return full data
+        user_level = self.pool.get('res.users').get_level(cr, uid, context)
+        if user_level > 2:
+            return all_records
+        
+        # otherwise, apply _filter_records function to data and return it
+        all_records = self._filter_records(cr, uid, all_records, context=context)
+        return all_records
+
     def read(self, cr, uid, ids, fields=None, context=None, load='_classic_read'):
         if fields and not 'contact_id' in fields:
             fields.append('contact_id')
@@ -234,8 +256,8 @@
         #    fields.append('region')
             
         res = super(role, self).read(cr, uid, ids, fields, context, load)
-        if not fields or any([field in fields for field in self._FIELD_DENY]):
-            res = self.filter_email(cr, uid, ids, res, context)
+        #if not fields or any([field in fields for field in self._access_denied_fields]):
+        #    res = self._filter_records(cr, uid, ids, res, context)
         return res
         
     def _onePrimary(self, cr, uid, ids):

=== modified file 'mck_internal/practice.py'
--- mck_internal/practice.py	2012-10-09 20:40:19 +0000
+++ mck_internal/practice.py	2012-11-12 11:47:27 +0000
@@ -90,7 +90,7 @@
     def _check_email(self, cr, uid, ids):
         for contact in self.browse(cr,uid,ids):
             email = contact.email
-            if check_mail(email):
+            if email == "<Access Denied>" or check_mail(email):
                 return True
             else:
                 return False

_______________________________________________
Mailing list: https://launchpad.net/~openerp-dev-gtk
Post to     : [email protected]
Unsubscribe : https://launchpad.net/~openerp-dev-gtk
More help   : https://help.launchpad.net/ListHelp

Reply via email to