@@ -324,6 +324,43 @@ def run_once(index: int):
324324 assert len (model_spans ) == 3
325325
326326
327+ @pytest .mark .parametrize ("content_capture_mode" , [None , "NO_CONTENT" ])
328+ def test_content_capture_mode_does_not_gate_span_creation (
329+ monkeypatch ,
330+ span_exporter : InMemorySpanExporter ,
331+ tracer_provider : trace_api .TracerProvider ,
332+ content_capture_mode : str | None ,
333+ ):
334+ AgnoInstrumentor ().uninstrument ()
335+ if hasattr (get_extended_telemetry_handler , "_default_handler" ):
336+ delattr (get_extended_telemetry_handler , "_default_handler" )
337+ span_exporter .clear ()
338+
339+ env_var = "OTEL_INSTRUMENTATION_GENAI_CAPTURE_MESSAGE_CONTENT"
340+ if content_capture_mode is None :
341+ monkeypatch .delenv (env_var , raising = False )
342+ else :
343+ monkeypatch .setenv (env_var , content_capture_mode )
344+
345+ AgnoInstrumentor ().instrument (tracer_provider = tracer_provider )
346+
347+ agent = Agent (name = "NoContentAgent" , model = EchoModel (), tools = [])
348+ response = agent .run ("Say hello without content" )
349+
350+ assert response .content == "hello"
351+ spans = _spans_by_name (span_exporter )
352+ assert "invoke_agent NoContentAgent" in spans
353+ assert "chat echo-model" in spans
354+
355+ agent_attrs = spans ["invoke_agent NoContentAgent" ].attributes
356+ model_attrs = spans ["chat echo-model" ].attributes
357+ assert agent_attrs ["gen_ai.span.kind" ] == "AGENT"
358+ assert model_attrs ["gen_ai.span.kind" ] == "LLM"
359+ assert "gen_ai.input.messages" not in agent_attrs
360+ assert "gen_ai.output.messages" not in agent_attrs
361+ assert "gen_ai.output.messages" not in model_attrs
362+
363+
327364def test_async_function_call_emits_tool_span (
328365 span_exporter : InMemorySpanExporter ,
329366):
@@ -508,6 +545,39 @@ def test_tool_result_messages_do_not_duplicate_text_parts():
508545 assert parts [0 ].response == {"temperature" : 21 }
509546
510547
548+ def test_model_dump_objects_are_serialized_without_pydantic_base_class ():
549+ class ModelDumpToolCall :
550+ def model_dump (self , mode = "json" ):
551+ assert mode == "json"
552+ return {
553+ "id" : "call_1" ,
554+ "function" : {
555+ "name" : "get_weather" ,
556+ "arguments" : '{"city":"Hangzhou"}' ,
557+ },
558+ }
559+
560+ messages = convert_agent_input (
561+ [
562+ SimpleNamespace (
563+ role = "assistant" ,
564+ content = None ,
565+ tool_calls = [ModelDumpToolCall ()],
566+ )
567+ ]
568+ )
569+
570+ parts = messages [0 ].parts
571+ tool_calls = [
572+ part for part in parts if getattr (part , "type" , None ) == "tool_call"
573+ ]
574+
575+ assert len (tool_calls ) == 1
576+ assert tool_calls [0 ].id == "call_1"
577+ assert tool_calls [0 ].name == "get_weather"
578+ assert tool_calls [0 ].arguments == {"city" : "Hangzhou" }
579+
580+
511581def test_missing_finish_reason_is_not_reported ():
512582 agent = Agent (name = "NoFinishReasonAgent" , model = EchoModel (), tools = [])
513583 invocation = create_agent_invocation (agent , {"input" : "hello" })
0 commit comments