test_consumer__on_datanode_written.py 9.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186
  1. # Copyright 2021-2025 Avaiga Private Limited
  2. #
  3. # Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
  4. # the License. You may obtain a copy of the License at
  5. #
  6. # http://www.apache.org/licenses/LICENSE-2.0
  7. #
  8. # Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
  9. # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
  10. # specific language governing permissions and limitations under the License.
  11. from typing import Any
  12. from unittest import mock
  13. from unittest.mock import ANY
  14. from taipy import DataNode, Gui
  15. from taipy.core.config import DataNodeConfig
  16. from taipy.core.notification import Event, EventEntityType, EventOperation
  17. from taipy.event.event_consumer import GuiEventConsumer
  18. def cb_0(event: Event, datanode: DataNode, data: Any):
  19. ...
  20. def cb_1(event: Event, datanode: DataNode, data: Any, extra:str):
  21. ...
  22. def cb_for_state(state, event: Event, datanode: DataNode, data: Any):
  23. ...
  24. def test_on_datanode_written(data_node):
  25. consumer = GuiEventConsumer()
  26. with mock.patch("taipy.event.event_consumer.GuiEventConsumer._GuiEventConsumer__on_event") as mck:
  27. consumer.on_datanode_written(callback=cb_0)
  28. # test the on_datanode_written method delegates to on_event with the correct parameters
  29. mck.assert_called_once_with(callback=cb_0,
  30. callback_args=None,
  31. entity_type=EventEntityType.DATA_NODE,
  32. operation=EventOperation.UPDATE,
  33. attribute_name="last_edit_date",
  34. filter=ANY,
  35. broadcast=False)
  36. # check the filter method is correct
  37. actual_filter = mck.call_args.kwargs["filter"]
  38. event = Event(entity_type=EventEntityType.DATA_NODE,
  39. operation=EventOperation.UPDATE,
  40. entity_id=data_node.id,
  41. attribute_name="last_edit_date")
  42. assert actual_filter is not None
  43. with (mock.patch("taipy.get") as mck_get):
  44. mck_get.return_value = data_node
  45. filter_value = actual_filter(event)
  46. mck_get.assert_called_once_with(data_node.id)
  47. assert filter_value is True # No config provided, so the datanode passes the filter
  48. assert event.metadata["predefined_args"] == [data_node, data_node.read()]
  49. def test_on_datanode_written_multiple_configs(data_node):
  50. consumer = GuiEventConsumer()
  51. with mock.patch("taipy.event.event_consumer.GuiEventConsumer._GuiEventConsumer__on_event") as mck:
  52. consumer.on_datanode_written(callback=cb_0,
  53. datanode_config=[DataNodeConfig("dn0"), "dn1", DataNodeConfig("dn2"), "data_node"])
  54. # test the on_datanode_written method delegates to on_event with the correct parameters
  55. mck.assert_called_once_with(callback=cb_0,
  56. callback_args=None,
  57. entity_type=EventEntityType.DATA_NODE,
  58. operation=EventOperation.UPDATE,
  59. attribute_name="last_edit_date",
  60. filter=ANY,
  61. broadcast=False)
  62. # check the filter method is correct
  63. actual_filter = mck.call_args.kwargs["filter"]
  64. event = Event(entity_type=EventEntityType.DATA_NODE,
  65. operation=EventOperation.UPDATE,
  66. entity_id=data_node.id,
  67. attribute_name="last_edit_date")
  68. assert actual_filter is not None
  69. with (mock.patch("taipy.get") as mck_get):
  70. mck_get.return_value = data_node
  71. filter_value = actual_filter(event)
  72. mck_get.assert_called_once_with(data_node.id)
  73. assert filter_value is True # The datanode is from config 'data_node', so the datanode passes the filter
  74. assert event.metadata["predefined_args"] == [data_node, data_node.read()]
  75. def test_on_datanode_written_multiple_configs_no_matching(data_node):
  76. consumer = GuiEventConsumer()
  77. with mock.patch("taipy.event.event_consumer.GuiEventConsumer._GuiEventConsumer__on_event") as mck:
  78. consumer.on_datanode_written(callback=cb_0,
  79. datanode_config=[DataNodeConfig("dn0"), "dn1"])
  80. # test the on_datanode_written method delegates to on_event with the correct parameters
  81. mck.assert_called_once_with(callback=cb_0,
  82. callback_args=None,
  83. entity_type=EventEntityType.DATA_NODE,
  84. operation=EventOperation.UPDATE,
  85. attribute_name="last_edit_date",
  86. filter=ANY,
  87. broadcast=False)
  88. # check the filter method is correct
  89. actual_filter = mck.call_args.kwargs["filter"]
  90. event = Event(entity_type=EventEntityType.DATA_NODE,
  91. operation=EventOperation.UPDATE,
  92. entity_id=data_node.id,
  93. attribute_name="last_edit_date")
  94. assert actual_filter is not None
  95. with (mock.patch("taipy.get") as mck_get):
  96. mck_get.return_value = data_node
  97. f_val = actual_filter(event)
  98. mck_get.assert_called_once_with(data_node.id)
  99. assert not f_val # Datanode is not from any of the provided configs, so it should not pass the filter
  100. assert event.metadata.get("predefined_args") is None
  101. def test_on_datanode_written_with_args_and_matching_config(data_node):
  102. consumer = GuiEventConsumer()
  103. with mock.patch("taipy.event.event_consumer.GuiEventConsumer._GuiEventConsumer__on_event") as mck:
  104. consumer.on_datanode_written(callback=cb_1, callback_args=["foo"], datanode_config="data_node")
  105. # test the on_datanode_written method delegates to on_event with the correct parameters
  106. mck.assert_called_once_with(callback=cb_1,
  107. callback_args=["foo"],
  108. entity_type=EventEntityType.DATA_NODE,
  109. operation=EventOperation.UPDATE,
  110. attribute_name="last_edit_date",
  111. filter=ANY,
  112. broadcast=False)
  113. # check the filter method is correct
  114. actual_filter = mck.call_args.kwargs["filter"]
  115. assert actual_filter is not None
  116. event = Event(entity_type=EventEntityType.DATA_NODE,
  117. operation=EventOperation.UPDATE,
  118. entity_id=data_node.id,
  119. attribute_name="last_edit_date")
  120. with (mock.patch("taipy.get") as mck_get):
  121. mck_get.return_value = data_node
  122. filter_value = actual_filter(event)
  123. mck_get.assert_called_once_with(data_node.id)
  124. assert filter_value is True # datanode is from config 'data_node', so the datanode passes the filter
  125. assert event.metadata["predefined_args"] == [data_node, data_node.read()]
  126. def test_on_datanode_written_with_args_and_not_matching_config(data_node):
  127. consumer = GuiEventConsumer()
  128. with mock.patch("taipy.event.event_consumer.GuiEventConsumer._GuiEventConsumer__on_event") as mck:
  129. consumer.on_datanode_written(callback=cb_1, callback_args=["foo"], datanode_config="WRONG_CFG")
  130. # test the on_datanode_written method delegates to on_event with the correct parameters
  131. mck.assert_called_once_with(callback=cb_1,
  132. callback_args=["foo"],
  133. entity_type=EventEntityType.DATA_NODE,
  134. operation=EventOperation.UPDATE,
  135. attribute_name="last_edit_date",
  136. filter=ANY,
  137. broadcast=False)
  138. # check the filter method is correct
  139. actual_filter = mck.call_args.kwargs["filter"]
  140. assert actual_filter is not None
  141. event = Event(entity_type=EventEntityType.DATA_NODE,
  142. operation=EventOperation.UPDATE,
  143. entity_id=data_node.id,
  144. attribute_name="last_edit_date")
  145. with (mock.patch("taipy.get") as mck_get):
  146. mck_get.return_value = data_node
  147. filter_value = actual_filter(event)
  148. mck_get.assert_called_once_with(data_node.id)
  149. assert filter_value is False # datanode is not from WRONG_CFG, so it should not pass the filter
  150. assert event.metadata.get("predefined_args") is None # No need to cache the datanode in the metadata
  151. def test_on_datanode_written_with_broadcast(data_node):
  152. consumer = GuiEventConsumer(Gui())
  153. with mock.patch("taipy.event.event_consumer.GuiEventConsumer._GuiEventConsumer__on_event") as mck:
  154. consumer.broadcast_on_datanode_written(callback=cb_for_state)
  155. mck.assert_called_once_with(callback=cb_for_state,
  156. callback_args=None,
  157. entity_type=EventEntityType.DATA_NODE,
  158. operation=EventOperation.UPDATE,
  159. attribute_name="last_edit_date",
  160. filter=ANY,
  161. broadcast=True)