ragaai-catalyst 2.1.4.1b0__py3-none-any.whl → 2.1.5__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.
- ragaai_catalyst/__init__.py +23 -2
- ragaai_catalyst/dataset.py +462 -1
- ragaai_catalyst/evaluation.py +76 -7
- ragaai_catalyst/ragaai_catalyst.py +52 -10
- ragaai_catalyst/redteaming/__init__.py +7 -0
- ragaai_catalyst/redteaming/config/detectors.toml +13 -0
- ragaai_catalyst/redteaming/data_generator/scenario_generator.py +95 -0
- ragaai_catalyst/redteaming/data_generator/test_case_generator.py +120 -0
- ragaai_catalyst/redteaming/evaluator.py +125 -0
- ragaai_catalyst/redteaming/llm_generator.py +136 -0
- ragaai_catalyst/redteaming/llm_generator_old.py +83 -0
- ragaai_catalyst/redteaming/red_teaming.py +331 -0
- ragaai_catalyst/redteaming/requirements.txt +4 -0
- ragaai_catalyst/redteaming/tests/grok.ipynb +97 -0
- ragaai_catalyst/redteaming/tests/stereotype.ipynb +2258 -0
- ragaai_catalyst/redteaming/upload_result.py +38 -0
- ragaai_catalyst/redteaming/utils/issue_description.py +114 -0
- ragaai_catalyst/redteaming/utils/rt.png +0 -0
- ragaai_catalyst/redteaming_old.py +171 -0
- ragaai_catalyst/synthetic_data_generation.py +400 -22
- ragaai_catalyst/tracers/__init__.py +17 -1
- ragaai_catalyst/tracers/agentic_tracing/data/data_structure.py +4 -2
- ragaai_catalyst/tracers/agentic_tracing/tracers/agent_tracer.py +212 -148
- ragaai_catalyst/tracers/agentic_tracing/tracers/base.py +657 -247
- ragaai_catalyst/tracers/agentic_tracing/tracers/custom_tracer.py +50 -19
- ragaai_catalyst/tracers/agentic_tracing/tracers/llm_tracer.py +588 -177
- ragaai_catalyst/tracers/agentic_tracing/tracers/main_tracer.py +99 -100
- ragaai_catalyst/tracers/agentic_tracing/tracers/network_tracer.py +3 -3
- ragaai_catalyst/tracers/agentic_tracing/tracers/tool_tracer.py +230 -29
- ragaai_catalyst/tracers/agentic_tracing/upload/trace_uploader.py +358 -0
- ragaai_catalyst/tracers/agentic_tracing/upload/upload_agentic_traces.py +75 -20
- ragaai_catalyst/tracers/agentic_tracing/upload/upload_code.py +55 -11
- ragaai_catalyst/tracers/agentic_tracing/upload/upload_local_metric.py +74 -0
- ragaai_catalyst/tracers/agentic_tracing/upload/upload_trace_metric.py +47 -16
- ragaai_catalyst/tracers/agentic_tracing/utils/create_dataset_schema.py +4 -2
- ragaai_catalyst/tracers/agentic_tracing/utils/file_name_tracker.py +26 -3
- ragaai_catalyst/tracers/agentic_tracing/utils/llm_utils.py +182 -17
- ragaai_catalyst/tracers/agentic_tracing/utils/model_costs.json +1233 -497
- ragaai_catalyst/tracers/agentic_tracing/utils/span_attributes.py +81 -10
- ragaai_catalyst/tracers/agentic_tracing/utils/supported_llm_provider.toml +34 -0
- ragaai_catalyst/tracers/agentic_tracing/utils/system_monitor.py +215 -0
- ragaai_catalyst/tracers/agentic_tracing/utils/trace_utils.py +0 -32
- ragaai_catalyst/tracers/agentic_tracing/utils/unique_decorator.py +3 -1
- ragaai_catalyst/tracers/agentic_tracing/utils/zip_list_of_unique_files.py +73 -47
- ragaai_catalyst/tracers/distributed.py +300 -0
- ragaai_catalyst/tracers/exporters/__init__.py +3 -1
- ragaai_catalyst/tracers/exporters/dynamic_trace_exporter.py +160 -0
- ragaai_catalyst/tracers/exporters/ragaai_trace_exporter.py +129 -0
- ragaai_catalyst/tracers/langchain_callback.py +809 -0
- ragaai_catalyst/tracers/llamaindex_instrumentation.py +424 -0
- ragaai_catalyst/tracers/tracer.py +301 -55
- ragaai_catalyst/tracers/upload_traces.py +24 -7
- ragaai_catalyst/tracers/utils/convert_langchain_callbacks_output.py +61 -0
- ragaai_catalyst/tracers/utils/convert_llama_instru_callback.py +69 -0
- ragaai_catalyst/tracers/utils/extraction_logic_llama_index.py +74 -0
- ragaai_catalyst/tracers/utils/langchain_tracer_extraction_logic.py +82 -0
- ragaai_catalyst/tracers/utils/model_prices_and_context_window_backup.json +9365 -0
- ragaai_catalyst/tracers/utils/trace_json_converter.py +269 -0
- {ragaai_catalyst-2.1.4.1b0.dist-info → ragaai_catalyst-2.1.5.dist-info}/METADATA +367 -45
- ragaai_catalyst-2.1.5.dist-info/RECORD +97 -0
- {ragaai_catalyst-2.1.4.1b0.dist-info → ragaai_catalyst-2.1.5.dist-info}/WHEEL +1 -1
- ragaai_catalyst-2.1.4.1b0.dist-info/RECORD +0 -67
- {ragaai_catalyst-2.1.4.1b0.dist-info → ragaai_catalyst-2.1.5.dist-info}/LICENSE +0 -0
- {ragaai_catalyst-2.1.4.1b0.dist-info → ragaai_catalyst-2.1.5.dist-info}/top_level.txt +0 -0
@@ -6,6 +6,7 @@ import uuid
|
|
6
6
|
import os
|
7
7
|
import builtins
|
8
8
|
from pathlib import Path
|
9
|
+
import logging
|
9
10
|
|
10
11
|
from .base import BaseTracer
|
11
12
|
from .llm_tracer import LLMTracerMixin
|
@@ -57,10 +58,12 @@ class AgenticTracing(
|
|
57
58
|
|
58
59
|
self.project_name = user_detail["project_name"]
|
59
60
|
self.project_id = user_detail["project_id"]
|
60
|
-
# self.dataset_name = user_detail["dataset_name"]
|
61
61
|
self.trace_user_detail = user_detail["trace_user_detail"]
|
62
62
|
self.base_url = f"{RagaAICatalyst.BASE_URL}"
|
63
63
|
self.timeout = 10
|
64
|
+
|
65
|
+
# Add warning flag
|
66
|
+
self._warning_shown = False
|
64
67
|
|
65
68
|
BaseTracer.__init__(self, user_detail)
|
66
69
|
|
@@ -84,27 +87,23 @@ class AgenticTracing(
|
|
84
87
|
self.auto_instrument_custom = True
|
85
88
|
else:
|
86
89
|
# Set global active state
|
87
|
-
self.is_active =
|
88
|
-
any(auto_instrumentation.values())
|
89
|
-
if isinstance(auto_instrumentation, dict)
|
90
|
-
else bool(auto_instrumentation)
|
91
|
-
)
|
90
|
+
self.is_active = True
|
92
91
|
|
93
92
|
# Set individual components
|
94
93
|
if isinstance(auto_instrumentation, dict):
|
95
|
-
self.auto_instrument_llm = auto_instrumentation.get("llm",
|
96
|
-
self.auto_instrument_tool = auto_instrumentation.get("tool",
|
97
|
-
self.auto_instrument_agent = auto_instrumentation.get("agent",
|
94
|
+
self.auto_instrument_llm = auto_instrumentation.get("llm", True)
|
95
|
+
self.auto_instrument_tool = auto_instrumentation.get("tool", True)
|
96
|
+
self.auto_instrument_agent = auto_instrumentation.get("agent", True)
|
98
97
|
self.auto_instrument_user_interaction = auto_instrumentation.get(
|
99
|
-
"user_interaction",
|
98
|
+
"user_interaction", True
|
100
99
|
)
|
101
100
|
self.auto_instrument_file_io = auto_instrumentation.get(
|
102
|
-
"file_io",
|
101
|
+
"file_io", True
|
103
102
|
)
|
104
103
|
self.auto_instrument_network = auto_instrumentation.get(
|
105
|
-
"network",
|
104
|
+
"network", True
|
106
105
|
)
|
107
|
-
self.auto_instrument_custom = auto_instrumentation.get("custom",
|
106
|
+
self.auto_instrument_custom = auto_instrumentation.get("custom", True)
|
108
107
|
else:
|
109
108
|
# If boolean provided, apply to all components
|
110
109
|
self.auto_instrument_llm = bool(auto_instrumentation)
|
@@ -120,9 +119,6 @@ class AgenticTracing(
|
|
120
119
|
self.component_network_calls = {} # Store network calls per component
|
121
120
|
self.component_user_interaction = {}
|
122
121
|
|
123
|
-
# Create output directory if it doesn't exist
|
124
|
-
self.output_dir = Path("./traces") # Using default traces directory
|
125
|
-
self.output_dir.mkdir(exist_ok=True)
|
126
122
|
|
127
123
|
def start_component(self, component_id: str):
|
128
124
|
"""Start tracking network calls for a component"""
|
@@ -137,27 +133,38 @@ class AgenticTracing(
|
|
137
133
|
self.network_tracer.network_calls.copy()
|
138
134
|
)
|
139
135
|
self.network_tracer.network_calls = [] # Reset for next component
|
140
|
-
|
136
|
+
|
137
|
+
# Store user interactions for the component
|
141
138
|
for interaction in self.user_interaction_tracer.interactions:
|
142
139
|
interaction_component_id = interaction.get("component_id")
|
143
140
|
if interaction_component_id not in self.component_user_interaction:
|
144
141
|
self.component_user_interaction[interaction_component_id] = []
|
145
142
|
if interaction not in self.component_user_interaction[interaction_component_id]:
|
146
143
|
self.component_user_interaction[interaction_component_id].append(interaction)
|
144
|
+
|
145
|
+
# Only reset component_id if it matches the current one
|
146
|
+
# This ensures we don't reset a parent's component_id when a child component ends
|
147
|
+
if self.current_component_id.get() == component_id:
|
148
|
+
# Get the parent agent's component_id if it exists
|
149
|
+
parent_agent_id = self.current_agent_id.get()
|
150
|
+
# If there's a parent agent, set the component_id back to the parent's
|
151
|
+
if parent_agent_id:
|
152
|
+
self.current_component_id.set(parent_agent_id)
|
153
|
+
self.user_interaction_tracer.component_id.set(parent_agent_id)
|
154
|
+
else:
|
155
|
+
# Only reset to None if there's no parent
|
156
|
+
self.current_component_id.set(None)
|
157
|
+
self.user_interaction_tracer.component_id.set(None)
|
147
158
|
|
148
159
|
def start(self):
|
149
160
|
"""Start tracing"""
|
150
|
-
|
151
|
-
return
|
161
|
+
self.is_active = True
|
152
162
|
|
153
163
|
# Setup user interaction tracing
|
154
164
|
self.user_interaction_tracer.project_id.set(self.project_id)
|
155
165
|
self.user_interaction_tracer.trace_id.set(self.trace_id)
|
156
166
|
self.user_interaction_tracer.tracer = self
|
157
167
|
self.user_interaction_tracer.component_id.set(self.current_component_id.get())
|
158
|
-
builtins.print = self.user_interaction_tracer.traced_print
|
159
|
-
builtins.input = self.user_interaction_tracer.traced_input
|
160
|
-
builtins.open = self.user_interaction_tracer.traced_open
|
161
168
|
|
162
169
|
# Start base tracer (includes system info and resource monitoring)
|
163
170
|
super().start()
|
@@ -166,24 +173,13 @@ class AgenticTracing(
|
|
166
173
|
self.network_tracer.activate_patches()
|
167
174
|
|
168
175
|
# take care of the auto instrumentation
|
169
|
-
if self.auto_instrument_llm:
|
170
|
-
self.instrument_llm_calls()
|
171
|
-
|
172
|
-
if self.auto_instrument_tool:
|
173
|
-
self.instrument_tool_calls()
|
174
|
-
|
175
|
-
if self.auto_instrument_agent:
|
176
|
-
self.instrument_agent_calls()
|
177
|
-
|
178
|
-
if self.auto_instrument_custom:
|
179
|
-
self.instrument_custom_calls()
|
180
|
-
|
181
176
|
if self.auto_instrument_user_interaction:
|
182
|
-
|
183
177
|
ToolTracerMixin.instrument_user_interaction_calls(self)
|
184
178
|
LLMTracerMixin.instrument_user_interaction_calls(self)
|
185
179
|
AgentTracerMixin.instrument_user_interaction_calls(self)
|
186
180
|
CustomTracerMixin.instrument_user_interaction_calls(self)
|
181
|
+
builtins.print = self.user_interaction_tracer.traced_print
|
182
|
+
builtins.input = self.user_interaction_tracer.traced_input
|
187
183
|
|
188
184
|
if self.auto_instrument_network:
|
189
185
|
ToolTracerMixin.instrument_network_calls(self)
|
@@ -191,9 +187,24 @@ class AgenticTracing(
|
|
191
187
|
AgentTracerMixin.instrument_network_calls(self)
|
192
188
|
CustomTracerMixin.instrument_network_calls(self)
|
193
189
|
|
194
|
-
|
195
|
-
|
196
|
-
|
190
|
+
if self.auto_instrument_file_io:
|
191
|
+
ToolTracerMixin.instrument_file_io_calls(self)
|
192
|
+
LLMTracerMixin.instrument_file_io_calls(self)
|
193
|
+
AgentTracerMixin.instrument_file_io_calls(self)
|
194
|
+
CustomTracerMixin.instrument_file_io_calls(self)
|
195
|
+
builtins.open = self.user_interaction_tracer.traced_open
|
196
|
+
|
197
|
+
if self.auto_instrument_llm:
|
198
|
+
self.instrument_llm_calls()
|
199
|
+
|
200
|
+
if self.auto_instrument_tool:
|
201
|
+
self.instrument_tool_calls()
|
202
|
+
|
203
|
+
if self.auto_instrument_agent:
|
204
|
+
self.instrument_agent_calls()
|
205
|
+
|
206
|
+
if self.auto_instrument_custom:
|
207
|
+
self.instrument_custom_calls()
|
197
208
|
|
198
209
|
def stop(self):
|
199
210
|
"""Stop tracing and save results"""
|
@@ -225,6 +236,8 @@ class AgenticTracing(
|
|
225
236
|
total_cost = 0.0
|
226
237
|
total_tokens = 0
|
227
238
|
|
239
|
+
processed_components = set()
|
240
|
+
|
228
241
|
def process_component(component):
|
229
242
|
nonlocal total_cost, total_tokens
|
230
243
|
# Convert component to dict if it's an object
|
@@ -232,6 +245,11 @@ class AgenticTracing(
|
|
232
245
|
component.__dict__ if hasattr(component, "__dict__") else component
|
233
246
|
)
|
234
247
|
|
248
|
+
comp_id = comp_dict.get("id") or comp_dict.get("component_id")
|
249
|
+
if comp_id in processed_components:
|
250
|
+
return # Skip if already processed
|
251
|
+
processed_components.add(comp_id)
|
252
|
+
|
235
253
|
if comp_dict.get("type") == "llm":
|
236
254
|
info = comp_dict.get("info", {})
|
237
255
|
if isinstance(info, dict):
|
@@ -298,6 +316,47 @@ class AgenticTracing(
|
|
298
316
|
]
|
299
317
|
}
|
300
318
|
|
319
|
+
if component_data == None or component_data == {} or component_data.get("type", None) == None:
|
320
|
+
# Only show warning if it hasn't been shown before
|
321
|
+
if not self._warning_shown:
|
322
|
+
import toml
|
323
|
+
import os
|
324
|
+
from pathlib import Path
|
325
|
+
|
326
|
+
# Load supported LLM calls from TOML file
|
327
|
+
current_dir = Path(__file__).parent
|
328
|
+
toml_path = current_dir / "../utils/supported_llm_provider.toml"
|
329
|
+
try:
|
330
|
+
with open(toml_path, "r") as f:
|
331
|
+
config = toml.load(f)
|
332
|
+
supported_calls = ", ".join(config["supported_llm_calls"])
|
333
|
+
except Exception as e:
|
334
|
+
supported_calls = "Error loading supported LLM calls"
|
335
|
+
|
336
|
+
# ANSI escape codes for colors and formatting
|
337
|
+
RED = "\033[91m"
|
338
|
+
BOLD = "\033[1m"
|
339
|
+
RESET = "\033[0m"
|
340
|
+
BIG = "\033[1;2m" # Makes text slightly larger in supported terminals
|
341
|
+
|
342
|
+
warning_msg = f"""{RED}{BOLD}{BIG}
|
343
|
+
╔════════════════════════ COMPONENT DATA INCOMPLETE ════════════════════════╗
|
344
|
+
║ ║
|
345
|
+
║ Please ensure these requirements: ║
|
346
|
+
║ ✗ trace_llm decorator must have a stand alone llm call ║
|
347
|
+
║ ✗ trace_tool decorator must be a stand alone tool/function call ║
|
348
|
+
║ ✗ trace_agent decorator can have multiple/nested llm/tool/agent calls ║
|
349
|
+
║ ║
|
350
|
+
║ Supported LLM calls: ║
|
351
|
+
║ {supported_calls} ║
|
352
|
+
║ ║
|
353
|
+
╚══════════════════════════════════════════════════════════════════════════╝
|
354
|
+
{RESET}"""
|
355
|
+
# Use logger.warning for the message
|
356
|
+
logging.warning(warning_msg)
|
357
|
+
self._warning_shown = True
|
358
|
+
return
|
359
|
+
|
301
360
|
if component_data["type"] == "llm":
|
302
361
|
component = LLMComponent(**filtered_data)
|
303
362
|
elif component_data["type"] == "agent":
|
@@ -309,7 +368,7 @@ class AgenticTracing(
|
|
309
368
|
|
310
369
|
# Check if there's an active agent context
|
311
370
|
current_agent_id = self.current_agent_id.get()
|
312
|
-
if current_agent_id and component_data["type"] in ["llm", "tool"]:
|
371
|
+
if current_agent_id and component_data["type"] in ["llm", "tool", "custom"]:
|
313
372
|
# Add this component as a child of the current agent
|
314
373
|
current_children = self.agent_children.get()
|
315
374
|
current_children.append(component_data)
|
@@ -319,67 +378,7 @@ class AgenticTracing(
|
|
319
378
|
super().add_component(component)
|
320
379
|
|
321
380
|
# Handle error case
|
322
|
-
if is_error:
|
323
|
-
# Get the parent component if it exists
|
324
|
-
parent_id = component_data.get("parent_id")
|
325
|
-
children = self.agent_children.get()
|
326
|
-
|
327
|
-
# Set parent_id for all children
|
328
|
-
for child in children:
|
329
|
-
child["parent_id"] = parent_id
|
330
|
-
|
331
|
-
agent_tracer_mixin = AgentTracerMixin()
|
332
|
-
agent_tracer_mixin.component_network_calls = self.component_network_calls
|
333
|
-
agent_tracer_mixin.component_user_interaction = (
|
334
|
-
self.component_user_interaction
|
335
|
-
)
|
336
|
-
|
337
|
-
agent_tracer_mixin.span_attributes_dict[self.current_agent_name.get()] = (
|
338
|
-
SpanAttributes(self.current_agent_name.get())
|
339
|
-
)
|
340
|
-
|
341
|
-
# Create parent component with error info
|
342
|
-
parent_component = agent_tracer_mixin.create_agent_component(
|
343
|
-
component_id=parent_id,
|
344
|
-
hash_id=str(uuid.uuid4()),
|
345
|
-
source_hash_id=None,
|
346
|
-
type="agent",
|
347
|
-
name=self.current_agent_name.get(),
|
348
|
-
agent_type=self.agent_type.get(),
|
349
|
-
version=self.version.get(),
|
350
|
-
capabilities=self.capabilities.get(),
|
351
|
-
start_time=self.start_time,
|
352
|
-
end_time=datetime.now().astimezone().isoformat(),
|
353
|
-
memory_used=0,
|
354
|
-
input_data=self.input_data,
|
355
|
-
output_data=None,
|
356
|
-
children=children,
|
357
|
-
parent_id=None, # Add parent ID if exists
|
358
|
-
)
|
359
|
-
|
360
|
-
filtered_data = {
|
361
|
-
k: v
|
362
|
-
for k, v in parent_component.items()
|
363
|
-
if k
|
364
|
-
in [
|
365
|
-
"id",
|
366
|
-
"hash_id",
|
367
|
-
"source_hash_id",
|
368
|
-
"type",
|
369
|
-
"name",
|
370
|
-
"start_time",
|
371
|
-
"end_time",
|
372
|
-
"parent_id",
|
373
|
-
"info",
|
374
|
-
"data",
|
375
|
-
"network_calls",
|
376
|
-
"interactions",
|
377
|
-
"error",
|
378
|
-
]
|
379
|
-
}
|
380
|
-
parent_agent_component = AgentComponent(**filtered_data)
|
381
|
-
# Add the parent component to trace and stop tracing
|
382
|
-
super().add_component(parent_agent_component)
|
381
|
+
if is_error and not self.current_agent_id.get():
|
383
382
|
self.stop()
|
384
383
|
|
385
384
|
def __enter__(self):
|
@@ -41,7 +41,7 @@ class NetworkTracer:
|
|
41
41
|
|
42
42
|
# Extract protocol from URL
|
43
43
|
protocol = "https" if url.startswith("https") else "http"
|
44
|
-
|
44
|
+
|
45
45
|
self.network_calls.append(
|
46
46
|
{
|
47
47
|
"url": url,
|
@@ -57,11 +57,11 @@ class NetworkTracer:
|
|
57
57
|
"parent_id": None, # Will be set by the component
|
58
58
|
"request": {
|
59
59
|
"headers": request_headers,
|
60
|
-
"body": request_body
|
60
|
+
"body": request_body if request_body else None,
|
61
61
|
},
|
62
62
|
"response": {
|
63
63
|
"headers": response_headers,
|
64
|
-
"body": response_body
|
64
|
+
"body": response_body if response_body else None,
|
65
65
|
},
|
66
66
|
"error": str(error) if error else None,
|
67
67
|
}
|