kailash 0.3.2__py3-none-any.whl → 0.4.0__py3-none-any.whl
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.
- kailash/__init__.py +33 -1
- kailash/access_control/__init__.py +129 -0
- kailash/access_control/managers.py +461 -0
- kailash/access_control/rule_evaluators.py +467 -0
- kailash/access_control_abac.py +825 -0
- kailash/config/__init__.py +27 -0
- kailash/config/database_config.py +359 -0
- kailash/database/__init__.py +28 -0
- kailash/database/execution_pipeline.py +499 -0
- kailash/middleware/__init__.py +306 -0
- kailash/middleware/auth/__init__.py +33 -0
- kailash/middleware/auth/access_control.py +436 -0
- kailash/middleware/auth/auth_manager.py +422 -0
- kailash/middleware/auth/jwt_auth.py +477 -0
- kailash/middleware/auth/kailash_jwt_auth.py +616 -0
- kailash/middleware/communication/__init__.py +37 -0
- kailash/middleware/communication/ai_chat.py +989 -0
- kailash/middleware/communication/api_gateway.py +802 -0
- kailash/middleware/communication/events.py +470 -0
- kailash/middleware/communication/realtime.py +710 -0
- kailash/middleware/core/__init__.py +21 -0
- kailash/middleware/core/agent_ui.py +890 -0
- kailash/middleware/core/schema.py +643 -0
- kailash/middleware/core/workflows.py +396 -0
- kailash/middleware/database/__init__.py +63 -0
- kailash/middleware/database/base.py +113 -0
- kailash/middleware/database/base_models.py +525 -0
- kailash/middleware/database/enums.py +106 -0
- kailash/middleware/database/migrations.py +12 -0
- kailash/{api/database.py → middleware/database/models.py} +183 -291
- kailash/middleware/database/repositories.py +685 -0
- kailash/middleware/database/session_manager.py +19 -0
- kailash/middleware/mcp/__init__.py +38 -0
- kailash/middleware/mcp/client_integration.py +585 -0
- kailash/middleware/mcp/enhanced_server.py +576 -0
- kailash/nodes/__init__.py +25 -3
- kailash/nodes/admin/__init__.py +35 -0
- kailash/nodes/admin/audit_log.py +794 -0
- kailash/nodes/admin/permission_check.py +864 -0
- kailash/nodes/admin/role_management.py +823 -0
- kailash/nodes/admin/security_event.py +1519 -0
- kailash/nodes/admin/user_management.py +944 -0
- kailash/nodes/ai/a2a.py +24 -7
- kailash/nodes/ai/ai_providers.py +1 -0
- kailash/nodes/ai/embedding_generator.py +11 -11
- kailash/nodes/ai/intelligent_agent_orchestrator.py +99 -11
- kailash/nodes/ai/llm_agent.py +407 -2
- kailash/nodes/ai/self_organizing.py +85 -10
- kailash/nodes/api/auth.py +287 -6
- kailash/nodes/api/rest.py +151 -0
- kailash/nodes/auth/__init__.py +17 -0
- kailash/nodes/auth/directory_integration.py +1228 -0
- kailash/nodes/auth/enterprise_auth_provider.py +1328 -0
- kailash/nodes/auth/mfa.py +2338 -0
- kailash/nodes/auth/risk_assessment.py +872 -0
- kailash/nodes/auth/session_management.py +1093 -0
- kailash/nodes/auth/sso.py +1040 -0
- kailash/nodes/base.py +344 -13
- kailash/nodes/base_cycle_aware.py +4 -2
- kailash/nodes/base_with_acl.py +1 -1
- kailash/nodes/code/python.py +283 -10
- kailash/nodes/compliance/__init__.py +9 -0
- kailash/nodes/compliance/data_retention.py +1888 -0
- kailash/nodes/compliance/gdpr.py +2004 -0
- kailash/nodes/data/__init__.py +22 -2
- kailash/nodes/data/async_connection.py +469 -0
- kailash/nodes/data/async_sql.py +757 -0
- kailash/nodes/data/async_vector.py +598 -0
- kailash/nodes/data/readers.py +767 -0
- kailash/nodes/data/retrieval.py +360 -1
- kailash/nodes/data/sharepoint_graph.py +397 -21
- kailash/nodes/data/sql.py +94 -5
- kailash/nodes/data/streaming.py +68 -8
- kailash/nodes/data/vector_db.py +54 -4
- kailash/nodes/enterprise/__init__.py +13 -0
- kailash/nodes/enterprise/batch_processor.py +741 -0
- kailash/nodes/enterprise/data_lineage.py +497 -0
- kailash/nodes/logic/convergence.py +31 -9
- kailash/nodes/logic/operations.py +14 -3
- kailash/nodes/mixins/__init__.py +8 -0
- kailash/nodes/mixins/event_emitter.py +201 -0
- kailash/nodes/mixins/mcp.py +9 -4
- kailash/nodes/mixins/security.py +165 -0
- kailash/nodes/monitoring/__init__.py +7 -0
- kailash/nodes/monitoring/performance_benchmark.py +2497 -0
- kailash/nodes/rag/__init__.py +284 -0
- kailash/nodes/rag/advanced.py +1615 -0
- kailash/nodes/rag/agentic.py +773 -0
- kailash/nodes/rag/conversational.py +999 -0
- kailash/nodes/rag/evaluation.py +875 -0
- kailash/nodes/rag/federated.py +1188 -0
- kailash/nodes/rag/graph.py +721 -0
- kailash/nodes/rag/multimodal.py +671 -0
- kailash/nodes/rag/optimized.py +933 -0
- kailash/nodes/rag/privacy.py +1059 -0
- kailash/nodes/rag/query_processing.py +1335 -0
- kailash/nodes/rag/realtime.py +764 -0
- kailash/nodes/rag/registry.py +547 -0
- kailash/nodes/rag/router.py +837 -0
- kailash/nodes/rag/similarity.py +1854 -0
- kailash/nodes/rag/strategies.py +566 -0
- kailash/nodes/rag/workflows.py +575 -0
- kailash/nodes/security/__init__.py +19 -0
- kailash/nodes/security/abac_evaluator.py +1411 -0
- kailash/nodes/security/audit_log.py +91 -0
- kailash/nodes/security/behavior_analysis.py +1893 -0
- kailash/nodes/security/credential_manager.py +401 -0
- kailash/nodes/security/rotating_credentials.py +760 -0
- kailash/nodes/security/security_event.py +132 -0
- kailash/nodes/security/threat_detection.py +1103 -0
- kailash/nodes/testing/__init__.py +9 -0
- kailash/nodes/testing/credential_testing.py +499 -0
- kailash/nodes/transform/__init__.py +10 -2
- kailash/nodes/transform/chunkers.py +592 -1
- kailash/nodes/transform/processors.py +484 -14
- kailash/nodes/validation.py +321 -0
- kailash/runtime/access_controlled.py +1 -1
- kailash/runtime/async_local.py +41 -7
- kailash/runtime/docker.py +1 -1
- kailash/runtime/local.py +474 -55
- kailash/runtime/parallel.py +1 -1
- kailash/runtime/parallel_cyclic.py +1 -1
- kailash/runtime/testing.py +210 -2
- kailash/utils/migrations/__init__.py +25 -0
- kailash/utils/migrations/generator.py +433 -0
- kailash/utils/migrations/models.py +231 -0
- kailash/utils/migrations/runner.py +489 -0
- kailash/utils/secure_logging.py +342 -0
- kailash/workflow/__init__.py +16 -0
- kailash/workflow/cyclic_runner.py +3 -4
- kailash/workflow/graph.py +70 -2
- kailash/workflow/resilience.py +249 -0
- kailash/workflow/templates.py +726 -0
- {kailash-0.3.2.dist-info → kailash-0.4.0.dist-info}/METADATA +253 -20
- kailash-0.4.0.dist-info/RECORD +223 -0
- kailash/api/__init__.py +0 -17
- kailash/api/__main__.py +0 -6
- kailash/api/studio_secure.py +0 -893
- kailash/mcp/__main__.py +0 -13
- kailash/mcp/server_new.py +0 -336
- kailash/mcp/servers/__init__.py +0 -12
- kailash-0.3.2.dist-info/RECORD +0 -136
- {kailash-0.3.2.dist-info → kailash-0.4.0.dist-info}/WHEEL +0 -0
- {kailash-0.3.2.dist-info → kailash-0.4.0.dist-info}/entry_points.txt +0 -0
- {kailash-0.3.2.dist-info → kailash-0.4.0.dist-info}/licenses/LICENSE +0 -0
- {kailash-0.3.2.dist-info → kailash-0.4.0.dist-info}/top_level.txt +0 -0
@@ -0,0 +1,396 @@
|
|
1
|
+
"""
|
2
|
+
Workflow-based Architecture for Middleware Operations
|
3
|
+
=====================================================
|
4
|
+
|
5
|
+
This module demonstrates how to convert middleware operations into workflows
|
6
|
+
for maximum performance using SDK nodes, workflows, and runtime.
|
7
|
+
|
8
|
+
Key Optimizations:
|
9
|
+
- Session management as workflows
|
10
|
+
- Event processing as workflows
|
11
|
+
- Cleanup operations as scheduled workflows
|
12
|
+
- Error handling with retry workflows
|
13
|
+
"""
|
14
|
+
|
15
|
+
from datetime import datetime, timedelta, timezone
|
16
|
+
from typing import Any, Dict, Optional
|
17
|
+
|
18
|
+
from ...nodes.admin import PermissionCheckNode
|
19
|
+
from ...nodes.base import register_node
|
20
|
+
from ...nodes.enterprise import BatchProcessorNode, DataLineageNode
|
21
|
+
from ...nodes.security import AuditLogNode, SecurityEventNode
|
22
|
+
from ...nodes.transform import DataTransformer
|
23
|
+
from ...runtime.async_local import AsyncLocalRuntime
|
24
|
+
from ...workflow.builder import WorkflowBuilder
|
25
|
+
|
26
|
+
|
27
|
+
class MiddlewareWorkflows:
|
28
|
+
"""
|
29
|
+
Collection of workflow templates for common middleware operations.
|
30
|
+
|
31
|
+
These workflows replace custom code with SDK components for better
|
32
|
+
performance, reliability, and maintainability.
|
33
|
+
"""
|
34
|
+
|
35
|
+
@staticmethod
|
36
|
+
def create_session_workflow() -> WorkflowBuilder:
|
37
|
+
"""
|
38
|
+
Create a workflow for session creation with validation and setup.
|
39
|
+
|
40
|
+
Workflow steps:
|
41
|
+
1. Validate user credentials
|
42
|
+
2. Check permissions
|
43
|
+
3. Create session record
|
44
|
+
4. Initialize session state
|
45
|
+
5. Emit session created event
|
46
|
+
6. Log audit entry
|
47
|
+
|
48
|
+
Returns:
|
49
|
+
WorkflowBuilder configured for session creation
|
50
|
+
"""
|
51
|
+
builder = WorkflowBuilder()
|
52
|
+
|
53
|
+
# Add permission check node
|
54
|
+
permission_check = builder.add_node(
|
55
|
+
"PermissionCheckNode",
|
56
|
+
node_id="check_permissions",
|
57
|
+
config={
|
58
|
+
"name": "session_permission_check",
|
59
|
+
"permission": "session.create",
|
60
|
+
"resource_type": "session",
|
61
|
+
},
|
62
|
+
)
|
63
|
+
|
64
|
+
# Add data transformer for session initialization
|
65
|
+
session_init = builder.add_node(
|
66
|
+
"DataTransformer",
|
67
|
+
node_id="init_session",
|
68
|
+
config={
|
69
|
+
"name": "session_initializer",
|
70
|
+
"transformations": [
|
71
|
+
{
|
72
|
+
"operation": "add_field",
|
73
|
+
"field": "session_id",
|
74
|
+
"value": "{{ generate_uuid() }}",
|
75
|
+
},
|
76
|
+
{
|
77
|
+
"operation": "add_field",
|
78
|
+
"field": "created_at",
|
79
|
+
"value": "{{ current_timestamp() }}",
|
80
|
+
},
|
81
|
+
{"operation": "add_field", "field": "active", "value": True},
|
82
|
+
],
|
83
|
+
},
|
84
|
+
)
|
85
|
+
|
86
|
+
# Add security event logging
|
87
|
+
security_log = builder.add_node(
|
88
|
+
"SecurityEventNode",
|
89
|
+
node_id="log_security_event",
|
90
|
+
config={
|
91
|
+
"name": "session_security_logger",
|
92
|
+
"event_type": "session_created",
|
93
|
+
"severity": "info",
|
94
|
+
},
|
95
|
+
)
|
96
|
+
|
97
|
+
# Add audit log entry
|
98
|
+
audit_log = builder.add_node(
|
99
|
+
"AuditLogNode",
|
100
|
+
node_id="audit_session_creation",
|
101
|
+
config={
|
102
|
+
"name": "session_audit_logger",
|
103
|
+
"action": "create_session",
|
104
|
+
"resource_type": "session",
|
105
|
+
},
|
106
|
+
)
|
107
|
+
|
108
|
+
# Connect nodes
|
109
|
+
builder.add_connection(permission_check, "authorized", session_init, "input")
|
110
|
+
builder.add_connection(session_init, "output", security_log, "event_data")
|
111
|
+
builder.add_connection(security_log, "logged", audit_log, "input")
|
112
|
+
|
113
|
+
return builder
|
114
|
+
|
115
|
+
@staticmethod
|
116
|
+
def create_execution_monitoring_workflow() -> WorkflowBuilder:
|
117
|
+
"""
|
118
|
+
Create a workflow for monitoring execution progress.
|
119
|
+
|
120
|
+
Workflow steps:
|
121
|
+
1. Track execution state
|
122
|
+
2. Calculate progress
|
123
|
+
3. Emit progress events
|
124
|
+
4. Update execution record
|
125
|
+
5. Handle timeouts
|
126
|
+
|
127
|
+
Returns:
|
128
|
+
WorkflowBuilder configured for execution monitoring
|
129
|
+
"""
|
130
|
+
builder = WorkflowBuilder()
|
131
|
+
|
132
|
+
# Add data lineage tracking
|
133
|
+
lineage_tracker = builder.add_node(
|
134
|
+
"DataLineageNode",
|
135
|
+
node_id="track_lineage",
|
136
|
+
config={
|
137
|
+
"name": "execution_lineage_tracker",
|
138
|
+
"track_transformations": True,
|
139
|
+
"track_data_flow": True,
|
140
|
+
},
|
141
|
+
)
|
142
|
+
|
143
|
+
# Add progress calculator
|
144
|
+
progress_calc = builder.add_node(
|
145
|
+
"PythonCodeNode",
|
146
|
+
node_id="calculate_progress",
|
147
|
+
config={
|
148
|
+
"name": "progress_calculator",
|
149
|
+
"code": """
|
150
|
+
completed_nodes = len([n for n in execution_data['nodes'] if n['status'] == 'completed'])
|
151
|
+
total_nodes = len(execution_data['nodes'])
|
152
|
+
progress = (completed_nodes / total_nodes * 100) if total_nodes > 0 else 0
|
153
|
+
result = {
|
154
|
+
'progress': progress,
|
155
|
+
'completed': completed_nodes,
|
156
|
+
'total': total_nodes,
|
157
|
+
'status': 'completed' if progress == 100 else 'running'
|
158
|
+
}
|
159
|
+
""",
|
160
|
+
},
|
161
|
+
)
|
162
|
+
|
163
|
+
# Add event emitter (would use EventEmitterNode when available)
|
164
|
+
event_emitter = builder.add_node(
|
165
|
+
"PythonCodeNode",
|
166
|
+
node_id="emit_progress_event",
|
167
|
+
config={
|
168
|
+
"name": "progress_event_emitter",
|
169
|
+
"code": """
|
170
|
+
# In production, use EventEmitterNode
|
171
|
+
event_data = {
|
172
|
+
'type': 'workflow.progress',
|
173
|
+
'execution_id': execution_id,
|
174
|
+
'progress': progress_data['progress'],
|
175
|
+
'status': progress_data['status']
|
176
|
+
}
|
177
|
+
result = {'event_emitted': True, 'event_data': event_data}
|
178
|
+
""",
|
179
|
+
},
|
180
|
+
)
|
181
|
+
|
182
|
+
# Connect nodes
|
183
|
+
builder.add_connection(
|
184
|
+
lineage_tracker, "lineage", progress_calc, "execution_data"
|
185
|
+
)
|
186
|
+
builder.add_connection(progress_calc, "result", event_emitter, "progress_data")
|
187
|
+
|
188
|
+
return builder
|
189
|
+
|
190
|
+
@staticmethod
|
191
|
+
def create_cleanup_workflow() -> WorkflowBuilder:
|
192
|
+
"""
|
193
|
+
Create a workflow for session cleanup operations.
|
194
|
+
|
195
|
+
Workflow steps:
|
196
|
+
1. Identify expired sessions
|
197
|
+
2. Cancel active executions
|
198
|
+
3. Archive session data
|
199
|
+
4. Remove from active sessions
|
200
|
+
5. Emit cleanup events
|
201
|
+
|
202
|
+
Returns:
|
203
|
+
WorkflowBuilder configured for cleanup operations
|
204
|
+
"""
|
205
|
+
builder = WorkflowBuilder()
|
206
|
+
|
207
|
+
# Add batch processor for efficient cleanup
|
208
|
+
batch_cleanup = builder.add_node(
|
209
|
+
"BatchProcessorNode",
|
210
|
+
node_id="batch_cleanup",
|
211
|
+
config={"name": "session_batch_cleanup"},
|
212
|
+
)
|
213
|
+
|
214
|
+
# Add data transformer for archival
|
215
|
+
archiver = builder.add_node(
|
216
|
+
"DataTransformer",
|
217
|
+
node_id="archive_sessions",
|
218
|
+
config={
|
219
|
+
"name": "session_archiver",
|
220
|
+
"transformations": [
|
221
|
+
{
|
222
|
+
"operation": "add_field",
|
223
|
+
"field": "archived_at",
|
224
|
+
"value": "{{ current_timestamp() }}",
|
225
|
+
},
|
226
|
+
{"operation": "update_field", "field": "active", "value": False},
|
227
|
+
],
|
228
|
+
},
|
229
|
+
)
|
230
|
+
|
231
|
+
# Add audit logging
|
232
|
+
audit_cleanup = builder.add_node(
|
233
|
+
"AuditLogNode",
|
234
|
+
node_id="audit_cleanup",
|
235
|
+
config={
|
236
|
+
"name": "cleanup_audit_logger",
|
237
|
+
"action": "cleanup_sessions",
|
238
|
+
"resource_type": "session",
|
239
|
+
},
|
240
|
+
)
|
241
|
+
|
242
|
+
# Connect nodes
|
243
|
+
builder.add_connection(batch_cleanup, "batches", archiver, "sessions")
|
244
|
+
builder.add_connection(archiver, "output", audit_cleanup, "cleanup_data")
|
245
|
+
|
246
|
+
return builder
|
247
|
+
|
248
|
+
@staticmethod
|
249
|
+
def create_error_handling_workflow() -> WorkflowBuilder:
|
250
|
+
"""
|
251
|
+
Create a workflow for error handling with retries.
|
252
|
+
|
253
|
+
Workflow steps:
|
254
|
+
1. Capture error details
|
255
|
+
2. Determine retry strategy
|
256
|
+
3. Execute retry if applicable
|
257
|
+
4. Log error if retry fails
|
258
|
+
5. Emit error events
|
259
|
+
|
260
|
+
Returns:
|
261
|
+
WorkflowBuilder configured for error handling
|
262
|
+
"""
|
263
|
+
builder = WorkflowBuilder()
|
264
|
+
|
265
|
+
# Add error analyzer
|
266
|
+
error_analyzer = builder.add_node(
|
267
|
+
"PythonCodeNode",
|
268
|
+
node_id="analyze_error",
|
269
|
+
config={
|
270
|
+
"name": "error_analyzer",
|
271
|
+
"code": """
|
272
|
+
error_type = error_data.get('type', 'unknown')
|
273
|
+
retry_count = error_data.get('retry_count', 0)
|
274
|
+
max_retries = 3
|
275
|
+
|
276
|
+
should_retry = retry_count < max_retries and error_type in ['timeout', 'network', 'temporary']
|
277
|
+
retry_delay = min(2 ** retry_count, 60) # Exponential backoff
|
278
|
+
|
279
|
+
result = {
|
280
|
+
'should_retry': should_retry,
|
281
|
+
'retry_delay': retry_delay,
|
282
|
+
'retry_count': retry_count + 1,
|
283
|
+
'error_type': error_type
|
284
|
+
}
|
285
|
+
""",
|
286
|
+
},
|
287
|
+
)
|
288
|
+
|
289
|
+
# Add security event for error
|
290
|
+
security_error = builder.add_node(
|
291
|
+
"SecurityEventNode",
|
292
|
+
node_id="log_error_event",
|
293
|
+
config={
|
294
|
+
"name": "error_security_logger",
|
295
|
+
"event_type": "execution_error",
|
296
|
+
"severity": "warning",
|
297
|
+
},
|
298
|
+
)
|
299
|
+
|
300
|
+
# Connect nodes
|
301
|
+
builder.add_connection(error_analyzer, "result", security_error, "error_info")
|
302
|
+
|
303
|
+
return builder
|
304
|
+
|
305
|
+
|
306
|
+
class WorkflowBasedMiddleware:
|
307
|
+
"""
|
308
|
+
Example of how to use workflows for middleware operations.
|
309
|
+
|
310
|
+
This demonstrates replacing custom code with workflow-based
|
311
|
+
implementations for better performance and maintainability.
|
312
|
+
"""
|
313
|
+
|
314
|
+
def __init__(self):
|
315
|
+
"""Initialize workflow-based middleware."""
|
316
|
+
self.runtime = AsyncLocalRuntime(debug=True, max_concurrency=10)
|
317
|
+
|
318
|
+
# Pre-build common workflows
|
319
|
+
self.workflows = {
|
320
|
+
"session_creation": MiddlewareWorkflows.create_session_workflow().build(),
|
321
|
+
"execution_monitoring": MiddlewareWorkflows.create_execution_monitoring_workflow().build(),
|
322
|
+
"cleanup": MiddlewareWorkflows.create_cleanup_workflow().build(),
|
323
|
+
"error_handling": MiddlewareWorkflows.create_error_handling_workflow().build(),
|
324
|
+
}
|
325
|
+
|
326
|
+
async def create_session(self, user_id: str, metadata: Dict[str, Any]) -> str:
|
327
|
+
"""
|
328
|
+
Create a session using workflow-based approach.
|
329
|
+
|
330
|
+
Args:
|
331
|
+
user_id: User identifier
|
332
|
+
metadata: Session metadata
|
333
|
+
|
334
|
+
Returns:
|
335
|
+
Session ID
|
336
|
+
"""
|
337
|
+
inputs = {"user_id": user_id, "metadata": metadata}
|
338
|
+
|
339
|
+
# Execute session creation workflow
|
340
|
+
results, run_id = await self.runtime.execute(
|
341
|
+
self.workflows["session_creation"], parameters=inputs
|
342
|
+
)
|
343
|
+
|
344
|
+
return results.get("session_id")
|
345
|
+
|
346
|
+
async def monitor_execution(
|
347
|
+
self, execution_id: str, execution_data: Dict[str, Any]
|
348
|
+
):
|
349
|
+
"""
|
350
|
+
Monitor execution progress using workflow.
|
351
|
+
|
352
|
+
Args:
|
353
|
+
execution_id: Execution identifier
|
354
|
+
execution_data: Current execution state
|
355
|
+
"""
|
356
|
+
inputs = {"execution_id": execution_id, "execution_data": execution_data}
|
357
|
+
|
358
|
+
# Execute monitoring workflow
|
359
|
+
await self.runtime.execute(
|
360
|
+
self.workflows["execution_monitoring"], parameters=inputs
|
361
|
+
)
|
362
|
+
|
363
|
+
async def cleanup_sessions(self, timeout_minutes: int = 60):
|
364
|
+
"""
|
365
|
+
Run cleanup workflow for expired sessions.
|
366
|
+
|
367
|
+
Args:
|
368
|
+
timeout_minutes: Session timeout in minutes
|
369
|
+
"""
|
370
|
+
inputs = {
|
371
|
+
"timeout_minutes": timeout_minutes,
|
372
|
+
"current_time": datetime.now(timezone.utc),
|
373
|
+
}
|
374
|
+
|
375
|
+
# Execute cleanup workflow
|
376
|
+
await self.runtime.execute(self.workflows["cleanup"], parameters=inputs)
|
377
|
+
|
378
|
+
async def handle_error(self, error_data: Dict[str, Any]):
|
379
|
+
"""
|
380
|
+
Handle errors using workflow-based retry logic.
|
381
|
+
|
382
|
+
Args:
|
383
|
+
error_data: Error information including type and context
|
384
|
+
"""
|
385
|
+
# Execute error handling workflow
|
386
|
+
results, _ = await self.runtime.execute(
|
387
|
+
self.workflows["error_handling"], parameters={"error_data": error_data}
|
388
|
+
)
|
389
|
+
|
390
|
+
if results.get("should_retry"):
|
391
|
+
# Schedule retry using appropriate mechanism
|
392
|
+
pass
|
393
|
+
|
394
|
+
|
395
|
+
# Export workflow templates for reuse
|
396
|
+
__all__ = ["MiddlewareWorkflows", "WorkflowBasedMiddleware"]
|
@@ -0,0 +1,63 @@
|
|
1
|
+
"""
|
2
|
+
Enterprise Database Layer for Kailash Middleware
|
3
|
+
|
4
|
+
Consolidates existing Kailash database implementations with middleware-specific
|
5
|
+
enhancements for workflow management, user data, and audit logging.
|
6
|
+
|
7
|
+
Features:
|
8
|
+
- Enhanced SQLAlchemy models with middleware integration
|
9
|
+
- Repository pattern with event streaming
|
10
|
+
- Multi-tenant data isolation
|
11
|
+
- Advanced permission models
|
12
|
+
- Audit logging with real-time events
|
13
|
+
- Connection pooling and optimization
|
14
|
+
"""
|
15
|
+
|
16
|
+
from .migrations import MiddlewareMigrationRunner
|
17
|
+
from .models import (
|
18
|
+
AccessLogModel,
|
19
|
+
Base,
|
20
|
+
CustomNodeModel,
|
21
|
+
NodePermissionModel,
|
22
|
+
UserGroupMemberModel,
|
23
|
+
UserGroupModel,
|
24
|
+
UserPreferencesModel,
|
25
|
+
WorkflowExecutionModel,
|
26
|
+
WorkflowModel,
|
27
|
+
WorkflowPermissionModel,
|
28
|
+
WorkflowTemplateModel,
|
29
|
+
WorkflowVersionModel,
|
30
|
+
)
|
31
|
+
from .repositories import (
|
32
|
+
MiddlewareExecutionRepository,
|
33
|
+
MiddlewarePermissionRepository,
|
34
|
+
MiddlewareUserRepository,
|
35
|
+
MiddlewareWorkflowRepository,
|
36
|
+
)
|
37
|
+
from .session_manager import MiddlewareDatabaseManager, get_middleware_db_session
|
38
|
+
|
39
|
+
__all__ = [
|
40
|
+
# Models
|
41
|
+
"Base",
|
42
|
+
"WorkflowModel",
|
43
|
+
"WorkflowVersionModel",
|
44
|
+
"CustomNodeModel",
|
45
|
+
"WorkflowExecutionModel",
|
46
|
+
"UserPreferencesModel",
|
47
|
+
"WorkflowTemplateModel",
|
48
|
+
"WorkflowPermissionModel",
|
49
|
+
"NodePermissionModel",
|
50
|
+
"AccessLogModel",
|
51
|
+
"UserGroupModel",
|
52
|
+
"UserGroupMemberModel",
|
53
|
+
# Repositories
|
54
|
+
"MiddlewareWorkflowRepository",
|
55
|
+
"MiddlewareExecutionRepository",
|
56
|
+
"MiddlewareUserRepository",
|
57
|
+
"MiddlewarePermissionRepository",
|
58
|
+
# Session Management
|
59
|
+
"MiddlewareDatabaseManager",
|
60
|
+
"get_middleware_db_session",
|
61
|
+
# Migrations
|
62
|
+
"MiddlewareMigrationRunner",
|
63
|
+
]
|
@@ -0,0 +1,113 @@
|
|
1
|
+
"""
|
2
|
+
Base models and mixins for middleware database layer.
|
3
|
+
|
4
|
+
Provides common functionality for all database models.
|
5
|
+
"""
|
6
|
+
|
7
|
+
import uuid
|
8
|
+
from datetime import datetime, timezone
|
9
|
+
from typing import Any, Dict, Optional
|
10
|
+
|
11
|
+
from sqlalchemy import Boolean, Column, DateTime, Integer, String, event
|
12
|
+
from sqlalchemy.ext.declarative import declared_attr
|
13
|
+
from sqlalchemy.sql import func
|
14
|
+
|
15
|
+
|
16
|
+
class TenantMixin:
|
17
|
+
"""Multi-tenant support for all models."""
|
18
|
+
|
19
|
+
@declared_attr
|
20
|
+
def tenant_id(cls):
|
21
|
+
return Column(String(255), nullable=False, default="default", index=True)
|
22
|
+
|
23
|
+
|
24
|
+
class AuditMixin:
|
25
|
+
"""Audit trail support for all models."""
|
26
|
+
|
27
|
+
@declared_attr
|
28
|
+
def created_at(cls):
|
29
|
+
return Column(DateTime(timezone=True), nullable=False, default=func.now())
|
30
|
+
|
31
|
+
@declared_attr
|
32
|
+
def updated_at(cls):
|
33
|
+
return Column(DateTime(timezone=True), onupdate=func.now())
|
34
|
+
|
35
|
+
@declared_attr
|
36
|
+
def created_by(cls):
|
37
|
+
return Column(String(255))
|
38
|
+
|
39
|
+
@declared_attr
|
40
|
+
def updated_by(cls):
|
41
|
+
return Column(String(255))
|
42
|
+
|
43
|
+
|
44
|
+
class SoftDeleteMixin:
|
45
|
+
"""Soft delete support for compliance."""
|
46
|
+
|
47
|
+
@declared_attr
|
48
|
+
def deleted_at(cls):
|
49
|
+
return Column(DateTime(timezone=True))
|
50
|
+
|
51
|
+
@declared_attr
|
52
|
+
def deleted_by(cls):
|
53
|
+
return Column(String(255))
|
54
|
+
|
55
|
+
@property
|
56
|
+
def is_deleted(self) -> bool:
|
57
|
+
"""Check if entity is soft deleted."""
|
58
|
+
return self.deleted_at is not None
|
59
|
+
|
60
|
+
def soft_delete(self, deleted_by: str):
|
61
|
+
"""Mark entity as deleted."""
|
62
|
+
self.deleted_at = datetime.now(timezone.utc)
|
63
|
+
self.deleted_by = deleted_by
|
64
|
+
|
65
|
+
|
66
|
+
class VersionMixin:
|
67
|
+
"""Version control support."""
|
68
|
+
|
69
|
+
@declared_attr
|
70
|
+
def version(cls):
|
71
|
+
return Column(Integer, nullable=False, default=1)
|
72
|
+
|
73
|
+
def increment_version(self):
|
74
|
+
"""Increment version number."""
|
75
|
+
self.version = (self.version or 0) + 1
|
76
|
+
|
77
|
+
|
78
|
+
class SecurityMixin:
|
79
|
+
"""Security classification support."""
|
80
|
+
|
81
|
+
@declared_attr
|
82
|
+
def security_classification(cls):
|
83
|
+
return Column(String(50), default="internal")
|
84
|
+
|
85
|
+
@declared_attr
|
86
|
+
def access_permissions(cls):
|
87
|
+
return Column(String, default="{}") # JSON stored as string for compatibility
|
88
|
+
|
89
|
+
|
90
|
+
class ComplianceMixin:
|
91
|
+
"""Compliance tracking support."""
|
92
|
+
|
93
|
+
@declared_attr
|
94
|
+
def compliance_requirements(cls):
|
95
|
+
return Column(String, default="[]") # JSON array as string
|
96
|
+
|
97
|
+
@declared_attr
|
98
|
+
def retention_until(cls):
|
99
|
+
return Column(DateTime(timezone=True))
|
100
|
+
|
101
|
+
|
102
|
+
class BaseMixin(TenantMixin, AuditMixin):
|
103
|
+
"""Common mixins for most models."""
|
104
|
+
|
105
|
+
pass
|
106
|
+
|
107
|
+
|
108
|
+
class EnterpriseBaseMixin(
|
109
|
+
TenantMixin, AuditMixin, SoftDeleteMixin, VersionMixin, SecurityMixin
|
110
|
+
):
|
111
|
+
"""Full enterprise features for critical models."""
|
112
|
+
|
113
|
+
pass
|