From cb35581a6b737c55564b1283f46dd5db19e791ae Mon Sep 17 00:00:00 2001 From: Holger Brunn Date: Wed, 14 Jan 2015 15:17:28 +0100 Subject: [PATCH 1/4] [ADD] auth_dynamic_groups --- auth_dynamic_groups/__init__.py | 21 +++++++ auth_dynamic_groups/__openerp__.py | 55 +++++++++++++++++ auth_dynamic_groups/model/__init__.py | 22 +++++++ auth_dynamic_groups/model/res_groups.py | 78 +++++++++++++++++++++++++ auth_dynamic_groups/model/res_users.py | 53 +++++++++++++++++ auth_dynamic_groups/view/res_groups.xml | 30 ++++++++++ 6 files changed, 259 insertions(+) create mode 100644 auth_dynamic_groups/__init__.py create mode 100644 auth_dynamic_groups/__openerp__.py create mode 100644 auth_dynamic_groups/model/__init__.py create mode 100644 auth_dynamic_groups/model/res_groups.py create mode 100644 auth_dynamic_groups/model/res_users.py create mode 100644 auth_dynamic_groups/view/res_groups.xml diff --git a/auth_dynamic_groups/__init__.py b/auth_dynamic_groups/__init__.py new file mode 100644 index 000000000..4d083ea93 --- /dev/null +++ b/auth_dynamic_groups/__init__.py @@ -0,0 +1,21 @@ +# -*- coding: utf-8 -*- +############################################################################## +# +# OpenERP, Open Source Management Solution +# This module copyright (C) 2013 Therp BV (). +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# 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 Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################## +import model diff --git a/auth_dynamic_groups/__openerp__.py b/auth_dynamic_groups/__openerp__.py new file mode 100644 index 000000000..e97b5b47f --- /dev/null +++ b/auth_dynamic_groups/__openerp__.py @@ -0,0 +1,55 @@ +# -*- coding: utf-8 -*- +############################################################################## +# +# OpenERP, Open Source Management Solution +# This module copyright (C) 2013 Therp BV (). +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# 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 Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################## +{ + "name" : "Dynamic groups", + "version" : "1.0", + "author" : "Therp BV", + "complexity": "normal", + "description": """ +Description +----------- +This module allows defining groups whose membership is a condition expressed as +python code. For every user, it is evaluated during login if she belongs to +the group or not. + +Usage +----- +Check `Dynamic` on a group you want to be dynamic. Now fill in the condition, +using `user` which is a browse record of the user in question that evaluates +truthy if the user is supposed to be a member of the group and falsy if not. + +There is a constraint on the field to check for validity if this expression. +When you're satisfied, click the button `Evaluate` to prefill the group's +members. The condition will be checked now for every user who logs in. + """, + "category" : "Tools", + "depends" : [ + 'base', + ], + "data" : [ + 'view/res_groups.xml', + ], + "auto_install": False, + "installable": True, + "external_dependencies" : { + 'python' : [], + }, +} diff --git a/auth_dynamic_groups/model/__init__.py b/auth_dynamic_groups/model/__init__.py new file mode 100644 index 000000000..688da41fd --- /dev/null +++ b/auth_dynamic_groups/model/__init__.py @@ -0,0 +1,22 @@ +# -*- coding: utf-8 -*- +############################################################################## +# +# OpenERP, Open Source Management Solution +# This module copyright (C) 2013 Therp BV (). +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# 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 Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################## +import res_users +import res_groups diff --git a/auth_dynamic_groups/model/res_groups.py b/auth_dynamic_groups/model/res_groups.py new file mode 100644 index 000000000..b484731ce --- /dev/null +++ b/auth_dynamic_groups/model/res_groups.py @@ -0,0 +1,78 @@ +# -*- coding: utf-8 -*- +############################################################################## +# +# OpenERP, Open Source Management Solution +# This module copyright (C) 2013 Therp BV (). +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# 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 Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################## +import logging +from openerp.osv.orm import Model +from openerp.osv import fields +from openerp.tools.safe_eval import safe_eval +from openerp import SUPERUSER_ID + + +class res_groups(Model): + _inherit = 'res.groups' + + _columns = { + 'is_dynamic': fields.boolean('Dynamic'), + 'dynamic_group_condition': fields.text( + 'Condition', help=''' + The condition to be met for a user to be a member of this + group. It is evaluated as python code at login time, you get + `user' passed as a browse record''') + } + + def eval_dynamic_group_condition(self, cr, uid, ids, context=None): + result = True + user = self.pool.get('res.users').browse(cr, SUPERUSER_ID, uid, + context=context) + for this in self.browse(cr, uid, ids, context=context): + result &= bool( + safe_eval( + this.dynamic_group_condition, + { + 'user': user, + 'any': any, + 'all': all, + 'filter': filter, + })) + return result + + def _check_dynamic_group_condition(self, cr, uid, ids, context=None): + try: + for this in self.browse(cr, uid, ids, context=context): + if this.is_dynamic: + this.eval_dynamic_group_condition() + except (NameError, SyntaxError, TypeError) as e: + logging.info(e) + return False + return True + + _constraints = [ + (_check_dynamic_group_condition, + 'The condition doesn\'t evaluate correctly!', + ['dynamic_group_condition']), + ] + + def action_evaluate(self, cr, uid, ids, context=None): + user_obj = self.pool.get('res.users') + for user in user_obj.browse( + cr, uid, + user_obj.search(cr, uid, [], context=context), + context=context): + user_obj.update_dynamic_groups(user.id, cr.dbname) diff --git a/auth_dynamic_groups/model/res_users.py b/auth_dynamic_groups/model/res_users.py new file mode 100644 index 000000000..89109c61c --- /dev/null +++ b/auth_dynamic_groups/model/res_users.py @@ -0,0 +1,53 @@ +# -*- coding: utf-8 -*- +############################################################################## +# +# OpenERP, Open Source Management Solution +# This module copyright (C) 2013 Therp BV (). +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# 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 Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +############################################################################## +import logging +from openerp.osv.orm import Model +from openerp.osv import fields +from openerp import pooler, SUPERUSER_ID + +class res_users(Model): + _inherit = 'res.users' + + def login(self, db, login, password): + uid = super(res_users, self).login(db, login, password) + + if uid: + self.update_dynamic_groups(uid, db) + + return uid + + def update_dynamic_groups(self, uid, db): + cr = pooler.get_db(db).cursor() + pool = pooler.get_pool(db) + user = pool.get('res.users').browse(cr, SUPERUSER_ID, uid) + groups_obj = pool.get('res.groups') + user.write( + { + 'groups_id': [(4, dynamic_group.id) + if dynamic_group.eval_dynamic_group_condition() + else (3, dynamic_group.id) + for dynamic_group in groups_obj.browse( + cr, uid, + groups_obj.search(cr, uid, + [('is_dynamic', '=', True)]))] + }) + cr.commit() + cr.close() diff --git a/auth_dynamic_groups/view/res_groups.xml b/auth_dynamic_groups/view/res_groups.xml new file mode 100644 index 000000000..fdc2be61d --- /dev/null +++ b/auth_dynamic_groups/view/res_groups.xml @@ -0,0 +1,30 @@ + + + + + form + res.groups + + + + + + + {'readonly': [('is_dynamic', '=', True)]} + + + +