Simplify trigger action

We use now a selection field to choose the action to trigger.
It is safer and more user friendly.

issue9096
review272961003
This commit is contained in:
Cédric Krier
2020-03-28 23:56:19 +01:00
parent 2ab5a7797d
commit b1e0c03707
6 changed files with 43 additions and 34 deletions
+1
View File
@@ -1,3 +1,4 @@
* Simplify trigger action
* Run trigger in the queue
* Do not copy Binary content with file_id
* Replace memoize with functools.lru_cache
+22 -4
View File
@@ -5,6 +5,7 @@ import time
from sql import Literal, Null, Select
from sql.aggregate import Count, Max
from sql.functions import CurrentTimestamp
from sql.operators import Concat
from trytond.model.exceptions import ValidationError
from trytond.i18n import gettext
@@ -55,8 +56,7 @@ class Trigger(DeactivableMixin, ModelSQL, ModelView):
help='Set a minimum time delay between call to "Action Function" '
'for the same record.\n'
'empty for no delay.')
action_model = fields.Many2One('ir.model', 'Action Model', required=True)
action_function = fields.Char('Action Function', required=True)
action = fields.Selection([], "Action", required=True)
_get_triggers_cache = Cache('ir_trigger.get_triggers')
@classmethod
@@ -81,6 +81,8 @@ class Trigger(DeactivableMixin, ModelSQL, ModelView):
super(Trigger, cls).__register__(module_name)
table_h = cls.__table_handler__(module_name)
# Migration from 3.4:
# change minimum_delay into timedelta minimum_time_delay
if table.column_exist('minimum_delay'):
@@ -95,6 +97,21 @@ class Trigger(DeactivableMixin, ModelSQL, ModelView):
where=sql_table.id == id_))
table.drop_column('minimum_delay')
# Migration from 5.4: merge action
if (table_h.column_exist('action_model')
and table_h.column_exist('action_function')):
pool = Pool()
Model = pool.get('ir.model')
model = Model.__table__()
action_model = model.select(
model.model, where=model.id == sql_table.action_model)
cursor.execute(*sql_table.update(
[sql_table.action],
[Concat(action_model, Concat(
'|', sql_table.action_function))]))
table_h.drop_column('action_model')
table_h.drop_column('action_function')
@classmethod
def validate(cls, triggers):
super(Trigger, cls).validate(triggers)
@@ -187,7 +204,8 @@ class Trigger(DeactivableMixin, ModelSQL, ModelView):
pool = Pool()
TriggerLog = pool.get('ir.trigger.log')
Model = pool.get(self.model.model)
ActionModel = pool.get(self.action_model.model)
model, method = self.action.split('|')
ActionModel = pool.get(model)
cursor = Transaction().connection.cursor()
trigger_log = TriggerLog.__table__()
@@ -255,7 +273,7 @@ class Trigger(DeactivableMixin, ModelSQL, ModelView):
records = Model.browse(ids)
if records:
getattr(ActionModel, self.action_function)(records, self)
getattr(ActionModel, method)(records, self)
if self.limit_number or self.minimum_time_delay:
to_create = []
for record in records:
+2 -4
View File
@@ -24,8 +24,6 @@ this repository contains the full copyright notices and license terms. -->
<field name="limit_number"/>
<label name="minimum_time_delay"/>
<field name="minimum_time_delay"/>
<label name="action_model"/>
<field name="action_model"/>
<label name="action_function"/>
<field name="action_function"/>
<label name="action"/>
<field name="action"/>
</form>
+1
View File
@@ -8,4 +8,5 @@ this repository contains the full copyright notices and license terms. -->
<field name="on_create"/>
<field name="on_write"/>
<field name="on_delete"/>
<field name="action"/>
</tree>
+5 -25
View File
@@ -45,17 +45,13 @@ class TriggerTestCase(unittest.TestCase):
model, = Model.search([
('model', '=', 'test.triggered'),
])
action_model, = Model.search([
('model', '=', 'test.trigger_action'),
])
values = {
'name': 'Test',
'model': model.id,
'on_time': True,
'condition': 'true',
'action_model': action_model.id,
'action_function': 'test',
'action': 'test.trigger_action|trigger',
}
self.assertTrue(Trigger.create([values]))
@@ -93,17 +89,13 @@ class TriggerTestCase(unittest.TestCase):
model, = Model.search([
('model', '=', 'test.triggered'),
])
action_model, = Model.search([
('model', '=', 'test.trigger_action'),
])
trigger, = Trigger.create([{
'name': 'Test',
'model': model.id,
'on_create': True,
'condition': 'true',
'action_model': action_model.id,
'action_function': 'trigger',
'action': 'test.trigger_action|trigger',
}])
triggered, = Triggered.create([{
@@ -175,17 +167,13 @@ class TriggerTestCase(unittest.TestCase):
model, = Model.search([
('model', '=', 'test.triggered'),
])
action_model, = Model.search([
('model', '=', 'test.trigger_action'),
])
trigger, = Trigger.create([{
'name': 'Test',
'model': model.id,
'on_write': True,
'condition': 'true',
'action_model': action_model.id,
'action_function': 'trigger',
'action': 'test.trigger_action|trigger',
}])
triggered, = Triggered.create([{
@@ -311,9 +299,6 @@ class TriggerTestCase(unittest.TestCase):
model, = Model.search([
('model', '=', 'test.triggered'),
])
action_model, = Model.search([
('model', '=', 'test.trigger_action'),
])
triggered, = Triggered.create([{
'name': 'Test',
@@ -324,8 +309,7 @@ class TriggerTestCase(unittest.TestCase):
'model': model.id,
'on_delete': True,
'condition': 'true',
'action_model': action_model.id,
'action_function': 'trigger',
'action': 'test.trigger_action|trigger',
}])
Triggered.delete([triggered])
@@ -406,17 +390,13 @@ class TriggerTestCase(unittest.TestCase):
model, = Model.search([
('model', '=', 'test.triggered'),
])
action_model, = Model.search([
('model', '=', 'test.trigger_action'),
])
trigger, = Trigger.create([{
'name': 'Test',
'model': model.id,
'on_time': True,
'condition': 'true',
'action_model': action_model.id,
'action_function': 'trigger',
'action': 'test.trigger_action|trigger',
}])
triggered, = Triggered.create([{
+12 -1
View File
@@ -1,11 +1,21 @@
# This file is part of Tryton. The COPYRIGHT file at the top level of
# this repository contains the full copyright notices and license terms.
from trytond.model import ModelSQL, fields
from trytond.pool import Pool
from trytond.pool import Pool, PoolMeta
TRIGGER_LOGS = []
class Trigger(metaclass=PoolMeta):
__name__ = 'ir.trigger'
@classmethod
def __setup__(cls):
super().__setup__()
cls.action.selection.append(
('test.trigger_action|trigger', "Test Trigger"))
class Triggered(ModelSQL):
'Triggered'
__name__ = 'test.triggered'
@@ -26,6 +36,7 @@ class TriggerAction(ModelSQL):
def register(module):
Pool.register(
Trigger,
Triggered,
TriggerAction,
module=module, type_='model')