bamboo-engine 2.6.0__tar.gz → 2.6.2__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/PKG-INFO +3 -3
  2. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/__version__.py +1 -1
  3. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/engine.py +52 -5
  4. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/conditional_parallel_gateway.py +15 -2
  5. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/exclusive_gateway.py +14 -0
  6. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/pyproject.toml +3 -3
  7. bamboo-engine-2.6.0/setup.py +0 -43
  8. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/LICENSE +0 -0
  9. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/__init__.py +0 -0
  10. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/api.py +0 -0
  11. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/__init__.py +0 -0
  12. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/builder.py +0 -0
  13. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/flow/__init__.py +0 -0
  14. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/flow/activity.py +0 -0
  15. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/flow/base.py +0 -0
  16. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/flow/data.py +0 -0
  17. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/flow/event.py +0 -0
  18. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/builder/flow/gateway.py +0 -0
  19. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/config.py +0 -0
  20. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/context.py +0 -0
  21. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/__init__.py +0 -0
  22. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/interfaces.py +0 -0
  23. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/models/__init__.py +0 -0
  24. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/models/event.py +0 -0
  25. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/models/handler.py +0 -0
  26. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/models/interrupt.py +0 -0
  27. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/models/node.py +0 -0
  28. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/eri/models/runtime.py +0 -0
  29. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/exceptions.py +0 -0
  30. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handler.py +0 -0
  31. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/__init__.py +0 -0
  32. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/converge_gateway.py +0 -0
  33. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/empty_end_event.py +0 -0
  34. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/empty_start_event.py +0 -0
  35. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/executable_end_event.py +0 -0
  36. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/parallel_gateway.py +0 -0
  37. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/service_activity.py +0 -0
  38. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/handlers/subprocess.py +0 -0
  39. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/interrupt.py +0 -0
  40. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/local.py +0 -0
  41. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/metrics.py +0 -0
  42. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/states.py +0 -0
  43. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/template/__init__.py +0 -0
  44. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/template/sandbox.py +0 -0
  45. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/template/template.py +0 -0
  46. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/__init__.py +0 -0
  47. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/boolrule/__init__.py +0 -0
  48. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/boolrule/boolrule.py +0 -0
  49. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/collections.py +0 -0
  50. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/constants.py +0 -0
  51. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/graph.py +0 -0
  52. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/host.py +0 -0
  53. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/mako_safety.py +0 -0
  54. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/mako_utils/__init__.py +0 -0
  55. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/mako_utils/checker.py +0 -0
  56. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/mako_utils/code_extract.py +0 -0
  57. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/mako_utils/exceptions.py +0 -0
  58. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/mako_utils/visitors.py +0 -0
  59. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/object.py +0 -0
  60. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/utils/string.py +0 -0
  61. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/validator/__init__.py +0 -0
  62. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/validator/api.py +0 -0
  63. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/validator/connection.py +0 -0
  64. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/validator/gateway.py +0 -0
  65. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/validator/rules.py +0 -0
  66. {bamboo-engine-2.6.0 → bamboo_engine-2.6.2}/bamboo_engine/validator/utils.py +0 -0
@@ -1,10 +1,10 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: bamboo-engine
3
- Version: 2.6.0
3
+ Version: 2.6.2
4
4
  Summary: Bamboo-engine is a general-purpose workflow engine
5
5
  License: MIT
6
- Author: homholueng
7
- Author-email: homholueng@gmail.com
6
+ Author: blueking
7
+ Author-email: blueking@tencent.com
8
8
  Requires-Python: >=3.6,<3.8
9
9
  Classifier: License :: OSI Approved :: MIT License
10
10
  Classifier: Programming Language :: Python :: 3
@@ -11,4 +11,4 @@ an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express o
11
11
  specific language governing permissions and limitations under the License.
12
12
  """
13
13
 
14
- __version__ = "2.5.3"
14
+ __version__ = "2.6.2"
@@ -78,11 +78,31 @@ class Engine:
78
78
  """
79
79
 
80
80
  PURE_SKIP_ENABLE_NODE_TYPE = {NodeType.ServiceActivity, NodeType.EmptyStartEvent}
81
+ CALLBACK_LOCK_RETRY_HEADER = "callback_lock_retry_times"
82
+ CALLBACK_LOCK_RETRY_LIMIT = 3
81
83
 
82
84
  def __init__(self, runtime: EngineRuntimeInterface):
83
85
  self.runtime = runtime
84
86
  self._hostname = get_hostname()
85
87
 
88
+ def _schedule_lock_retry_count(self, headers: Optional[dict]) -> int:
89
+ if not headers:
90
+ return 0
91
+
92
+ try:
93
+ return int(headers.get(self.CALLBACK_LOCK_RETRY_HEADER, 0))
94
+ except (TypeError, ValueError):
95
+ return 0
96
+
97
+ def _callback_lock_retry_context(self, node_id: str, callback_data_id: Optional[int]):
98
+ if not callback_data_id:
99
+ return None, False
100
+
101
+ callback_data = self.runtime.get_callback_data(callback_data_id)
102
+ node = self.runtime.get_node(node_id)
103
+ service = self.runtime.get_service(code=node.code, version=node.version)
104
+ return callback_data, service.callback_lock_retryable(callback_data=callback_data.data)
105
+
86
106
  # api
87
107
  def run_pipeline(
88
108
  self,
@@ -993,25 +1013,52 @@ class Engine:
993
1013
  interrupter.check_and_set(ScheduleKeyPoint.APPLY_LOCK_DONE, lock_get=lock_get)
994
1014
 
995
1015
  if not lock_get:
996
- # only retry at multiple calback type
997
- if schedule.type is not ScheduleType.MULTIPLE_CALLBACK:
1016
+ callback_data = None
1017
+ # only retry at multiple callback type
1018
+ should_retry = schedule.type is ScheduleType.MULTIPLE_CALLBACK
1019
+ if not should_retry:
1020
+ callback_data, should_retry = self._callback_lock_retry_context(node_id, callback_data_id)
1021
+ retry_count = self._schedule_lock_retry_count(headers)
1022
+ if should_retry and retry_count >= self.CALLBACK_LOCK_RETRY_LIMIT:
1023
+ logger.error(
1024
+ "root pipeline[%s] schedule(%s) %s with version %s callback data(%s) retry exhausted "
1025
+ "after %s attempts, callback_data=%s",
1026
+ root_pipeline_id,
1027
+ schedule_id,
1028
+ node_id,
1029
+ schedule.version,
1030
+ callback_data_id,
1031
+ retry_count,
1032
+ callback_data.data if callback_data else None,
1033
+ )
1034
+ return
1035
+
1036
+ if not should_retry:
998
1037
  logger.info(
999
- "root pipeline[%s] schedule(%s) %s with version %s is not multiple callback type, will not retry to get lock", # noqa
1038
+ "root pipeline[%s] schedule(%s) %s with version %s callback data(%s) "
1039
+ "will not retry to get lock",
1000
1040
  root_pipeline_id,
1001
1041
  schedule_id,
1002
1042
  node_id,
1003
1043
  schedule.version,
1044
+ callback_data_id,
1004
1045
  )
1005
1046
  return
1006
1047
 
1007
1048
  try_after = random.randint(1, 5)
1049
+ retry_headers = dict(headers or {})
1050
+ if schedule.type is ScheduleType.CALLBACK:
1051
+ retry_headers[self.CALLBACK_LOCK_RETRY_HEADER] = self._schedule_lock_retry_count(headers) + 1
1008
1052
  logger.info(
1009
- "root pipeline[%s] schedule(%s) lock %s with data %s fetch fail, try after %s",
1053
+ "root pipeline[%s] schedule(%s) lock %s with data %s fetch fail, try after %s, "
1054
+ "retry_count=%s, callback_data=%s",
1010
1055
  root_pipeline_id,
1011
1056
  node_id,
1012
1057
  schedule_id,
1013
1058
  callback_data_id,
1014
1059
  try_after,
1060
+ retry_headers.get(self.CALLBACK_LOCK_RETRY_HEADER, 0),
1061
+ callback_data.data if callback_data else None,
1015
1062
  )
1016
1063
  self.runtime.set_next_schedule(
1017
1064
  process_id=process_id,
@@ -1019,7 +1066,7 @@ class Engine:
1019
1066
  schedule_id=schedule_id,
1020
1067
  callback_data_id=callback_data_id,
1021
1068
  schedule_after=try_after,
1022
- headers=headers,
1069
+ headers=retry_headers,
1023
1070
  )
1024
1071
  return
1025
1072
 
@@ -14,11 +14,12 @@ specific language governing permissions and limitations under the License.
14
14
  import json
15
15
  import logging
16
16
  from typing import Optional
17
- from bamboo_engine.interrupt import ExecuteKeyPoint
17
+
18
+ from pyparsing import ParseException
18
19
 
19
20
  from bamboo_engine.utils.boolrule import BoolRule
20
21
  from bamboo_engine.template.template import Template
21
-
22
+ from bamboo_engine.interrupt import ExecuteKeyPoint
22
23
  from bamboo_engine import states, metrics
23
24
  from bamboo_engine.eri import NodeType, ProcessInfo, ExecuteInterruptPoint
24
25
  from bamboo_engine.context import Context
@@ -116,6 +117,18 @@ class ConditionalParallelGatewayHandler(NodeHandler):
116
117
  resolved_evaluate,
117
118
  result,
118
119
  )
120
+ except ParseException as e:
121
+ logger.exception(f"[conditional_parallel_gateway] evaluation parse error: {e}")
122
+ return self._execute_fail(
123
+ ex_data="evaluate[{}] fail with data[{}]:"
124
+ "please check if some variable not exists or the expression is unsupported, "
125
+ "related reference is "
126
+ '<a href="https://boolrule.readthedocs.io/en/latest/expressions.html">boolrule</a>'.format(
127
+ c.evaluation, json.dumps(hydrated_context)
128
+ ),
129
+ version=version,
130
+ ignore_boring_set=recover_point is not None,
131
+ )
119
132
  except Exception as e:
120
133
  # test failed
121
134
  return self._execute_fail(
@@ -14,6 +14,8 @@ import json
14
14
  import logging
15
15
  from typing import Optional
16
16
 
17
+ from pyparsing import ParseException
18
+
17
19
  from bamboo_engine import states, metrics
18
20
  from bamboo_engine.context import Context
19
21
  from bamboo_engine.template import Template
@@ -121,6 +123,18 @@ class ExclusiveGatewayHandler(NodeHandler):
121
123
  resolved_evaluate,
122
124
  result,
123
125
  )
126
+ except ParseException as e:
127
+ logger.exception(f"[exclusive_gateway] evaluation parse error: {e}")
128
+ return self._execute_fail(
129
+ ex_data="evaluate[{}] fail with data[{}]:"
130
+ "please check if some variable not exists or the expression is unsupported, "
131
+ "related reference is "
132
+ '<a href="https://boolrule.readthedocs.io/en/latest/expressions.html">boolrule</a>'.format(
133
+ c.evaluation, json.dumps(hydrated_context)
134
+ ),
135
+ version=version,
136
+ ignore_boring_set=recover_point is not None,
137
+ )
124
138
  except Exception as e:
125
139
  # test failed
126
140
  return self._execute_fail(
@@ -1,8 +1,8 @@
1
1
  [tool.poetry]
2
2
  name = "bamboo-engine"
3
- version = "2.6.0"
3
+ version = "2.6.2"
4
4
  description = "Bamboo-engine is a general-purpose workflow engine"
5
- authors = ["homholueng <homholueng@gmail.com>"]
5
+ authors = ["blueking <blueking@tencent.com>"]
6
6
  license = "MIT"
7
7
 
8
8
  [tool.poetry.dependencies]
@@ -20,7 +20,7 @@ coverage = {extras = ["toml"], version = "^5.5"}
20
20
  flake8 = "^4.0.1"
21
21
 
22
22
  [build-system]
23
- requires = ["poetry-core>=1.0.0"]
23
+ requires = ["poetry-core==1.6.1"]
24
24
  build-backend = "poetry.core.masonry.api"
25
25
 
26
26
  [tool.black]
@@ -1,43 +0,0 @@
1
- # -*- coding: utf-8 -*-
2
- from setuptools import setup
3
-
4
- packages = \
5
- ['bamboo_engine',
6
- 'bamboo_engine.builder',
7
- 'bamboo_engine.builder.flow',
8
- 'bamboo_engine.eri',
9
- 'bamboo_engine.eri.models',
10
- 'bamboo_engine.handlers',
11
- 'bamboo_engine.template',
12
- 'bamboo_engine.utils',
13
- 'bamboo_engine.utils.boolrule',
14
- 'bamboo_engine.utils.mako_utils',
15
- 'bamboo_engine.validator']
16
-
17
- package_data = \
18
- {'': ['*']}
19
-
20
- install_requires = \
21
- ['Mako>=1.1.4,<2.0.0',
22
- 'Werkzeug>=1.0.0,<2.0.0',
23
- 'prometheus-client>=0.9.0,<0.10.0',
24
- 'pyparsing>=2.2.0,<3.0.0']
25
-
26
- setup_kwargs = {
27
- 'name': 'bamboo-engine',
28
- 'version': '2.6.0',
29
- 'description': 'Bamboo-engine is a general-purpose workflow engine',
30
- 'long_description': 'None',
31
- 'author': 'homholueng',
32
- 'author_email': 'homholueng@gmail.com',
33
- 'maintainer': 'None',
34
- 'maintainer_email': 'None',
35
- 'url': 'None',
36
- 'packages': packages,
37
- 'package_data': package_data,
38
- 'install_requires': install_requires,
39
- 'python_requires': '>=3.6,<3.8',
40
- }
41
-
42
-
43
- setup(**setup_kwargs)
File without changes