kailash 0.6.2__py3-none-any.whl → 0.6.4__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.
Files changed (131) hide show
  1. kailash/__init__.py +3 -3
  2. kailash/api/custom_nodes_secure.py +3 -3
  3. kailash/api/gateway.py +1 -1
  4. kailash/api/studio.py +2 -3
  5. kailash/api/workflow_api.py +3 -4
  6. kailash/core/resilience/bulkhead.py +460 -0
  7. kailash/core/resilience/circuit_breaker.py +92 -10
  8. kailash/edge/discovery.py +86 -0
  9. kailash/mcp_server/__init__.py +334 -0
  10. kailash/mcp_server/advanced_features.py +1022 -0
  11. kailash/{mcp → mcp_server}/ai_registry_server.py +29 -4
  12. kailash/mcp_server/auth.py +789 -0
  13. kailash/mcp_server/client.py +712 -0
  14. kailash/mcp_server/discovery.py +1593 -0
  15. kailash/mcp_server/errors.py +673 -0
  16. kailash/mcp_server/oauth.py +1727 -0
  17. kailash/mcp_server/protocol.py +1126 -0
  18. kailash/mcp_server/registry_integration.py +587 -0
  19. kailash/mcp_server/server.py +1747 -0
  20. kailash/{mcp → mcp_server}/servers/ai_registry.py +2 -2
  21. kailash/mcp_server/transports.py +1169 -0
  22. kailash/mcp_server/utils/cache.py +510 -0
  23. kailash/middleware/auth/auth_manager.py +3 -3
  24. kailash/middleware/communication/api_gateway.py +2 -9
  25. kailash/middleware/communication/realtime.py +1 -1
  26. kailash/middleware/mcp/client_integration.py +1 -1
  27. kailash/middleware/mcp/enhanced_server.py +2 -2
  28. kailash/nodes/__init__.py +2 -0
  29. kailash/nodes/admin/audit_log.py +6 -6
  30. kailash/nodes/admin/permission_check.py +8 -8
  31. kailash/nodes/admin/role_management.py +32 -28
  32. kailash/nodes/admin/schema.sql +6 -1
  33. kailash/nodes/admin/schema_manager.py +13 -13
  34. kailash/nodes/admin/security_event.py +16 -20
  35. kailash/nodes/admin/tenant_isolation.py +3 -3
  36. kailash/nodes/admin/transaction_utils.py +3 -3
  37. kailash/nodes/admin/user_management.py +21 -22
  38. kailash/nodes/ai/a2a.py +11 -11
  39. kailash/nodes/ai/ai_providers.py +9 -12
  40. kailash/nodes/ai/embedding_generator.py +13 -14
  41. kailash/nodes/ai/intelligent_agent_orchestrator.py +19 -19
  42. kailash/nodes/ai/iterative_llm_agent.py +3 -3
  43. kailash/nodes/ai/llm_agent.py +213 -36
  44. kailash/nodes/ai/self_organizing.py +2 -2
  45. kailash/nodes/alerts/discord.py +4 -4
  46. kailash/nodes/api/graphql.py +6 -6
  47. kailash/nodes/api/http.py +12 -17
  48. kailash/nodes/api/rate_limiting.py +4 -4
  49. kailash/nodes/api/rest.py +15 -15
  50. kailash/nodes/auth/mfa.py +3 -4
  51. kailash/nodes/auth/risk_assessment.py +2 -2
  52. kailash/nodes/auth/session_management.py +5 -5
  53. kailash/nodes/auth/sso.py +143 -0
  54. kailash/nodes/base.py +6 -2
  55. kailash/nodes/base_async.py +16 -2
  56. kailash/nodes/base_with_acl.py +2 -2
  57. kailash/nodes/cache/__init__.py +9 -0
  58. kailash/nodes/cache/cache.py +1172 -0
  59. kailash/nodes/cache/cache_invalidation.py +870 -0
  60. kailash/nodes/cache/redis_pool_manager.py +595 -0
  61. kailash/nodes/code/async_python.py +2 -1
  62. kailash/nodes/code/python.py +196 -35
  63. kailash/nodes/compliance/data_retention.py +6 -6
  64. kailash/nodes/compliance/gdpr.py +5 -5
  65. kailash/nodes/data/__init__.py +10 -0
  66. kailash/nodes/data/optimistic_locking.py +906 -0
  67. kailash/nodes/data/readers.py +8 -8
  68. kailash/nodes/data/redis.py +349 -0
  69. kailash/nodes/data/sql.py +314 -3
  70. kailash/nodes/data/streaming.py +21 -0
  71. kailash/nodes/enterprise/__init__.py +8 -0
  72. kailash/nodes/enterprise/audit_logger.py +285 -0
  73. kailash/nodes/enterprise/batch_processor.py +22 -3
  74. kailash/nodes/enterprise/data_lineage.py +1 -1
  75. kailash/nodes/enterprise/mcp_executor.py +205 -0
  76. kailash/nodes/enterprise/service_discovery.py +150 -0
  77. kailash/nodes/enterprise/tenant_assignment.py +108 -0
  78. kailash/nodes/logic/async_operations.py +2 -2
  79. kailash/nodes/logic/convergence.py +1 -1
  80. kailash/nodes/logic/operations.py +1 -1
  81. kailash/nodes/monitoring/__init__.py +11 -1
  82. kailash/nodes/monitoring/health_check.py +456 -0
  83. kailash/nodes/monitoring/log_processor.py +817 -0
  84. kailash/nodes/monitoring/metrics_collector.py +627 -0
  85. kailash/nodes/monitoring/performance_benchmark.py +137 -11
  86. kailash/nodes/rag/advanced.py +7 -7
  87. kailash/nodes/rag/agentic.py +49 -2
  88. kailash/nodes/rag/conversational.py +3 -3
  89. kailash/nodes/rag/evaluation.py +3 -3
  90. kailash/nodes/rag/federated.py +3 -3
  91. kailash/nodes/rag/graph.py +3 -3
  92. kailash/nodes/rag/multimodal.py +3 -3
  93. kailash/nodes/rag/optimized.py +5 -5
  94. kailash/nodes/rag/privacy.py +3 -3
  95. kailash/nodes/rag/query_processing.py +6 -6
  96. kailash/nodes/rag/realtime.py +1 -1
  97. kailash/nodes/rag/registry.py +2 -6
  98. kailash/nodes/rag/router.py +1 -1
  99. kailash/nodes/rag/similarity.py +7 -7
  100. kailash/nodes/rag/strategies.py +4 -4
  101. kailash/nodes/security/abac_evaluator.py +6 -6
  102. kailash/nodes/security/behavior_analysis.py +5 -6
  103. kailash/nodes/security/credential_manager.py +1 -1
  104. kailash/nodes/security/rotating_credentials.py +11 -11
  105. kailash/nodes/security/threat_detection.py +8 -8
  106. kailash/nodes/testing/credential_testing.py +2 -2
  107. kailash/nodes/transform/processors.py +5 -5
  108. kailash/runtime/local.py +162 -14
  109. kailash/runtime/parameter_injection.py +425 -0
  110. kailash/runtime/parameter_injector.py +657 -0
  111. kailash/runtime/testing.py +2 -2
  112. kailash/testing/fixtures.py +2 -2
  113. kailash/workflow/builder.py +99 -18
  114. kailash/workflow/builder_improvements.py +207 -0
  115. kailash/workflow/input_handling.py +170 -0
  116. {kailash-0.6.2.dist-info → kailash-0.6.4.dist-info}/METADATA +21 -8
  117. {kailash-0.6.2.dist-info → kailash-0.6.4.dist-info}/RECORD +126 -101
  118. kailash/mcp/__init__.py +0 -53
  119. kailash/mcp/client.py +0 -445
  120. kailash/mcp/server.py +0 -292
  121. kailash/mcp/server_enhanced.py +0 -449
  122. kailash/mcp/utils/cache.py +0 -267
  123. /kailash/{mcp → mcp_server}/client_new.py +0 -0
  124. /kailash/{mcp → mcp_server}/utils/__init__.py +0 -0
  125. /kailash/{mcp → mcp_server}/utils/config.py +0 -0
  126. /kailash/{mcp → mcp_server}/utils/formatters.py +0 -0
  127. /kailash/{mcp → mcp_server}/utils/metrics.py +0 -0
  128. {kailash-0.6.2.dist-info → kailash-0.6.4.dist-info}/WHEEL +0 -0
  129. {kailash-0.6.2.dist-info → kailash-0.6.4.dist-info}/entry_points.txt +0 -0
  130. {kailash-0.6.2.dist-info → kailash-0.6.4.dist-info}/licenses/LICENSE +0 -0
  131. {kailash-0.6.2.dist-info → kailash-0.6.4.dist-info}/top_level.txt +0 -0
@@ -53,7 +53,7 @@ class DenseRetrievalNode(Node):
53
53
  )
54
54
 
55
55
  # Finds semantically similar content even without exact keywords
56
- results = await dense_retriever.run(
56
+ results = await dense_retriever.execute(
57
57
  query="How to make AI systems more intelligent",
58
58
  documents=documents
59
59
  )
@@ -189,7 +189,7 @@ class SparseRetrievalNode(Node):
189
189
  )
190
190
 
191
191
  # Excellent for technical queries with specific terms
192
- results = await sparse_retriever.run(
192
+ results = await sparse_retriever.execute(
193
193
  query="sklearn RandomForestClassifier hyperparameters",
194
194
  documents=technical_docs
195
195
  )
@@ -478,7 +478,7 @@ class ColBERTRetrievalNode(Node):
478
478
  )
479
479
 
480
480
  # Excellent for queries with multiple specific requirements
481
- results = await colbert.run(
481
+ results = await colbert.execute(
482
482
  query="transformer architecture with attention mechanism for NLP tasks",
483
483
  documents=research_papers
484
484
  )
@@ -739,7 +739,7 @@ class MultiVectorRetrievalNode(Node):
739
739
  multi_vector = MultiVectorRetrievalNode()
740
740
 
741
741
  # Retrieves based on full content + summary + keywords
742
- results = await multi_vector.run(
742
+ results = await multi_vector.execute(
743
743
  query="machine learning optimization techniques",
744
744
  documents=long_documents
745
745
  )
@@ -1037,7 +1037,7 @@ class CrossEncoderRerankNode(Node):
1037
1037
  )
1038
1038
 
1039
1039
  # Reranks initial results for maximum precision
1040
- reranked = await reranker.run(
1040
+ reranked = await reranker.execute(
1041
1041
  initial_results=fast_retrieval_results,
1042
1042
  query="specific implementation details of BERT fine-tuning"
1043
1043
  )
@@ -1277,7 +1277,7 @@ class HybridFusionNode(Node):
1277
1277
  )
1278
1278
 
1279
1279
  # Combines dense and sparse retrieval results optimally
1280
- fused = await fusion.run(
1280
+ fused = await fusion.execute(
1281
1281
  retrieval_results=[dense_results, sparse_results]
1282
1282
  )
1283
1283
 
@@ -1568,7 +1568,7 @@ class PropositionBasedRetrievalNode(Node):
1568
1568
  proposition_rag = PropositionBasedRetrievalNode()
1569
1569
 
1570
1570
  # Retrieves specific facts without surrounding noise
1571
- facts = await proposition_rag.run(
1571
+ facts = await proposition_rag.execute(
1572
1572
  documents=knowledge_base,
1573
1573
  query="What is the speed of light in vacuum?"
1574
1574
  )
@@ -412,7 +412,7 @@ class SemanticRAGNode(Node):
412
412
  self.workflow_node = create_semantic_rag_workflow(self.config)
413
413
 
414
414
  # Delegate to WorkflowNode
415
- return self.workflow_node.run(**kwargs)
415
+ return self.workflow_node.execute(**kwargs)
416
416
 
417
417
 
418
418
  @register_node()
@@ -458,7 +458,7 @@ class StatisticalRAGNode(Node):
458
458
  if not self.workflow_node:
459
459
  self.workflow_node = create_statistical_rag_workflow(self.config)
460
460
 
461
- return self.workflow_node.run(**kwargs)
461
+ return self.workflow_node.execute(**kwargs)
462
462
 
463
463
 
464
464
  @register_node()
@@ -517,7 +517,7 @@ class HybridRAGNode(Node):
517
517
  self.fusion_method = fusion_method
518
518
  self.workflow_node = create_hybrid_rag_workflow(self.config, fusion_method)
519
519
 
520
- return self.workflow_node.run(**kwargs)
520
+ return self.workflow_node.execute(**kwargs)
521
521
 
522
522
 
523
523
  @register_node()
@@ -563,4 +563,4 @@ class HierarchicalRAGNode(Node):
563
563
  if not self.workflow_node:
564
564
  self.workflow_node = create_hierarchical_rag_workflow(self.config)
565
565
 
566
- return self.workflow_node.run(**kwargs)
566
+ return self.workflow_node.execute(**kwargs)
@@ -194,7 +194,7 @@ class ABACPermissionEvaluatorNode(SecurityMixin, PerformanceMixin, LoggingMixin,
194
194
  ... "network": "corporate"
195
195
  ... }
196
196
  >>>
197
- >>> result = evaluator.run(
197
+ >>> result = evaluator.execute(
198
198
  ... user_context=user_context,
199
199
  ... resource_context=resource_context,
200
200
  ... environment_context=env_context,
@@ -770,7 +770,7 @@ class ABACPermissionEvaluatorNode(SecurityMixin, PerformanceMixin, LoggingMixin,
770
770
 
771
771
  async def execute_async(self, **kwargs) -> Dict[str, Any]:
772
772
  """Async execution method for test compatibility."""
773
- return self.run(**kwargs)
773
+ return self.execute(**kwargs)
774
774
 
775
775
  def _evaluate_permission(
776
776
  self, context: ABACContext, permission: str
@@ -1026,7 +1026,7 @@ class ABACPermissionEvaluatorNode(SecurityMixin, PerformanceMixin, LoggingMixin,
1026
1026
  )
1027
1027
 
1028
1028
  # Run AI analysis
1029
- ai_response = self.ai_agent.run(
1029
+ ai_response = self.ai_agent.execute(
1030
1030
  provider="ollama",
1031
1031
  model=self.ai_model.replace("ollama:", ""),
1032
1032
  messages=[{"role": "user", "content": prompt}],
@@ -1275,7 +1275,7 @@ Return a JSON object with this structure:
1275
1275
  }
1276
1276
 
1277
1277
  try:
1278
- self.audit_log_node.run(**audit_entry)
1278
+ self.audit_log_node.execute(**audit_entry)
1279
1279
  except Exception as e:
1280
1280
  self.log_with_context(
1281
1281
  "WARNING", f"Failed to audit permission decision: {e}"
@@ -1355,7 +1355,7 @@ RESPONSE FORMAT:
1355
1355
  }}
1356
1356
  """
1357
1357
 
1358
- ai_response = self.ai_agent.run(
1358
+ ai_response = self.ai_agent.execute(
1359
1359
  provider="ollama",
1360
1360
  model=self.ai_model.replace("ollama:", ""),
1361
1361
  messages=[{"role": "user", "content": prompt}],
@@ -1408,4 +1408,4 @@ RESPONSE FORMAT:
1408
1408
 
1409
1409
  async def async_run(self, **kwargs) -> Dict[str, Any]:
1410
1410
  """Async execution method for enterprise integration."""
1411
- return self.run(**kwargs)
1411
+ return self.execute(**kwargs)
@@ -16,7 +16,6 @@ from datetime import UTC, datetime, timedelta
16
16
  from typing import Any, Dict, List, Optional, Set, Tuple
17
17
 
18
18
  import numpy as np
19
-
20
19
  from kailash.nodes.ai.llm_agent import LLMAgentNode
21
20
  from kailash.nodes.base import Node, NodeParameter, register_node
22
21
  from kailash.nodes.mixins import LoggingMixin, PerformanceMixin, SecurityMixin
@@ -107,7 +106,7 @@ class BehaviorAnalysisNode(SecurityMixin, PerformanceMixin, LoggingMixin, Node):
107
106
  ... "data_volume_mb": 15.5
108
107
  ... }
109
108
  >>>
110
- >>> result = behavior_analyzer.run(
109
+ >>> result = behavior_analyzer.execute(
111
110
  ... action="analyze",
112
111
  ... user_id="user123",
113
112
  ... recent_activity=[activity]
@@ -417,7 +416,7 @@ class BehaviorAnalysisNode(SecurityMixin, PerformanceMixin, LoggingMixin, Node):
417
416
  # Create audit log entry
418
417
  if result.get("success", False):
419
418
  try:
420
- self.audit_log_node.run(
419
+ self.audit_log_node.execute(
421
420
  action="behavior_analysis",
422
421
  user_id=user_id or "unknown",
423
422
  result="success",
@@ -1185,7 +1184,7 @@ RESPONSE FORMAT:
1185
1184
  """
1186
1185
 
1187
1186
  # Run AI analysis
1188
- ai_response = self.ai_agent.run(
1187
+ ai_response = self.ai_agent.execute(
1189
1188
  provider="ollama",
1190
1189
  model=self.ai_model.replace("ollama:", ""),
1191
1190
  messages=[{"role": "user", "content": prompt}],
@@ -1370,7 +1369,7 @@ RESPONSE FORMAT:
1370
1369
  }
1371
1370
 
1372
1371
  try:
1373
- self.security_event_node.run(**security_event)
1372
+ self.security_event_node.execute(**security_event)
1374
1373
  except Exception as e:
1375
1374
  self.log_with_context("WARNING", f"Failed to log anomaly event: {e}")
1376
1375
 
@@ -1890,4 +1889,4 @@ RESPONSE FORMAT:
1890
1889
 
1891
1890
  async def async_run(self, **kwargs) -> Dict[str, Any]:
1892
1891
  """Async execution method for enterprise integration."""
1893
- return self.run(**kwargs)
1892
+ return self.execute(**kwargs)
@@ -398,4 +398,4 @@ class CredentialManagerNode(Node):
398
398
 
399
399
  async def async_run(self, **kwargs) -> Dict[str, Any]:
400
400
  """Async execution method for enterprise integration."""
401
- return self.run(**kwargs)
401
+ return self.execute(**kwargs)
@@ -255,7 +255,7 @@ class RotatingCredentialNode(Node):
255
255
  """Check if a credential is approaching expiration."""
256
256
  try:
257
257
  # Get current credential
258
- credential_result = self._credential_manager.run(
258
+ credential_result = self._credential_manager.execute(
259
259
  operation="get_credential", credential_name=credential_name
260
260
  )
261
261
 
@@ -314,7 +314,7 @@ class RotatingCredentialNode(Node):
314
314
  # Try each refresh source in order
315
315
  for source in refresh_sources:
316
316
  try:
317
- refresh_result = self._credential_manager.run(
317
+ refresh_result = self._credential_manager.execute(
318
318
  operation="get_credential",
319
319
  credential_name=credential_name,
320
320
  credential_sources=[source],
@@ -363,7 +363,7 @@ class RotatingCredentialNode(Node):
363
363
  # Step 1: Get current credential (for rollback if needed)
364
364
  current_credential = None
365
365
  if rollback_on_failure:
366
- current_result = self._credential_manager.run(
366
+ current_result = self._credential_manager.execute(
367
367
  operation="get_credential", credential_name=credential_name
368
368
  )
369
369
  if current_result.get("success"):
@@ -390,7 +390,7 @@ class RotatingCredentialNode(Node):
390
390
  new_credential = refresh_result["credential"]
391
391
 
392
392
  # Step 3: Validate new credential
393
- validation_result = self._credential_manager.run(
393
+ validation_result = self._credential_manager.execute(
394
394
  operation="validate_credential",
395
395
  credential_name=credential_name,
396
396
  credential_data=new_credential,
@@ -422,7 +422,7 @@ class RotatingCredentialNode(Node):
422
422
 
423
423
  temp_credential_name = f"{credential_name}_rotating_{int(time.time())}"
424
424
 
425
- store_result = self._credential_manager.run(
425
+ store_result = self._credential_manager.execute(
426
426
  operation="store_credential",
427
427
  credential_name=temp_credential_name,
428
428
  credential_data=new_credential,
@@ -445,7 +445,7 @@ class RotatingCredentialNode(Node):
445
445
  # For this example, we'll assume it passes
446
446
 
447
447
  # Atomic switch
448
- final_store_result = self._credential_manager.run(
448
+ final_store_result = self._credential_manager.execute(
449
449
  operation="store_credential",
450
450
  credential_name=credential_name,
451
451
  credential_data=new_credential,
@@ -454,7 +454,7 @@ class RotatingCredentialNode(Node):
454
454
  if not final_store_result.get("success"):
455
455
  # Rollback if requested
456
456
  if rollback_on_failure and current_credential:
457
- self._credential_manager.run(
457
+ self._credential_manager.execute(
458
458
  operation="store_credential",
459
459
  credential_name=credential_name,
460
460
  credential_data=current_credential,
@@ -476,13 +476,13 @@ class RotatingCredentialNode(Node):
476
476
  }
477
477
 
478
478
  # Clean up temporary credential
479
- self._credential_manager.run(
479
+ self._credential_manager.execute(
480
480
  operation="delete_credential", credential_name=temp_credential_name
481
481
  )
482
482
 
483
483
  else:
484
484
  # Direct replacement
485
- store_result = self._credential_manager.run(
485
+ store_result = self._credential_manager.execute(
486
486
  operation="store_credential",
487
487
  credential_name=credential_name,
488
488
  credential_data=new_credential,
@@ -491,7 +491,7 @@ class RotatingCredentialNode(Node):
491
491
  if not store_result.get("success"):
492
492
  # Rollback if requested
493
493
  if rollback_on_failure and current_credential:
494
- self._credential_manager.run(
494
+ self._credential_manager.execute(
495
495
  operation="store_credential",
496
496
  credential_name=credential_name,
497
497
  credential_data=current_credential,
@@ -757,4 +757,4 @@ class RotatingCredentialNode(Node):
757
757
 
758
758
  async def async_run(self, **kwargs) -> Dict[str, Any]:
759
759
  """Async execution method for enterprise integration."""
760
- return self.run(**kwargs)
760
+ return self.execute(**kwargs)
@@ -45,7 +45,7 @@ class ThreatDetectionNode(SecurityMixin, PerformanceMixin, LoggingMixin, Node):
45
45
  ... {"type": "login", "user": "admin", "ip": "192.168.1.100", "failed": True}
46
46
  ... ]
47
47
  >>>
48
- >>> threats = threat_detector.run(events=events)
48
+ >>> threats = threat_detector.execute(events=events)
49
49
  >>> print(f"Detected {len(threats['threats'])} threats")
50
50
  """
51
51
 
@@ -661,7 +661,7 @@ class ThreatDetectionNode(SecurityMixin, PerformanceMixin, LoggingMixin, Node):
661
661
  prompt = self._create_ai_analysis_prompt(event_summary, context)
662
662
 
663
663
  # Run AI analysis
664
- ai_response = self.ai_agent.run(
664
+ ai_response = self.ai_agent.execute(
665
665
  provider="ollama",
666
666
  model=self.ai_model.replace("ollama:", ""),
667
667
  messages=[{"role": "user", "content": prompt}],
@@ -923,7 +923,7 @@ If no threats are detected, return an empty array: []
923
923
  "source_ip": threat.get("source_ip", "unknown"),
924
924
  }
925
925
 
926
- self.security_event_node.run(**alert_event)
926
+ self.security_event_node.execute(**alert_event)
927
927
 
928
928
  def _block_ip(self, threat: Dict[str, Any]) -> None:
929
929
  """Block IP address associated with threat.
@@ -949,7 +949,7 @@ If no threats are detected, return an empty array: []
949
949
  "source_ip": ip,
950
950
  }
951
951
 
952
- self.security_event_node.run(**block_event)
952
+ self.security_event_node.execute(**block_event)
953
953
 
954
954
  def _lock_account(self, threat: Dict[str, Any]) -> None:
955
955
  """Lock user account associated with threat.
@@ -974,7 +974,7 @@ If no threats are detected, return an empty array: []
974
974
  "source_ip": threat.get("source_ip", "unknown"),
975
975
  }
976
976
 
977
- self.security_event_node.run(**lock_event)
977
+ self.security_event_node.execute(**lock_event)
978
978
 
979
979
  def _quarantine_resource(self, threat: Dict[str, Any]) -> None:
980
980
  """Quarantine resource associated with threat.
@@ -996,7 +996,7 @@ If no threats are detected, return an empty array: []
996
996
  "source_ip": threat.get("source_ip", "unknown"),
997
997
  }
998
998
 
999
- self.security_event_node.run(**quarantine_event)
999
+ self.security_event_node.execute(**quarantine_event)
1000
1000
 
1001
1001
  def _log_threat(self, threat: Dict[str, Any]) -> None:
1002
1002
  """Log threat to audit trail.
@@ -1014,7 +1014,7 @@ If no threats are detected, return an empty array: []
1014
1014
  "ip_address": threat.get("source_ip", "unknown"),
1015
1015
  }
1016
1016
 
1017
- self.audit_log_node.run(**log_entry)
1017
+ self.audit_log_node.execute(**log_entry)
1018
1018
 
1019
1019
  def _update_stats(
1020
1020
  self, events_processed: int, threats_detected: int, processing_time_ms: float
@@ -1100,4 +1100,4 @@ If no threats are detected, return an empty array: []
1100
1100
 
1101
1101
  async def async_run(self, **kwargs) -> Dict[str, Any]:
1102
1102
  """Async execution method for enterprise integration."""
1103
- return self.run(**kwargs)
1103
+ return self.execute(**kwargs)
@@ -39,7 +39,7 @@ class CredentialTestingNode(Node):
39
39
  Example:
40
40
  >>> # Test OAuth2 token expiration
41
41
  >>> tester = CredentialTestingNode()
42
- >>> result = tester.run(
42
+ >>> result = tester.execute(
43
43
  ... credential_type='oauth2',
44
44
  ... scenario='expired',
45
45
  ... mock_data={'client_id': 'test_client'}
@@ -48,7 +48,7 @@ class CredentialTestingNode(Node):
48
48
  >>> assert 'expired_token' in result['error_details']
49
49
  >>>
50
50
  >>> # Test successful API key validation
51
- >>> result = tester.run(
51
+ >>> result = tester.execute(
52
52
  ... credential_type='api_key',
53
53
  ... scenario='success',
54
54
  ... validation_rules={'key_length': 32}
@@ -68,7 +68,7 @@ class FilterNode(Node):
68
68
  Examples:
69
69
  >>> # Filter list of numbers
70
70
  >>> filter_node = FilterNode()
71
- >>> result = filter_node.run(
71
+ >>> result = filter_node.execute(
72
72
  ... data=[1, 2, 3, 4, 5],
73
73
  ... operator=">",
74
74
  ... value=3
@@ -81,7 +81,7 @@ class FilterNode(Node):
81
81
  ... {"name": "Bob", "age": 25},
82
82
  ... {"name": "Charlie", "age": 35}
83
83
  ... ]
84
- >>> result = filter_node.run(
84
+ >>> result = filter_node.execute(
85
85
  ... data=users,
86
86
  ... field="age",
87
87
  ... operator=">=",
@@ -96,7 +96,7 @@ class FilterNode(Node):
96
96
  ... {"title": "Java Development"},
97
97
  ... {"title": "Python for Data Science"}
98
98
  ... ]
99
- >>> result = filter_node.run(
99
+ >>> result = filter_node.execute(
100
100
  ... data=items,
101
101
  ... field="title",
102
102
  ... operator="contains",
@@ -110,7 +110,7 @@ class FilterNode(Node):
110
110
  ... {"value": None},
111
111
  ... {"value": 20}
112
112
  ... ]
113
- >>> result = filter_node.run(
113
+ >>> result = filter_node.execute(
114
114
  ... data=data_with_nulls,
115
115
  ... field="value",
116
116
  ... operator="!=",
@@ -570,7 +570,7 @@ class ContextualCompressorNode(Node):
570
570
  ... compression_ratio=0.6,
571
571
  ... relevance_threshold=0.7
572
572
  ... )
573
- >>> result = compressor.run(
573
+ >>> result = compressor.execute(
574
574
  ... query="machine learning algorithms",
575
575
  ... retrieved_docs=[{"content": "...", "metadata": {}}],
576
576
  ... compression_target=1500