diff --git a/base_filter_hidden/README.rst b/base_filter_hidden/README.rst new file mode 100644 index 0000000..b7bf6b2 --- /dev/null +++ b/base_filter_hidden/README.rst @@ -0,0 +1,88 @@ +================== +Base filter hidden +================== + +.. !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + !! This file is generated by oca-gen-addon-readme !! + !! changes will be overwritten. !! + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + +.. |badge1| image:: https://img.shields.io/badge/maturity-Alpha-red.png + :target: https://odoo-community.org/page/development-status + :alt: Alpha +.. |badge2| image:: https://img.shields.io/badge/licence-AGPL--3-blue.png + :target: http://www.gnu.org/licenses/agpl-3.0-standalone.html + :alt: License: AGPL-3 +.. |badge3| image:: https://img.shields.io/badge/github-OCA%2Fserver--ux-lightgray.png?logo=github + :target: https://github.com/OCA/server-ux/tree/11.0/base_filter_hidden + :alt: OCA/server-ux +.. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png + :target: https://translation.odoo-community.org/projects/server-ux-11-0/server-ux-11-0-base_filter_hidden + :alt: Translate me on Weblate +.. |badge5| image:: https://img.shields.io/badge/runbot-Try%20me-875A7B.png + :target: https://runbot.odoo-community.org/runbot/250/11.0 + :alt: Try me on Runbot + +|badge1| |badge2| |badge3| |badge4| |badge5| + +This addon is used to use some filters (ir.filters) only for the system purpose. +The advantage is filters defined as System Filters will not be loaded into the web interface. + + +Features: + +* Add 'is_system' field into ir.filters. +* During load of filters (during view load), ignore System filters. + +**Table of contents** + +.. contents:: + :local: + +Configuration +============= + +* By interface: + +- Browse into filters menu (technical main menu); +- Check the 'System' field for concerned filters. + +Bug Tracker +=========== + +Bugs are tracked on `GitHub Issues `_. +In case of trouble, please check there if your issue has already been reported. +If you spotted it first, help us smashing it by providing a detailed and welcomed +`feedback `_. + +Do not contact contributors directly about support or help with technical issues. + +Credits +======= + +Authors +~~~~~~~ + +* ACSONE SA/NV + +Contributors +~~~~~~~~~~~~ + +* François Honoré + +Maintainers +~~~~~~~~~~~ + +This module is maintained by the OCA. + +.. image:: https://odoo-community.org/logo.png + :alt: Odoo Community Association + :target: https://odoo-community.org + +OCA, or the Odoo Community Association, is a nonprofit organization whose +mission is to support the collaborative development of Odoo features and +promote its widespread use. + +This module is part of the `OCA/server-ux `_ project on GitHub. + +You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute. diff --git a/base_filter_hidden/__init__.py b/base_filter_hidden/__init__.py new file mode 100644 index 0000000..cb45f27 --- /dev/null +++ b/base_filter_hidden/__init__.py @@ -0,0 +1,2 @@ +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). +from . import models diff --git a/base_filter_hidden/__manifest__.py b/base_filter_hidden/__manifest__.py new file mode 100644 index 0000000..54bed51 --- /dev/null +++ b/base_filter_hidden/__manifest__.py @@ -0,0 +1,19 @@ +# Copyright 2018 ACSONE SA/NV () +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). +{ + 'name': "Base filter hidden", + 'description': """ + Add possibility to have Filters used only by the system (not visible)""", + 'author': 'ACSONE SA/NV,Odoo Community Association (OCA)', + 'website': "https://github.com/OCA/web", + 'category': 'Category', + 'version': '11.0.1.0.0', + 'license': 'AGPL-3', + 'depends': [ + 'base', + ], + 'data': [ + 'views/ir_filters.xml', + ], + 'development_status': 'Alpha', +} diff --git a/base_filter_hidden/models/__init__.py b/base_filter_hidden/models/__init__.py new file mode 100644 index 0000000..2ce3d93 --- /dev/null +++ b/base_filter_hidden/models/__init__.py @@ -0,0 +1,3 @@ +# Copyright 2018 ACSONE SA/NV () +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). +from . import ir_filters diff --git a/base_filter_hidden/models/ir_filters.py b/base_filter_hidden/models/ir_filters.py new file mode 100644 index 0000000..ae5ec4a --- /dev/null +++ b/base_filter_hidden/models/ir_filters.py @@ -0,0 +1,47 @@ +# Copyright 2018 ACSONE SA/NV () +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). +from odoo import api, fields, models + + +class IrFilters(models.Model): + _inherit = 'ir.filters' + + is_system = fields.Boolean( + string="System filter", + help="Define if this filter will be used for system purpose " + "(if yes, system filters are not loaded into views)", + default=False, + ) + + @api.model + def get_filters(self, model, action_id=None): + """ + Inherit to remove ir.filters where the is_system is True. + :param model: str + :param action_id: int (optional) + :return: list of dict + """ + result = super().get_filters(model, action_id=action_id) + if result: + result = self._remove_system_filters(result) + return result + + @api.model + def _remove_system_filters(self, result): + """ + Remove system filters from given result + :param result: list of dict + :return: list of dict + """ + # Load every id + filter_ids = [r.get('id') for r in result] + # Get only concerned filters where is_system is True (to remove them) + system_filter_ids = self.search([ + ('id', 'in', filter_ids), + ('is_system', '=', True), + ]).ids + # If no System filter, return directly the original result + if not system_filter_ids: + return result + # Re-create a list without system filters. + return [f for f in result if f.get('id') not in system_filter_ids] diff --git a/base_filter_hidden/readme/CONFIGURE.rst b/base_filter_hidden/readme/CONFIGURE.rst new file mode 100644 index 0000000..79cc18b --- /dev/null +++ b/base_filter_hidden/readme/CONFIGURE.rst @@ -0,0 +1,4 @@ +* By interface: + +- Browse into filters menu (technical main menu); +- Check the 'System' field for concerned filters. diff --git a/base_filter_hidden/readme/CONTRIBUTORS.rst b/base_filter_hidden/readme/CONTRIBUTORS.rst new file mode 100644 index 0000000..ab1764c --- /dev/null +++ b/base_filter_hidden/readme/CONTRIBUTORS.rst @@ -0,0 +1 @@ +* François Honoré diff --git a/base_filter_hidden/readme/DESCRIPTION.rst b/base_filter_hidden/readme/DESCRIPTION.rst new file mode 100644 index 0000000..8208ec3 --- /dev/null +++ b/base_filter_hidden/readme/DESCRIPTION.rst @@ -0,0 +1,8 @@ +This addon is used to use some filters (ir.filters) only for the system purpose. +The advantage is filters defined as System Filters will not be loaded into the web interface. + + +Features: + +* Add 'is_system' field into ir.filters. +* During load of filters (during view load), ignore System filters. diff --git a/base_filter_hidden/static/description/icon.png b/base_filter_hidden/static/description/icon.png new file mode 100644 index 0000000..650a1a8 Binary files /dev/null and b/base_filter_hidden/static/description/icon.png differ diff --git a/base_filter_hidden/tests/__init__.py b/base_filter_hidden/tests/__init__.py new file mode 100644 index 0000000..4697183 --- /dev/null +++ b/base_filter_hidden/tests/__init__.py @@ -0,0 +1,2 @@ +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). +from . import test_ir_filters diff --git a/base_filter_hidden/tests/test_ir_filters.py b/base_filter_hidden/tests/test_ir_filters.py new file mode 100644 index 0000000..2f3f15c --- /dev/null +++ b/base_filter_hidden/tests/test_ir_filters.py @@ -0,0 +1,102 @@ +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). +from uuid import uuid4 +from odoo.tests.common import TransactionCase + + +class IrFiltersTest(TransactionCase): + """ + Tests for ir.filters + """ + + def setUp(self): + super().setUp() + self.filter_obj = self.env['ir.filters'] + self.res_users_model = self.env.ref("base.model_res_users") + # Create basic filters + self.filter_system = self.filter_obj.create({ + 'name': str(uuid4()), + 'active': True, + 'model_id': self.res_users_model.model, + 'domain': [], + 'sort': [], + 'context': {}, + 'is_system': True, + }) + self.filter_normal = self.filter_obj.create({ + 'name': str(uuid4()), + 'active': True, + 'model_id': self.res_users_model.model, + 'domain': [], + 'sort': [], + 'context': {}, + 'is_system': False, + }) + self.filter_inactive = self.filter_obj.create({ + 'name': str(uuid4()), + 'active': False, + 'model_id': self.res_users_model.model, + 'domain': [], + 'sort': [], + 'context': {}, + 'is_system': False, + }) + self.filters = self.filter_inactive | self.filter_normal |\ + self.filter_system + + def test_get_filters_system(self): + """ + Test the function get_filters. + Expected behaviour: + - Returned filters must have is_system to False + :return: + """ + filters_result = self.filter_obj.get_filters( + self.res_users_model.model) + filter_ids = [r.get('id') for r in filters_result if r.get('id')] + filters = self.filter_obj.browse(filter_ids) + # Based on data from setUp, we should have filters in different states: + # active, inactive, is_system (False and True) + self.assertFalse(any(filters.mapped("is_system"))) + + # Now disable every filters from the setUp + self.filters.write({ + 'active': False, + }) + filters_result = self.filter_obj.get_filters( + self.res_users_model.model) + filter_ids = [r.get('id') for r in filters_result if r.get('id')] + filters = self.filter_obj.browse(filter_ids) + self.assertFalse(any(filters.mapped("is_system"))) + + # Disable every filters related to a model + # To test the case when we don't have any results + domain = [('model_id', '=', self.res_users_model.id)] + self.filter_obj.search(domain).write({ + 'active': False, + }) + filters_result = self.filter_obj.get_filters( + self.res_users_model.model) + filter_ids = [r.get('id') for r in filters_result if r.get('id')] + filters = self.filter_obj.browse(filter_ids) + self.assertFalse(any(filters.mapped("is_system"))) + + # Re-active them + self.filters.write({ + 'active': True, + }) + filters_result = self.filter_obj.get_filters( + self.res_users_model.model) + filter_ids = [r.get('id') for r in filters_result if r.get('id')] + filters = self.filter_obj.browse(filter_ids) + self.assertFalse(any(filters.mapped("is_system"))) + + # Set is_system to True for these filters + self.filters.write({ + 'active': True, + }) + filters_result = self.filter_obj.get_filters( + self.res_users_model.model) + filter_ids = [r.get('id') for r in filters_result if r.get('id')] + filters = self.filter_obj.browse(filter_ids) + self.assertFalse(any(filters.mapped("is_system"))) + return diff --git a/base_filter_hidden/views/ir_filters.xml b/base_filter_hidden/views/ir_filters.xml new file mode 100644 index 0000000..aed1ff4 --- /dev/null +++ b/base_filter_hidden/views/ir_filters.xml @@ -0,0 +1,28 @@ + + + + + ir.filters.tree (in system_filter) + ir.filters + + + + + + + + + + + ir.filters.form (in system_filter) + ir.filters + + + + + + + + + diff --git a/setup/base_filter_hidden/odoo/addons/base_filter_hidden b/setup/base_filter_hidden/odoo/addons/base_filter_hidden new file mode 120000 index 0000000..6201e04 --- /dev/null +++ b/setup/base_filter_hidden/odoo/addons/base_filter_hidden @@ -0,0 +1 @@ +../../../../base_filter_hidden \ No newline at end of file diff --git a/setup/base_filter_hidden/setup.cfg b/setup/base_filter_hidden/setup.cfg new file mode 100644 index 0000000..3c6e79c --- /dev/null +++ b/setup/base_filter_hidden/setup.cfg @@ -0,0 +1,2 @@ +[bdist_wheel] +universal=1 diff --git a/setup/base_filter_hidden/setup.py b/setup/base_filter_hidden/setup.py new file mode 100644 index 0000000..28c57bb --- /dev/null +++ b/setup/base_filter_hidden/setup.py @@ -0,0 +1,6 @@ +import setuptools + +setuptools.setup( + setup_requires=['setuptools-odoo'], + odoo_addon=True, +)