monocle-apptrace 0.5.3__py3-none-any.whl → 0.6.6__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.
Potentially problematic release.
This version of monocle-apptrace might be problematic. Click here for more details.
- monocle_apptrace/exporters/file_exporter.py +7 -1
- monocle_apptrace/instrumentation/common/constants.py +8 -0
- monocle_apptrace/instrumentation/common/instrumentor.py +1 -1
- monocle_apptrace/instrumentation/common/span_handler.py +75 -24
- monocle_apptrace/instrumentation/common/utils.py +63 -6
- monocle_apptrace/instrumentation/common/wrapper.py +111 -42
- monocle_apptrace/instrumentation/common/wrapper_method.py +6 -2
- monocle_apptrace/instrumentation/metamodel/a2a/methods.py +1 -1
- monocle_apptrace/instrumentation/metamodel/adk/_helper.py +7 -4
- monocle_apptrace/instrumentation/metamodel/adk/entities/agent.py +6 -1
- monocle_apptrace/instrumentation/metamodel/agents/_helper.py +8 -8
- monocle_apptrace/instrumentation/metamodel/agents/entities/inference.py +9 -2
- monocle_apptrace/instrumentation/metamodel/aiohttp/_helper.py +1 -1
- monocle_apptrace/instrumentation/metamodel/anthropic/entities/inference.py +1 -4
- monocle_apptrace/instrumentation/metamodel/azfunc/_helper.py +1 -1
- monocle_apptrace/instrumentation/metamodel/botocore/_helper.py +5 -0
- monocle_apptrace/instrumentation/metamodel/botocore/entities/inference.py +4 -0
- monocle_apptrace/instrumentation/metamodel/fastapi/_helper.py +4 -4
- monocle_apptrace/instrumentation/metamodel/fastapi/methods.py +4 -4
- monocle_apptrace/instrumentation/metamodel/finish_types.py +32 -1
- monocle_apptrace/instrumentation/metamodel/flask/_helper.py +3 -3
- monocle_apptrace/instrumentation/metamodel/hugging_face/__init__.py +0 -0
- monocle_apptrace/instrumentation/metamodel/hugging_face/_helper.py +138 -0
- monocle_apptrace/instrumentation/metamodel/hugging_face/entities/__init__.py +0 -0
- monocle_apptrace/instrumentation/metamodel/hugging_face/entities/inference.py +94 -0
- monocle_apptrace/instrumentation/metamodel/hugging_face/methods.py +23 -0
- monocle_apptrace/instrumentation/metamodel/lambdafunc/_helper.py +1 -1
- monocle_apptrace/instrumentation/metamodel/langchain/entities/inference.py +1 -4
- monocle_apptrace/instrumentation/metamodel/langgraph/_helper.py +34 -8
- monocle_apptrace/instrumentation/metamodel/langgraph/entities/inference.py +8 -3
- monocle_apptrace/instrumentation/metamodel/langgraph/langgraph_processor.py +88 -19
- monocle_apptrace/instrumentation/metamodel/langgraph/methods.py +22 -6
- monocle_apptrace/instrumentation/metamodel/llamaindex/_helper.py +30 -10
- monocle_apptrace/instrumentation/metamodel/llamaindex/entities/agent.py +4 -3
- monocle_apptrace/instrumentation/metamodel/llamaindex/llamaindex_processor.py +15 -7
- monocle_apptrace/instrumentation/metamodel/llamaindex/methods.py +1 -8
- monocle_apptrace/instrumentation/metamodel/mcp/_helper.py +7 -6
- monocle_apptrace/instrumentation/metamodel/mistral/_helper.py +98 -49
- monocle_apptrace/instrumentation/metamodel/mistral/entities/inference.py +15 -9
- monocle_apptrace/instrumentation/metamodel/mistral/entities/retrieval.py +41 -0
- monocle_apptrace/instrumentation/metamodel/mistral/methods.py +10 -1
- monocle_apptrace/instrumentation/metamodel/openai/_helper.py +47 -7
- monocle_apptrace/instrumentation/metamodel/openai/entities/inference.py +20 -4
- monocle_apptrace/instrumentation/metamodel/openai/methods.py +1 -1
- monocle_apptrace/instrumentation/metamodel/strands/_helper.py +44 -0
- monocle_apptrace/instrumentation/metamodel/strands/entities/agent.py +179 -0
- monocle_apptrace/instrumentation/metamodel/strands/entities/tool.py +62 -0
- monocle_apptrace/instrumentation/metamodel/strands/methods.py +20 -0
- {monocle_apptrace-0.5.3.dist-info → monocle_apptrace-0.6.6.dist-info}/METADATA +23 -79
- {monocle_apptrace-0.5.3.dist-info → monocle_apptrace-0.6.6.dist-info}/RECORD +53 -46
- monocle_apptrace/README.md +0 -101
- monocle_apptrace/mcp_server.py +0 -94
- monocle_apptrace-0.5.3.dist-info/licenses/NOTICE +0 -4
- {monocle_apptrace-0.5.3.dist-info → monocle_apptrace-0.6.6.dist-info}/WHEEL +0 -0
- {monocle_apptrace-0.5.3.dist-info → monocle_apptrace-0.6.6.dist-info}/entry_points.txt +0 -0
- {monocle_apptrace-0.5.3.dist-info → monocle_apptrace-0.6.6.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,28 +1,35 @@
|
|
|
1
1
|
# pylint: disable=protected-access
|
|
2
|
+
import logging
|
|
3
|
+
import os
|
|
2
4
|
from contextlib import contextmanager
|
|
3
5
|
import os
|
|
4
|
-
from typing import AsyncGenerator, Iterator
|
|
6
|
+
from typing import AsyncGenerator, Iterator
|
|
5
7
|
import logging
|
|
6
8
|
from opentelemetry.trace import Tracer
|
|
7
|
-
from opentelemetry.trace.propagation import
|
|
8
|
-
from opentelemetry.trace import propagation
|
|
9
|
+
from opentelemetry.trace.propagation import set_span_in_context, get_current_span
|
|
9
10
|
from opentelemetry.context import set_value, attach, detach, get_value
|
|
10
|
-
from opentelemetry.context import create_key, get_value, set_value
|
|
11
|
-
from opentelemetry.context.context import Context
|
|
12
11
|
from opentelemetry.trace.span import INVALID_SPAN, Span
|
|
13
12
|
from opentelemetry.trace.status import StatusCode
|
|
14
13
|
|
|
14
|
+
from monocle_apptrace.instrumentation.common.constants import (
|
|
15
|
+
ADD_NEW_WORKFLOW,
|
|
16
|
+
AGENTIC_SPANS,
|
|
17
|
+
WORKFLOW_TYPE_KEY,
|
|
18
|
+
)
|
|
19
|
+
from monocle_apptrace.instrumentation.common.scope_wrapper import monocle_trace_scope
|
|
15
20
|
from monocle_apptrace.instrumentation.common.span_handler import SpanHandler
|
|
16
21
|
from monocle_apptrace.instrumentation.common.utils import (
|
|
22
|
+
get_current_monocle_span,
|
|
23
|
+
remove_scope,
|
|
24
|
+
set_monocle_span_in_context,
|
|
25
|
+
set_scope,
|
|
17
26
|
set_scopes,
|
|
18
27
|
with_tracer_wrapper,
|
|
19
28
|
set_scope,
|
|
20
29
|
remove_scope,
|
|
21
30
|
get_current_monocle_span,
|
|
22
|
-
set_monocle_span_in_context
|
|
31
|
+
set_monocle_span_in_context,
|
|
23
32
|
)
|
|
24
|
-
from monocle_apptrace.instrumentation.common.constants import WORKFLOW_TYPE_KEY, ADD_NEW_WORKFLOW, AGENTIC_SPANS
|
|
25
|
-
from monocle_apptrace.instrumentation.common.scope_wrapper import monocle_trace_scope
|
|
26
33
|
|
|
27
34
|
logger = logging.getLogger(__name__)
|
|
28
35
|
ISOLATE_MONOCLE_SPANS = os.getenv("MONOCLE_ISOLATE_SPANS", "true").lower() == "true"
|
|
@@ -53,7 +60,9 @@ def post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, return_
|
|
|
53
60
|
try:
|
|
54
61
|
if parent_span == INVALID_SPAN:
|
|
55
62
|
parent_span = None
|
|
56
|
-
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, return_value, span, parent_span, ex
|
|
63
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, return_value, span, parent_span, ex,
|
|
64
|
+
is_post_exec=True)
|
|
65
|
+
return_value = SpanHandler.replace_placeholders_in_response(return_value, span)
|
|
57
66
|
except Exception as e:
|
|
58
67
|
logger.info(f"Warning: Error occurred in hydrate_span: {e}")
|
|
59
68
|
|
|
@@ -61,6 +70,7 @@ def post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, return_
|
|
|
61
70
|
handler.post_task_processing(to_wrap, wrapped, instance, args, kwargs, return_value, ex, span, parent_span)
|
|
62
71
|
except Exception as e:
|
|
63
72
|
logger.info(f"Warning: Error occurred in post_task_processing: {e}")
|
|
73
|
+
return return_value
|
|
64
74
|
|
|
65
75
|
def get_span_name(to_wrap, instance):
|
|
66
76
|
if to_wrap.get("span_name"):
|
|
@@ -87,19 +97,32 @@ def monocle_wrapper_span_processor(tracer: Tracer, handler: SpanHandler, to_wrap
|
|
|
87
97
|
span.end()
|
|
88
98
|
else:
|
|
89
99
|
ex:Exception = None
|
|
90
|
-
to_wrap = get_wrapper_with_next_processor(to_wrap, handler, instance, args, kwargs)
|
|
100
|
+
to_wrap = get_wrapper_with_next_processor(to_wrap, handler, instance, span, parent_span, args, kwargs)
|
|
91
101
|
if has_more_processors(to_wrap):
|
|
92
102
|
try:
|
|
93
|
-
|
|
103
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, None, span, parent_span, ex,
|
|
104
|
+
is_post_exec=False)
|
|
105
|
+
except Exception as e:
|
|
106
|
+
logger.info(f"Warning: Error occurred in hydrate_span pre_process_span: {e}")
|
|
107
|
+
try:
|
|
108
|
+
with monocle_trace_scope(get_builtin_scope_names(to_wrap)):
|
|
109
|
+
return_value, span_status = monocle_wrapper_span_processor(tracer, handler, to_wrap, wrapped, instance, source_path, False, args, kwargs)
|
|
94
110
|
except Exception as e:
|
|
95
111
|
ex = e
|
|
96
112
|
raise
|
|
97
113
|
finally:
|
|
98
|
-
|
|
114
|
+
return_value = post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, return_value, span, parent_span ,ex)
|
|
99
115
|
else:
|
|
100
116
|
try:
|
|
101
|
-
|
|
102
|
-
|
|
117
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, None, span, parent_span, ex,
|
|
118
|
+
is_post_exec=False)
|
|
119
|
+
except Exception as e:
|
|
120
|
+
logger.info(f"Warning: Error occurred in hydrate_span pre_process_span: {e}")
|
|
121
|
+
try:
|
|
122
|
+
skip_execution, return_value = SpanHandler.skip_execution(span)
|
|
123
|
+
if not skip_execution:
|
|
124
|
+
with SpanHandler.workflow_type(to_wrap, span):
|
|
125
|
+
return_value = wrapped(*args, **kwargs)
|
|
103
126
|
except Exception as e:
|
|
104
127
|
ex = e
|
|
105
128
|
raise
|
|
@@ -108,10 +131,11 @@ def monocle_wrapper_span_processor(tracer: Tracer, handler: SpanHandler, to_wrap
|
|
|
108
131
|
post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, ret_val, span, parent_span ,ex)
|
|
109
132
|
if not auto_close_span:
|
|
110
133
|
span.end()
|
|
134
|
+
return ret_val
|
|
111
135
|
if ex is None and not auto_close_span and to_wrap.get("output_processor") and to_wrap.get("output_processor").get("response_processor"):
|
|
112
136
|
to_wrap.get("output_processor").get("response_processor")(to_wrap, return_value, post_process_span_internal)
|
|
113
137
|
else:
|
|
114
|
-
post_process_span_internal(return_value)
|
|
138
|
+
return_value = post_process_span_internal(return_value)
|
|
115
139
|
span_status = span.status
|
|
116
140
|
return return_value, span_status
|
|
117
141
|
|
|
@@ -121,7 +145,9 @@ def monocle_wrapper(tracer: Tracer, handler: SpanHandler, to_wrap, wrapped, inst
|
|
|
121
145
|
token = None
|
|
122
146
|
try:
|
|
123
147
|
try:
|
|
124
|
-
pre_trace_token = handler.pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
148
|
+
pre_trace_token, alternate_to_wrapp = handler.pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
149
|
+
if alternate_to_wrapp is not None:
|
|
150
|
+
to_wrap = alternate_to_wrapp
|
|
125
151
|
except Exception as e:
|
|
126
152
|
logger.info(f"Warning: Error occurred in pre_tracing: {e}")
|
|
127
153
|
if to_wrap.get('skip_span', False) or handler.skip_span(to_wrap, wrapped, instance, args, kwargs):
|
|
@@ -160,31 +186,46 @@ async def amonocle_wrapper_span_processor(tracer: Tracer, handler: SpanHandler,
|
|
|
160
186
|
span.end()
|
|
161
187
|
else:
|
|
162
188
|
ex:Exception = None
|
|
163
|
-
to_wrap = get_wrapper_with_next_processor(to_wrap, handler, instance, args, kwargs)
|
|
189
|
+
to_wrap = get_wrapper_with_next_processor(to_wrap, handler, instance, span, parent_span,args, kwargs)
|
|
164
190
|
if has_more_processors(to_wrap):
|
|
165
191
|
try:
|
|
166
|
-
|
|
192
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, None, span, parent_span, ex,
|
|
193
|
+
is_post_exec=False)
|
|
194
|
+
except Exception as e:
|
|
195
|
+
logger.info(f"Warning: Error occurred in hydrate_span pre_process_span: {e}")
|
|
196
|
+
|
|
197
|
+
try:
|
|
198
|
+
with monocle_trace_scope(get_builtin_scope_names(to_wrap)):
|
|
199
|
+
return_value, span_status = await amonocle_wrapper_span_processor(tracer, handler, to_wrap, wrapped, instance, source_path, False, args, kwargs)
|
|
167
200
|
except Exception as e:
|
|
168
201
|
ex = e
|
|
169
202
|
raise
|
|
170
203
|
finally:
|
|
171
|
-
|
|
204
|
+
return_value = post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, return_value, span, parent_span ,ex)
|
|
172
205
|
else:
|
|
173
206
|
try:
|
|
174
|
-
|
|
175
|
-
|
|
207
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, None, span, parent_span, ex,
|
|
208
|
+
is_post_exec=False)
|
|
209
|
+
except Exception as e:
|
|
210
|
+
logger.info(f"Warning: Error occurred in hydrate_span pre_process_span: {e}")
|
|
211
|
+
try:
|
|
212
|
+
skip_execution, return_value = SpanHandler.skip_execution(span)
|
|
213
|
+
if not skip_execution:
|
|
214
|
+
with SpanHandler.workflow_type(to_wrap, span):
|
|
215
|
+
return_value = await wrapped(*args, **kwargs)
|
|
176
216
|
except Exception as e:
|
|
177
217
|
ex = e
|
|
178
218
|
raise
|
|
179
219
|
finally:
|
|
180
220
|
def post_process_span_internal(ret_val):
|
|
181
|
-
post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, ret_val, span, parent_span, ex)
|
|
221
|
+
ret_val = post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, ret_val, span, parent_span, ex)
|
|
182
222
|
if not auto_close_span:
|
|
183
223
|
span.end()
|
|
224
|
+
return ret_val
|
|
184
225
|
if ex is None and not auto_close_span and to_wrap.get("output_processor") and to_wrap.get("output_processor").get("response_processor"):
|
|
185
226
|
to_wrap.get("output_processor").get("response_processor")(to_wrap, return_value, post_process_span_internal)
|
|
186
227
|
else:
|
|
187
|
-
post_process_span_internal(return_value)
|
|
228
|
+
return_value = post_process_span_internal(return_value)
|
|
188
229
|
span_status = span.status
|
|
189
230
|
return return_value, span_status
|
|
190
231
|
|
|
@@ -208,35 +249,50 @@ async def amonocle_iter_wrapper_span_processor(tracer: Tracer, handler: SpanHand
|
|
|
208
249
|
span.end()
|
|
209
250
|
else:
|
|
210
251
|
ex:Exception = None
|
|
211
|
-
to_wrap = get_wrapper_with_next_processor(to_wrap, handler, instance, args, kwargs)
|
|
252
|
+
to_wrap = get_wrapper_with_next_processor(to_wrap, handler, span, parent_span, instance, args, kwargs)
|
|
212
253
|
if has_more_processors(to_wrap):
|
|
213
254
|
try:
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
255
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, None, span, parent_span, ex,
|
|
256
|
+
is_post_exec=False)
|
|
257
|
+
except Exception as e:
|
|
258
|
+
logger.info(f"Warning: Error occurred in hydrate_span pre_process_span: {e}")
|
|
259
|
+
try:
|
|
260
|
+
with monocle_trace_scope(get_builtin_scope_names(to_wrap)):
|
|
261
|
+
async for item in amonocle_iter_wrapper_span_processor(tracer, handler, to_wrap, wrapped, instance, source_path, False, args, kwargs):
|
|
262
|
+
last_item = item
|
|
263
|
+
yield item
|
|
217
264
|
except Exception as e:
|
|
218
265
|
ex = e
|
|
219
266
|
raise
|
|
220
267
|
finally:
|
|
221
|
-
post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, last_item, span, parent_span, ex)
|
|
268
|
+
last_item = post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, last_item, span, parent_span, ex)
|
|
222
269
|
else:
|
|
223
270
|
try:
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
271
|
+
handler.hydrate_span(to_wrap, wrapped, instance, args, kwargs, None, span, parent_span, ex,
|
|
272
|
+
is_post_exec=False)
|
|
273
|
+
except Exception as e:
|
|
274
|
+
logger.info(f"Warning: Error occurred in hydrate_span pre_process_span: {e}")
|
|
275
|
+
try:
|
|
276
|
+
skip_execution, last_item = SpanHandler.skip_execution(span)
|
|
277
|
+
if not skip_execution:
|
|
278
|
+
with SpanHandler.workflow_type(to_wrap, span):
|
|
279
|
+
async for item in wrapped(*args, **kwargs):
|
|
280
|
+
last_item = item
|
|
281
|
+
yield item
|
|
282
|
+
else:
|
|
283
|
+
yield last_item
|
|
228
284
|
except Exception as e:
|
|
229
285
|
ex = e
|
|
230
286
|
raise
|
|
231
287
|
finally:
|
|
232
288
|
def post_process_span_internal(ret_val):
|
|
233
|
-
post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, ret_val, span, parent_span, ex)
|
|
289
|
+
ret_val = post_process_span(handler, to_wrap, wrapped, instance, args, kwargs, ret_val, span, parent_span, ex)
|
|
234
290
|
if not auto_close_span:
|
|
235
291
|
span.end()
|
|
236
292
|
if ex is None and not auto_close_span and to_wrap.get("output_processor") and to_wrap.get("output_processor").get("response_processor"):
|
|
237
293
|
to_wrap.get("output_processor").get("response_processor")(to_wrap, None, post_process_span_internal)
|
|
238
294
|
else:
|
|
239
|
-
post_process_span_internal(last_item)
|
|
295
|
+
last_item = post_process_span_internal(last_item)
|
|
240
296
|
return
|
|
241
297
|
|
|
242
298
|
async def amonocle_wrapper(tracer: Tracer, handler: SpanHandler, to_wrap, wrapped, instance, source_path, args, kwargs):
|
|
@@ -245,7 +301,9 @@ async def amonocle_wrapper(tracer: Tracer, handler: SpanHandler, to_wrap, wrappe
|
|
|
245
301
|
pre_trace_token = None
|
|
246
302
|
try:
|
|
247
303
|
try:
|
|
248
|
-
pre_trace_token = handler.pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
304
|
+
pre_trace_token, alternate_to_wrapp = handler.pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
305
|
+
if alternate_to_wrapp is not None:
|
|
306
|
+
to_wrap = alternate_to_wrapp
|
|
249
307
|
except Exception as e:
|
|
250
308
|
logger.info(f"Warning: Error occurred in pre_tracing: {e}")
|
|
251
309
|
if to_wrap.get('skip_span', False) or handler.skip_span(to_wrap, wrapped, instance, args, kwargs):
|
|
@@ -271,7 +329,9 @@ async def amonocle_iter_wrapper(tracer: Tracer, handler: SpanHandler, to_wrap, w
|
|
|
271
329
|
pre_trace_token = None
|
|
272
330
|
try:
|
|
273
331
|
try:
|
|
274
|
-
pre_trace_token = handler.pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
332
|
+
pre_trace_token, alternate_to_wrapp = handler.pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
333
|
+
if alternate_to_wrapp is not None:
|
|
334
|
+
to_wrap = alternate_to_wrapp
|
|
275
335
|
except Exception as e:
|
|
276
336
|
logger.info(f"Warning: Error occurred in pre_tracing: {e}")
|
|
277
337
|
if to_wrap.get('skip_span', False) or handler.skip_span(to_wrap, wrapped, instance, args, kwargs):
|
|
@@ -373,13 +433,14 @@ def evaluate_scope_values(args, kwargs, to_wrap, scope_values):
|
|
|
373
433
|
@contextmanager
|
|
374
434
|
def start_as_monocle_span(tracer: Tracer, name: str, auto_close_span: bool) -> Iterator["Span"]:
|
|
375
435
|
""" Wrapper to OTEL start_as_current_span to isolate monocle and non monocle spans.
|
|
376
|
-
This
|
|
436
|
+
This essentially links monocle and non-monocle spans separately which is default behavior.
|
|
377
437
|
It can be optionally overridden by setting the environment variable MONOCLE_ISOLATE_SPANS to false.
|
|
378
438
|
"""
|
|
379
439
|
if not ISOLATE_MONOCLE_SPANS:
|
|
380
440
|
# If not isolating, use the default start_as_current_span
|
|
381
441
|
yield tracer.start_as_current_span(name, end_on_exit=auto_close_span)
|
|
382
442
|
return
|
|
443
|
+
|
|
383
444
|
original_span = get_current_span()
|
|
384
445
|
monocle_span_token = attach(set_span_in_context(get_current_monocle_span()))
|
|
385
446
|
with tracer.start_as_current_span(name, end_on_exit=auto_close_span) as span:
|
|
@@ -391,18 +452,26 @@ def start_as_monocle_span(tracer: Tracer, name: str, auto_close_span: bool) -> I
|
|
|
391
452
|
detach(monocle_span_token)
|
|
392
453
|
|
|
393
454
|
def get_builtin_scope_names(to_wrap) -> str:
|
|
394
|
-
output_processor =
|
|
395
|
-
|
|
455
|
+
output_processor = None
|
|
456
|
+
if "output_processor" in to_wrap:
|
|
457
|
+
output_processor = to_wrap.get("output_processor", None)
|
|
458
|
+
if "output_processor_list" in to_wrap:
|
|
459
|
+
for processor in to_wrap["output_processor_list"]:
|
|
460
|
+
if processor.get("type", None) in AGENTIC_SPANS:
|
|
461
|
+
output_processor = processor
|
|
462
|
+
break
|
|
463
|
+
|
|
464
|
+
span_type = output_processor.get("type", None) if output_processor and isinstance(output_processor, dict) else None
|
|
396
465
|
if span_type and span_type in AGENTIC_SPANS:
|
|
397
466
|
return span_type
|
|
398
467
|
return None
|
|
399
468
|
|
|
400
|
-
def get_wrapper_with_next_processor(to_wrap, handler, instance, args, kwargs):
|
|
469
|
+
def get_wrapper_with_next_processor(to_wrap, handler, instance, span, parent_span, args, kwargs):
|
|
401
470
|
if has_more_processors(to_wrap):
|
|
402
471
|
next_output_processor_list = to_wrap.get('output_processor_list',[]).copy()
|
|
403
472
|
while len(next_output_processor_list) > 0:
|
|
404
473
|
next_output_processor = next_output_processor_list.pop(0)
|
|
405
|
-
if handler.should_skip(next_output_processor, instance, args, kwargs):
|
|
474
|
+
if handler.should_skip(next_output_processor, instance, span, parent_span, args, kwargs):
|
|
406
475
|
next_output_processor = None
|
|
407
476
|
else:
|
|
408
477
|
break
|
|
@@ -412,4 +481,4 @@ def get_wrapper_with_next_processor(to_wrap, handler, instance, args, kwargs):
|
|
|
412
481
|
return to_wrap
|
|
413
482
|
|
|
414
483
|
def has_more_processors(to_wrap) -> bool:
|
|
415
|
-
return len(to_wrap.get('output_processor_list', [])) > 0
|
|
484
|
+
return len(to_wrap.get('output_processor_list', [])) > 0
|
|
@@ -5,6 +5,7 @@ from monocle_apptrace.instrumentation.common.span_handler import SpanHandler, No
|
|
|
5
5
|
from monocle_apptrace.instrumentation.metamodel.azureaiinference.methods import AZURE_AI_INFERENCE_METHODS
|
|
6
6
|
from monocle_apptrace.instrumentation.metamodel.botocore.methods import BOTOCORE_METHODS
|
|
7
7
|
from monocle_apptrace.instrumentation.metamodel.botocore.handlers.botocore_span_handler import BotoCoreSpanHandler
|
|
8
|
+
from monocle_apptrace.instrumentation.metamodel.hugging_face.methods import HUGGING_FACE_METHODS
|
|
8
9
|
from monocle_apptrace.instrumentation.metamodel.langchain.methods import (
|
|
9
10
|
LANGCHAIN_METHODS,
|
|
10
11
|
)
|
|
@@ -38,6 +39,7 @@ from monocle_apptrace.instrumentation.metamodel.a2a.methods import A2A_CLIENT_ME
|
|
|
38
39
|
from monocle_apptrace.instrumentation.metamodel.litellm.methods import LITELLM_METHODS
|
|
39
40
|
from monocle_apptrace.instrumentation.metamodel.adk.methods import ADK_METHODS
|
|
40
41
|
from monocle_apptrace.instrumentation.metamodel.mistral.methods import MISTRAL_METHODS
|
|
42
|
+
from monocle_apptrace.instrumentation.metamodel.strands.methods import STRAND_METHODS
|
|
41
43
|
|
|
42
44
|
class WrapperMethod:
|
|
43
45
|
def __init__(
|
|
@@ -109,7 +111,9 @@ DEFAULT_METHODS_LIST = (
|
|
|
109
111
|
A2A_CLIENT_METHODS +
|
|
110
112
|
LITELLM_METHODS +
|
|
111
113
|
ADK_METHODS +
|
|
112
|
-
MISTRAL_METHODS
|
|
114
|
+
MISTRAL_METHODS +
|
|
115
|
+
HUGGING_FACE_METHODS +
|
|
116
|
+
STRAND_METHODS
|
|
113
117
|
)
|
|
114
118
|
|
|
115
119
|
MONOCLE_SPAN_HANDLERS: Dict[str, SpanHandler] = {
|
|
@@ -131,5 +135,5 @@ MONOCLE_SPAN_HANDLERS: Dict[str, SpanHandler] = {
|
|
|
131
135
|
"llamaindex_tool_handler": LlamaIndexToolHandler(),
|
|
132
136
|
"llamaindex_agent_handler": LlamaIndexAgentHandler(),
|
|
133
137
|
"llamaindex_single_agent_tool_handler": LlamaIndexSingleAgenttToolHandlerWrapper(),
|
|
134
|
-
"lambda_func_handler": lambdaSpanHandler()
|
|
138
|
+
"lambda_func_handler": lambdaSpanHandler()
|
|
135
139
|
}
|
|
@@ -4,6 +4,7 @@ This module provides utility functions to extract various attributes from agent
|
|
|
4
4
|
"""
|
|
5
5
|
|
|
6
6
|
from ast import arguments
|
|
7
|
+
import json
|
|
7
8
|
from typing import Any, Dict, Optional
|
|
8
9
|
from monocle_apptrace.instrumentation.metamodel.finish_types import map_adk_finish_reason_to_finish_type
|
|
9
10
|
|
|
@@ -82,7 +83,7 @@ def extract_agent_input(arguments: Dict[str, Any]) -> Any:
|
|
|
82
83
|
Returns:
|
|
83
84
|
Any: The extracted input data
|
|
84
85
|
"""
|
|
85
|
-
return arguments['args'][0].user_content.parts[0].text
|
|
86
|
+
return [arguments['args'][0].user_content.parts[0].text]
|
|
86
87
|
|
|
87
88
|
def extract_agent_request_input(arguments: Dict[str, Any]) -> Any:
|
|
88
89
|
"""
|
|
@@ -94,7 +95,7 @@ def extract_agent_request_input(arguments: Dict[str, Any]) -> Any:
|
|
|
94
95
|
Returns:
|
|
95
96
|
Any: The extracted input data
|
|
96
97
|
"""
|
|
97
|
-
return arguments['kwargs']['new_message'].parts[0].text if 'new_message' in arguments['kwargs'] else
|
|
98
|
+
return [arguments['kwargs']['new_message'].parts[0].text] if 'new_message' in arguments['kwargs'] else []
|
|
98
99
|
|
|
99
100
|
def extract_agent_response(result: Any) -> Any:
|
|
100
101
|
"""
|
|
@@ -107,7 +108,9 @@ def extract_agent_response(result: Any) -> Any:
|
|
|
107
108
|
Any: The extracted response data
|
|
108
109
|
"""
|
|
109
110
|
if result:
|
|
110
|
-
return result.content.parts[0].text
|
|
111
|
+
return str(result.content.parts[0].text)
|
|
112
|
+
else:
|
|
113
|
+
return ""
|
|
111
114
|
|
|
112
115
|
def get_tool_name(instance: Any) -> str:
|
|
113
116
|
"""
|
|
@@ -179,7 +182,7 @@ def extract_tool_input(arguments: Dict[str, Any]) -> Any:
|
|
|
179
182
|
Returns:
|
|
180
183
|
Any: The extracted input data
|
|
181
184
|
"""
|
|
182
|
-
return
|
|
185
|
+
return json.dumps(arguments['kwargs'].get('args', {}))
|
|
183
186
|
|
|
184
187
|
def extract_tool_response(result: Any) -> Any:
|
|
185
188
|
"""
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
from monocle_apptrace.instrumentation.common.constants import SPAN_SUBTYPES, SPAN_TYPES
|
|
2
2
|
from monocle_apptrace.instrumentation.common.utils import get_error_message
|
|
3
3
|
from monocle_apptrace.instrumentation.metamodel.adk import _helper
|
|
4
|
+
from monocle_apptrace.instrumentation.common.utils import get_error_message
|
|
4
5
|
AGENT = {
|
|
5
6
|
"type": SPAN_TYPES.AGENTIC_INVOCATION,
|
|
6
7
|
"subtype": SPAN_SUBTYPES.ROUTING,
|
|
@@ -34,7 +35,7 @@ AGENT = {
|
|
|
34
35
|
"attributes": [
|
|
35
36
|
{
|
|
36
37
|
"_comment": "this is Agent input",
|
|
37
|
-
"attribute": "
|
|
38
|
+
"attribute": "input",
|
|
38
39
|
"accessor": lambda arguments: _helper.extract_agent_input(arguments)
|
|
39
40
|
}
|
|
40
41
|
]
|
|
@@ -42,6 +43,10 @@ AGENT = {
|
|
|
42
43
|
{
|
|
43
44
|
"name":"data.output",
|
|
44
45
|
"attributes": [
|
|
46
|
+
{
|
|
47
|
+
"attribute": "error_code",
|
|
48
|
+
"accessor": lambda arguments: get_error_message(arguments)
|
|
49
|
+
},
|
|
45
50
|
{
|
|
46
51
|
"_comment": "this is response from LLM",
|
|
47
52
|
"attribute": "response",
|
|
@@ -50,21 +50,21 @@ def extract_agent_input(arguments):
|
|
|
50
50
|
if len(arguments["args"]) > 1:
|
|
51
51
|
input_data = arguments["args"][1]
|
|
52
52
|
if isinstance(input_data, str):
|
|
53
|
-
return input_data
|
|
53
|
+
return [input_data]
|
|
54
54
|
elif isinstance(input_data, list):
|
|
55
55
|
# Handle list of input items
|
|
56
|
-
return
|
|
56
|
+
return input_data
|
|
57
57
|
|
|
58
58
|
# Fallback to kwargs
|
|
59
59
|
if "original_input" in arguments["kwargs"]:
|
|
60
60
|
input_data = arguments["kwargs"]["original_input"]
|
|
61
61
|
if isinstance(input_data, str):
|
|
62
|
-
return input_data
|
|
62
|
+
return [input_data]
|
|
63
63
|
elif isinstance(input_data, list):
|
|
64
|
-
return
|
|
64
|
+
return input_data
|
|
65
65
|
except Exception as e:
|
|
66
66
|
logger.warning("Warning: Error occurred in extract_agent_input: %s", str(e))
|
|
67
|
-
return
|
|
67
|
+
return []
|
|
68
68
|
|
|
69
69
|
|
|
70
70
|
def get_agent_name(arguments) -> str:
|
|
@@ -134,12 +134,12 @@ def extract_tool_input(arguments):
|
|
|
134
134
|
1
|
|
135
135
|
] # Second argument is usually the JSON string with params
|
|
136
136
|
if isinstance(tool_input, str):
|
|
137
|
-
return
|
|
137
|
+
return tool_input
|
|
138
138
|
elif isinstance(tool_input, dict):
|
|
139
|
-
return
|
|
139
|
+
return get_json_dumps(tool_input)
|
|
140
140
|
|
|
141
141
|
# Fallback to all args
|
|
142
|
-
return
|
|
142
|
+
return str(arguments["args"])
|
|
143
143
|
except Exception as e:
|
|
144
144
|
logger.warning("Warning: Error occurred in extract_tool_input: %s", str(e))
|
|
145
145
|
return []
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
from monocle_apptrace.instrumentation.common.constants import AGENT_REQUEST_SPAN_NAME, SPAN_SUBTYPES, SPAN_TYPES
|
|
2
2
|
from monocle_apptrace.instrumentation.common.utils import get_error_message
|
|
3
3
|
from monocle_apptrace.instrumentation.metamodel.agents import _helper
|
|
4
|
+
from monocle_apptrace.instrumentation.common.utils import get_error_message
|
|
4
5
|
|
|
5
6
|
AGENT = {
|
|
6
7
|
"type": SPAN_TYPES.AGENTIC_INVOCATION,
|
|
@@ -35,7 +36,7 @@ AGENT = {
|
|
|
35
36
|
"attributes": [
|
|
36
37
|
{
|
|
37
38
|
"_comment": "this is Agent input",
|
|
38
|
-
"attribute": "
|
|
39
|
+
"attribute": "input",
|
|
39
40
|
"accessor": lambda arguments: _helper.extract_agent_input(
|
|
40
41
|
arguments
|
|
41
42
|
),
|
|
@@ -45,6 +46,10 @@ AGENT = {
|
|
|
45
46
|
{
|
|
46
47
|
"name": "data.output",
|
|
47
48
|
"attributes": [
|
|
49
|
+
{
|
|
50
|
+
"attribute": "error_code",
|
|
51
|
+
"accessor": lambda arguments: get_error_message(arguments)
|
|
52
|
+
},
|
|
48
53
|
{
|
|
49
54
|
"_comment": "this is response from Agent",
|
|
50
55
|
"attribute": "response",
|
|
@@ -73,7 +78,7 @@ AGENT = {
|
|
|
73
78
|
}
|
|
74
79
|
|
|
75
80
|
AGENT_REQUEST = {
|
|
76
|
-
"type":
|
|
81
|
+
"type": SPAN_TYPES.AGENTIC_REQUEST,
|
|
77
82
|
"subtype": SPAN_SUBTYPES.PLANNING,
|
|
78
83
|
"attributes": [
|
|
79
84
|
[
|
|
@@ -123,6 +128,7 @@ TOOLS = {
|
|
|
123
128
|
{
|
|
124
129
|
"_comment": "tool type",
|
|
125
130
|
"attribute": "type",
|
|
131
|
+
"phase": "post_execution",
|
|
126
132
|
"accessor": lambda arguments: _helper.get_tool_type(arguments["span"]),
|
|
127
133
|
},
|
|
128
134
|
{
|
|
@@ -201,6 +207,7 @@ AGENT_DELEGATION = {
|
|
|
201
207
|
{
|
|
202
208
|
"_comment": "name of the target agent",
|
|
203
209
|
"attribute": "to_agent",
|
|
210
|
+
"phase": "post_execution",
|
|
204
211
|
"accessor": lambda arguments: _helper.extract_handoff_target(arguments),
|
|
205
212
|
},
|
|
206
213
|
]
|
|
@@ -67,7 +67,7 @@ def get_function_name(args) -> str:
|
|
|
67
67
|
class aiohttpSpanHandler(SpanHandler):
|
|
68
68
|
|
|
69
69
|
def pre_tracing(self, to_wrap, wrapped, instance, args, kwargs):
|
|
70
|
-
return aiohttp_pre_tracing(args)
|
|
70
|
+
return aiohttp_pre_tracing(args), None
|
|
71
71
|
|
|
72
72
|
def post_tracing(self, to_wrap, wrapped, instance, args, kwargs, return_value, token):
|
|
73
73
|
aiohttp_post_tracing(token)
|
|
@@ -6,6 +6,7 @@ from monocle_apptrace.instrumentation.common.utils import (get_error_message, re
|
|
|
6
6
|
|
|
7
7
|
INFERENCE = {
|
|
8
8
|
"type": SPAN_TYPES.INFERENCE,
|
|
9
|
+
"subtype": lambda arguments: _helper.agent_inference_type(arguments),
|
|
9
10
|
"attributes": [
|
|
10
11
|
[
|
|
11
12
|
{
|
|
@@ -80,10 +81,6 @@ INFERENCE = {
|
|
|
80
81
|
"_comment": "finish type mapped from finish reason",
|
|
81
82
|
"attribute": "finish_type",
|
|
82
83
|
"accessor": lambda arguments: _helper.map_finish_reason_to_finish_type(_helper.extract_finish_reason(arguments))
|
|
83
|
-
},
|
|
84
|
-
{
|
|
85
|
-
"attribute": "inference_sub_type",
|
|
86
|
-
"accessor": lambda arguments: _helper.agent_inference_type(arguments)
|
|
87
84
|
}
|
|
88
85
|
]
|
|
89
86
|
}
|
|
@@ -84,7 +84,7 @@ def azure_func_post_tracing(token):
|
|
|
84
84
|
class azureSpanHandler(SpanHandler):
|
|
85
85
|
|
|
86
86
|
def pre_tracing(self, to_wrap, wrapped, instance, args, kwargs):
|
|
87
|
-
return azure_func_pre_tracing(kwargs)
|
|
87
|
+
return azure_func_pre_tracing(kwargs), None
|
|
88
88
|
|
|
89
89
|
def post_tracing(self, to_wrap, wrapped, instance, args, kwargs, return_value, token):
|
|
90
90
|
azure_func_post_tracing(token)
|
|
@@ -7,6 +7,8 @@ import logging
|
|
|
7
7
|
import json
|
|
8
8
|
from io import BytesIO
|
|
9
9
|
from functools import wraps
|
|
10
|
+
|
|
11
|
+
from rfc3986 import urlparse
|
|
10
12
|
from monocle_apptrace.instrumentation.common.span_handler import SpanHandler
|
|
11
13
|
from monocle_apptrace.instrumentation.common.utils import ( get_exception_message, get_json_dumps, get_status_code,)
|
|
12
14
|
from monocle_apptrace.instrumentation.metamodel.finish_types import map_bedrock_finish_reason_to_finish_type
|
|
@@ -194,3 +196,6 @@ def extract_finish_reason(arguments):
|
|
|
194
196
|
def map_finish_reason_to_finish_type(finish_reason):
|
|
195
197
|
"""Map Bedrock finish_reason/stopReason to finish_type."""
|
|
196
198
|
return map_bedrock_finish_reason_to_finish_type(finish_reason)
|
|
199
|
+
|
|
200
|
+
def extract_provider_name(instance):
|
|
201
|
+
return urlparse(instance.meta.endpoint_url).hostname
|
|
@@ -15,6 +15,10 @@ INFERENCE = {
|
|
|
15
15
|
{
|
|
16
16
|
"attribute": "inference_endpoint",
|
|
17
17
|
"accessor": lambda arguments: arguments['instance'].meta.endpoint_url
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
"attribute": "provider_name",
|
|
21
|
+
"accessor": lambda arguments: _helper.extract_provider_name(arguments['instance'])
|
|
18
22
|
}
|
|
19
23
|
],
|
|
20
24
|
[
|
|
@@ -77,12 +77,12 @@ class FastAPISpanHandler(SpanHandler):
|
|
|
77
77
|
fastapi_pre_tracing(scope)
|
|
78
78
|
return super().pre_tracing(to_wrap, wrapped, instance, args, kwargs)
|
|
79
79
|
|
|
80
|
-
def post_tracing(self, to_wrap, wrapped, instance, args, kwargs, return_value):
|
|
80
|
+
def post_tracing(self, to_wrap, wrapped, instance, args, kwargs, return_value, token):
|
|
81
81
|
fastapi_post_tracing()
|
|
82
|
-
return super().post_tracing(to_wrap, wrapped, instance, args, kwargs, return_value)
|
|
82
|
+
return super().post_tracing(to_wrap, wrapped, instance, args, kwargs, return_value, token)
|
|
83
83
|
|
|
84
84
|
class FastAPIResponseSpanHandler(SpanHandler):
|
|
85
|
-
def post_tracing(self, to_wrap, wrapped, instance, args, kwargs, return_value):
|
|
85
|
+
def post_tracing(self, to_wrap, wrapped, instance, args, kwargs, return_value, token):
|
|
86
86
|
try:
|
|
87
87
|
ctx = get_current()
|
|
88
88
|
if ctx is not None:
|
|
@@ -92,4 +92,4 @@ class FastAPIResponseSpanHandler(SpanHandler):
|
|
|
92
92
|
return_value, parent_span=parent_span)
|
|
93
93
|
except Exception as e:
|
|
94
94
|
logger.info(f"Failed to propagate fastapi response: {e}")
|
|
95
|
-
super().post_tracing(to_wrap, wrapped, instance, args, kwargs, return_value)
|
|
95
|
+
super().post_tracing(to_wrap, wrapped, instance, args, kwargs, return_value, token)
|
|
@@ -3,10 +3,10 @@ from monocle_apptrace.instrumentation.metamodel.fastapi.entities.http import FAS
|
|
|
3
3
|
|
|
4
4
|
FASTAPI_METHODS = [
|
|
5
5
|
{
|
|
6
|
-
"package": "fastapi",
|
|
7
|
-
"object": "
|
|
8
|
-
"method": "
|
|
9
|
-
"wrapper_method":
|
|
6
|
+
"package": "fastapi.routing",
|
|
7
|
+
"object": "APIRoute",
|
|
8
|
+
"method": "handle",
|
|
9
|
+
"wrapper_method": atask_wrapper,
|
|
10
10
|
"span_name": "fastapi.request",
|
|
11
11
|
"span_handler": "fastapi_handler",
|
|
12
12
|
"output_processor": FASTAPI_HTTP_PROCESSOR,
|