From df8fdac10113b3b72fc95ccf91fafaa23e3c9ac8 Mon Sep 17 00:00:00 2001 From: Din Date: Sun, 14 Sep 2025 04:52:34 +0100 Subject: [PATCH 1/6] cohere v2 instrumentor --- pyproject.toml | 3 +- .../instrumentation/cohere/__init__.py | 382 ++++++ .../instrumentation/cohere/config.py | 3 + .../instrumentation/cohere/event_emitter.py | 159 +++ .../instrumentation/cohere/event_models.py | 41 + .../instrumentation/cohere/span_utils.py | 335 ++++++ .../instrumentation/cohere/streaming.py | 222 ++++ .../instrumentation/cohere/utils.py | 77 ++ .../tracing/_instrument_initializers.py | 2 +- .../test_cohere/__init__.py | 1 + .../test_chat/test_cohere_chat_legacy.yaml | 85 ++ .../test_cohere_chat_legacy_async.yaml | 81 ++ ...est_cohere_chat_legacy_with_streaming.yaml | 299 +++++ ...here_chat_legacy_with_streaming_async.yaml | 375 ++++++ ..._cohere_chat_with_events_with_content.yaml | 85 ++ ...e_chat_with_events_with_content_async.yaml | 83 ++ ...here_chat_with_events_with_no_content.yaml | 85 ++ ...hat_with_events_with_no_content_async.yaml | 83 ++ .../test_chat/test_cohere_v2_chat_legacy.yaml | 74 ++ ..._cohere_v2_chat_legacy_with_streaming.yaml | 658 +++++++++++ ...e_v2_chat_legacy_with_streaming_async.yaml | 551 +++++++++ ...at_legacy_with_tool_calls_and_history.yaml | 164 +++ ...acy_with_tool_calls_and_history_async.yaml | 163 +++ ..._legacy_with_tool_calls_and_streaming.yaml | 248 ++++ ...y_with_tool_calls_and_streaming_async.yaml | 283 +++++ .../test_cohere_completion_legacy.yaml | 79 ++ ...e_completion_with_events_with_content.yaml | 79 ++ ...ompletion_with_events_with_no_content.yaml | 79 ++ .../test_cohere_v2_embed_legacy.yaml | 92 ++ .../test_cohere_v2_embed_legacy_async.yaml | 92 ++ .../test_cohere_rerank_legacy.yaml | 82 ++ ...ohere_rerank_with_events_with_content.yaml | 82 ++ ...re_rerank_with_events_with_no_content.yaml | 82 ++ .../test_cohere_v2_rerank_legacy.yaml | 76 ++ .../test_cohere_v2_rerank_legacy_async.yaml | 76 ++ .../test_cohere/conftest.py | 117 ++ .../test_cohere/test_chat.py | 1032 +++++++++++++++++ .../test_cohere/test_completion.py | 111 ++ .../test_cohere/test_embed.py | 120 ++ .../test_cohere/test_rerank.py | 379 ++++++ 40 files changed, 7118 insertions(+), 2 deletions(-) create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/config.py create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_emitter.py create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_models.py create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/span_utils.py create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py create mode 100644 src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/utils.py create mode 100644 tests/test_instrumentations/test_cohere/__init__.py create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_legacy.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_content.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_no_content.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_legacy.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_content.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_no_content.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy.yaml create mode 100644 tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy_async.yaml create mode 100644 tests/test_instrumentations/test_cohere/conftest.py create mode 100644 tests/test_instrumentations/test_cohere/test_chat.py create mode 100644 tests/test_instrumentations/test_cohere/test_completion.py create mode 100644 tests/test_instrumentations/test_cohere/test_embed.py create mode 100644 tests/test_instrumentations/test_cohere/test_rerank.py diff --git a/pyproject.toml b/pyproject.toml index 710bc84c..ae7c8f36 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -136,6 +136,7 @@ dev = [ "groq>=0.30.0", "anthropic[bedrock]>=0.60.0", "langchain-openai>=0.3.32", + "cohere>=5.18.0", ] [build-system] @@ -146,4 +147,4 @@ build-backend = "uv_build" members = ["examples/fastapi-app"] [tool.ruff] -target-version = "py310" \ No newline at end of file +target-version = "py310" diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py new file mode 100644 index 00000000..4795574f --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py @@ -0,0 +1,382 @@ +"""OpenTelemetry Cohere instrumentation""" + +import logging +from typing import Collection, Union + +from opentelemetry import context as context_api +from opentelemetry._events import EventLogger, get_event_logger +from .config import Config +from .event_emitter import ( + emit_input_event, + emit_response_events, +) +from .span_utils import ( + set_input_content_attributes, + set_response_content_attributes, + set_span_request_attributes, + set_span_response_attributes, +) +from .streaming import ( + process_chat_v1_streaming_response, + aprocess_chat_v1_streaming_response, + process_chat_v2_streaming_response, + aprocess_chat_v2_streaming_response, +) +from .utils import dont_throw, should_emit_events +from lmnr.version import __version__ +from opentelemetry.instrumentation.instrumentor import BaseInstrumentor +from opentelemetry.instrumentation.utils import ( + _SUPPRESS_INSTRUMENTATION_KEY, + unwrap, +) +from opentelemetry.semconv_ai import ( + SUPPRESS_LANGUAGE_MODEL_INSTRUMENTATION_KEY, + LLMRequestTypeValues, + SpanAttributes, +) +from opentelemetry.trace import ( + SpanKind, + Status, + StatusCode, + Tracer, + get_tracer, + use_span, +) +from wrapt import wrap_function_wrapper + +logger = logging.getLogger(__name__) + +_instruments = ("cohere >=4.2.7, <6",) + +WRAPPED_METHODS = [ + { + "module": "cohere.client", + "object": "Client", + "method": "generate", + "span_name": "cohere.completion", + }, + { + "module": "cohere.client", + "object": "Client", + "method": "chat", + "span_name": "cohere.chat", + }, + { + "module": "cohere.client", + "object": "Client", + "method": "chat_stream", + "span_name": "cohere.chat", + "stream_process_func": process_chat_v1_streaming_response, + }, + { + "module": "cohere.client", + "object": "Client", + "method": "rerank", + "span_name": "cohere.rerank", + }, + { + "module": "cohere.client", + "object": "Client", + "method": "embed", + "span_name": "cohere.embed", + }, + { + "module": "cohere.client_v2", + "object": "ClientV2", + "method": "chat", + "span_name": "cohere.chat", + }, + { + "module": "cohere.client_v2", + "object": "ClientV2", + "method": "chat_stream", + "span_name": "cohere.chat", + "stream_process_func": process_chat_v2_streaming_response, + }, + { + "module": "cohere.client_v2", + "object": "ClientV2", + "method": "rerank", + "span_name": "cohere.rerank", + }, + { + "module": "cohere.client_v2", + "object": "ClientV2", + "method": "embed", + "span_name": "cohere.embed", + }, + # Async methods that return AsyncIterator must be wrapped with sync wrapper + { + "module": "cohere.client", + "object": "AsyncClient", + "method": "chat_stream", + "span_name": "cohere.chat", + "stream_process_func": aprocess_chat_v1_streaming_response, + }, + { + "module": "cohere.client_v2", + "object": "AsyncClientV2", + "method": "chat_stream", + "span_name": "cohere.chat", + "stream_process_func": aprocess_chat_v2_streaming_response, + }, +] + +WRAPPED_AMETHODS = [ + { + "module": "cohere.client", + "object": "AsyncClient", + "method": "generate", + "span_name": "cohere.completion", + }, + { + "module": "cohere.client", + "object": "AsyncClient", + "method": "chat", + "span_name": "cohere.chat", + }, + { + "module": "cohere.client", + "object": "AsyncClient", + "method": "rerank", + "span_name": "cohere.rerank", + }, + { + "module": "cohere.client", + "object": "AsyncClient", + "method": "embed", + "span_name": "cohere.embed", + }, + { + "module": "cohere.client_v2", + "object": "AsyncClientV2", + "method": "chat", + "span_name": "cohere.chat", + }, + { + "module": "cohere.client_v2", + "object": "AsyncClientV2", + "method": "rerank", + "span_name": "cohere.rerank", + }, + { + "module": "cohere.client_v2", + "object": "AsyncClientV2", + "method": "embed", + "span_name": "cohere.embed", + }, +] + + +def _with_tracer_wrapper(func): + """Helper for providing tracer for wrapper functions.""" + + def _with_tracer(tracer, event_logger, to_wrap): + def wrapper(wrapped, instance, args, kwargs): + return func(tracer, event_logger, to_wrap, wrapped, instance, args, kwargs) + + return wrapper + + return _with_tracer + + +def _llm_request_type_by_method(method_name): + if method_name in ["chat", "chat_stream"]: + return LLMRequestTypeValues.CHAT + elif method_name in ["generate", "generate_stream"]: + return LLMRequestTypeValues.COMPLETION + elif method_name == "rerank": + return LLMRequestTypeValues.RERANK + elif method_name == "embed": + return LLMRequestTypeValues.EMBEDDING + else: + return LLMRequestTypeValues.UNKNOWN + + +@dont_throw +def _handle_input_content(span, event_logger, llm_request_type, kwargs): + set_input_content_attributes(span, llm_request_type, kwargs) + if should_emit_events(): + emit_input_event(event_logger, llm_request_type, kwargs) + + +@dont_throw +def _handle_response_content(span, event_logger, llm_request_type, response): + set_response_content_attributes(span, llm_request_type, response) + if should_emit_events(): + emit_response_events(event_logger, llm_request_type, response) + + +@_with_tracer_wrapper +def _wrap( + tracer: Tracer, + event_logger: Union[EventLogger, None], + to_wrap, + wrapped, + instance, + args, + kwargs, +): + """Instruments and calls every function defined in TO_WRAP.""" + if context_api.get_value(_SUPPRESS_INSTRUMENTATION_KEY) or context_api.get_value( + SUPPRESS_LANGUAGE_MODEL_INSTRUMENTATION_KEY + ): + return wrapped(*args, **kwargs) + + name = to_wrap.get("span_name") + llm_request_type = _llm_request_type_by_method(to_wrap.get("method")) + span = tracer.start_span( + name, + kind=SpanKind.CLIENT, + attributes={ + SpanAttributes.LLM_SYSTEM: "Cohere", + SpanAttributes.LLM_REQUEST_TYPE: llm_request_type.value, + }, + ) + + with use_span(span, end_on_exit=False): + set_span_request_attributes(span, kwargs) + _handle_input_content(span, event_logger, llm_request_type, kwargs) + + try: + response = wrapped(*args, **kwargs) + except Exception as e: + if span.is_recording(): + span.set_status(Status(StatusCode.ERROR, str(e))) + span.record_exception(e) + span.end() + raise + + if to_wrap.get("stream_process_func"): + return to_wrap.get("stream_process_func")( + span, event_logger, llm_request_type, response + ) + + set_span_response_attributes(span, response) + _handle_response_content(span, event_logger, llm_request_type, response) + span.end() + return response + + +@_with_tracer_wrapper +async def _awrap( + tracer: Tracer, + event_logger: Union[EventLogger, None], + to_wrap, + wrapped, + instance, + args, + kwargs, +): + """Instruments and calls every function defined in TO_WRAP.""" + if context_api.get_value(_SUPPRESS_INSTRUMENTATION_KEY) or context_api.get_value( + SUPPRESS_LANGUAGE_MODEL_INSTRUMENTATION_KEY + ): + return await wrapped(*args, **kwargs) + + name = to_wrap.get("span_name") + llm_request_type = _llm_request_type_by_method(to_wrap.get("method")) + with tracer.start_as_current_span( + name, + kind=SpanKind.CLIENT, + attributes={ + SpanAttributes.LLM_SYSTEM: "Cohere", + SpanAttributes.LLM_REQUEST_TYPE: llm_request_type.value, + }, + ) as span: + set_span_request_attributes(span, kwargs) + _handle_input_content(span, event_logger, llm_request_type, kwargs) + + try: + response = await wrapped(*args, **kwargs) + except Exception as e: + if span.is_recording(): + span.set_status(Status(StatusCode.ERROR, str(e))) + span.record_exception(e) + span.end() + raise + + set_span_response_attributes(span, response) + _handle_response_content(span, event_logger, llm_request_type, response) + + return response + + +class CohereInstrumentor(BaseInstrumentor): + """An instrumentor for Cohere's client library.""" + + def __init__(self, exception_logger=None, use_legacy_attributes=True): + super().__init__() + Config.exception_logger = exception_logger + Config.use_legacy_attributes = use_legacy_attributes + + def instrumentation_dependencies(self) -> Collection[str]: + return _instruments + + def _instrument(self, **kwargs): + tracer_provider = kwargs.get("tracer_provider") + tracer = get_tracer(__name__, __version__, tracer_provider) + + event_logger = None + if not Config.use_legacy_attributes: + event_logger_provider = kwargs.get("event_logger_provider") + event_logger = get_event_logger( + __name__, __version__, event_logger_provider=event_logger_provider + ) + for wrapped_method in WRAPPED_METHODS: + wrap_module = wrapped_method.get("module") + wrap_object = wrapped_method.get("object") + wrap_method = wrapped_method.get("method") + try: + wrap_function_wrapper( + wrap_module, + f"{wrap_object}.{wrap_method}", + _wrap(tracer, event_logger, wrapped_method), + ) + except (ImportError, ModuleNotFoundError, AttributeError): + logger.debug( + f"Failed to instrument {wrap_module}.{wrap_object}.{wrap_method}" + ) + + for wrapped_method in WRAPPED_AMETHODS: + wrap_module = wrapped_method.get("module") + wrap_object = wrapped_method.get("object") + wrap_method = wrapped_method.get("method") + try: + wrap_function_wrapper( + wrap_module, + f"{wrap_object}.{wrap_method}", + _awrap(tracer, event_logger, wrapped_method), + ) + except (ImportError, ModuleNotFoundError, AttributeError): + logger.debug( + f"Failed to instrument {wrap_module}.{wrap_object}.{wrap_method}" + ) + + def _uninstrument(self, **kwargs): + for wrapped_method in WRAPPED_METHODS: + wrap_module = wrapped_method.get("module") + wrap_object = wrapped_method.get("object") + wrap_method = wrapped_method.get("method") + try: + unwrap( + f"{wrap_module}.{wrap_object}", + wrap_method, + ) + except (ImportError, ModuleNotFoundError, AttributeError): + logger.debug( + f"Failed to uninstrument {wrap_module}.{wrap_object}.{wrap_method}" + ) + for wrapped_method in WRAPPED_AMETHODS: + wrap_module = wrapped_method.get("module") + wrap_object = wrapped_method.get("object") + wrap_method = wrapped_method.get("method") + try: + unwrap( + f"{wrap_module}.{wrap_object}", + wrap_method, + ) + except (ImportError, ModuleNotFoundError, AttributeError): + logger.debug( + f"Failed to uninstrument {wrap_module}.{wrap_object}.{wrap_method}" + ) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/config.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/config.py new file mode 100644 index 00000000..44199c03 --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/config.py @@ -0,0 +1,3 @@ +class Config: + exception_logger = None + use_legacy_attributes = True diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_emitter.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_emitter.py new file mode 100644 index 00000000..77eaec4b --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_emitter.py @@ -0,0 +1,159 @@ +from dataclasses import asdict +from enum import Enum +from typing import Union + +from opentelemetry._events import Event, EventLogger +from .event_models import ChoiceEvent, MessageEvent +from .utils import ( + should_emit_events, + should_send_prompts, +) +from opentelemetry.semconv._incubating.attributes import ( + gen_ai_attributes as GenAIAttributes, +) +from opentelemetry.semconv_ai import ( + LLMRequestTypeValues, +) + + +class Roles(Enum): + USER = "user" + ASSISTANT = "assistant" + SYSTEM = "system" + TOOL = "tool" + + +VALID_MESSAGE_ROLES = {role.value for role in Roles} +"""The valid roles for naming the message event.""" + +EVENT_ATTRIBUTES = { + GenAIAttributes.GEN_AI_SYSTEM: GenAIAttributes.GenAiSystemValues.COHERE.value +} +"""The attributes to be used for the event.""" + + +def emit_input_event(event_logger, llm_request_type: str, kwargs): + if not should_emit_events() or event_logger is None: + return + event_params = {} + + if llm_request_type == LLMRequestTypeValues.CHAT: + event_params = {"content": kwargs.get("message"), "role": "user"} + elif llm_request_type == LLMRequestTypeValues.RERANK: + event_params = { + "content": { + "query": kwargs.get("query"), + "documents": kwargs.get("documents"), + }, + "role": "user", + } + elif llm_request_type == LLMRequestTypeValues.COMPLETION: + event_params = {"content": kwargs.get("prompt"), "role": "user"} + + emit_event(MessageEvent(**event_params), event_logger) + + +def emit_response_events(event_logger, llm_request_type: str, response): + if not should_emit_events() or event_logger is None: + return + + if llm_request_type == LLMRequestTypeValues.COMPLETION: + for index, generation in enumerate(response.generations): + emit_event( + _parse_response_event(index, llm_request_type, generation), + event_logger, + ) + else: + emit_event(_parse_response_event(0, llm_request_type, response), event_logger) + + +def emit_event( + event: Union[MessageEvent, ChoiceEvent], event_logger: Union[EventLogger, None] +) -> None: + """ + Emit an event to the OpenTelemetry SDK. + + Args: + event: The event to emit. + """ + if not should_emit_events() or event_logger is None: + return + + if isinstance(event, MessageEvent): + _emit_message_event(event, event_logger) + elif isinstance(event, ChoiceEvent): + _emit_choice_event(event, event_logger) + else: + raise TypeError("Unsupported event type") + + +def _emit_message_event(event: MessageEvent, event_logger: EventLogger) -> None: + body = asdict(event) + + if event.role in VALID_MESSAGE_ROLES: + name = "gen_ai.{}.message".format(event.role) + # According to the semantic conventions, the role is conditionally required if available + # and not equal to the "role" in the message name. So, remove the role from the body if + # it is the same as the in the event name. + body.pop("role", None) + else: + name = "gen_ai.user.message" + + # According to the semantic conventions, only the assistant role has tool call + if event.role != Roles.ASSISTANT.value and event.tool_calls is not None: + del body["tool_calls"] + elif event.tool_calls is None: + del body["tool_calls"] + + if not should_send_prompts(): + del body["content"] + if body.get("tool_calls") is not None: + for tool_call in body["tool_calls"]: + tool_call["function"].pop("arguments", None) + + event_logger.emit(Event(name=name, body=body, attributes=EVENT_ATTRIBUTES)) + + +def _emit_choice_event(event: ChoiceEvent, event_logger: EventLogger) -> None: + body = asdict(event) + if event.message["role"] == Roles.ASSISTANT.value: + # According to the semantic conventions, the role is conditionally required if available + # and not equal to "assistant", so remove the role from the body if it is "assistant". + body["message"].pop("role", None) + + if event.tool_calls is None: + del body["tool_calls"] + + if not should_send_prompts(): + body["message"].pop("content", None) + if body.get("tool_calls") is not None: + for tool_call in body["tool_calls"]: + tool_call["function"].pop("arguments", None) + + event_logger.emit( + Event(name="gen_ai.choice", body=body, attributes=EVENT_ATTRIBUTES) + ) + + +def _parse_response_event(index: int, llm_request_type: str, response) -> ChoiceEvent: + event_params = {"index": index, "finish_reason": "unknown"} + + if llm_request_type == LLMRequestTypeValues.RERANK: + event_params["message"] = { + "content": [ + { + "index": result.index, + "document": result.document, + "relevance_score": result.relevance_score, + } + for result in response.results + ], + "role": "assistant", + } + elif ( + llm_request_type == LLMRequestTypeValues.CHAT or LLMRequestTypeValues.COMPLETION + ): + event_params["message"] = {"content": response.text, "role": "assistant"} + event_params["finish_reason"] = response.finish_reason + + return ChoiceEvent(**event_params) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_models.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_models.py new file mode 100644 index 00000000..e3b5f3cc --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/event_models.py @@ -0,0 +1,41 @@ +from dataclasses import dataclass +from typing import Any, List, Literal, Optional, TypedDict + + +class _FunctionToolCall(TypedDict): + function_name: str + arguments: Optional[dict[str, Any]] + + +class ToolCall(TypedDict): + """Represents a tool call in the AI model.""" + + id: str + function: _FunctionToolCall + type: Literal["function"] + + +class CompletionMessage(TypedDict): + """Represents a message in the AI model.""" + + content: Any + role: str = "assistant" + + +@dataclass +class MessageEvent: + """Represents an input event for the AI model.""" + + content: Any + role: str = "user" + tool_calls: Optional[List[ToolCall]] = None + + +@dataclass +class ChoiceEvent: + """Represents a completion event for the AI model.""" + + index: int + message: CompletionMessage + finish_reason: str = "unknown" + tool_calls: Optional[List[ToolCall]] = None diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/span_utils.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/span_utils.py new file mode 100644 index 00000000..3f5bfa9b --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/span_utils.py @@ -0,0 +1,335 @@ +from .utils import ( + dont_throw, + dump_object, + should_send_prompts, + to_dict, + should_emit_events, +) +from opentelemetry.semconv._incubating.attributes.gen_ai_attributes import ( + GEN_AI_COMPLETION, + GEN_AI_RESPONSE_ID, + GEN_AI_PROMPT, + GEN_AI_REQUEST_MODEL, + GEN_AI_REQUEST_MAX_TOKENS, + GEN_AI_REQUEST_TEMPERATURE, + GEN_AI_REQUEST_TOP_P, + GEN_AI_REQUEST_TOP_K, + GEN_AI_REQUEST_STOP_SEQUENCES, + GEN_AI_RESPONSE_FINISH_REASONS, +) +from opentelemetry.semconv_ai import ( + LLMRequestTypeValues, + SpanAttributes, +) +from opentelemetry.trace.status import Status, StatusCode + + +def _set_span_attribute(span, name, value): + if value is not None: + if value != "": + span.set_attribute(name, value) + return + + +@dont_throw +def set_input_content_attributes(span, llm_request_type, kwargs): + if not span.is_recording(): + return + + if should_send_prompts() and not should_emit_events(): + if llm_request_type == LLMRequestTypeValues.COMPLETION: + _set_span_attribute(span, f"{GEN_AI_PROMPT}.0.role", "user") + _set_span_attribute( + span, f"{GEN_AI_PROMPT}.0.content", kwargs.get("prompt") + ) + # client V1 + elif llm_request_type == LLMRequestTypeValues.CHAT and kwargs.get("message"): + user_message_index = 0 + if system_message := kwargs.get("preamble"): + _set_span_attribute(span, f"{GEN_AI_PROMPT}.0.role", "system") + _set_span_attribute(span, f"{GEN_AI_PROMPT}.0.content", system_message) + user_message_index = 1 + _set_span_attribute( + span, f"{GEN_AI_PROMPT}.{user_message_index}.role", "user" + ) + _set_span_attribute( + span, + f"{GEN_AI_PROMPT}.{user_message_index}.content", + kwargs.get("message"), + ) + # client V2 + elif llm_request_type == LLMRequestTypeValues.CHAT and kwargs.get("messages"): + for index, message in enumerate(kwargs.get("messages")): + message_dict = to_dict(message) + _set_span_attribute( + span, f"{GEN_AI_PROMPT}.{index}.role", message_dict.get("role") + ) + _set_span_attribute( + span, + f"{GEN_AI_PROMPT}.{index}.content", + message_dict.get("content"), + ) + + if kwargs.get("tools"): + for index, tool in enumerate(kwargs.get("tools")): + function = tool.get("function") + if not function: + continue + _set_span_attribute( + span, + f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.{index}.name", + function.get("name"), + ) + _set_span_attribute( + span, + f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.{index}.description", + function.get("description"), + ) + _set_span_attribute( + span, + f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.{index}.parameters", + dump_object(function.get("parameters")), + ) + elif llm_request_type == LLMRequestTypeValues.RERANK: + for index, document in enumerate(kwargs.get("documents", [])): + _set_span_attribute(span, f"{GEN_AI_PROMPT}.{index}.role", "system") + _set_span_attribute(span, f"{GEN_AI_PROMPT}.{index}.content", document) + + _set_span_attribute( + span, + f"{GEN_AI_PROMPT}.{len(kwargs.get('documents'))}.role", + "user", + ) + _set_span_attribute( + span, + f"{GEN_AI_PROMPT}.{len(kwargs.get('documents'))}.content", + kwargs.get("query"), + ) + elif llm_request_type == LLMRequestTypeValues.EMBEDDING: + _set_span_attribute( + span, + f"{GEN_AI_PROMPT}.0.role", + "user", + ) + inputs = kwargs.get("inputs") + if not inputs: + texts = kwargs.get("texts") + inputs = [{"type": "text", "text": text} for text in texts] + _set_span_attribute( + span, + f"{GEN_AI_PROMPT}.0.content", + dump_object(inputs), + ) + + +@dont_throw +def set_response_content_attributes(span, llm_request_type, response): + if not span.is_recording(): + return + + if should_send_prompts(): + if llm_request_type == LLMRequestTypeValues.CHAT: + _set_span_chat_response(span, response) + elif llm_request_type == LLMRequestTypeValues.COMPLETION: + _set_span_generations_response(span, response) + elif llm_request_type == LLMRequestTypeValues.RERANK: + _set_span_rerank_response(span, response) + span.set_status(Status(StatusCode.OK)) + + +@dont_throw +def set_span_request_attributes(span, kwargs): + if not span.is_recording(): + return + + _set_span_attribute(span, GEN_AI_REQUEST_MODEL, kwargs.get("model")) + _set_span_attribute( + span, GEN_AI_REQUEST_MAX_TOKENS, kwargs.get("max_tokens_to_sample") + ) + _set_span_attribute(span, GEN_AI_REQUEST_TEMPERATURE, kwargs.get("temperature")) + _set_span_attribute( + span, GEN_AI_REQUEST_TOP_P, kwargs.get("p", kwargs.get("top_p")) + ) + _set_span_attribute( + span, GEN_AI_REQUEST_TOP_K, kwargs.get("k", kwargs.get("top_k")) + ) + + if stop_sequences := kwargs.get("stop_sequences", []): + _set_span_attribute( + span, GEN_AI_REQUEST_STOP_SEQUENCES, dump_object(stop_sequences) + ) + + # TODO: Migrate to GEN_AI_REQUEST_FREQUENCY_PENALTY and GEN_AI_REQUEST_PRESENCE_PENALTY + _set_span_attribute( + span, SpanAttributes.LLM_FREQUENCY_PENALTY, kwargs.get("frequency_penalty") + ) + _set_span_attribute( + span, SpanAttributes.LLM_PRESENCE_PENALTY, kwargs.get("presence_penalty") + ) + + +@dont_throw +def set_span_response_attributes(span, response): + if not span.is_recording(): + return + + response_dict = to_dict(response) + # Cohere API v1 + if response_dict.get("response_id"): + _set_span_attribute(span, GEN_AI_RESPONSE_ID, response_dict.get("response_id")) + # Cohere API v2 + elif response_dict.get("id"): + _set_span_attribute(span, GEN_AI_RESPONSE_ID, response_dict.get("id")) + + # Cohere v4 + if token_count := response_dict.get("token_count"): + token_count_dict = to_dict(token_count) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_TOTAL_TOKENS, + token_count_dict.get("total_tokens"), + ) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS, + token_count_dict.get("response_tokens"), + ) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_PROMPT_TOKENS, + token_count_dict.get("prompt_tokens"), + ) + + # Cohere v5 + if response_dict.get("meta"): + meta_dict = to_dict(response_dict.get("meta", {})) + billed_units = meta_dict.get("billed_units", {}) + billed_units_dict = to_dict(billed_units) + input_tokens = billed_units_dict.get("input_tokens", 0) + output_tokens = billed_units_dict.get("output_tokens", 0) + + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_TOTAL_TOKENS, + input_tokens + output_tokens, + ) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS, + output_tokens, + ) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_PROMPT_TOKENS, + input_tokens, + ) + + # Cohere API v2 + if response_dict.get("usage"): + # usage also has usage.tokens of type UsageTokens. This usually + # has the same number of output tokens, but many more input tokens + # (possibly pre-prompted)") + usage_dict = to_dict(response_dict.get("usage", {})) + billed_units_dict = to_dict(usage_dict.get("billed_units", {})) + input_tokens = billed_units_dict.get("input_tokens", 0) + output_tokens = billed_units_dict.get("output_tokens", 0) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_TOTAL_TOKENS, + input_tokens + output_tokens, + ) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS, + output_tokens, + ) + _set_span_attribute( + span, + SpanAttributes.LLM_USAGE_PROMPT_TOKENS, + input_tokens, + ) + + +def _set_span_chat_response(span, response): + index = 0 + prefix = f"{GEN_AI_COMPLETION}.{index}" + _set_span_attribute(span, f"{prefix}.role", "assistant") + + response_dict = to_dict(response) + + if finish_reason := response_dict.get("finish_reason"): + _set_span_attribute(span, GEN_AI_RESPONSE_FINISH_REASONS, [finish_reason]) + + # Cohere API v1 + if text := response_dict.get("text"): + _set_span_attribute(span, f"{prefix}.content", text) + # Cohere API v2 + elif message := response_dict.get("message"): + message_dict = to_dict(message) + content = message_dict.get("content") or [] + if tool_plan := message_dict.get("tool_plan"): + content.append( + { + "type": "text", + "text": tool_plan, + } + ) + # TODO: Add citations, similarly to tool_plan + _set_span_attribute(span, f"{prefix}.content", dump_object(content)) + if tool_calls := message_dict.get("tool_calls"): + tool_call_index = 0 + for tool_call in tool_calls: + if not tool_call.get("function"): + continue + function = tool_call.get("function") + if tool_call.get("id"): + _set_span_attribute( + span, + f"{prefix}.tool_calls.{tool_call_index}.id", + tool_call.get("id"), + ) + if function.get("name"): + _set_span_attribute( + span, + f"{prefix}.tool_calls.{tool_call_index}.name", + function.get("name"), + ) + if function.get("arguments"): + # no dump_object here, since it's already a string (OpenAI-like) + _set_span_attribute( + span, + f"{prefix}.tool_calls.{tool_call_index}.arguments", + function.get("arguments"), + ) + tool_call_index += 1 + + +def _set_span_generations_response(span, response): + _set_span_attribute(span, GEN_AI_RESPONSE_ID, response.id) + if hasattr(response, "generations"): + generations = response.generations # Cohere v5 + else: + generations = response # Cohere v4 + + for index, generation in enumerate(generations): + prefix = f"{SpanAttributes.LLM_COMPLETIONS}.{index}" + _set_span_attribute(span, f"{prefix}.content", generation.text) + _set_span_attribute(span, f"gen_ai.response.{index}.id", generation.id) + + +def _set_span_rerank_response(span, response): + _set_span_attribute(span, GEN_AI_RESPONSE_ID, response.id) + for idx, doc in enumerate(response.results): + prefix = f"{SpanAttributes.LLM_COMPLETIONS}.{idx}" + _set_span_attribute(span, f"{prefix}.role", "assistant") + content = f"Doc {doc.index}, Score: {doc.relevance_score}" + if hasattr(doc, "document") and doc.document: + if hasattr(doc.document, "text"): + content += f"\n{doc.document.text}" + else: + content += f"\n{doc.document.get('text')}" + _set_span_attribute( + span, + f"{prefix}.content", + content, + ) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py new file mode 100644 index 00000000..4c7426e9 --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py @@ -0,0 +1,222 @@ +from .event_emitter import emit_response_events +from .utils import ( + dont_throw, + should_send_prompts, + to_dict, + should_emit_events, +) +from .span_utils import set_span_response_attributes, _set_span_chat_response +from opentelemetry.semconv_ai import SpanAttributes +from opentelemetry.trace.status import Status, StatusCode + +DEFAULT_MESSAGE = { + "content": [], + "role": "assistant", + "tool_calls": [], + "tool_plan": "", + # TODO: Add citations +} + + +@dont_throw +def process_chat_v1_streaming_response(span, event_logger, llm_request_type, response): + # This naive version assumes we've always successfully streamed till the end + # and have received a StreamEndChatResponse, which includes the full response + final_response = None + try: + for item in response: + span.add_event(name=f"{SpanAttributes.LLM_CONTENT_COMPLETION_CHUNK}") + + item_to_yield = item + if getattr(item, "event_type", None) == "stream-end" and hasattr( + item, "response" + ): + final_response = item.response + + yield item_to_yield + + set_span_response_attributes(span, final_response) + if should_emit_events(): + emit_response_events(event_logger, llm_request_type, final_response) + elif should_send_prompts(): + _set_span_chat_response(span, final_response) + span.set_status(Status(StatusCode.OK)) + finally: + span.end() + + +@dont_throw +async def aprocess_chat_v1_streaming_response( + span, event_logger, llm_request_type, response +): + # This naive version assumes we've always successfully streamed till the end + # and have received a StreamEndChatResponse, which includes the full response + final_response = None + try: + async for item in response: + span.add_event(name=f"{SpanAttributes.LLM_CONTENT_COMPLETION_CHUNK}") + + item_to_yield = item + if getattr(item, "event_type", None) == "stream-end" and hasattr( + item, "response" + ): + final_response = item.response + + yield item_to_yield + set_span_response_attributes(span, final_response) + if should_emit_events(): + emit_response_events(event_logger, llm_request_type, final_response) + elif should_send_prompts(): + _set_span_chat_response(span, final_response) + span.set_status(Status(StatusCode.OK)) + finally: + span.end() + + +@dont_throw +def process_chat_v2_streaming_response(span, event_logger, llm_request_type, response): + final_response = { + "finish_reason": None, + "message": DEFAULT_MESSAGE, + "usage": {}, + "id": "", + "error": None, + } + current_content_item = {"type": "text", "thinking": None, "text": ""} + current_tool_call_item = { + "id": "", + "type": "function", + "function": {"name": "", "arguments": "", "description": ""}, + } + try: + for item in response: + span.add_event(name=f"{SpanAttributes.LLM_CONTENT_COMPLETION_CHUNK}") + item_to_yield = item + try: + _accumulate_stream_item( + item, current_content_item, current_tool_call_item, final_response + ) + except Exception: + pass + yield item_to_yield + + set_span_response_attributes(span, final_response) + if should_emit_events(): + emit_response_events(event_logger, llm_request_type, final_response) + elif should_send_prompts(): + _set_span_chat_response(span, final_response) + + if final_response.get("error"): + span.set_status(Status(StatusCode.ERROR, final_response.get("error"))) + span.record_exception(final_response.get("error")) + else: + span.set_status(Status(StatusCode.OK)) + finally: + span.end() + + +@dont_throw +async def aprocess_chat_v2_streaming_response( + span, event_logger, llm_request_type, response +): + final_response = { + "finish_reason": None, + "message": DEFAULT_MESSAGE, + "usage": {}, + "id": "", + "error": None, + } + current_content_item = {"type": "text", "thinking": None, "text": ""} + current_tool_call_item = { + "id": "", + "type": "function", + "function": {"name": "", "arguments": "", "description": ""}, + } + async for item in response: + span.add_event(name=f"{SpanAttributes.LLM_CONTENT_COMPLETION_CHUNK}") + item_to_yield = item + try: + _accumulate_stream_item( + item, current_content_item, current_tool_call_item, final_response + ) + except Exception: + pass + yield item_to_yield + + set_span_response_attributes(span, final_response) + if should_emit_events(): + emit_response_events(event_logger, llm_request_type, final_response) + elif should_send_prompts(): + _set_span_chat_response(span, final_response) + if final_response.get("error"): + span.set_status(Status(StatusCode.ERROR, final_response.get("error"))) + span.record_exception(final_response.get("error")) + else: + span.set_status(Status(StatusCode.OK)) + span.end() + + +# accumulated items are passed in by reference +def _accumulate_stream_item( + item, current_content_item, current_tool_call_item, final_response +): + item_dict = to_dict(item) + if item_dict.get("type") == "message-start": + final_response["message"] = (item_dict.get("delta") or {}).get( + "message" + ) or DEFAULT_MESSAGE + final_response["id"] = item_dict.get("id") + elif item_dict.get("type") == "content-start": + new_content_item = ((item_dict.get("delta") or {}).get("message") or {}).get( + "content" + ) + current_content_item.clear() + current_content_item.update(new_content_item or {}) + elif item_dict.get("type") == "content-delta": + new_thinking = ( + ((item_dict.get("delta") or {}).get("message") or {}).get("content") or {} + ).get("thinking") + if new_thinking: + existing_thinking = current_content_item.get("thinking") + current_content_item["thinking"] = (existing_thinking or "") + new_thinking + new_text = ( + ((item_dict.get("delta") or {}).get("message") or {}).get("content") or {} + ).get("text") + if new_text: + existing_text = current_content_item.get("text") + current_content_item["text"] = (existing_text or "") + new_text + elif item_dict.get("type") == "content-end": + final_response["message"]["content"].append({**current_content_item}) + elif item_dict.get("type") == "tool-plan-delta": + new_tool_plan = ((item_dict.get("delta") or {}).get("message") or {}).get( + "tool_plan" + ) + if new_tool_plan: + existing_tool_plan = final_response["message"].get("tool_plan") + final_response["message"]["tool_plan"] = ( + existing_tool_plan or "" + ) + new_tool_plan + elif item_dict.get("type") == "tool-call-start": + new_tool_call_item = ((item_dict.get("delta") or {}).get("message") or {}).get( + "tool_calls" + ) + current_tool_call_item.update(new_tool_call_item or {}) + elif item_dict.get("type") == "tool-call-delta": + message = (item_dict.get("delta") or {}).get("message") or {} + new_arguments = ((message.get("tool_calls") or {}).get("function") or {}).get( + "arguments" + ) + if new_arguments: + existing_arguments = (current_tool_call_item.get("function") or {}).get( + "arguments" + ) + current_tool_call_item["function"]["arguments"] = ( + existing_arguments or "" + ) + new_arguments + elif item_dict.get("type") == "tool-call-end": + final_response["message"]["tool_calls"].append({**current_tool_call_item}) + elif item_dict.get("type") == "message-end": + final_response["usage"] = (item_dict.get("delta") or {}).get("usage") or {} + final_response["finish_reason"] = (item_dict.get("delta") or {}).get( + "finish_reason" + ) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/utils.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/utils.py new file mode 100644 index 00000000..b4342b1d --- /dev/null +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/utils.py @@ -0,0 +1,77 @@ +import dataclasses +import json +import logging +import os +import traceback + +from opentelemetry import context as context_api +from .config import Config + +DO_TRACE_CONTENT = "LMNR_TRACE_CONTENT" + + +def dont_throw(func): + """ + A decorator that wraps the passed in function and logs exceptions instead of throwing them. + + @param func: The function to wrap + @return: The wrapper function + """ + # Obtain a logger specific to the function's module + logger = logging.getLogger(func.__module__) + + def wrapper(*args, **kwargs): + try: + return func(*args, **kwargs) + except Exception as e: + logger.debug( + "OpenLLMetry failed to trace in %s, error: %s", + func.__name__, + traceback.format_exc(), + ) + if Config.exception_logger: + Config.exception_logger(e) + + return wrapper + + +def should_send_prompts(): + return ( + os.getenv(DO_TRACE_CONTENT) or "true" + ).lower() == "true" or context_api.get_value("override_enable_content_tracing") + + +def should_emit_events() -> bool: + """ + Checks if the instrumentation isn't using the legacy attributes + and if the event logger is not None. + """ + return not Config.use_legacy_attributes + + +def dump_object(obj): + try: + if hasattr(obj, "model_dump_json") and callable(obj.model_dump_json): + return obj.model_dump_json() + except Exception: + pass + try: + return json.dumps(obj) + except Exception: + return "" + + +def to_dict(obj): + try: + if hasattr(obj, "model_dump") and callable(obj.model_dump): + return obj.model_dump() + except Exception: + pass + if isinstance(obj, dict): + return obj + if dataclasses.is_dataclass(obj): + return dataclasses.asdict(obj) + try: + return dict(obj) + except Exception: + return obj diff --git a/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py b/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py index 352f9a02..f6c78da1 100644 --- a/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py +++ b/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py @@ -125,7 +125,7 @@ def init_instrumentor(self, *args, **kwargs) -> BaseInstrumentor | None: if not is_package_installed("opentelemetry-instrumentation-cohere"): return None - from opentelemetry.instrumentation.cohere import CohereInstrumentor + from ..opentelemetry.instrumentation.cohere import CohereInstrumentor return CohereInstrumentor() diff --git a/tests/test_instrumentations/test_cohere/__init__.py b/tests/test_instrumentations/test_cohere/__init__.py new file mode 100644 index 00000000..d8e96c60 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/__init__.py @@ -0,0 +1 @@ +"""unit tests.""" diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy.yaml new file mode 100644 index 00000000..c57c044e --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy.yaml @@ -0,0 +1,85 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "stream": false, "model": "command"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '80' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"response_id":"440f51f4-3e47-44b6-a5d7-5ba33edcfc58","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye:\n\nWhy did the + pirate want to join the circus? \n\nArrrr, because he wanted to be a trapeze + arrrrrrtist! \n\nYe scurvy dogs and seafaring scalawags better than that ye + hath seen the last! \n\nHonestly, I be tired of these pirate puns, I need + a pirate holiday on a nice quiet beach, with not enough rum to get too crazy + but just enough to forget all me worries.","generation_id":"4f73027b-5f1f-478c-9906-97d0ec74e19a","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye:\n\nWhy did the pirate want + to join the circus? \n\nArrrr, because he wanted to be a trapeze arrrrrrtist! + \n\nYe scurvy dogs and seafaring scalawags better than that ye hath seen the + last! \n\nHonestly, I be tired of these pirate puns, I need a pirate holiday + on a nice quiet beach, with not enough rum to get too crazy but just enough + to forget all me worries."}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"billed_units":{"input_tokens":58,"output_tokens":119},"tokens":{"input_tokens":69,"output_tokens":119}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '1251' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:26 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + num_chars: + - '321' + num_tokens: + - '177' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - ded13e833664521180c334614f2de562 + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '3858' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_async.yaml new file mode 100644 index 00000000..2125d439 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_async.yaml @@ -0,0 +1,81 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "model": "command", "stream": + false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '80' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.6.1 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"response_id":"ea2d074c-4f25-47cb-bef8-b00dc2ae991b","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye: \n\nI spoke + with an astronomer and argh, matey, she told me the Sun would be blowin'' + up! But cheer up, me hearties, it''ll happen in five billion years. We''ve + got plenty of time to find a new treasure trove before then!","generation_id":"41bd7ae5-511d-449f-a64d-dd54e5d697e4","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye: \n\nI spoke with an astronomer + and argh, matey, she told me the Sun would be blowin'' up! But cheer up, me + hearties, it''ll happen in five billion years. We''ve got plenty of time to + find a new treasure trove before then!"}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"warnings":["model + ''command'' is deprecated and will be removed September 15 2025. Please consider + upgrading to a newer model to avoid future service disruptions"],"billed_units":{"input_tokens":7,"output_tokens":80},"tokens":{"input_tokens":69,"output_tokens":81}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '1127' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 01:23:07 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '324' + num_tokens: + - '87' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 37d8ceb858f86160192181d6ece63b36 + x-envoy-upstream-service-time: + - '2401' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming.yaml new file mode 100644 index 00000000..7355ab09 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming.yaml @@ -0,0 +1,299 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "model": "command", "stream": + true}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '79' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.6.1 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"is_finished":false,"event_type":"stream-start","generation_id":"a7cd9d01-255f-44a2-a186-834f942bf61e"} + + {"is_finished":false,"event_type":"text-generation","text":"Ar"} + + {"is_finished":false,"event_type":"text-generation","text":"rr"} + + {"is_finished":false,"event_type":"text-generation","text":"r"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" mate"} + + {"is_finished":false,"event_type":"text-generation","text":"y"} + + {"is_finished":false,"event_type":"text-generation","text":"!"} + + {"is_finished":false,"event_type":"text-generation","text":" Sh"} + + {"is_finished":false,"event_type":"text-generation","text":"iver"} + + {"is_finished":false,"event_type":"text-generation","text":" me"} + + {"is_finished":false,"event_type":"text-generation","text":" tim"} + + {"is_finished":false,"event_type":"text-generation","text":"bers"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" here"} + + {"is_finished":false,"event_type":"text-generation","text":"''s"} + + {"is_finished":false,"event_type":"text-generation","text":" a"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":"-"} + + {"is_finished":false,"event_type":"text-generation","text":"themed"} + + {"is_finished":false,"event_type":"text-generation","text":" joke"} + + {"is_finished":false,"event_type":"text-generation","text":" for"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":":"} + + {"is_finished":false,"event_type":"text-generation","text":"\n\nWhy"} + + {"is_finished":false,"event_type":"text-generation","text":" did"} + + {"is_finished":false,"event_type":"text-generation","text":" the"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":" go"} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" the"} + + {"is_finished":false,"event_type":"text-generation","text":" dentist"} + + {"is_finished":false,"event_type":"text-generation","text":"?"} + + {"is_finished":false,"event_type":"text-generation","text":"\n\nA"} + + {"is_finished":false,"event_type":"text-generation","text":":"} + + {"is_finished":false,"event_type":"text-generation","text":" Because"} + + {"is_finished":false,"event_type":"text-generation","text":" he"} + + {"is_finished":false,"event_type":"text-generation","text":" wanted"} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" find"} + + {"is_finished":false,"event_type":"text-generation","text":" some"} + + {"is_finished":false,"event_type":"text-generation","text":" treasure"} + + {"is_finished":false,"event_type":"text-generation","text":"!"} + + {"is_finished":false,"event_type":"text-generation","text":" AR"} + + {"is_finished":false,"event_type":"text-generation","text":"RR"} + + {"is_finished":false,"event_type":"text-generation","text":"RR"} + + {"is_finished":false,"event_type":"text-generation","text":"!!!"} + + {"is_finished":false,"event_type":"text-generation","text":" \n\nP"} + + {"is_finished":false,"event_type":"text-generation","text":"irates"} + + {"is_finished":false,"event_type":"text-generation","text":" love"} + + {"is_finished":false,"event_type":"text-generation","text":" loot"} + + {"is_finished":false,"event_type":"text-generation","text":"in"} + + {"is_finished":false,"event_type":"text-generation","text":"''"} + + {"is_finished":false,"event_type":"text-generation","text":" gold"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" sometimes"} + + {"is_finished":false,"event_type":"text-generation","text":" forget"} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" take"} + + {"is_finished":false,"event_type":"text-generation","text":" care"} + + {"is_finished":false,"event_type":"text-generation","text":" of"} + + {"is_finished":false,"event_type":"text-generation","text":" their"} + + {"is_finished":false,"event_type":"text-generation","text":" teeth"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" so"} + + {"is_finished":false,"event_type":"text-generation","text":" I"} + + {"is_finished":false,"event_type":"text-generation","text":" hope"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":" appreciate"} + + {"is_finished":false,"event_type":"text-generation","text":" me"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":"-"} + + {"is_finished":false,"event_type":"text-generation","text":"themed"} + + {"is_finished":false,"event_type":"text-generation","text":" joke"} + + {"is_finished":false,"event_type":"text-generation","text":" there"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":" sc"} + + {"is_finished":false,"event_type":"text-generation","text":"ur"} + + {"is_finished":false,"event_type":"text-generation","text":"vy"} + + {"is_finished":false,"event_type":"text-generation","text":" dog"} + + {"is_finished":false,"event_type":"text-generation","text":"!"} + + {"is_finished":false,"event_type":"text-generation","text":" \n\nIf"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":" want"} + + {"is_finished":false,"event_type":"text-generation","text":" more"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":" humor"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" let"} + + {"is_finished":false,"event_type":"text-generation","text":" me"} + + {"is_finished":false,"event_type":"text-generation","text":" know"} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" I"} + + {"is_finished":false,"event_type":"text-generation","text":"''ll"} + + {"is_finished":false,"event_type":"text-generation","text":" be"} + + {"is_finished":false,"event_type":"text-generation","text":" happy"} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" sail"} + + {"is_finished":false,"event_type":"text-generation","text":" through"} + + {"is_finished":false,"event_type":"text-generation","text":" some"} + + {"is_finished":false,"event_type":"text-generation","text":" more"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":"-"} + + {"is_finished":false,"event_type":"text-generation","text":"y"} + + {"is_finished":false,"event_type":"text-generation","text":" comedy"} + + {"is_finished":false,"event_type":"text-generation","text":"!"} + + {"is_finished":true,"event_type":"stream-end","response":{"response_id":"12c00d26-e3bb-48c0-8c49-262155b57d64","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-themed joke for ye:\n\nWhy did + the pirate go to the dentist?\n\nA: Because he wanted to find some treasure! + ARRRRR!!! \n\nPirates love lootin'' gold, and sometimes forget to take care + of their teeth, so I hope ye appreciate me pirate-themed joke there, ye scurvy + dog! \n\nIf ye want more pirate humor, let me know and I''ll be happy to sail + through some more pirate-y comedy!","generation_id":"a7cd9d01-255f-44a2-a186-834f942bf61e","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-themed joke for ye:\n\nWhy did the pirate go + to the dentist?\n\nA: Because he wanted to find some treasure! ARRRRR!!! \n\nPirates + love lootin'' gold, and sometimes forget to take care of their teeth, so I + hope ye appreciate me pirate-themed joke there, ye scurvy dog! \n\nIf ye want + more pirate humor, let me know and I''ll be happy to sail through some more + pirate-y comedy!"}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"warnings":["model + ''command'' is deprecated and will be removed September 15 2025. Please consider + upgrading to a newer model to avoid future service disruptions"],"billed_units":{"input_tokens":7,"output_tokens":115},"tokens":{"input_tokens":69,"output_tokens":116}}},"finish_reason":"COMPLETE"} + + ' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/stream+json + date: + - Sun, 14 Sep 2025 01:29:39 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 2a0bada75306984d0beeabdf7afde1ac + x-envoy-upstream-service-time: + - '79' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming_async.yaml new file mode 100644 index 00000000..dc708e98 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_legacy_with_streaming_async.yaml @@ -0,0 +1,375 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "model": "command", "stream": + true}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '79' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.6.1 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"is_finished":false,"event_type":"stream-start","generation_id":"613783cf-5a8b-4d4e-b34e-d6c2223a3387"} + + {"is_finished":false,"event_type":"text-generation","text":"Ar"} + + {"is_finished":false,"event_type":"text-generation","text":"rr"} + + {"is_finished":false,"event_type":"text-generation","text":"r"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" mate"} + + {"is_finished":false,"event_type":"text-generation","text":"y"} + + {"is_finished":false,"event_type":"text-generation","text":"!"} + + {"is_finished":false,"event_type":"text-generation","text":" Sh"} + + {"is_finished":false,"event_type":"text-generation","text":"iver"} + + {"is_finished":false,"event_type":"text-generation","text":" me"} + + {"is_finished":false,"event_type":"text-generation","text":" tim"} + + {"is_finished":false,"event_type":"text-generation","text":"bers"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" here"} + + {"is_finished":false,"event_type":"text-generation","text":"''s"} + + {"is_finished":false,"event_type":"text-generation","text":" a"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":"-"} + + {"is_finished":false,"event_type":"text-generation","text":"style"} + + {"is_finished":false,"event_type":"text-generation","text":" joke"} + + {"is_finished":false,"event_type":"text-generation","text":" for"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":":"} + + {"is_finished":false,"event_type":"text-generation","text":" \n\nI"} + + {"is_finished":false,"event_type":"text-generation","text":" asked"} + + {"is_finished":false,"event_type":"text-generation","text":" the"} + + {"is_finished":false,"event_type":"text-generation","text":" captain"} + + {"is_finished":false,"event_type":"text-generation","text":" if"} + + {"is_finished":false,"event_type":"text-generation","text":" we"} + + {"is_finished":false,"event_type":"text-generation","text":" could"} + + {"is_finished":false,"event_type":"text-generation","text":" go"} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" get"} + + {"is_finished":false,"event_type":"text-generation","text":" ourselves"} + + {"is_finished":false,"event_type":"text-generation","text":" a"} + + {"is_finished":false,"event_type":"text-generation","text":" snack"} + + {"is_finished":false,"event_type":"text-generation","text":"."} + + {"is_finished":false,"event_type":"text-generation","text":" He"} + + {"is_finished":false,"event_type":"text-generation","text":" looked"} + + {"is_finished":false,"event_type":"text-generation","text":" at"} + + {"is_finished":false,"event_type":"text-generation","text":" me"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" all"} + + {"is_finished":false,"event_type":"text-generation","text":" seas"} + + {"is_finished":false,"event_type":"text-generation","text":"ick"} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" green"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" yelled"} + + {"is_finished":false,"event_type":"text-generation","text":":"} + + {"is_finished":false,"event_type":"text-generation","text":" \""} + + {"is_finished":false,"event_type":"text-generation","text":"A"} + + {"is_finished":false,"event_type":"text-generation","text":"ye"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" mate"} + + {"is_finished":false,"event_type":"text-generation","text":"y"} + + {"is_finished":false,"event_type":"text-generation","text":"!\""} + + {"is_finished":false,"event_type":"text-generation","text":" \n\nThis"} + + {"is_finished":false,"event_type":"text-generation","text":" classic"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":" pun"} + + {"is_finished":false,"event_type":"text-generation","text":" combines"} + + {"is_finished":false,"event_type":"text-generation","text":" elements"} + + {"is_finished":false,"event_type":"text-generation","text":" of"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":" vocabulary"} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" humor"} + + {"is_finished":false,"event_type":"text-generation","text":":"} + + {"is_finished":false,"event_type":"text-generation","text":" using"} + + {"is_finished":false,"event_type":"text-generation","text":" the"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":"-"} + + {"is_finished":false,"event_type":"text-generation","text":"esque"} + + {"is_finished":false,"event_type":"text-generation","text":" expression"} + + {"is_finished":false,"event_type":"text-generation","text":" \""} + + {"is_finished":false,"event_type":"text-generation","text":"A"} + + {"is_finished":false,"event_type":"text-generation","text":"ye"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" mate"} + + {"is_finished":false,"event_type":"text-generation","text":"y"} + + {"is_finished":false,"event_type":"text-generation","text":"\""} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" express"} + + {"is_finished":false,"event_type":"text-generation","text":" agreement"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" while"} + + {"is_finished":false,"event_type":"text-generation","text":" also"} + + {"is_finished":false,"event_type":"text-generation","text":" playing"} + + {"is_finished":false,"event_type":"text-generation","text":" on"} + + {"is_finished":false,"event_type":"text-generation","text":" the"} + + {"is_finished":false,"event_type":"text-generation","text":" phrase"} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" highlight"} + + {"is_finished":false,"event_type":"text-generation","text":" the"} + + {"is_finished":false,"event_type":"text-generation","text":" captain"} + + {"is_finished":false,"event_type":"text-generation","text":"''s"} + + {"is_finished":false,"event_type":"text-generation","text":" discomfort"} + + {"is_finished":false,"event_type":"text-generation","text":"ing"} + + {"is_finished":false,"event_type":"text-generation","text":" sea"} + + {"is_finished":false,"event_type":"text-generation","text":" sickness"} + + {"is_finished":false,"event_type":"text-generation","text":"."} + + {"is_finished":false,"event_type":"text-generation","text":" \n\nI"} + + {"is_finished":false,"event_type":"text-generation","text":" hope"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":" find"} + + {"is_finished":false,"event_type":"text-generation","text":" this"} + + {"is_finished":false,"event_type":"text-generation","text":" joke"} + + {"is_finished":false,"event_type":"text-generation","text":" to"} + + {"is_finished":false,"event_type":"text-generation","text":" be"} + + {"is_finished":false,"event_type":"text-generation","text":" a"} + + {"is_finished":false,"event_type":"text-generation","text":" fun"} + + {"is_finished":false,"event_type":"text-generation","text":" little"} + + {"is_finished":false,"event_type":"text-generation","text":" treasure"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" if"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":" be"} + + {"is_finished":false,"event_type":"text-generation","text":" want"} + + {"is_finished":false,"event_type":"text-generation","text":"in"} + + {"is_finished":false,"event_type":"text-generation","text":"''"} + + {"is_finished":false,"event_type":"text-generation","text":" more"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" let"} + + {"is_finished":false,"event_type":"text-generation","text":" me"} + + {"is_finished":false,"event_type":"text-generation","text":" know"} + + {"is_finished":false,"event_type":"text-generation","text":","} + + {"is_finished":false,"event_type":"text-generation","text":" and"} + + {"is_finished":false,"event_type":"text-generation","text":" I"} + + {"is_finished":false,"event_type":"text-generation","text":" shall"} + + {"is_finished":false,"event_type":"text-generation","text":" provide"} + + {"is_finished":false,"event_type":"text-generation","text":" ye"} + + {"is_finished":false,"event_type":"text-generation","text":" with"} + + {"is_finished":false,"event_type":"text-generation","text":" a"} + + {"is_finished":false,"event_type":"text-generation","text":" bounty"} + + {"is_finished":false,"event_type":"text-generation","text":" of"} + + {"is_finished":false,"event_type":"text-generation","text":" pirate"} + + {"is_finished":false,"event_type":"text-generation","text":"-"} + + {"is_finished":false,"event_type":"text-generation","text":"themed"} + + {"is_finished":false,"event_type":"text-generation","text":" humor"} + + {"is_finished":false,"event_type":"text-generation","text":"!"} + + {"is_finished":true,"event_type":"stream-end","response":{"response_id":"dcdb9a85-a8dc-4f4c-9779-f7c1801248f3","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye: \n\nI asked + the captain if we could go and get ourselves a snack. He looked at me, all + seasick and green, and yelled: \"Aye, matey!\" \n\nThis classic pirate pun + combines elements of pirate vocabulary and humor: using the pirate-esque expression + \"Aye, matey\" to express agreement, while also playing on the phrase to highlight + the captain''s discomforting sea sickness. \n\nI hope ye find this joke to + be a fun little treasure, and if ye be wantin'' more, let me know, and I shall + provide ye with a bounty of pirate-themed humor!","generation_id":"613783cf-5a8b-4d4e-b34e-d6c2223a3387","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye: \n\nI asked the captain if + we could go and get ourselves a snack. He looked at me, all seasick and green, + and yelled: \"Aye, matey!\" \n\nThis classic pirate pun combines elements + of pirate vocabulary and humor: using the pirate-esque expression \"Aye, matey\" + to express agreement, while also playing on the phrase to highlight the captain''s + discomforting sea sickness. \n\nI hope ye find this joke to be a fun little + treasure, and if ye be wantin'' more, let me know, and I shall provide ye + with a bounty of pirate-themed humor!"}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"warnings":["model + ''command'' is deprecated and will be removed September 15 2025. Please consider + upgrading to a newer model to avoid future service disruptions"],"billed_units":{"input_tokens":7,"output_tokens":149},"tokens":{"input_tokens":69,"output_tokens":150}}},"finish_reason":"COMPLETE"} + + ' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/stream+json + date: + - Sun, 14 Sep 2025 01:46:21 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 421516367f70f3860d54828ee98b1718 + x-envoy-upstream-service-time: + - '79' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content.yaml new file mode 100644 index 00000000..c57c044e --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content.yaml @@ -0,0 +1,85 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "stream": false, "model": "command"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '80' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"response_id":"440f51f4-3e47-44b6-a5d7-5ba33edcfc58","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye:\n\nWhy did the + pirate want to join the circus? \n\nArrrr, because he wanted to be a trapeze + arrrrrrtist! \n\nYe scurvy dogs and seafaring scalawags better than that ye + hath seen the last! \n\nHonestly, I be tired of these pirate puns, I need + a pirate holiday on a nice quiet beach, with not enough rum to get too crazy + but just enough to forget all me worries.","generation_id":"4f73027b-5f1f-478c-9906-97d0ec74e19a","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye:\n\nWhy did the pirate want + to join the circus? \n\nArrrr, because he wanted to be a trapeze arrrrrrtist! + \n\nYe scurvy dogs and seafaring scalawags better than that ye hath seen the + last! \n\nHonestly, I be tired of these pirate puns, I need a pirate holiday + on a nice quiet beach, with not enough rum to get too crazy but just enough + to forget all me worries."}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"billed_units":{"input_tokens":58,"output_tokens":119},"tokens":{"input_tokens":69,"output_tokens":119}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '1251' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:26 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + num_chars: + - '321' + num_tokens: + - '177' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - ded13e833664521180c334614f2de562 + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '3858' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content_async.yaml new file mode 100644 index 00000000..be1d5078 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_content_async.yaml @@ -0,0 +1,83 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "model": "command", "stream": + false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '80' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.6.1 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"response_id":"e17775dc-ffad-456f-a239-48d8329428bf","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye: \n\nI asked + the captain if we could go and get ourselves a snack. He looked at me, scowlin'' + and said, \"You snooze, you lose!\" Aargh, it would seem I am the pirate who + snores after all me rum! \n\nPirates chuckled and laughed, they did, and ye + will too! \n\nArrrr!","generation_id":"73b9bc6c-7620-4cf5-9c76-4a1518da3e6e","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye: \n\nI asked the captain if + we could go and get ourselves a snack. He looked at me, scowlin'' and said, + \"You snooze, you lose!\" Aargh, it would seem I am the pirate who snores + after all me rum! \n\nPirates chuckled and laughed, they did, and ye will + too! \n\nArrrr!"}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"warnings":["model + ''command'' is deprecated and will be removed September 15 2025. Please consider + upgrading to a newer model to avoid future service disruptions"],"billed_units":{"input_tokens":7,"output_tokens":100},"tokens":{"input_tokens":69,"output_tokens":101}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '1223' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 01:23:12 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '324' + num_tokens: + - '107' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 48d68a3c9e1310932498b50f0824b055 + x-envoy-upstream-service-time: + - '5508' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content.yaml new file mode 100644 index 00000000..c57c044e --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content.yaml @@ -0,0 +1,85 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "stream": false, "model": "command"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '80' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"response_id":"440f51f4-3e47-44b6-a5d7-5ba33edcfc58","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye:\n\nWhy did the + pirate want to join the circus? \n\nArrrr, because he wanted to be a trapeze + arrrrrrtist! \n\nYe scurvy dogs and seafaring scalawags better than that ye + hath seen the last! \n\nHonestly, I be tired of these pirate puns, I need + a pirate holiday on a nice quiet beach, with not enough rum to get too crazy + but just enough to forget all me worries.","generation_id":"4f73027b-5f1f-478c-9906-97d0ec74e19a","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye:\n\nWhy did the pirate want + to join the circus? \n\nArrrr, because he wanted to be a trapeze arrrrrrtist! + \n\nYe scurvy dogs and seafaring scalawags better than that ye hath seen the + last! \n\nHonestly, I be tired of these pirate puns, I need a pirate holiday + on a nice quiet beach, with not enough rum to get too crazy but just enough + to forget all me worries."}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"billed_units":{"input_tokens":58,"output_tokens":119},"tokens":{"input_tokens":69,"output_tokens":119}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '1251' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:26 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + num_chars: + - '321' + num_tokens: + - '177' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - ded13e833664521180c334614f2de562 + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '3858' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content_async.yaml new file mode 100644 index 00000000..02b9a9f6 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_chat_with_events_with_no_content_async.yaml @@ -0,0 +1,83 @@ +interactions: +- request: + body: '{"message": "Tell me a joke, pirate style", "model": "command", "stream": + false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '80' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.6.1 + method: POST + uri: https://api.cohere.com/v1/chat + response: + body: + string: '{"response_id":"c0b03212-d862-46a1-aa94-2fa6f491fd17","text":"Arrrr, + matey! Shiver me timbers, here''s a pirate-style joke for ye: \n\nI asked + the pirate captain how he lost his leg. He said, \"I was just a kid, matey!\" + \n\nArrrr, matey! Now ye squiggly little skeleton and walk the plank laughing + like a pirate! \n\nIf ye want more pirate jokes, I can make ye walk the plank + and whip ye with me cannonball launcher!","generation_id":"a3203475-c8f3-488d-8682-f6da563cd1d7","chat_history":[{"role":"USER","message":"Tell + me a joke, pirate style"},{"role":"CHATBOT","message":"Arrrr, matey! Shiver + me timbers, here''s a pirate-style joke for ye: \n\nI asked the pirate captain + how he lost his leg. He said, \"I was just a kid, matey!\" \n\nArrrr, matey! + Now ye squiggly little skeleton and walk the plank laughing like a pirate! + \n\nIf ye want more pirate jokes, I can make ye walk the plank and whip ye + with me cannonball launcher!"}],"finish_reason":"COMPLETE","meta":{"api_version":{"version":"1"},"warnings":["model + ''command'' is deprecated and will be removed September 15 2025. Please consider + upgrading to a newer model to avoid future service disruptions"],"billed_units":{"input_tokens":7,"output_tokens":99},"tokens":{"input_tokens":69,"output_tokens":100}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '1264' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 01:23:16 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '324' + num_tokens: + - '106' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - c3f40eb96fedb33840b13a84344b7f6e + x-envoy-upstream-service-time: + - '2980' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy.yaml new file mode 100644 index 00000000..bf2fa694 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy.yaml @@ -0,0 +1,74 @@ +interactions: +- request: + body: '{"model": "command", "messages": [{"role": "user", "content": "Tell me + a joke, pirate style"}], "stream": false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '112' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: "{\"id\":\"83e3e297-264b-478e-9b22-5058386292ed\",\"message\":{\"role\":\"assistant\",\"content\":[{\"type\":\"text\",\"text\":\"Arrrr, + matey! Shiver me timbers, here\u2019s a pirate-themed joke for ye: \\n\\nI + stumbled upon a shipwreck on the ocean floor,\\nBut instead of gold or silver, + all I found was dough.\\nI couldn\u2019t believe me peepers, so I rubbed me + eyes,\\nBut it was just a pizza restaurant, and I couldn\u2019t help but cry.\"}]},\"finish_reason\":\"COMPLETE\",\"usage\":{\"billed_units\":{\"input_tokens\":7,\"output_tokens\":88},\"tokens\":{\"input_tokens\":69,\"output_tokens\":89}}}" + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '552' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 01:50:19 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '324' + num_tokens: + - '95' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 3ea490a581ea0c90e48fbdccabff104b + x-envoy-upstream-service-time: + - '2637' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming.yaml new file mode 100644 index 00000000..77de902e --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming.yaml @@ -0,0 +1,658 @@ +interactions: +- request: + body: '{"model": "command", "messages": [{"role": "user", "content": "Tell me + a joke, pirate style"}], "stream": true}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '111' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: 'event: message-start + + data: {"id":"6cd6ce61-bb3b-46f6-907e-fcfab45e51b6","type":"message-start","delta":{"message":{"role":"assistant","content":[],"tool_plan":"","tool_calls":[],"citations":[]}}} + + + event: content-start + + data: {"type":"content-start","index":0,"delta":{"message":{"content":{"type":"text","text":""}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"Ar"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"r"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + mate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"y"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + Sh"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"iver"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + me"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + tim"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"bers"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + here"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"''s"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + a"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"-"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"style"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + joke"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + for"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":":"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"\n\nWhy"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + did"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + the"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + want"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + to"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + go"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + to"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + the"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + dentist"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"?"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + \n\nA"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":":"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + Because"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + he"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + was"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + looking"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + for"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + a"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + treasure"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + chest"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + \n\nAr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"r"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + mate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"y"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + I"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + hope"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + laughed"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + arr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"r"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rs"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + off"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + \n\nIf"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + want"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + more"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + jokes"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + I"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"''ll"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + be"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + happy"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + to"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + make"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + walk"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + the"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + plank"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + with"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + more"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + hilarious"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + tales"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"."}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + \n\n Let"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + me"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + know"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + if"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + want"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + me"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + to"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + sail"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + through"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + more"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"-"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"themed"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + humor"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-end + + data: {"type":"content-end","index":0} + + + event: message-end + + data: {"type":"message-end","delta":{"finish_reason":"COMPLETE","usage":{"billed_units":{"input_tokens":7,"output_tokens":109},"tokens":{"input_tokens":69,"output_tokens":110}}}} + + + data: [DONE] + + + ' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - text/event-stream + date: + - Sun, 14 Sep 2025 01:59:14 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 936e9f001e13e2cbf9988a12da8ca483 + x-envoy-upstream-service-time: + - '70' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming_async.yaml new file mode 100644 index 00000000..2f98a1c6 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_streaming_async.yaml @@ -0,0 +1,551 @@ +interactions: +- request: + body: '{"model": "command", "messages": [{"role": "user", "content": "Tell me + a joke, pirate style"}], "stream": true}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '111' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: 'event: message-start + + data: {"id":"599ae0aa-0ef6-49e4-b7f4-e2fafc40ca2c","type":"message-start","delta":{"message":{"role":"assistant","content":[],"tool_plan":"","tool_calls":[],"citations":[]}}} + + + event: content-start + + data: {"type":"content-start","index":0,"delta":{"message":{"content":{"type":"text","text":""}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"Ar"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"r"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + mate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"y"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + Sh"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"iver"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + me"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + tim"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"bers"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + here"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"''s"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + a"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"-"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"style"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + joke"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + for"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":":"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"\n\nWhy"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + did"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + the"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + want"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + to"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + join"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + the"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + circus"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"?"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + \n\nAr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"r"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + because"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + he"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + wanted"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + to"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + be"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + a"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + tra"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"pe"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"ze"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + arr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rr"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"r"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"rc"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"at"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + \n\nHo"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ho"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ho"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + sc"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"ur"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"vy"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + dog"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":","}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + like"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + it"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"?"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + These"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + pirate"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + jokes"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + sh"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"an"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"''t"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + be"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + sc"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"upp"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"ering"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + ye"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + any"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + time"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + soon"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"."}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":" + Avast"}}}} + + + event: content-delta + + data: {"type":"content-delta","index":0,"delta":{"message":{"content":{"text":"!"}}}} + + + event: content-end + + data: {"type":"content-end","index":0} + + + event: message-end + + data: {"type":"message-end","delta":{"finish_reason":"COMPLETE","usage":{"billed_units":{"input_tokens":7,"output_tokens":89},"tokens":{"input_tokens":69,"output_tokens":89}}}} + + + data: [DONE] + + + ' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - text/event-stream + date: + - Sun, 14 Sep 2025 02:19:39 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - bc877ec6699cd83aa9c7d1952c3fbb20 + x-envoy-upstream-service-time: + - '81' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history.yaml new file mode 100644 index 00000000..3658fc44 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history.yaml @@ -0,0 +1,164 @@ +interactions: +- request: + body: '{"model": "command-r", "messages": [{"role": "user", "content": "What is + the weather and current time in Tokyo?"}], "tools": [{"type": "function", "function": + {"name": "get_weather", "description": "Get the current weather in a given location", + "parameters": {"type": "object", "properties": {"location": {"type": "string", + "description": "The city and state, e.g. San Francisco, CA"}}, "required": ["location"]}}}, + {"type": "function", "function": {"name": "get_time", "description": "Get the + current time in a given location", "parameters": {"type": "object", "properties": + {"location": {"type": "string", "description": "The city and state, e.g. San + Francisco, CA"}}, "required": ["location"]}}}], "stream": false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '717' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: '{"id":"965405bb-b9da-4dc5-b329-e708a795e188","message":{"role":"assistant","tool_plan":"I + will search for the current time and weather in Tokyo.","tool_calls":[{"id":"get_time_dp3men9jrvhf","type":"function","function":{"name":"get_time","arguments":"{\"location\":\"Tokyo\"}"}},{"id":"get_weather_d7arjgsc96yf","type":"function","function":{"name":"get_weather","arguments":"{\"location\":\"Tokyo\"}"}}]},"finish_reason":"TOOL_CALL","usage":{"billed_units":{"input_tokens":62,"output_tokens":28},"tokens":{"input_tokens":968,"output_tokens":83}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '547' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 02:36:03 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '4591' + num_tokens: + - '90' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command-r' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 42d840ed9dd60e834b9f33cc4a811aa8 + x-envoy-upstream-service-time: + - '1761' + status: + code: 200 + message: OK +- request: + body: '{"model": "command-r", "messages": [{"role": "user", "content": "What is + the weather and current time in Tokyo?"}, {"role": "assistant", "content": null, + "tool_calls": [{"id": "get_time_dp3men9jrvhf", "type": "function", "function": + {"name": "get_time", "arguments": "{\"location\":\"Tokyo\"}"}}, {"id": "get_weather_d7arjgsc96yf", + "type": "function", "function": {"name": "get_weather", "arguments": "{\"location\":\"Tokyo\"}"}}]}, + {"role": "tool", "tool_call_id": "get_time_dp3men9jrvhf", "content": "4:20 PM"}, + {"role": "tool", "tool_call_id": "get_weather_d7arjgsc96yf", "content": "Sunny + 20 degrees Celsius"}], "tools": [{"type": "function", "function": {"name": "get_weather", + "description": "Get the current weather in a given location", "parameters": + {"type": "object", "properties": {"location": {"type": "string", "description": + "The city and state, e.g. San Francisco, CA"}}, "required": ["location"]}}}, + {"type": "function", "function": {"name": "get_time", "description": "Get the + current time in a given location", "parameters": {"type": "object", "properties": + {"location": {"type": "string", "description": "The city and state, e.g. San + Francisco, CA"}}, "required": ["location"]}}}], "stream": false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1217' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: "{\"id\":\"00f7ec58-cd22-4b62-b068-0e7ece6bbf67\",\"message\":{\"role\":\"assistant\",\"content\":[{\"type\":\"text\",\"text\":\"The + current time in Tokyo is 4:20 PM and the weather is sunny with a temperature + of 20\xB0C.\"}],\"citations\":[{\"start\":29,\"end\":36,\"text\":\"4:20 PM\",\"sources\":[{\"type\":\"tool\",\"id\":\"get_time_dp3men9jrvhf:0\",\"tool_output\":{\"content\":\"4:20 + PM\"}}],\"type\":\"TEXT_CONTENT\"},{\"start\":56,\"end\":89,\"text\":\"sunny + with a temperature of 20\xB0C.\",\"sources\":[{\"type\":\"tool\",\"id\":\"get_weather_d7arjgsc96yf:0\",\"tool_output\":{\"content\":\"Sunny + 20 degrees Celsius\"}}],\"type\":\"TEXT_CONTENT\"}]},\"finish_reason\":\"COMPLETE\",\"usage\":{\"billed_units\":{\"input_tokens\":94,\"output_tokens\":27},\"tokens\":{\"input_tokens\":1094,\"output_tokens\":102}}}" + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '719' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 02:36:05 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '5100' + num_tokens: + - '121' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command-r' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - f6bf3b4e64a9e3a3355b5c7050aa95fd + x-envoy-upstream-service-time: + - '1282' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history_async.yaml new file mode 100644 index 00000000..4ddc1cda --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_history_async.yaml @@ -0,0 +1,163 @@ +interactions: +- request: + body: '{"model": "command-r7b-12-2024", "messages": [{"role": "user", "content": + "What is the weather and current time in Tokyo?"}], "tools": [{"type": "function", + "function": {"name": "get_weather", "description": "Get the current weather + in a given location", "parameters": {"type": "object", "properties": {"location": + {"type": "string", "description": "The city and state, e.g. San Francisco, CA"}}, + "required": ["location"]}}}, {"type": "function", "function": {"name": "get_time", + "description": "Get the current time in a given location", "parameters": {"type": + "object", "properties": {"location": {"type": "string", "description": "The + city and state, e.g. San Francisco, CA"}}, "required": ["location"]}}}], "stream": + false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '727' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: '{"id":"b7391518-e53e-4486-98ea-fabffcde31c2","message":{"role":"assistant","tool_plan":"I + will use the get_weather and get_time tools to find the weather and current + time in Tokyo.","tool_calls":[{"id":"get_weather_mznfyh090g90","type":"function","function":{"name":"get_weather","arguments":"{\"location\":\"Tokyo\"}"}},{"id":"get_time_eksdqe8f9g4y","type":"function","function":{"name":"get_time","arguments":"{\"location\":\"Tokyo\"}"}}]},"finish_reason":"TOOL_CALL","usage":{"billed_units":{"input_tokens":62,"output_tokens":38},"tokens":{"input_tokens":1531,"output_tokens":89}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '584' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 03:04:15 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '7120' + num_tokens: + - '100' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 4b063f6ebf94617b855602c20dfb9f77 + x-envoy-upstream-service-time: + - '582' + status: + code: 200 + message: OK +- request: + body: '{"model": "command-r7b-12-2024", "messages": [{"role": "user", "content": + "What is the weather and current time in Tokyo?"}, {"role": "assistant", "content": + null, "tool_calls": [{"id": "get_weather_mznfyh090g90", "type": "function", + "function": {"name": "get_weather", "arguments": "{\"location\":\"Tokyo\"}"}}, + {"id": "get_time_eksdqe8f9g4y", "type": "function", "function": {"name": "get_time", + "arguments": "{\"location\":\"Tokyo\"}"}}]}, {"role": "tool", "tool_call_id": + "get_weather_mznfyh090g90", "content": "4:20 PM"}, {"role": "tool", "tool_call_id": + "get_time_eksdqe8f9g4y", "content": "Sunny 20 degrees Celsius"}], "tools": [{"type": + "function", "function": {"name": "get_weather", "description": "Get the current + weather in a given location", "parameters": {"type": "object", "properties": + {"location": {"type": "string", "description": "The city and state, e.g. San + Francisco, CA"}}, "required": ["location"]}}}, {"type": "function", "function": + {"name": "get_time", "description": "Get the current time in a given location", + "parameters": {"type": "object", "properties": {"location": {"type": "string", + "description": "The city and state, e.g. San Francisco, CA"}}, "required": ["location"]}}}], + "stream": false}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1227' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: '{"id":"8289d4ee-a83b-4ce2-b7e1-245d9778fcf5","message":{"role":"assistant","content":[{"type":"text","text":"The + weather in Tokyo is currently sunny and 20 degrees Celsius. The current time + is 4:20 PM."}],"citations":[{"start":34,"end":39,"text":"sunny","sources":[{"type":"tool","id":"get_time_eksdqe8f9g4y:0","tool_output":{"content":"Sunny + 20 degrees Celsius"}}],"type":"TEXT_CONTENT"},{"start":44,"end":63,"text":"20 + degrees Celsius.","sources":[{"type":"tool","id":"get_time_eksdqe8f9g4y:0","tool_output":{"content":"Sunny + 20 degrees Celsius"}}],"type":"TEXT_CONTENT"},{"start":84,"end":92,"text":"4:20 + PM.","sources":[{"type":"tool","id":"get_weather_mznfyh090g90:0","tool_output":{"content":"4:20 + PM"}}],"type":"TEXT_CONTENT"}]},"finish_reason":"COMPLETE","usage":{"billed_units":{"input_tokens":78,"output_tokens":25},"tokens":{"input_tokens":1694,"output_tokens":57}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '877' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 03:04:15 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '7791' + num_tokens: + - '103' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 55736c33493297302f3e7a5baf0b265c + x-envoy-upstream-service-time: + - '393' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming.yaml new file mode 100644 index 00000000..049e9c3d --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming.yaml @@ -0,0 +1,248 @@ +interactions: +- request: + body: '{"model": "command-r", "messages": [{"role": "user", "content": "What is + the weather and current time in Tokyo?"}], "tools": [{"type": "function", "function": + {"name": "get_weather", "description": "Get the current weather in a given location", + "parameters": {"type": "object", "properties": {"location": {"type": "string", + "description": "The city and state, e.g. San Francisco, CA"}}, "required": ["location"]}}}, + {"type": "function", "function": {"name": "get_time", "description": "Get the + current time in a given location", "parameters": {"type": "object", "properties": + {"location": {"type": "string", "description": "The city and state, e.g. San + Francisco, CA"}}, "required": ["location"]}}}], "stream": true}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '716' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: 'event: message-start + + data: {"id":"e6d757a9-f0f3-40fe-9b8a-44cdc3bd18a7","type":"message-start","delta":{"message":{"role":"assistant","content":[],"tool_plan":"","tool_calls":[],"citations":[]}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":"I"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" will"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" search"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" for"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" the"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" current"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" time"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" and"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" weather"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" in"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" Tokyo"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":"."}}} + + + event: tool-call-start + + data: {"type":"tool-call-start","index":0,"delta":{"message":{"tool_calls":{"id":"get_time_dg5wwc00d8v5","type":"function","function":{"name":"get_time","arguments":""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"{\n \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"location"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"\":"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":" + \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"Tokyo"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"\""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"\n"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"}"}}}}} + + + event: tool-call-end + + data: {"type":"tool-call-end","index":0} + + + event: tool-call-start + + data: {"type":"tool-call-start","index":1,"delta":{"message":{"tool_calls":{"id":"get_weather_bc8241gkqss5","type":"function","function":{"name":"get_weather","arguments":""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"{\n \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"location"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"\":"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":" + \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"Tokyo"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"\""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"\n"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"}"}}}}} + + + event: tool-call-end + + data: {"type":"tool-call-end","index":1} + + + event: message-end + + data: {"type":"message-end","delta":{"finish_reason":"TOOL_CALL","usage":{"billed_units":{"input_tokens":62,"output_tokens":28},"tokens":{"input_tokens":968,"output_tokens":83}}}} + + + data: [DONE] + + + ' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - text/event-stream + date: + - Sun, 14 Sep 2025 02:50:46 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command-r' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 356637ec837563f4f9042748f80d7d28 + x-envoy-upstream-service-time: + - '270' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming_async.yaml new file mode 100644 index 00000000..d689d213 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_chat/test_cohere_v2_chat_legacy_with_tool_calls_and_streaming_async.yaml @@ -0,0 +1,283 @@ +interactions: +- request: + body: '{"model": "command-r", "messages": [{"role": "user", "content": "What is + the weather and current time in Tokyo?"}], "tools": [{"type": "function", "function": + {"name": "get_weather", "description": "Get the current weather in a given location", + "parameters": {"type": "object", "properties": {"location": {"type": "string", + "description": "The city and state, e.g. San Francisco, CA"}}, "required": ["location"]}}}, + {"type": "function", "function": {"name": "get_time", "description": "Get the + current time in a given location", "parameters": {"type": "object", "properties": + {"location": {"type": "string", "description": "The city and state, e.g. San + Francisco, CA"}}, "required": ["location"]}}}], "stream": true}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '716' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/chat + response: + body: + string: 'event: message-start + + data: {"id":"ce257b09-c6da-4aed-b722-6384504180f5","type":"message-start","delta":{"message":{"role":"assistant","content":[],"tool_plan":"","tool_calls":[],"citations":[]}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":"I"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" will"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" search"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" for"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" the"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" current"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" time"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" and"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" weather"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" in"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" Tokyo"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" and"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" relay"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" this"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" information"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" to"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" the"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":" user"}}} + + + event: tool-plan-delta + + data: {"type":"tool-plan-delta","delta":{"message":{"tool_plan":"."}}} + + + event: tool-call-start + + data: {"type":"tool-call-start","index":0,"delta":{"message":{"tool_calls":{"id":"get_time_mp1131yrhbga","type":"function","function":{"name":"get_time","arguments":""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"{\n \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"location"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"\":"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":" + \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"Tokyo"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"\""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"\n"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":0,"delta":{"message":{"tool_calls":{"function":{"arguments":"}"}}}}} + + + event: tool-call-end + + data: {"type":"tool-call-end","index":0} + + + event: tool-call-start + + data: {"type":"tool-call-start","index":1,"delta":{"message":{"tool_calls":{"id":"get_weather_yxz1xx2m07cn","type":"function","function":{"name":"get_weather","arguments":""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"{\n \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"location"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"\":"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":" + \""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"Tokyo"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"\""}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"\n"}}}}} + + + event: tool-call-delta + + data: {"type":"tool-call-delta","index":1,"delta":{"message":{"tool_calls":{"function":{"arguments":"}"}}}}} + + + event: tool-call-end + + data: {"type":"tool-call-end","index":1} + + + event: message-end + + data: {"type":"message-end","delta":{"finish_reason":"TOOL_CALL","usage":{"billed_units":{"input_tokens":62,"output_tokens":35},"tokens":{"input_tokens":968,"output_tokens":90}}}} + + + data: [DONE] + + + ' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - text/event-stream + date: + - Sun, 14 Sep 2025 03:00:27 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-api-warning: + - model 'command-r' is deprecated and will be removed September 15 2025. Please + consider upgrading to a newer model to avoid future service disruptions + x-debug-trace-id: + - 471c84acae7cecba8477f34ef53ed722 + x-envoy-upstream-service-time: + - '134' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_legacy.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_legacy.yaml new file mode 100644 index 00000000..bf439aee --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_legacy.yaml @@ -0,0 +1,79 @@ +interactions: +- request: + body: '{"prompt": "Tell me a joke, pirate style", "stream": false, "model": "command"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '79' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/generate + response: + body: + string: '{"id":"64c671fc-c536-41fc-adbd-5f7c81177371","generations":[{"id":"13255d0a-eef8-47fc-91f7-d2607d228fbf","text":" + Arrrr, matey! Shiver me timbers, here''s a pirate-themed joke for ye:\n\nWhy + did the pirate go to the dentist?\n\nA: To get a buccaneer bicuspid! \n\nArrrr, + matey! Now ye scurvy dog better fetch me some loot, or I''ll be making ye + walk the plank!'' \n\nRated ARRRR for pirate jokes. \n\nYe scurvy pirate humor + may be silly, but it be mighty appreciated by ye pirate-loving mates! \n\nSniffle, + snort, ''argh''!","finish_reason":"COMPLETE"}],"prompt":"Tell me a joke, pirate + style","meta":{"api_version":{"version":"1"},"billed_units":{"input_tokens":7,"output_tokens":129}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-length: + - '682' + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:31 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + num_chars: + - '421' + num_tokens: + - '136' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 75c5f7ef8cfc3eb1a1704b53a7acf45c + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '3953' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_content.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_content.yaml new file mode 100644 index 00000000..bf439aee --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_content.yaml @@ -0,0 +1,79 @@ +interactions: +- request: + body: '{"prompt": "Tell me a joke, pirate style", "stream": false, "model": "command"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '79' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/generate + response: + body: + string: '{"id":"64c671fc-c536-41fc-adbd-5f7c81177371","generations":[{"id":"13255d0a-eef8-47fc-91f7-d2607d228fbf","text":" + Arrrr, matey! Shiver me timbers, here''s a pirate-themed joke for ye:\n\nWhy + did the pirate go to the dentist?\n\nA: To get a buccaneer bicuspid! \n\nArrrr, + matey! Now ye scurvy dog better fetch me some loot, or I''ll be making ye + walk the plank!'' \n\nRated ARRRR for pirate jokes. \n\nYe scurvy pirate humor + may be silly, but it be mighty appreciated by ye pirate-loving mates! \n\nSniffle, + snort, ''argh''!","finish_reason":"COMPLETE"}],"prompt":"Tell me a joke, pirate + style","meta":{"api_version":{"version":"1"},"billed_units":{"input_tokens":7,"output_tokens":129}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-length: + - '682' + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:31 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + num_chars: + - '421' + num_tokens: + - '136' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 75c5f7ef8cfc3eb1a1704b53a7acf45c + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '3953' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_no_content.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_no_content.yaml new file mode 100644 index 00000000..bf439aee --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_completion/test_cohere_completion_with_events_with_no_content.yaml @@ -0,0 +1,79 @@ +interactions: +- request: + body: '{"prompt": "Tell me a joke, pirate style", "stream": false, "model": "command"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '79' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/generate + response: + body: + string: '{"id":"64c671fc-c536-41fc-adbd-5f7c81177371","generations":[{"id":"13255d0a-eef8-47fc-91f7-d2607d228fbf","text":" + Arrrr, matey! Shiver me timbers, here''s a pirate-themed joke for ye:\n\nWhy + did the pirate go to the dentist?\n\nA: To get a buccaneer bicuspid! \n\nArrrr, + matey! Now ye scurvy dog better fetch me some loot, or I''ll be making ye + walk the plank!'' \n\nRated ARRRR for pirate jokes. \n\nYe scurvy pirate humor + may be silly, but it be mighty appreciated by ye pirate-loving mates! \n\nSniffle, + snort, ''argh''!","finish_reason":"COMPLETE"}],"prompt":"Tell me a joke, pirate + style","meta":{"api_version":{"version":"1"},"billed_units":{"input_tokens":7,"output_tokens":129}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-length: + - '682' + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:31 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + num_chars: + - '421' + num_tokens: + - '136' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 75c5f7ef8cfc3eb1a1704b53a7acf45c + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '3953' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy.yaml new file mode 100644 index 00000000..22d5ddeb --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy.yaml @@ -0,0 +1,92 @@ +interactions: +- request: + body: '{"texts": ["Carson City is the capital city of the American state of Nevada. + At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands in the + Pacific Ocean that are a political division controlled by the United States. + Its capital is Saipan.", "Charlotte Amalie is the capital and largest city of + the United States Virgin Islands. It has about 20,000 people. The city is on + the island of Saint Thomas.", "Washington, D.C. (also known as simply Washington + or D.C., and officially as the District of Columbia) is the capital of the United + States. It is a federal district. ", "Capital punishment (the death penalty) + has existed in the United States since before the United States was a country. + As of 2017, capital punishment is legal in 30 of the 50 states.", "North Dakota + is a state in the United States. 672,591 people lived in North Dakota in the + year 2010. The capital and seat of government is Bismarck."], "model": "embed-english-light-v3.0", + "input_type": "search_document"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1072' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/embed + response: + body: + string: '{"id":"74d7aae4-2939-4002-b4d4-352dfcca03cf","texts":["carson city + is the capital city of the american state of nevada. at the 2010 united states + census, carson city had a population of 55, 274.","the commonwealth of the + northern mariana islands is a group of islands in the pacific ocean that are + a political division controlled by the united states. its capital is saipan.","charlotte + amalie is the capital and largest city of the united states virgin islands. + it has about 20, 000 people. the city is on the island of saint thomas.","washington, + d. c. ( also known as simply washington or d. c., and officially as the district + of columbia ) is the capital of the united states. it is a federal district.","capital + punishment ( the death penalty ) has existed in the united states since before + the united states was a country. as of 2017, capital punishment is legal in + 30 of the 50 states.","north dakota is a state in the united states. 672, + 591 people lived in north dakota in the year 2010. the capital and seat of + government is bismarck."],"embeddings":{"float":[[0.032318115,-0.031188965,-0.06604004,0.028823853,-0.017730713,-0.07757568,0.02305603,0.008758545,-0.004558563,0.0725708,-0.112976074,-0.05142212,0.08526611,-0.11383057,-0.052337646,-0.010803223,0.02848816,-0.08453369,0.06365967,-0.0647583,-0.066467285,0.10449219,0.037841797,-0.01134491,-0.020523071,-0.15917969,-0.07720947,-0.015106201,-0.032836914,0.092041016,-0.018463135,-0.034179688,0.06137085,0.05404663,0.090270996,-0.061828613,0.058654785,-0.013000488,-0.046081543,0.0552063,0.022109985,0.12646484,0.0031318665,-0.083984375,-0.050231934,0.049804688,-0.059020996,-0.005924225,0.018157959,0.0066566467,0.07446289,0.015808105,0.014984131,0.050750732,-0.046936035,0.05807495,0.014465332,-0.038238525,-0.03869629,-0.017227173,-0.07739258,-0.015258789,-0.03845215,-0.056762695,0.006286621,0.061553955,0.035858154,-0.11004639,-0.011672974,-0.03036499,0.06286621,-0.1060791,-0.059020996,0.006324768,0.01586914,0.0066566467,-0.054748535,0.077819824,0.057861328,0.0647583,0.0703125,-0.039733887,-0.002840042,-0.05999756,-0.01676941,0.0871582,0.010658264,-0.0004172325,0.035980225,-0.033081055,0.03692627,0.007045746,-0.009506226,-0.06738281,-0.04168701,0.029342651,0.029571533,0.021896362,0.0037384033,-0.03656006,0.010749817,0.022064209,-0.028366089,-0.032226562,-0.076660156,-0.017486572,-0.013084412,0.09246826,-0.057495117,0.020462036,-0.054656982,0.040130615,0.0236969,-0.016052246,-0.0001552105,-0.019485474,0.0647583,-0.03112793,-0.055541992,-0.0025463104,0.008453369,-0.078308105,0.0211792,0.022064209,0.07940674,-0.016464233,-0.00052022934,-0.03543091,-0.00015723705,-0.0035209656,0.02571106,0.052093506,-0.016708374,0.00015437603,-0.02027893,-0.012313843,0.009552002,-0.08026123,-0.002363205,0.007045746,0.099731445,0.10467529,-0.009651184,-0.0029239655,-0.025146484,0.024047852,0.049987793,0.001156807,-0.03353882,0.06359863,0.04699707,0.068603516,-0.0064888,-0.03265381,-0.11920166,-0.024337769,0.076660156,-0.02432251,0.018936157,0.06915283,0.081726074,0.04827881,0.05166626,0.058532715,-0.024627686,0.12609863,-0.056396484,-0.0836792,-0.041503906,0.099853516,0.04751587,-0.053100586,-0.10449219,0.004146576,0.07098389,-0.019332886,-0.011924744,0.015197754,0.0034313202,0.10321045,-0.031341553,0.06750488,-0.015274048,0.01651001,-0.043792725,-0.05328369,-0.012451172,0.0074691772,0.015182495,-0.1126709,-0.0066566467,-0.044708252,0.0078125,-0.048095703,-0.042144775,0.04611206,0.02571106,0.039764404,0.13635254,-0.056488037,0.049194336,-0.000101327896,0.0090789795,0.011520386,0.05960083,0.0058059692,0.05392456,0.07324219,-0.031280518,0.021255493,0.028701782,0.015602112,0.08117676,-0.0814209,0.031677246,0.011810303,0.04449463,-0.0023326874,-0.055725098,0.020965576,0.02708435,-0.017166138,-0.02859497,0.050933838,-0.14575195,0.0072898865,0.011299133,-0.087524414,0.04525757,-0.05581665,0.08959961,0.017547607,-0.03250122,-0.013885498,0.016662598,0.058441162,0.0418396,-0.04449463,-0.04171753,0.0067481995,0.059692383,0.07330322,-0.05407715,0.052642822,-0.09564209,-0.06951904,-0.09051514,-0.06842041,0.041992188,-0.023101807,-0.12731934,-0.068603516,0.008605957,-0.024154663,-0.05618286,-0.0007596016,0.048858643,0.080322266,0.034332275,0.029922485,0.021591187,-0.060546875,0.0067863464,-0.032836914,0.0052452087,-0.0057868958,-0.066589355,0.03062439,-0.025802612,0.053100586,-0.04852295,-0.027313232,-0.082336426,0.059265137,0.010284424,0.006843567,-0.03491211,-0.007019043,0.03225708,0.043884277,0.0059394836,0.0015859604,0.055908203,-0.011398315,-0.027038574,-0.023956299,-0.023971558,0.030197144,-0.064697266,-0.035980225,-0.06097412,-0.08117676,-0.0066375732,0.02935791,0.014526367,-0.032836914,-0.023468018,0.02998352,-0.045776367,0.023529053,0.054870605,0.11138916,0.0970459,0.024261475,0.024993896,-0.042785645,0.05102539,0.042419434,-0.015396118,0.034576416,-0.013397217,-0.025054932,0.12060547,0.06756592,0.005558014,0.022003174,-0.037384033,-0.081970215,0.020751953,-0.00844574,0.096191406,-0.025253296,-0.029266357,0.06347656,0.026382446,0.041625977,0.033996582,0.0042800903,-0.06161499,0.05419922,-0.028427124,-0.0025024414,0.0035476685,0.01637268,-0.072509766,-0.039154053,0.0146102905,0.080444336,0.043914795,-0.055480957,-0.010917664,-0.08526611,-0.09661865,-0.011268616,-0.018676758,0.05532837,0.05255127,-0.005821228,-0.036895752,-0.026931763,0.05645752,-0.0440979,0.048095703,-0.07019043,0.053466797,-0.0007586479,-0.04925537,0.02911377,0.010520935,-0.04714966,0.021331787,-0.017669678,-0.02519226,-0.011955261,-0.0067100525,-0.072021484,-0.06890869,-0.021774292,-0.026809692,0.0053100586,0.030426025,0.07354736,0.059417725,0.03579712,0.0031528473,0.0541687,-0.049926758,-0.015083313,0.03427124,0.023666382,0.0014266968,0.048431396,-0.02142334,-0.046936035],[0.034454346,-0.03652954,0.121520996,-0.08618164,0.015960693,-0.0647583,0.07354736,0.061431885,0.020614624,0.0012788773,0.01612854,-0.06121826,-0.031555176,-0.012077332,0.011062622,0.028533936,-0.041137695,-0.0619812,-0.005203247,0.009513855,0.059814453,0.10748291,-0.10455322,-0.0046157837,0.07940674,-0.037994385,0.027359009,-0.013954163,0.03793335,-0.0154418945,-0.0038108826,-0.04257202,0.001666069,-0.023635864,0.04272461,0.0022354126,0.01902771,-0.033691406,0.04284668,-0.09857178,-0.047088623,0.046966553,0.04144287,0.056274414,0.0030555725,0.024154663,-0.089782715,-0.0038490295,-0.064941406,0.065979004,0.07495117,-0.07989502,-0.044799805,0.037628174,0.014404297,0.050598145,-0.0028591156,0.039276123,0.07159424,-0.005203247,0.03491211,0.04373169,-0.036956787,0.0014915466,0.016952515,0.032470703,0.047821045,0.048461914,-0.0126571655,-0.120666504,-0.053863525,0.0046463013,0.001964569,-0.0049324036,-0.008514404,0.013000488,0.02154541,-0.0019817352,0.0018005371,0.0032482147,0.06921387,0.0725708,0.010566711,-0.038726807,0.06774902,-0.029159546,-0.022445679,0.048980713,0.035858154,0.017593384,-0.023590088,0.029800415,0.11895752,-0.044555664,-0.030014038,0.10961914,-0.06185913,0.025619507,0.078552246,0.00066518784,0.018478394,0.09680176,0.029006958,-0.10253906,-0.09057617,0.10040283,0.02909851,0.019546509,0.09918213,0.038360596,-0.03149414,0.020339966,0.008979797,-0.05429077,0.015419006,-0.10192871,0.036010742,-0.032226562,-0.057800293,0.011566162,0.047302246,-0.10986328,0.032104492,-0.05227661,0.072509766,-0.025558472,-0.060333252,-0.0859375,0.058044434,-0.07659912,0.017227173,0.03225708,0.029953003,0.0049057007,0.066833496,-0.03881836,-0.093322754,-0.121398926,-0.049560547,0.04348755,0.081848145,0.017074585,0.06604004,0.012817383,0.076293945,0.017150879,0.05645752,-0.019622803,-0.011665344,0.059692383,-0.036132812,0.030273438,-0.026519775,-0.01612854,-0.0715332,-0.06964111,-0.00009262562,-0.04336548,-0.0076560974,-0.025924683,0.03741455,-0.017227173,-0.07318115,0.031280518,0.03692627,0.04373169,-0.00016987324,0.039978027,-0.06707764,0.056884766,0.01789856,0.020141602,0.040100098,0.00365448,-0.031982422,-0.06933594,0.014656067,0.08898926,-0.035949707,-0.0044441223,-0.070739746,-0.02696228,0.03866577,-0.055114746,-0.06756592,0.047912598,-0.04788208,0.009780884,0.05569458,-0.019882202,0.0050239563,0.00630188,-0.024841309,0.0670166,-0.06097412,-0.08166504,0.03845215,0.050842285,0.06524658,0.056243896,0.03942871,0.07824707,-0.039794922,0.028961182,0.01651001,0.022445679,-0.018295288,0.01234436,-0.012367249,-0.010047913,-0.05227661,-0.003730774,0.0065078735,-0.075805664,0.045715332,0.0054779053,-0.013648987,-0.012496948,-0.05001831,0.032409668,0.06311035,-0.06149292,0.01586914,0.042510986,-0.078063965,-0.090270996,-0.05392456,-0.080200195,-0.030578613,0.02947998,0.060333252,0.031921387,-0.051239014,-0.018066406,-0.075927734,-0.044281006,0.08831787,-0.020645142,-0.04043579,0.011634827,0.13012695,0.049804688,0.000052154064,0.02406311,-0.008621216,-0.052001953,0.016433716,-0.05758667,-0.010757446,-0.09307861,-0.038269043,-0.06121826,-0.0007548332,-0.026184082,-0.03793335,0.008018494,0.049468994,-0.074035645,-0.075683594,-0.11462402,-0.0032215118,-0.10650635,0.018737793,-0.010734558,0.052825928,-0.0647583,-0.011070251,0.11224365,-0.064331055,0.019821167,0.012611389,-0.013900757,-0.0869751,-0.024307251,-0.0055770874,-0.04748535,0.048431396,-0.009002686,0.06866455,0.01777649,-0.07507324,0.0012559891,0.053955078,0.01499176,-0.048217773,-0.076293945,-0.015792847,-0.0036640167,0.043518066,0.032806396,0.016662598,-0.0042800903,0.066589355,-0.03555298,0.08325195,-0.019073486,-0.0049057007,0.037994385,0.015975952,0.04800415,0.04434204,0.021896362,0.049346924,-0.029891968,0.041992188,-0.027038574,-0.03314209,-0.011871338,-0.0473938,0.039978027,0.013793945,-0.032684326,-0.10632324,-0.015365601,0.08276367,-0.13671875,0.017105103,-0.02003479,0.011482239,-0.021026611,0.026184082,-0.05117798,0.03289795,0.0026416779,0.005493164,0.0087509155,-0.06365967,-0.05126953,0.14074707,0.078552246,0.044189453,0.054351807,0.021331787,-0.04321289,0.05429077,0.012863159,-0.04675293,0.0647583,0.03717041,-0.015625,-0.007347107,-0.014808655,-0.019546509,0.08428955,-0.0018234253,0.0039978027,0.05596924,-0.05166626,0.0657959,0.010360718,-0.021240234,-0.013412476,-0.068481445,-0.0071907043,-0.035247803,0.1352539,0.00015163422,0.005306244,-0.004173279,-0.07537842,0.001042366,0.0970459,0.017227173,0.010757446,-0.0871582,-0.016784668,0.022140503,0.08355713,0.0060768127,0.020050049,-0.047088623,-0.04949951,-0.029464722,-0.060180664,-0.0748291,0.015022278,-0.113586426,0.02998352,-0.031280518,0.08190918,0.021072388,0.019744873,-0.046020508,-0.025680542],[-0.015945435,-0.07232666,0.059020996,-0.00674057,-0.022827148,-0.076049805,-0.0012760162,0.0026111603,-0.06463623,0.018249512,0.015525818,-0.0031166077,-0.05810547,-0.08911133,-0.047058105,0.06060791,0.010871887,-0.04232788,0.04763794,-0.027435303,0.036865234,-0.0010910034,-0.011474609,-0.082336426,0.03857422,-0.105895996,-0.04067993,-0.0033340454,-0.004055023,0.011619568,0.025878906,-0.09338379,0.03466797,0.101257324,-0.00484848,-0.030944824,0.08190918,0.030944824,0.09967041,-0.010047913,0.031158447,0.1307373,-0.030303955,0.054534912,-0.025772095,0.0362854,-0.093688965,0.0463562,-0.008277893,0.032196045,0.10046387,-0.047851562,-0.043914795,0.035064697,-0.0016546249,-0.079956055,-0.04046631,-0.059692383,-0.01184082,-0.052947998,0.05810547,-0.04827881,-0.013977051,0.0031147003,-0.007843018,0.008590698,0.021560669,0.045898438,0.010368347,-0.04776001,0.04031372,-0.047851562,-0.014808655,0.039276123,0.029846191,-0.015129089,-0.1194458,0.04776001,0.058624268,0.06890869,0.062408447,-0.024398804,0.027053833,-0.014198303,-0.015533447,0.004470825,-0.012992859,0.15161133,0.02558899,0.036010742,-0.04058838,-0.0042495728,-0.04788208,-0.053741455,-0.034454346,0.03302002,0.00013899803,0.02468872,-0.009315491,-0.01411438,0.009315491,0.09118652,0.043823242,0.008178711,-0.0063934326,0.1005249,0.055419922,-0.023025513,0.1673584,-0.025909424,-0.10070801,0.028579712,-0.02394104,-0.019042969,-0.037139893,-0.04446411,0.11053467,-0.046875,-0.125,-0.050964355,-0.044769287,-0.037628174,0.025314331,-0.01828003,-0.027877808,-0.024932861,0.02482605,-0.0149002075,-0.04626465,-0.028518677,0.0023345947,0.14550781,0.012290955,-0.005760193,-0.02168274,-0.0063972473,-0.0050964355,-0.17602539,-0.0635376,-0.011413574,0.06384277,0.057617188,0.06524658,-0.031707764,0.072509766,0.0049819946,-0.034301758,0.010658264,-0.0045547485,-0.012321472,-0.030151367,-0.003025055,-0.057403564,-0.0049858093,-0.0050239563,0.0096206665,0.07055664,-0.05923462,0.091308594,0.06109619,0.09655762,0.045288086,0.0072631836,0.024597168,0.012573242,-0.0038795471,-0.09234619,-0.005214691,-0.099365234,-0.051757812,0.016113281,-0.025222778,-0.01058197,0.02909851,0.004776001,-0.012046814,0.0592041,0.09832764,0.007411957,0.028213501,-0.07458496,0.06915283,-0.0044441223,0.08026123,0.031036377,-0.0017576218,0.008041382,-0.0037059784,-0.029693604,-0.11248779,0.057403564,-0.039398193,-0.021865845,0.013717651,-0.032714844,-0.00072050095,-0.015960693,0.070007324,0.041137695,-0.027008057,0.045410156,0.018798828,-0.011192322,0.058013916,0.0395813,-0.057037354,0.008903503,0.049926758,-0.05505371,-0.0058555603,-0.030090332,0.02835083,0.085754395,-0.09814453,-0.034210205,0.029205322,0.006828308,-0.035980225,0.030914307,-0.017730713,0.0637207,0.061309814,-0.06933594,-0.011940002,-0.085632324,-0.042907715,0.01927185,-0.069885254,0.026123047,0.03543091,0.07513428,0.024673462,-0.051483154,-0.057006836,-0.036621094,-0.0019521713,-0.04159546,-0.047058105,-0.03201294,-0.015533447,0.033172607,0.0063934326,0.0056266785,0.0061569214,-0.015838623,-0.035980225,0.0023937225,-0.052246094,0.0413208,-0.03387451,-0.0053901672,-0.055633545,-0.05267334,-0.0074386597,-0.05645752,-0.026367188,0.029922485,-0.001376152,-0.016860962,0.04257202,0.12609863,0.04421997,0.025680542,-0.05630493,0.02293396,0.026916504,-0.09680176,0.059143066,0.10864258,-0.011512756,0.029205322,-0.08605957,-0.08300781,0.027511597,-0.040283203,0.018295288,0.02822876,-0.009185791,0.020858765,0.034454346,-0.09637451,-0.029769897,0.044555664,-0.008552551,-0.043395996,-0.056793213,-0.086242676,0.05206299,-0.0016241074,0.0368042,0.025344849,0.00289917,-0.015350342,0.10571289,0.036590576,0.04510498,-0.07330322,0.026657104,-0.053863525,0.09020996,0.046447754,-0.0033073425,-0.02822876,-0.028503418,-0.0039100647,0.027770996,-0.103271484,0.0074882507,-0.043670654,0.03338623,0.062561035,-0.021209717,-0.022399902,0.058898926,-0.026611328,-0.15673828,-0.008369446,-0.07055664,0.033355713,-0.010986328,0.0158844,-0.04147339,-0.045410156,0.042663574,0.035247803,-0.03366089,0.012123108,-0.02999878,0.02168274,0.09649658,-0.064941406,0.011291504,0.002790451,-0.11151123,-0.012588501,-0.009407043,-0.0012493134,0.034118652,0.07318115,-0.0028057098,-0.004142761,-0.042510986,-0.03086853,-0.0309906,-0.008293152,-0.01158905,-0.0041542053,-0.04269409,-0.056610107,0.018310547,0.12670898,-0.015960693,0.061828613,-0.042907715,-0.042816162,0.012069702,-0.049041748,0.02168274,0.09411621,0.052642822,-0.044799805,0.002380371,-0.026168823,0.014884949,0.036621094,0.017715454,0.029510498,0.001452446,0.05593872,-0.013168335,0.016830444,0.033203125,0.03753662,0.09295654,0.001619339,-0.06555176,-0.06970215,0.07635498,0.10284424,0.06286621,0.03866577,-0.014808655,-0.030700684,0.011665344],[0.023895264,0.068847656,0.006034851,0.028060913,-0.05328369,-0.009185791,0.060424805,0.041656494,0.0046844482,0.053833008,-0.03933716,-0.10253906,0.035247803,-0.029067993,-0.046081543,-0.0692749,0.050323486,-0.014419556,-0.13452148,0.10430908,0.02848816,0.099121094,-0.030380249,-0.021591187,0.017044067,-0.05532837,0.020233154,0.03793335,-0.046081543,0.006538391,-0.017456055,-0.04333496,-0.0042381287,0.05114746,0.050872803,-0.06048584,-0.010108948,0.08874512,0.077819824,0.03842163,-0.03805542,0.012298584,-0.02230835,-0.049926758,-0.0637207,0.059783936,-0.061340332,-0.0005903244,-0.027633667,-0.0051002502,0.07897949,0.0128479,0.026153564,0.06109619,-0.010406494,0.07324219,-0.016204834,0.038238525,0.039093018,0.068603516,-0.04385376,0.013381958,-0.097717285,0.07714844,0.08972168,0.007522583,0.009849548,-0.008621216,-0.044281006,-0.08929443,0.020462036,0.02432251,-0.028198242,0.048309326,0.06036377,0.041656494,-0.03781128,-0.003484726,0.009277344,0.033325195,0.045837402,-0.013435364,-0.08917236,-0.018630981,-0.0053977966,-0.05496216,0.026687622,0.046325684,-0.0102005005,-0.083862305,-0.039916992,0.015853882,0.030349731,-0.053375244,-0.13916016,-0.07104492,0.011192322,0.02861023,-0.009750366,-0.0070228577,-0.020553589,0.026885986,-0.087768555,-0.03845215,-0.0037899017,0.011253357,0.039093018,0.050231934,0.06524658,-0.044769287,-0.12695312,0.064941406,0.082214355,-0.022003174,0.06335449,-0.060791016,-0.015823364,-0.08758545,-0.04940796,-0.054901123,0.011428833,-0.0602417,-0.0010309219,-0.05630493,0.025421143,-0.11773682,0.04623413,0.02230835,0.06970215,-0.010093689,0.07043457,-0.00032758713,0.032684326,0.027252197,-0.076049805,-0.009773254,-0.05834961,-0.03491211,0.046905518,0.072021484,0.047821045,0.046905518,0.013969421,-0.06402588,0.0259552,-0.0051193237,-0.068603516,0.045013428,-0.022644043,0.053619385,-0.024673462,-0.0970459,0.07287598,-0.00092840195,-0.047454834,0.0023727417,0.047424316,-0.038909912,0.05053711,-0.07910156,0.047973633,0.020111084,-0.018310547,0.056549072,0.043823242,0.028427124,0.033355713,-0.020828247,-0.022369385,-0.0044670105,-0.034484863,0.05606079,0.06689453,0.016448975,-0.0025863647,-0.033081055,0.027145386,0.017715454,0.06439209,0.023742676,0.02067566,0.0075531006,-0.032470703,0.00894928,0.032470703,-0.037963867,-0.05239868,-0.033355713,0.019210815,0.0075683594,-0.07324219,0.04699707,-0.062469482,-0.02432251,-0.022064209,0.06524658,0.031021118,0.028060913,0.06524658,-0.075683594,0.109558105,0.09075928,-0.06945801,0.057434082,0.028717041,0.014465332,0.06768799,0.07672119,-0.038482666,0.01939392,0.0006918907,0.028793335,0.023345947,-0.07287598,-0.0006403923,-0.05596924,0.037231445,-0.029510498,-0.13354492,0.0029182434,-0.036071777,-0.016586304,-0.022155762,-0.00012993813,-0.07324219,-0.07312012,-0.039642334,0.000323534,-0.07421875,-0.020431519,0.040130615,-0.0118637085,-0.031799316,0.05255127,-0.030349731,0.059753418,-0.00793457,0.04788208,0.013397217,0.03881836,0.087768555,0.008453369,-0.08496094,-0.0030136108,-0.042663574,-0.059448242,-0.10845947,-0.08081055,0.015449524,-0.031158447,-0.03111267,0.045013428,0.028274536,0.032196045,0.0040016174,0.003479004,-0.041992188,0.051879883,-0.041137695,0.015670776,0.087402344,-0.049957275,-0.030670166,0.03387451,-0.0082473755,-0.039733887,-0.026977539,0.17346191,0.016845703,-0.037261963,0.0395813,-0.0579834,-0.06329346,0.0211792,-0.034851074,0.009643555,-0.0022029877,-0.0018224716,0.0496521,0.043151855,-0.10510254,-0.112854004,-0.01625061,-0.06915283,-0.038482666,-0.06604004,0.02708435,-0.01411438,0.000036120415,-0.07312012,-0.031951904,-0.10949707,-0.034301758,-0.009742737,0.14343262,-0.05218506,-0.05496216,0.00089263916,0.012397766,0.09448242,0.061920166,-0.0008125305,-0.04559326,0.0340271,0.04260254,0.04714966,0.029953003,-0.011390686,-0.042175293,0.07940674,0.014419556,0.061676025,-0.056762695,0.027328491,-0.0032367706,-0.0501709,0.00919342,-0.047454834,0.026992798,-0.01638794,0.023635864,0.037109375,0.022262573,0.037841797,-0.020233154,0.02178955,0.078125,-0.027862549,-0.029037476,0.13830566,0.04107666,0.06124878,-0.038116455,-0.06970215,0.07836914,0.091552734,0.025848389,-0.010284424,-0.068115234,0.066589355,-0.06549072,0.017349243,-0.04434204,-0.028152466,0.037017822,0.024597168,0.07019043,0.028945923,0.032226562,0.041503906,-0.0132369995,0.06903076,-0.016159058,-0.025756836,0.1116333,-0.03491211,0.12097168,-0.026412964,-0.018936157,-0.020721436,-0.0090408325,0.02407837,-0.049713135,0.044006348,-0.06951904,-0.070617676,0.048950195,0.005092621,-0.039886475,-0.078430176,-0.015083313,-0.00013649464,0.07702637,-0.015701294,-0.020248413,0.00020170212,-0.014472961,-0.025680542,-0.043548584,-0.033447266,-0.028747559,0.039093018,0.028823853,0.0046157837],[0.00020253658,-0.041259766,-0.050048828,0.021270752,-0.0020771027,-0.026123047,0.01802063,0.01550293,0.11578369,-0.0039100647,-0.008293152,0.0049362183,-0.026031494,-0.0027580261,-0.07513428,-0.051116943,-0.026763916,-0.0104522705,-0.11810303,-0.021057129,0.04272461,0.10571289,-0.008979797,0.0209198,0.0748291,-0.009735107,0.01133728,-0.047912598,-0.052825928,0.022247314,-0.043304443,-0.0357666,-0.026672363,-0.037261963,-0.04522705,-0.125,0.05508423,0.02142334,-0.0035800934,0.033050537,-0.025878906,0.079711914,-0.015640259,-0.008049011,-0.06359863,-0.009727478,-0.07873535,-0.005443573,-0.011245728,-0.049804688,0.0005683899,0.01739502,0.06311035,0.021057129,0.020202637,-0.052490234,-0.022277832,0.03869629,0.049682617,0.011077881,-0.09802246,-0.03366089,-0.057739258,-0.02243042,0.012130737,-0.04171753,-0.0031795502,-0.06124878,0.023040771,-0.025024414,0.038238525,-0.015235901,0.013214111,0.11791992,-0.074157715,-0.00032138824,0.0096206665,0.046203613,0.0051994324,-0.013908386,0.047088623,-0.07318115,0.066345215,0.016143799,-0.033966064,-0.0052337646,-0.022735596,0.14147949,-0.018814087,-0.013504028,0.024902344,-0.0068855286,-0.029968262,-0.08685303,-0.08728027,0.0048599243,-0.04537964,0.07208252,-0.043823242,-0.01461792,0.018325806,-0.029037476,-0.10369873,0.004928589,0.0635376,0.061431885,0.001868248,0.04925537,0.022583008,0.08691406,-0.12536621,0.10986328,0.06890869,0.053833008,0.1418457,-0.029159546,0.011741638,-0.003332138,0.0131073,-0.0098724365,0.029006958,-0.07086182,-0.079589844,-0.057159424,0.09313965,-0.03930664,0.0395813,0.051940918,0.043273926,-0.10070801,0.008346558,0.0084991455,-0.07647705,0.00970459,-0.10217285,-0.017990112,0.022079468,-0.06756592,0.0025634766,-0.010353088,0.023956299,0.046203613,0.05618286,-0.067993164,0.01776123,-0.056427002,-0.031143188,0.00223732,-0.07293701,0.0012731552,-0.03050232,-0.100097656,-0.023529053,-0.026397705,-0.039367676,0.033081055,0.0340271,-0.047790527,0.03970337,0.020477295,-0.0016918182,0.054382324,-0.048217773,0.09008789,0.054016113,0.05206299,0.017654419,0.008979797,-0.013267517,0.06124878,0.03866577,-0.012138367,-0.043151855,0.010681152,0.052978516,-0.012451172,0.009094238,0.059814453,0.003967285,-0.004497528,0.011047363,-0.05819702,-0.04937744,0.051116943,-0.0209198,0.020355225,-0.04486084,0.056610107,-0.009933472,-0.0040245056,-0.040374756,0.009857178,-0.043304443,0.05419922,-0.043182373,0.06512451,-0.03543091,0.025131226,0.05026245,-0.053833008,0.03479004,-0.051116943,-0.019714355,-0.0025177002,0.07897949,-0.016677856,0.091796875,0.060028076,0.022583008,0.018447876,0.04864502,0.06512451,0.043762207,-0.06628418,0.02330017,-0.04574585,0.006755829,-0.063964844,-0.04748535,0.059417725,0.013061523,-0.020233154,0.016174316,-0.017227173,-0.083496094,-0.09301758,-0.06677246,0.009025574,0.03463745,-0.056854248,0.0035800934,0.011131287,-0.05038452,-0.04937744,-0.0075531006,0.018676758,0.109680176,0.13598633,0.060546875,-0.016799927,0.03857422,0.00573349,-0.056762695,-0.01965332,-0.07293701,-0.048919678,-0.04953003,0.03274536,-0.039245605,0.02645874,-0.06890869,0.035186768,0.00932312,0.006378174,-0.0062675476,0.07434082,-0.06323242,0.049072266,-0.052703857,-0.07659912,0.1295166,-0.0015335083,0.057739258,-0.00073337555,0.034820557,-0.046081543,-0.07696533,0.08215332,-0.05496216,-0.0072021484,0.044158936,-0.024627686,-0.029373169,0.027145386,-0.056488037,0.08190918,0.01889038,-0.049041748,-0.025009155,-0.02722168,-0.099975586,-0.029312134,0.0071258545,-0.030166626,0.027511597,0.000726223,0.01171875,0.066589355,0.12060547,0.0056114197,-0.040100098,-0.07513428,-0.092041016,-0.013175964,0.05734253,-0.036895752,-0.16882324,-0.004055023,0.060302734,0.009147644,0.0541687,-0.009407043,0.00356102,-0.021896362,0.059295654,0.014976501,-0.022521973,0.0026760101,-0.029922485,0.103637695,-0.020996094,0.04547119,0.00522995,0.013801575,-0.05770874,-0.056243896,-0.0025177002,-0.031585693,-0.010528564,0.0048713684,-0.020568848,0.015144348,0.072387695,0.053894043,-0.023666382,0.09265137,0.060302734,-0.037078857,0.0103302,0.095703125,-0.006515503,0.08087158,-0.02722168,-0.016525269,-0.00030183792,0.019454956,-0.070373535,0.007095337,-0.037017822,0.056549072,0.009063721,-0.007221222,-0.09069824,0.0058670044,0.08300781,-0.02154541,0.11328125,0.017944336,0.044067383,-0.014709473,0.045288086,0.08001709,0.008842468,0.024627686,0.048461914,-0.05255127,0.06970215,0.013076782,-0.010353088,-0.038085938,-0.05886841,-0.002796173,-0.0060691833,0.027328491,-0.031188965,-0.062805176,-0.06695557,0.09466553,-0.024383545,0.008201599,0.021728516,-0.0033035278,0.052368164,0.03466797,-0.023788452,0.08288574,0.07293701,-0.04611206,-0.011650085,-0.009521484,0.01838684,-0.12011719,0.11987305,-0.007411957],[-0.013893127,-0.002084732,0.037261963,-0.08105469,-0.034240723,-0.08312988,0.025115967,0.06695557,-0.03173828,0.040649414,0.0043296814,-0.023513794,0.076293945,-0.06854248,-0.060058594,-0.03942871,0.016357422,-0.04486084,-0.004180908,-0.01852417,0.0113220215,0.16430664,0.018630981,-0.012702942,0.12176514,-0.04437256,0.010147095,-0.033050537,0.012901306,-0.0018806458,0.014823914,-0.049926758,0.030334473,-0.026351929,0.033203125,-0.055358887,0.02268982,0.031097412,0.048980713,-0.006916046,-0.06488037,0.03604126,0.06201172,-0.08660889,-0.027572632,0.05206299,-0.072387695,0.005821228,-0.000016391277,-0.048828125,0.07635498,-0.035888672,0.030212402,0.05822754,0.08496094,-0.017715454,-0.05026245,-0.0118637085,0.019989014,-0.040649414,-0.04046631,-0.021240234,-0.023468018,-0.00036263466,0.107177734,0.06488037,-0.018203735,-0.0042915344,-0.030136108,-0.10467529,0.019592285,-0.0234375,0.013946533,0.02947998,-0.045410156,-0.022949219,-0.013221741,0.04220581,0.013641357,0.008865356,-0.0024337769,-0.025115967,-0.022064209,-0.0069999695,0.06304932,-0.0075531006,-0.082092285,0.082214355,0.029647827,0.020080566,0.0068473816,-0.020263672,0.018127441,-0.09661865,-0.037109375,0.023406982,0.010398865,0.08496094,0.032348633,0.000054836273,-0.035949707,0.03729248,-0.02557373,-0.0021400452,-0.079833984,-0.0018882751,-0.037017822,0.077941895,0.0053977966,0.0095825195,-0.10205078,-0.017364502,0.03781128,0.04675293,0.091796875,-0.1385498,0.066467285,-0.020751953,-0.053833008,0.026031494,-0.027938843,-0.09790039,-0.043060303,0.030227661,0.074645996,-0.042114258,0.052764893,-0.0062675476,0.014060974,0.0019102097,-0.02003479,0.036499023,-0.06933594,-0.03994751,-0.042510986,0.013015747,-0.021499634,-0.04751587,-0.045135498,0.020584106,0.028366089,0.10784912,0.059570312,-0.021331787,0.014564514,-0.024993896,0.11279297,-0.0657959,-0.026977539,0.059753418,-0.056518555,0.026611328,-0.034332275,-0.056396484,-0.019882202,-0.04006958,0.047027588,-0.0826416,-0.029586792,-0.04208374,0.07873535,-0.0045661926,0.0005311966,0.027572632,0.11395264,0.053466797,-0.08312988,-0.05340576,-0.013885498,0.017684937,-0.0053138733,-0.06149292,0.026809692,0.053863525,0.056243896,-0.034301758,-0.009902954,0.030227661,0.0256958,0.066833496,-0.008468628,-0.04333496,0.0056991577,0.020111084,-0.028366089,0.009506226,0.035095215,-0.020904541,-0.028900146,-0.06915283,0.016967773,-0.054534912,-0.03567505,0.058135986,-0.0435791,-0.015670776,0.03970337,0.057434082,0.049682617,-0.051330566,0.06488037,0.013900757,-0.030593872,0.06781006,0.12182617,0.024932861,0.02078247,0.14355469,0.06591797,0.0069351196,0.008773804,0.027557373,0.05633545,-0.10858154,-0.061920166,-0.053497314,-0.007835388,-0.019042969,0.015670776,0.0065994263,0.026275635,-0.03945923,-0.015182495,0.059417725,-0.096069336,-0.04989624,-0.06225586,-0.012916565,0.026153564,-0.008003235,0.14807129,0.015129089,-0.044555664,-0.041625977,-0.046325684,0.039611816,0.09887695,0.039611816,-0.08312988,-0.011375427,0.09454346,-0.0016365051,-0.07312012,-0.021469116,-0.028671265,-0.07897949,-0.124938965,-0.07318115,-0.06072998,-0.019561768,-0.09753418,0.003967285,0.037872314,0.0007991791,0.03479004,-0.023010254,-0.032470703,0.05606079,0.013221741,-0.048950195,0.042999268,-0.06542969,-0.07495117,-0.0552063,0.08892822,0.035888672,-0.06384277,0.08831787,-0.039001465,0.11834717,-0.02142334,-0.08483887,-0.09613037,0.03555298,-0.037628174,0.014678955,0.010017395,-0.038208008,-0.027572632,0.00856781,-0.06616211,-0.009941101,0.06335449,0.009796143,-0.06378174,-0.020233154,0.043395996,0.05706787,0.02230835,-0.014968872,-0.014030457,-0.109436035,-0.013519287,-0.0077552795,0.101135254,0.027709961,-0.11627197,0.020843506,0.06713867,0.022567749,0.059631348,0.031921387,0.02861023,0.0044021606,0.03567505,0.07446289,0.007621765,0.0054855347,-0.00060367584,0.034118652,0.014129639,-0.030197144,-0.0018558502,0.071777344,0.06100464,-0.054840088,-0.035949707,-0.020706177,0.070617676,-0.035217285,-0.0005097389,0.0013685226,0.017211914,0.07354736,0.0058670044,-0.050567627,0.010406494,-0.05316162,-0.021392822,0.1104126,0.017715454,0.02015686,0.017715454,-0.04611206,-0.03451538,-0.020584106,-0.014701843,0.0065994263,-0.044555664,-0.0680542,0.02571106,-0.06939697,-0.075927734,0.06982422,-0.026382446,0.020263672,0.12512207,0.058807373,-0.014953613,-0.10321045,0.02897644,0.027740479,-0.0033302307,-0.010604858,0.077941895,0.022720337,0.022537231,0.027252197,0.015716553,0.02279663,-0.026641846,0.043548584,0.029266357,0.041625977,-0.01802063,0.0024337769,0.0112838745,0.03665161,0.026550293,0.024658203,-0.013092041,0.004169464,0.044952393,0.06591797,-0.056488037,0.07647705,-0.051086426,-0.03955078,-0.09399414,0.016036987,-0.04309082,-0.05795288,-0.024536133,0.06549072]]},"meta":{"api_version":{"version":"2"},"billed_units":{"input_tokens":208}},"response_type":"embeddings_by_type"}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 03:17:07 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '967' + num_tokens: + - '208' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 5bf14e94670880a3e6e9ac76e2a6cba8 + x-envoy-upstream-service-time: + - '45' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy_async.yaml new file mode 100644 index 00000000..d7215f06 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_embed/test_cohere_v2_embed_legacy_async.yaml @@ -0,0 +1,92 @@ +interactions: +- request: + body: '{"texts": ["Carson City is the capital city of the American state of Nevada. + At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands in the + Pacific Ocean that are a political division controlled by the United States. + Its capital is Saipan.", "Charlotte Amalie is the capital and largest city of + the United States Virgin Islands. It has about 20,000 people. The city is on + the island of Saint Thomas.", "Washington, D.C. (also known as simply Washington + or D.C., and officially as the District of Columbia) is the capital of the United + States. It is a federal district. ", "Capital punishment (the death penalty) + has existed in the United States since before the United States was a country. + As of 2017, capital punishment is legal in 30 of the 50 states.", "North Dakota + is a state in the United States. 672,591 people lived in North Dakota in the + year 2010. The capital and seat of government is Bismarck."], "model": "embed-english-light-v3.0", + "input_type": "search_document"}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1072' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/embed + response: + body: + string: '{"id":"3bc87f83-0534-4478-af7d-fee196c92758","texts":["carson city + is the capital city of the american state of nevada. at the 2010 united states + census, carson city had a population of 55, 274.","the commonwealth of the + northern mariana islands is a group of islands in the pacific ocean that are + a political division controlled by the united states. its capital is saipan.","charlotte + amalie is the capital and largest city of the united states virgin islands. + it has about 20, 000 people. the city is on the island of saint thomas.","washington, + d. c. ( also known as simply washington or d. c., and officially as the district + of columbia ) is the capital of the united states. it is a federal district.","capital + punishment ( the death penalty ) has existed in the united states since before + the united states was a country. as of 2017, capital punishment is legal in + 30 of the 50 states.","north dakota is a state in the united states. 672, + 591 people lived in north dakota in the year 2010. the capital and seat of + government is bismarck."],"embeddings":{"float":[[0.032318115,-0.031188965,-0.06604004,0.028823853,-0.017730713,-0.07757568,0.02305603,0.008758545,-0.004558563,0.0725708,-0.112976074,-0.05142212,0.08526611,-0.11383057,-0.052337646,-0.010803223,0.02848816,-0.08453369,0.06365967,-0.0647583,-0.066467285,0.10449219,0.037841797,-0.01134491,-0.020523071,-0.15917969,-0.07720947,-0.015106201,-0.032836914,0.092041016,-0.018463135,-0.034179688,0.06137085,0.05404663,0.090270996,-0.061828613,0.058654785,-0.013000488,-0.046081543,0.0552063,0.022109985,0.12646484,0.0031318665,-0.083984375,-0.050231934,0.049804688,-0.059020996,-0.005924225,0.018157959,0.0066566467,0.07446289,0.015808105,0.014984131,0.050750732,-0.046936035,0.05807495,0.014465332,-0.038238525,-0.03869629,-0.017227173,-0.07739258,-0.015258789,-0.03845215,-0.056762695,0.006286621,0.061553955,0.035858154,-0.11004639,-0.011672974,-0.03036499,0.06286621,-0.1060791,-0.059020996,0.006324768,0.01586914,0.0066566467,-0.054748535,0.077819824,0.057861328,0.0647583,0.0703125,-0.039733887,-0.002840042,-0.05999756,-0.01676941,0.0871582,0.010658264,-0.0004172325,0.035980225,-0.033081055,0.03692627,0.007045746,-0.009506226,-0.06738281,-0.04168701,0.029342651,0.029571533,0.021896362,0.0037384033,-0.03656006,0.010749817,0.022064209,-0.028366089,-0.032226562,-0.076660156,-0.017486572,-0.013084412,0.09246826,-0.057495117,0.020462036,-0.054656982,0.040130615,0.0236969,-0.016052246,-0.0001552105,-0.019485474,0.0647583,-0.03112793,-0.055541992,-0.0025463104,0.008453369,-0.078308105,0.0211792,0.022064209,0.07940674,-0.016464233,-0.00052022934,-0.03543091,-0.00015723705,-0.0035209656,0.02571106,0.052093506,-0.016708374,0.00015437603,-0.02027893,-0.012313843,0.009552002,-0.08026123,-0.002363205,0.007045746,0.099731445,0.10467529,-0.009651184,-0.0029239655,-0.025146484,0.024047852,0.049987793,0.001156807,-0.03353882,0.06359863,0.04699707,0.068603516,-0.0064888,-0.03265381,-0.11920166,-0.024337769,0.076660156,-0.02432251,0.018936157,0.06915283,0.081726074,0.04827881,0.05166626,0.058532715,-0.024627686,0.12609863,-0.056396484,-0.0836792,-0.041503906,0.099853516,0.04751587,-0.053100586,-0.10449219,0.004146576,0.07098389,-0.019332886,-0.011924744,0.015197754,0.0034313202,0.10321045,-0.031341553,0.06750488,-0.015274048,0.01651001,-0.043792725,-0.05328369,-0.012451172,0.0074691772,0.015182495,-0.1126709,-0.0066566467,-0.044708252,0.0078125,-0.048095703,-0.042144775,0.04611206,0.02571106,0.039764404,0.13635254,-0.056488037,0.049194336,-0.000101327896,0.0090789795,0.011520386,0.05960083,0.0058059692,0.05392456,0.07324219,-0.031280518,0.021255493,0.028701782,0.015602112,0.08117676,-0.0814209,0.031677246,0.011810303,0.04449463,-0.0023326874,-0.055725098,0.020965576,0.02708435,-0.017166138,-0.02859497,0.050933838,-0.14575195,0.0072898865,0.011299133,-0.087524414,0.04525757,-0.05581665,0.08959961,0.017547607,-0.03250122,-0.013885498,0.016662598,0.058441162,0.0418396,-0.04449463,-0.04171753,0.0067481995,0.059692383,0.07330322,-0.05407715,0.052642822,-0.09564209,-0.06951904,-0.09051514,-0.06842041,0.041992188,-0.023101807,-0.12731934,-0.068603516,0.008605957,-0.024154663,-0.05618286,-0.0007596016,0.048858643,0.080322266,0.034332275,0.029922485,0.021591187,-0.060546875,0.0067863464,-0.032836914,0.0052452087,-0.0057868958,-0.066589355,0.03062439,-0.025802612,0.053100586,-0.04852295,-0.027313232,-0.082336426,0.059265137,0.010284424,0.006843567,-0.03491211,-0.007019043,0.03225708,0.043884277,0.0059394836,0.0015859604,0.055908203,-0.011398315,-0.027038574,-0.023956299,-0.023971558,0.030197144,-0.064697266,-0.035980225,-0.06097412,-0.08117676,-0.0066375732,0.02935791,0.014526367,-0.032836914,-0.023468018,0.02998352,-0.045776367,0.023529053,0.054870605,0.11138916,0.0970459,0.024261475,0.024993896,-0.042785645,0.05102539,0.042419434,-0.015396118,0.034576416,-0.013397217,-0.025054932,0.12060547,0.06756592,0.005558014,0.022003174,-0.037384033,-0.081970215,0.020751953,-0.00844574,0.096191406,-0.025253296,-0.029266357,0.06347656,0.026382446,0.041625977,0.033996582,0.0042800903,-0.06161499,0.05419922,-0.028427124,-0.0025024414,0.0035476685,0.01637268,-0.072509766,-0.039154053,0.0146102905,0.080444336,0.043914795,-0.055480957,-0.010917664,-0.08526611,-0.09661865,-0.011268616,-0.018676758,0.05532837,0.05255127,-0.005821228,-0.036895752,-0.026931763,0.05645752,-0.0440979,0.048095703,-0.07019043,0.053466797,-0.0007586479,-0.04925537,0.02911377,0.010520935,-0.04714966,0.021331787,-0.017669678,-0.02519226,-0.011955261,-0.0067100525,-0.072021484,-0.06890869,-0.021774292,-0.026809692,0.0053100586,0.030426025,0.07354736,0.059417725,0.03579712,0.0031528473,0.0541687,-0.049926758,-0.015083313,0.03427124,0.023666382,0.0014266968,0.048431396,-0.02142334,-0.046936035],[0.034454346,-0.03652954,0.121520996,-0.08618164,0.015960693,-0.0647583,0.07354736,0.061431885,0.020614624,0.0012788773,0.01612854,-0.06121826,-0.031555176,-0.012077332,0.011062622,0.028533936,-0.041137695,-0.0619812,-0.005203247,0.009513855,0.059814453,0.10748291,-0.10455322,-0.0046157837,0.07940674,-0.037994385,0.027359009,-0.013954163,0.03793335,-0.0154418945,-0.0038108826,-0.04257202,0.001666069,-0.023635864,0.04272461,0.0022354126,0.01902771,-0.033691406,0.04284668,-0.09857178,-0.047088623,0.046966553,0.04144287,0.056274414,0.0030555725,0.024154663,-0.089782715,-0.0038490295,-0.064941406,0.065979004,0.07495117,-0.07989502,-0.044799805,0.037628174,0.014404297,0.050598145,-0.0028591156,0.039276123,0.07159424,-0.005203247,0.03491211,0.04373169,-0.036956787,0.0014915466,0.016952515,0.032470703,0.047821045,0.048461914,-0.0126571655,-0.120666504,-0.053863525,0.0046463013,0.001964569,-0.0049324036,-0.008514404,0.013000488,0.02154541,-0.0019817352,0.0018005371,0.0032482147,0.06921387,0.0725708,0.010566711,-0.038726807,0.06774902,-0.029159546,-0.022445679,0.048980713,0.035858154,0.017593384,-0.023590088,0.029800415,0.11895752,-0.044555664,-0.030014038,0.10961914,-0.06185913,0.025619507,0.078552246,0.00066518784,0.018478394,0.09680176,0.029006958,-0.10253906,-0.09057617,0.10040283,0.02909851,0.019546509,0.09918213,0.038360596,-0.03149414,0.020339966,0.008979797,-0.05429077,0.015419006,-0.10192871,0.036010742,-0.032226562,-0.057800293,0.011566162,0.047302246,-0.10986328,0.032104492,-0.05227661,0.072509766,-0.025558472,-0.060333252,-0.0859375,0.058044434,-0.07659912,0.017227173,0.03225708,0.029953003,0.0049057007,0.066833496,-0.03881836,-0.093322754,-0.121398926,-0.049560547,0.04348755,0.081848145,0.017074585,0.06604004,0.012817383,0.076293945,0.017150879,0.05645752,-0.019622803,-0.011665344,0.059692383,-0.036132812,0.030273438,-0.026519775,-0.01612854,-0.0715332,-0.06964111,-0.00009262562,-0.04336548,-0.0076560974,-0.025924683,0.03741455,-0.017227173,-0.07318115,0.031280518,0.03692627,0.04373169,-0.00016987324,0.039978027,-0.06707764,0.056884766,0.01789856,0.020141602,0.040100098,0.00365448,-0.031982422,-0.06933594,0.014656067,0.08898926,-0.035949707,-0.0044441223,-0.070739746,-0.02696228,0.03866577,-0.055114746,-0.06756592,0.047912598,-0.04788208,0.009780884,0.05569458,-0.019882202,0.0050239563,0.00630188,-0.024841309,0.0670166,-0.06097412,-0.08166504,0.03845215,0.050842285,0.06524658,0.056243896,0.03942871,0.07824707,-0.039794922,0.028961182,0.01651001,0.022445679,-0.018295288,0.01234436,-0.012367249,-0.010047913,-0.05227661,-0.003730774,0.0065078735,-0.075805664,0.045715332,0.0054779053,-0.013648987,-0.012496948,-0.05001831,0.032409668,0.06311035,-0.06149292,0.01586914,0.042510986,-0.078063965,-0.090270996,-0.05392456,-0.080200195,-0.030578613,0.02947998,0.060333252,0.031921387,-0.051239014,-0.018066406,-0.075927734,-0.044281006,0.08831787,-0.020645142,-0.04043579,0.011634827,0.13012695,0.049804688,0.000052154064,0.02406311,-0.008621216,-0.052001953,0.016433716,-0.05758667,-0.010757446,-0.09307861,-0.038269043,-0.06121826,-0.0007548332,-0.026184082,-0.03793335,0.008018494,0.049468994,-0.074035645,-0.075683594,-0.11462402,-0.0032215118,-0.10650635,0.018737793,-0.010734558,0.052825928,-0.0647583,-0.011070251,0.11224365,-0.064331055,0.019821167,0.012611389,-0.013900757,-0.0869751,-0.024307251,-0.0055770874,-0.04748535,0.048431396,-0.009002686,0.06866455,0.01777649,-0.07507324,0.0012559891,0.053955078,0.01499176,-0.048217773,-0.076293945,-0.015792847,-0.0036640167,0.043518066,0.032806396,0.016662598,-0.0042800903,0.066589355,-0.03555298,0.08325195,-0.019073486,-0.0049057007,0.037994385,0.015975952,0.04800415,0.04434204,0.021896362,0.049346924,-0.029891968,0.041992188,-0.027038574,-0.03314209,-0.011871338,-0.0473938,0.039978027,0.013793945,-0.032684326,-0.10632324,-0.015365601,0.08276367,-0.13671875,0.017105103,-0.02003479,0.011482239,-0.021026611,0.026184082,-0.05117798,0.03289795,0.0026416779,0.005493164,0.0087509155,-0.06365967,-0.05126953,0.14074707,0.078552246,0.044189453,0.054351807,0.021331787,-0.04321289,0.05429077,0.012863159,-0.04675293,0.0647583,0.03717041,-0.015625,-0.007347107,-0.014808655,-0.019546509,0.08428955,-0.0018234253,0.0039978027,0.05596924,-0.05166626,0.0657959,0.010360718,-0.021240234,-0.013412476,-0.068481445,-0.0071907043,-0.035247803,0.1352539,0.00015163422,0.005306244,-0.004173279,-0.07537842,0.001042366,0.0970459,0.017227173,0.010757446,-0.0871582,-0.016784668,0.022140503,0.08355713,0.0060768127,0.020050049,-0.047088623,-0.04949951,-0.029464722,-0.060180664,-0.0748291,0.015022278,-0.113586426,0.02998352,-0.031280518,0.08190918,0.021072388,0.019744873,-0.046020508,-0.025680542],[-0.015945435,-0.07232666,0.059020996,-0.00674057,-0.022827148,-0.076049805,-0.0012760162,0.0026111603,-0.06463623,0.018249512,0.015525818,-0.0031166077,-0.05810547,-0.08911133,-0.047058105,0.06060791,0.010871887,-0.04232788,0.04763794,-0.027435303,0.036865234,-0.0010910034,-0.011474609,-0.082336426,0.03857422,-0.105895996,-0.04067993,-0.0033340454,-0.004055023,0.011619568,0.025878906,-0.09338379,0.03466797,0.101257324,-0.00484848,-0.030944824,0.08190918,0.030944824,0.09967041,-0.010047913,0.031158447,0.1307373,-0.030303955,0.054534912,-0.025772095,0.0362854,-0.093688965,0.0463562,-0.008277893,0.032196045,0.10046387,-0.047851562,-0.043914795,0.035064697,-0.0016546249,-0.079956055,-0.04046631,-0.059692383,-0.01184082,-0.052947998,0.05810547,-0.04827881,-0.013977051,0.0031147003,-0.007843018,0.008590698,0.021560669,0.045898438,0.010368347,-0.04776001,0.04031372,-0.047851562,-0.014808655,0.039276123,0.029846191,-0.015129089,-0.1194458,0.04776001,0.058624268,0.06890869,0.062408447,-0.024398804,0.027053833,-0.014198303,-0.015533447,0.004470825,-0.012992859,0.15161133,0.02558899,0.036010742,-0.04058838,-0.0042495728,-0.04788208,-0.053741455,-0.034454346,0.03302002,0.00013899803,0.02468872,-0.009315491,-0.01411438,0.009315491,0.09118652,0.043823242,0.008178711,-0.0063934326,0.1005249,0.055419922,-0.023025513,0.1673584,-0.025909424,-0.10070801,0.028579712,-0.02394104,-0.019042969,-0.037139893,-0.04446411,0.11053467,-0.046875,-0.125,-0.050964355,-0.044769287,-0.037628174,0.025314331,-0.01828003,-0.027877808,-0.024932861,0.02482605,-0.0149002075,-0.04626465,-0.028518677,0.0023345947,0.14550781,0.012290955,-0.005760193,-0.02168274,-0.0063972473,-0.0050964355,-0.17602539,-0.0635376,-0.011413574,0.06384277,0.057617188,0.06524658,-0.031707764,0.072509766,0.0049819946,-0.034301758,0.010658264,-0.0045547485,-0.012321472,-0.030151367,-0.003025055,-0.057403564,-0.0049858093,-0.0050239563,0.0096206665,0.07055664,-0.05923462,0.091308594,0.06109619,0.09655762,0.045288086,0.0072631836,0.024597168,0.012573242,-0.0038795471,-0.09234619,-0.005214691,-0.099365234,-0.051757812,0.016113281,-0.025222778,-0.01058197,0.02909851,0.004776001,-0.012046814,0.0592041,0.09832764,0.007411957,0.028213501,-0.07458496,0.06915283,-0.0044441223,0.08026123,0.031036377,-0.0017576218,0.008041382,-0.0037059784,-0.029693604,-0.11248779,0.057403564,-0.039398193,-0.021865845,0.013717651,-0.032714844,-0.00072050095,-0.015960693,0.070007324,0.041137695,-0.027008057,0.045410156,0.018798828,-0.011192322,0.058013916,0.0395813,-0.057037354,0.008903503,0.049926758,-0.05505371,-0.0058555603,-0.030090332,0.02835083,0.085754395,-0.09814453,-0.034210205,0.029205322,0.006828308,-0.035980225,0.030914307,-0.017730713,0.0637207,0.061309814,-0.06933594,-0.011940002,-0.085632324,-0.042907715,0.01927185,-0.069885254,0.026123047,0.03543091,0.07513428,0.024673462,-0.051483154,-0.057006836,-0.036621094,-0.0019521713,-0.04159546,-0.047058105,-0.03201294,-0.015533447,0.033172607,0.0063934326,0.0056266785,0.0061569214,-0.015838623,-0.035980225,0.0023937225,-0.052246094,0.0413208,-0.03387451,-0.0053901672,-0.055633545,-0.05267334,-0.0074386597,-0.05645752,-0.026367188,0.029922485,-0.001376152,-0.016860962,0.04257202,0.12609863,0.04421997,0.025680542,-0.05630493,0.02293396,0.026916504,-0.09680176,0.059143066,0.10864258,-0.011512756,0.029205322,-0.08605957,-0.08300781,0.027511597,-0.040283203,0.018295288,0.02822876,-0.009185791,0.020858765,0.034454346,-0.09637451,-0.029769897,0.044555664,-0.008552551,-0.043395996,-0.056793213,-0.086242676,0.05206299,-0.0016241074,0.0368042,0.025344849,0.00289917,-0.015350342,0.10571289,0.036590576,0.04510498,-0.07330322,0.026657104,-0.053863525,0.09020996,0.046447754,-0.0033073425,-0.02822876,-0.028503418,-0.0039100647,0.027770996,-0.103271484,0.0074882507,-0.043670654,0.03338623,0.062561035,-0.021209717,-0.022399902,0.058898926,-0.026611328,-0.15673828,-0.008369446,-0.07055664,0.033355713,-0.010986328,0.0158844,-0.04147339,-0.045410156,0.042663574,0.035247803,-0.03366089,0.012123108,-0.02999878,0.02168274,0.09649658,-0.064941406,0.011291504,0.002790451,-0.11151123,-0.012588501,-0.009407043,-0.0012493134,0.034118652,0.07318115,-0.0028057098,-0.004142761,-0.042510986,-0.03086853,-0.0309906,-0.008293152,-0.01158905,-0.0041542053,-0.04269409,-0.056610107,0.018310547,0.12670898,-0.015960693,0.061828613,-0.042907715,-0.042816162,0.012069702,-0.049041748,0.02168274,0.09411621,0.052642822,-0.044799805,0.002380371,-0.026168823,0.014884949,0.036621094,0.017715454,0.029510498,0.001452446,0.05593872,-0.013168335,0.016830444,0.033203125,0.03753662,0.09295654,0.001619339,-0.06555176,-0.06970215,0.07635498,0.10284424,0.06286621,0.03866577,-0.014808655,-0.030700684,0.011665344],[0.023895264,0.068847656,0.006034851,0.028060913,-0.05328369,-0.009185791,0.060424805,0.041656494,0.0046844482,0.053833008,-0.03933716,-0.10253906,0.035247803,-0.029067993,-0.046081543,-0.0692749,0.050323486,-0.014419556,-0.13452148,0.10430908,0.02848816,0.099121094,-0.030380249,-0.021591187,0.017044067,-0.05532837,0.020233154,0.03793335,-0.046081543,0.006538391,-0.017456055,-0.04333496,-0.0042381287,0.05114746,0.050872803,-0.06048584,-0.010108948,0.08874512,0.077819824,0.03842163,-0.03805542,0.012298584,-0.02230835,-0.049926758,-0.0637207,0.059783936,-0.061340332,-0.0005903244,-0.027633667,-0.0051002502,0.07897949,0.0128479,0.026153564,0.06109619,-0.010406494,0.07324219,-0.016204834,0.038238525,0.039093018,0.068603516,-0.04385376,0.013381958,-0.097717285,0.07714844,0.08972168,0.007522583,0.009849548,-0.008621216,-0.044281006,-0.08929443,0.020462036,0.02432251,-0.028198242,0.048309326,0.06036377,0.041656494,-0.03781128,-0.003484726,0.009277344,0.033325195,0.045837402,-0.013435364,-0.08917236,-0.018630981,-0.0053977966,-0.05496216,0.026687622,0.046325684,-0.0102005005,-0.083862305,-0.039916992,0.015853882,0.030349731,-0.053375244,-0.13916016,-0.07104492,0.011192322,0.02861023,-0.009750366,-0.0070228577,-0.020553589,0.026885986,-0.087768555,-0.03845215,-0.0037899017,0.011253357,0.039093018,0.050231934,0.06524658,-0.044769287,-0.12695312,0.064941406,0.082214355,-0.022003174,0.06335449,-0.060791016,-0.015823364,-0.08758545,-0.04940796,-0.054901123,0.011428833,-0.0602417,-0.0010309219,-0.05630493,0.025421143,-0.11773682,0.04623413,0.02230835,0.06970215,-0.010093689,0.07043457,-0.00032758713,0.032684326,0.027252197,-0.076049805,-0.009773254,-0.05834961,-0.03491211,0.046905518,0.072021484,0.047821045,0.046905518,0.013969421,-0.06402588,0.0259552,-0.0051193237,-0.068603516,0.045013428,-0.022644043,0.053619385,-0.024673462,-0.0970459,0.07287598,-0.00092840195,-0.047454834,0.0023727417,0.047424316,-0.038909912,0.05053711,-0.07910156,0.047973633,0.020111084,-0.018310547,0.056549072,0.043823242,0.028427124,0.033355713,-0.020828247,-0.022369385,-0.0044670105,-0.034484863,0.05606079,0.06689453,0.016448975,-0.0025863647,-0.033081055,0.027145386,0.017715454,0.06439209,0.023742676,0.02067566,0.0075531006,-0.032470703,0.00894928,0.032470703,-0.037963867,-0.05239868,-0.033355713,0.019210815,0.0075683594,-0.07324219,0.04699707,-0.062469482,-0.02432251,-0.022064209,0.06524658,0.031021118,0.028060913,0.06524658,-0.075683594,0.109558105,0.09075928,-0.06945801,0.057434082,0.028717041,0.014465332,0.06768799,0.07672119,-0.038482666,0.01939392,0.0006918907,0.028793335,0.023345947,-0.07287598,-0.0006403923,-0.05596924,0.037231445,-0.029510498,-0.13354492,0.0029182434,-0.036071777,-0.016586304,-0.022155762,-0.00012993813,-0.07324219,-0.07312012,-0.039642334,0.000323534,-0.07421875,-0.020431519,0.040130615,-0.0118637085,-0.031799316,0.05255127,-0.030349731,0.059753418,-0.00793457,0.04788208,0.013397217,0.03881836,0.087768555,0.008453369,-0.08496094,-0.0030136108,-0.042663574,-0.059448242,-0.10845947,-0.08081055,0.015449524,-0.031158447,-0.03111267,0.045013428,0.028274536,0.032196045,0.0040016174,0.003479004,-0.041992188,0.051879883,-0.041137695,0.015670776,0.087402344,-0.049957275,-0.030670166,0.03387451,-0.0082473755,-0.039733887,-0.026977539,0.17346191,0.016845703,-0.037261963,0.0395813,-0.0579834,-0.06329346,0.0211792,-0.034851074,0.009643555,-0.0022029877,-0.0018224716,0.0496521,0.043151855,-0.10510254,-0.112854004,-0.01625061,-0.06915283,-0.038482666,-0.06604004,0.02708435,-0.01411438,0.000036120415,-0.07312012,-0.031951904,-0.10949707,-0.034301758,-0.009742737,0.14343262,-0.05218506,-0.05496216,0.00089263916,0.012397766,0.09448242,0.061920166,-0.0008125305,-0.04559326,0.0340271,0.04260254,0.04714966,0.029953003,-0.011390686,-0.042175293,0.07940674,0.014419556,0.061676025,-0.056762695,0.027328491,-0.0032367706,-0.0501709,0.00919342,-0.047454834,0.026992798,-0.01638794,0.023635864,0.037109375,0.022262573,0.037841797,-0.020233154,0.02178955,0.078125,-0.027862549,-0.029037476,0.13830566,0.04107666,0.06124878,-0.038116455,-0.06970215,0.07836914,0.091552734,0.025848389,-0.010284424,-0.068115234,0.066589355,-0.06549072,0.017349243,-0.04434204,-0.028152466,0.037017822,0.024597168,0.07019043,0.028945923,0.032226562,0.041503906,-0.0132369995,0.06903076,-0.016159058,-0.025756836,0.1116333,-0.03491211,0.12097168,-0.026412964,-0.018936157,-0.020721436,-0.0090408325,0.02407837,-0.049713135,0.044006348,-0.06951904,-0.070617676,0.048950195,0.005092621,-0.039886475,-0.078430176,-0.015083313,-0.00013649464,0.07702637,-0.015701294,-0.020248413,0.00020170212,-0.014472961,-0.025680542,-0.043548584,-0.033447266,-0.028747559,0.039093018,0.028823853,0.0046157837],[0.00020253658,-0.041259766,-0.050048828,0.021270752,-0.0020771027,-0.026123047,0.01802063,0.01550293,0.11578369,-0.0039100647,-0.008293152,0.0049362183,-0.026031494,-0.0027580261,-0.07513428,-0.051116943,-0.026763916,-0.0104522705,-0.11810303,-0.021057129,0.04272461,0.10571289,-0.008979797,0.0209198,0.0748291,-0.009735107,0.01133728,-0.047912598,-0.052825928,0.022247314,-0.043304443,-0.0357666,-0.026672363,-0.037261963,-0.04522705,-0.125,0.05508423,0.02142334,-0.0035800934,0.033050537,-0.025878906,0.079711914,-0.015640259,-0.008049011,-0.06359863,-0.009727478,-0.07873535,-0.005443573,-0.011245728,-0.049804688,0.0005683899,0.01739502,0.06311035,0.021057129,0.020202637,-0.052490234,-0.022277832,0.03869629,0.049682617,0.011077881,-0.09802246,-0.03366089,-0.057739258,-0.02243042,0.012130737,-0.04171753,-0.0031795502,-0.06124878,0.023040771,-0.025024414,0.038238525,-0.015235901,0.013214111,0.11791992,-0.074157715,-0.00032138824,0.0096206665,0.046203613,0.0051994324,-0.013908386,0.047088623,-0.07318115,0.066345215,0.016143799,-0.033966064,-0.0052337646,-0.022735596,0.14147949,-0.018814087,-0.013504028,0.024902344,-0.0068855286,-0.029968262,-0.08685303,-0.08728027,0.0048599243,-0.04537964,0.07208252,-0.043823242,-0.01461792,0.018325806,-0.029037476,-0.10369873,0.004928589,0.0635376,0.061431885,0.001868248,0.04925537,0.022583008,0.08691406,-0.12536621,0.10986328,0.06890869,0.053833008,0.1418457,-0.029159546,0.011741638,-0.003332138,0.0131073,-0.0098724365,0.029006958,-0.07086182,-0.079589844,-0.057159424,0.09313965,-0.03930664,0.0395813,0.051940918,0.043273926,-0.10070801,0.008346558,0.0084991455,-0.07647705,0.00970459,-0.10217285,-0.017990112,0.022079468,-0.06756592,0.0025634766,-0.010353088,0.023956299,0.046203613,0.05618286,-0.067993164,0.01776123,-0.056427002,-0.031143188,0.00223732,-0.07293701,0.0012731552,-0.03050232,-0.100097656,-0.023529053,-0.026397705,-0.039367676,0.033081055,0.0340271,-0.047790527,0.03970337,0.020477295,-0.0016918182,0.054382324,-0.048217773,0.09008789,0.054016113,0.05206299,0.017654419,0.008979797,-0.013267517,0.06124878,0.03866577,-0.012138367,-0.043151855,0.010681152,0.052978516,-0.012451172,0.009094238,0.059814453,0.003967285,-0.004497528,0.011047363,-0.05819702,-0.04937744,0.051116943,-0.0209198,0.020355225,-0.04486084,0.056610107,-0.009933472,-0.0040245056,-0.040374756,0.009857178,-0.043304443,0.05419922,-0.043182373,0.06512451,-0.03543091,0.025131226,0.05026245,-0.053833008,0.03479004,-0.051116943,-0.019714355,-0.0025177002,0.07897949,-0.016677856,0.091796875,0.060028076,0.022583008,0.018447876,0.04864502,0.06512451,0.043762207,-0.06628418,0.02330017,-0.04574585,0.006755829,-0.063964844,-0.04748535,0.059417725,0.013061523,-0.020233154,0.016174316,-0.017227173,-0.083496094,-0.09301758,-0.06677246,0.009025574,0.03463745,-0.056854248,0.0035800934,0.011131287,-0.05038452,-0.04937744,-0.0075531006,0.018676758,0.109680176,0.13598633,0.060546875,-0.016799927,0.03857422,0.00573349,-0.056762695,-0.01965332,-0.07293701,-0.048919678,-0.04953003,0.03274536,-0.039245605,0.02645874,-0.06890869,0.035186768,0.00932312,0.006378174,-0.0062675476,0.07434082,-0.06323242,0.049072266,-0.052703857,-0.07659912,0.1295166,-0.0015335083,0.057739258,-0.00073337555,0.034820557,-0.046081543,-0.07696533,0.08215332,-0.05496216,-0.0072021484,0.044158936,-0.024627686,-0.029373169,0.027145386,-0.056488037,0.08190918,0.01889038,-0.049041748,-0.025009155,-0.02722168,-0.099975586,-0.029312134,0.0071258545,-0.030166626,0.027511597,0.000726223,0.01171875,0.066589355,0.12060547,0.0056114197,-0.040100098,-0.07513428,-0.092041016,-0.013175964,0.05734253,-0.036895752,-0.16882324,-0.004055023,0.060302734,0.009147644,0.0541687,-0.009407043,0.00356102,-0.021896362,0.059295654,0.014976501,-0.022521973,0.0026760101,-0.029922485,0.103637695,-0.020996094,0.04547119,0.00522995,0.013801575,-0.05770874,-0.056243896,-0.0025177002,-0.031585693,-0.010528564,0.0048713684,-0.020568848,0.015144348,0.072387695,0.053894043,-0.023666382,0.09265137,0.060302734,-0.037078857,0.0103302,0.095703125,-0.006515503,0.08087158,-0.02722168,-0.016525269,-0.00030183792,0.019454956,-0.070373535,0.007095337,-0.037017822,0.056549072,0.009063721,-0.007221222,-0.09069824,0.0058670044,0.08300781,-0.02154541,0.11328125,0.017944336,0.044067383,-0.014709473,0.045288086,0.08001709,0.008842468,0.024627686,0.048461914,-0.05255127,0.06970215,0.013076782,-0.010353088,-0.038085938,-0.05886841,-0.002796173,-0.0060691833,0.027328491,-0.031188965,-0.062805176,-0.06695557,0.09466553,-0.024383545,0.008201599,0.021728516,-0.0033035278,0.052368164,0.03466797,-0.023788452,0.08288574,0.07293701,-0.04611206,-0.011650085,-0.009521484,0.01838684,-0.12011719,0.11987305,-0.007411957],[-0.013893127,-0.002084732,0.037261963,-0.08105469,-0.034240723,-0.08312988,0.025115967,0.06695557,-0.03173828,0.040649414,0.0043296814,-0.023513794,0.076293945,-0.06854248,-0.060058594,-0.03942871,0.016357422,-0.04486084,-0.004180908,-0.01852417,0.0113220215,0.16430664,0.018630981,-0.012702942,0.12176514,-0.04437256,0.010147095,-0.033050537,0.012901306,-0.0018806458,0.014823914,-0.049926758,0.030334473,-0.026351929,0.033203125,-0.055358887,0.02268982,0.031097412,0.048980713,-0.006916046,-0.06488037,0.03604126,0.06201172,-0.08660889,-0.027572632,0.05206299,-0.072387695,0.005821228,-0.000016391277,-0.048828125,0.07635498,-0.035888672,0.030212402,0.05822754,0.08496094,-0.017715454,-0.05026245,-0.0118637085,0.019989014,-0.040649414,-0.04046631,-0.021240234,-0.023468018,-0.00036263466,0.107177734,0.06488037,-0.018203735,-0.0042915344,-0.030136108,-0.10467529,0.019592285,-0.0234375,0.013946533,0.02947998,-0.045410156,-0.022949219,-0.013221741,0.04220581,0.013641357,0.008865356,-0.0024337769,-0.025115967,-0.022064209,-0.0069999695,0.06304932,-0.0075531006,-0.082092285,0.082214355,0.029647827,0.020080566,0.0068473816,-0.020263672,0.018127441,-0.09661865,-0.037109375,0.023406982,0.010398865,0.08496094,0.032348633,0.000054836273,-0.035949707,0.03729248,-0.02557373,-0.0021400452,-0.079833984,-0.0018882751,-0.037017822,0.077941895,0.0053977966,0.0095825195,-0.10205078,-0.017364502,0.03781128,0.04675293,0.091796875,-0.1385498,0.066467285,-0.020751953,-0.053833008,0.026031494,-0.027938843,-0.09790039,-0.043060303,0.030227661,0.074645996,-0.042114258,0.052764893,-0.0062675476,0.014060974,0.0019102097,-0.02003479,0.036499023,-0.06933594,-0.03994751,-0.042510986,0.013015747,-0.021499634,-0.04751587,-0.045135498,0.020584106,0.028366089,0.10784912,0.059570312,-0.021331787,0.014564514,-0.024993896,0.11279297,-0.0657959,-0.026977539,0.059753418,-0.056518555,0.026611328,-0.034332275,-0.056396484,-0.019882202,-0.04006958,0.047027588,-0.0826416,-0.029586792,-0.04208374,0.07873535,-0.0045661926,0.0005311966,0.027572632,0.11395264,0.053466797,-0.08312988,-0.05340576,-0.013885498,0.017684937,-0.0053138733,-0.06149292,0.026809692,0.053863525,0.056243896,-0.034301758,-0.009902954,0.030227661,0.0256958,0.066833496,-0.008468628,-0.04333496,0.0056991577,0.020111084,-0.028366089,0.009506226,0.035095215,-0.020904541,-0.028900146,-0.06915283,0.016967773,-0.054534912,-0.03567505,0.058135986,-0.0435791,-0.015670776,0.03970337,0.057434082,0.049682617,-0.051330566,0.06488037,0.013900757,-0.030593872,0.06781006,0.12182617,0.024932861,0.02078247,0.14355469,0.06591797,0.0069351196,0.008773804,0.027557373,0.05633545,-0.10858154,-0.061920166,-0.053497314,-0.007835388,-0.019042969,0.015670776,0.0065994263,0.026275635,-0.03945923,-0.015182495,0.059417725,-0.096069336,-0.04989624,-0.06225586,-0.012916565,0.026153564,-0.008003235,0.14807129,0.015129089,-0.044555664,-0.041625977,-0.046325684,0.039611816,0.09887695,0.039611816,-0.08312988,-0.011375427,0.09454346,-0.0016365051,-0.07312012,-0.021469116,-0.028671265,-0.07897949,-0.124938965,-0.07318115,-0.06072998,-0.019561768,-0.09753418,0.003967285,0.037872314,0.0007991791,0.03479004,-0.023010254,-0.032470703,0.05606079,0.013221741,-0.048950195,0.042999268,-0.06542969,-0.07495117,-0.0552063,0.08892822,0.035888672,-0.06384277,0.08831787,-0.039001465,0.11834717,-0.02142334,-0.08483887,-0.09613037,0.03555298,-0.037628174,0.014678955,0.010017395,-0.038208008,-0.027572632,0.00856781,-0.06616211,-0.009941101,0.06335449,0.009796143,-0.06378174,-0.020233154,0.043395996,0.05706787,0.02230835,-0.014968872,-0.014030457,-0.109436035,-0.013519287,-0.0077552795,0.101135254,0.027709961,-0.11627197,0.020843506,0.06713867,0.022567749,0.059631348,0.031921387,0.02861023,0.0044021606,0.03567505,0.07446289,0.007621765,0.0054855347,-0.00060367584,0.034118652,0.014129639,-0.030197144,-0.0018558502,0.071777344,0.06100464,-0.054840088,-0.035949707,-0.020706177,0.070617676,-0.035217285,-0.0005097389,0.0013685226,0.017211914,0.07354736,0.0058670044,-0.050567627,0.010406494,-0.05316162,-0.021392822,0.1104126,0.017715454,0.02015686,0.017715454,-0.04611206,-0.03451538,-0.020584106,-0.014701843,0.0065994263,-0.044555664,-0.0680542,0.02571106,-0.06939697,-0.075927734,0.06982422,-0.026382446,0.020263672,0.12512207,0.058807373,-0.014953613,-0.10321045,0.02897644,0.027740479,-0.0033302307,-0.010604858,0.077941895,0.022720337,0.022537231,0.027252197,0.015716553,0.02279663,-0.026641846,0.043548584,0.029266357,0.041625977,-0.01802063,0.0024337769,0.0112838745,0.03665161,0.026550293,0.024658203,-0.013092041,0.004169464,0.044952393,0.06591797,-0.056488037,0.07647705,-0.051086426,-0.03955078,-0.09399414,0.016036987,-0.04309082,-0.05795288,-0.024536133,0.06549072]]},"meta":{"api_version":{"version":"2"},"billed_units":{"input_tokens":208}},"response_type":"embeddings_by_type"}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Transfer-Encoding: + - chunked + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 03:17:07 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + num_chars: + - '967' + num_tokens: + - '208' + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 06931949a01aec81c801d99d17c414a1 + x-envoy-upstream-service-time: + - '48' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_legacy.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_legacy.yaml new file mode 100644 index 00000000..5c153cb0 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_legacy.yaml @@ -0,0 +1,82 @@ +interactions: +- request: + body: '{"query": "What is the capital of the United States?", "documents": ["Carson + City is the capital city of the American state of Nevada. At the 2010 United + States Census, Carson City had a population of 55,274.", "The Commonwealth of + the Northern Mariana Islands is a group of islands in the Pacific Ocean that + are a political division controlled by the United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States Virgin + Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially as + the District of Columbia) is the capital of the United States. It is a federal + district. ", "Capital punishment (the death penalty) has existed in the United + States since before the United States was a country. As of 2017, capital punishment + is legal in 30 of the 50 states.", "North Dakota is a state in the United States. + 672,591 people lived in North Dakota in the year 2010. The capital and seat + of government is Bismarck."], "model": "rerank-multilingual-v2.0", "top_n": + 3}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1109' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/rerank + response: + body: + string: '{"id":"c995b490-c717-411c-8fd0-8bf993cd8382","results":[{"index":3,"relevance_score":0.9999989},{"index":2,"relevance_score":0.9003547},{"index":0,"relevance_score":0.6807725}],"meta":{"api_version":{"version":"1"},"billed_units":{"search_units":1}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-length: + - '250' + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:32 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 2269bebe485f3f0672490152a0b327f0 + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '29' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_content.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_content.yaml new file mode 100644 index 00000000..5c153cb0 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_content.yaml @@ -0,0 +1,82 @@ +interactions: +- request: + body: '{"query": "What is the capital of the United States?", "documents": ["Carson + City is the capital city of the American state of Nevada. At the 2010 United + States Census, Carson City had a population of 55,274.", "The Commonwealth of + the Northern Mariana Islands is a group of islands in the Pacific Ocean that + are a political division controlled by the United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States Virgin + Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially as + the District of Columbia) is the capital of the United States. It is a federal + district. ", "Capital punishment (the death penalty) has existed in the United + States since before the United States was a country. As of 2017, capital punishment + is legal in 30 of the 50 states.", "North Dakota is a state in the United States. + 672,591 people lived in North Dakota in the year 2010. The capital and seat + of government is Bismarck."], "model": "rerank-multilingual-v2.0", "top_n": + 3}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1109' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/rerank + response: + body: + string: '{"id":"c995b490-c717-411c-8fd0-8bf993cd8382","results":[{"index":3,"relevance_score":0.9999989},{"index":2,"relevance_score":0.9003547},{"index":0,"relevance_score":0.6807725}],"meta":{"api_version":{"version":"1"},"billed_units":{"search_units":1}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-length: + - '250' + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:32 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 2269bebe485f3f0672490152a0b327f0 + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '29' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_no_content.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_no_content.yaml new file mode 100644 index 00000000..5c153cb0 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_rerank_with_events_with_no_content.yaml @@ -0,0 +1,82 @@ +interactions: +- request: + body: '{"query": "What is the capital of the United States?", "documents": ["Carson + City is the capital city of the American state of Nevada. At the 2010 United + States Census, Carson City had a population of 55,274.", "The Commonwealth of + the Northern Mariana Islands is a group of islands in the Pacific Ocean that + are a political division controlled by the United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States Virgin + Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially as + the District of Columbia) is the capital of the United States. It is a federal + district. ", "Capital punishment (the death penalty) has existed in the United + States since before the United States was a country. As of 2017, capital punishment + is legal in 30 of the 50 states.", "North Dakota is a state in the United States. + 672,591 people lived in North Dakota in the year 2010. The capital and seat + of government is Bismarck."], "model": "rerank-multilingual-v2.0", "top_n": + 3}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1109' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - python-httpx/0.27.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.5.3 + method: POST + uri: https://api.cohere.com/v1/rerank + response: + body: + string: '{"id":"c995b490-c717-411c-8fd0-8bf993cd8382","results":[{"index":3,"relevance_score":0.9999989},{"index":2,"relevance_score":0.9003547},{"index":0,"relevance_score":0.6807725}],"meta":{"api_version":{"version":"1"},"billed_units":{"search_units":1}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-length: + - '250' + content-type: + - application/json + date: + - Wed, 29 May 2024 08:41:32 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 UTC + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 2269bebe485f3f0672490152a0b327f0 + x-endpoint-monthly-call-limit: + - '1000' + x-envoy-upstream-service-time: + - '29' + x-trial-endpoint-call-limit: + - '40' + x-trial-endpoint-call-remaining: + - '39' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy.yaml new file mode 100644 index 00000000..34322354 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy.yaml @@ -0,0 +1,76 @@ +interactions: +- request: + body: '{"model": "rerank-english-v3.0", "query": "What is the capital of the United + States?", "documents": ["Carson City is the capital city of the American state + of Nevada. At the 2010 United States Census, Carson City had a population of + 55,274.", "The Commonwealth of the Northern Mariana Islands is a group of islands + in the Pacific Ocean that are a political division controlled by the United + States. Its capital is Saipan.", "Charlotte Amalie is the capital and largest + city of the United States Virgin Islands. It has about 20,000 people. The city + is on the island of Saint Thomas.", "Washington, D.C. (also known as simply + Washington or D.C., and officially as the District of Columbia) is the capital + of the United States. It is a federal district. ", "Capital punishment (the + death penalty) has existed in the United States since before the United States + was a country. As of 2017, capital punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived in North + Dakota in the year 2010. The capital and seat of government is Bismarck."], + "top_n": 3}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1104' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/rerank + response: + body: + string: '{"id":"26c7d7a0-ca6f-49b3-a685-1e44a732603d","results":[{"index":3,"relevance_score":0.999071},{"index":4,"relevance_score":0.7779754},{"index":1,"relevance_score":0.08882029}],"meta":{"api_version":{"version":"2"},"billed_units":{"search_units":1}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '250' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 03:08:05 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 67ff3eb8118c2ae80c643e001ecff172 + x-envoy-upstream-service-time: + - '44' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy_async.yaml b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy_async.yaml new file mode 100644 index 00000000..d2efd539 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/cassettes/test_rerank/test_cohere_v2_rerank_legacy_async.yaml @@ -0,0 +1,76 @@ +interactions: +- request: + body: '{"model": "rerank-english-v3.0", "query": "What is the capital of the United + States?", "documents": ["Carson City is the capital city of the American state + of Nevada. At the 2010 United States Census, Carson City had a population of + 55,274.", "The Commonwealth of the Northern Mariana Islands is a group of islands + in the Pacific Ocean that are a political division controlled by the United + States. Its capital is Saipan.", "Charlotte Amalie is the capital and largest + city of the United States Virgin Islands. It has about 20,000 people. The city + is on the island of Saint Thomas.", "Washington, D.C. (also known as simply + Washington or D.C., and officially as the District of Columbia) is the capital + of the United States. It is a federal district. ", "Capital punishment (the + death penalty) has existed in the United States since before the United States + was a country. As of 2017, capital punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived in North + Dakota in the year 2010. The capital and seat of government is Bismarck."], + "top_n": 3}' + headers: + accept: + - '*/*' + accept-encoding: + - gzip, deflate + connection: + - keep-alive + content-length: + - '1104' + content-type: + - application/json + host: + - api.cohere.com + user-agent: + - cohere/5.18.0 + x-fern-language: + - Python + x-fern-sdk-name: + - cohere + x-fern-sdk-version: + - 5.18.0 + method: POST + uri: https://api.cohere.com/v2/rerank + response: + body: + string: '{"id":"4a07fec0-e0d2-438d-a52a-986e465aa7bb","results":[{"index":3,"relevance_score":0.999071},{"index":4,"relevance_score":0.7779754},{"index":1,"relevance_score":0.08882029}],"meta":{"api_version":{"version":"2"},"billed_units":{"search_units":1}}}' + headers: + Alt-Svc: + - h3=":443"; ma=2592000,h3-29=":443"; ma=2592000 + Content-Length: + - '250' + Via: + - 1.1 google + access-control-expose-headers: + - X-Debug-Trace-ID + cache-control: + - no-cache, no-store, no-transform, must-revalidate, private, max-age=0 + content-type: + - application/json + date: + - Sun, 14 Sep 2025 03:08:05 GMT + expires: + - Thu, 01 Jan 1970 00:00:00 GMT + pragma: + - no-cache + server: + - envoy + vary: + - Origin + x-accel-expires: + - '0' + x-debug-trace-id: + - 7874a0d2c0ac809c78a02164b072f7f6 + x-envoy-upstream-service-time: + - '47' + status: + code: 200 + message: OK +version: 1 diff --git a/tests/test_instrumentations/test_cohere/conftest.py b/tests/test_instrumentations/test_cohere/conftest.py new file mode 100644 index 00000000..b831b633 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/conftest.py @@ -0,0 +1,117 @@ +"""Unit tests configuration module.""" + +import os + +import cohere +import pytest +from lmnr.opentelemetry_lib.opentelemetry.instrumentation.cohere import ( + CohereInstrumentor, +) +from lmnr.opentelemetry_lib.opentelemetry.instrumentation.cohere.utils import ( + DO_TRACE_CONTENT, +) +from opentelemetry.sdk._events import EventLoggerProvider +from opentelemetry.sdk._logs import LoggerProvider +from opentelemetry.sdk._logs.export import ( + InMemoryLogExporter, + SimpleLogRecordProcessor, +) +from opentelemetry.sdk.trace import TracerProvider +from opentelemetry.sdk.trace.export import SimpleSpanProcessor + + +@pytest.fixture(scope="function", name="tracer_provider") +def fixture_tracer_provider(span_exporter): + provider = TracerProvider() + provider.add_span_processor(SimpleSpanProcessor(span_exporter)) + return provider + + +@pytest.fixture(scope="function", name="log_exporter") +def fixture_log_exporter(): + exporter = InMemoryLogExporter() + yield exporter + + +@pytest.fixture(scope="function", name="event_logger_provider") +def fixture_event_logger_provider(log_exporter): + provider = LoggerProvider() + provider.add_log_record_processor(SimpleLogRecordProcessor(log_exporter)) + event_logger_provider = EventLoggerProvider(provider) + + return event_logger_provider + + +@pytest.fixture +def cohere_client(): + return cohere.Client(os.environ.get("COHERE_API_KEY")) + + +@pytest.fixture +def async_cohere_client(): + return cohere.AsyncClient(os.environ.get("COHERE_API_KEY")) + + +@pytest.fixture +def cohere_client_v2(): + return cohere.ClientV2(os.environ.get("COHERE_API_KEY")) + + +@pytest.fixture +def async_cohere_client_v2(): + return cohere.AsyncClientV2(os.environ.get("COHERE_API_KEY")) + + +@pytest.fixture(scope="function") +def instrument_legacy(tracer_provider): + instrumentor = CohereInstrumentor() + instrumentor.instrument( + tracer_provider=tracer_provider, + ) + + yield instrumentor + + instrumentor.uninstrument() + + +@pytest.fixture(scope="function") +def instrument_with_content(tracer_provider, event_logger_provider): + os.environ.update({DO_TRACE_CONTENT: "True"}) + + instrumentor = CohereInstrumentor(use_legacy_attributes=False) + instrumentor.instrument( + tracer_provider=tracer_provider, + event_logger_provider=event_logger_provider, + ) + + yield instrumentor + + os.environ.pop(DO_TRACE_CONTENT, None) + instrumentor.uninstrument() + + +@pytest.fixture(scope="function") +def instrument_with_no_content(tracer_provider, event_logger_provider): + os.environ.update({DO_TRACE_CONTENT: "False"}) + + instrumentor = CohereInstrumentor(use_legacy_attributes=False) + instrumentor.instrument( + tracer_provider=tracer_provider, + event_logger_provider=event_logger_provider, + ) + + yield instrumentor + + os.environ.pop(DO_TRACE_CONTENT, None) + instrumentor.uninstrument() + + +@pytest.fixture(autouse=True) +def environment(): + if "COHERE_API_KEY" not in os.environ: + os.environ["COHERE_API_KEY"] = "test_api_key" + + +@pytest.fixture(scope="module") +def vcr_config(): + return {"filter_headers": ["authorization"]} diff --git a/tests/test_instrumentations/test_cohere/test_chat.py b/tests/test_instrumentations/test_cohere/test_chat.py new file mode 100644 index 00000000..ecbe200b --- /dev/null +++ b/tests/test_instrumentations/test_cohere/test_chat.py @@ -0,0 +1,1032 @@ +import json +import pytest +from opentelemetry.sdk._logs import LogData +from opentelemetry.semconv._incubating.attributes import ( + event_attributes as EventAttributes, +) +from opentelemetry.semconv._incubating.attributes import ( + gen_ai_attributes as GenAIAttributes, +) +from opentelemetry.semconv_ai import SpanAttributes + + +TOOLS = [ + { + "type": "function", + "function": { + "name": "get_weather", + "description": "Get the current weather in a given location", + "parameters": { + "type": "object", + "properties": { + "location": { + "type": "string", + "description": "The city and state, e.g. San Francisco, CA" + } + }, + "required": ["location"] + } + } + }, + { + "type": "function", + "function": { + "name": "get_time", + "description": "Get the current time in a given location", + "parameters": { + "type": "object", + "properties": { + "location": { + "type": "string", + "description": "The city and state, e.g. San Francisco, CA" + } + }, + "required": ["location"] + } + } + } +] + + +@pytest.mark.vcr +def test_cohere_chat_legacy( + span_exporter, log_exporter, instrument_legacy, cohere_client +): + res = cohere_client.chat(model="command", message="Tell me a joke, pirate style") + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content") + == res.text + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 58 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "440f51f4-3e47-44b6-a5d7-5ba33edcfc58" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_v2_chat_legacy( + span_exporter, log_exporter, instrument_legacy, cohere_client_v2 +): + res = cohere_client_v2.chat( + model="command", messages=[{"role": "user", "content": "Tell me a joke, pirate style"}] + ) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + json.loads(cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [ + { + "type": "text", + "text": res.message.content[-1].text + } + ] + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 7 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "83e3e297-264b-478e-9b22-5058386292ed" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_chat_legacy_with_streaming( + span_exporter, log_exporter, instrument_legacy, cohere_client +): + stream = cohere_client.chat_stream(model="command", message="Tell me a joke, pirate style") + + res = "" + for chunk in stream: + if chunk.event_type == "text-generation": + res += chunk.text + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content") + == res + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 7 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "12c00d26-e3bb-48c0-8c49-262155b57d64" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_v2_chat_legacy_with_streaming( + span_exporter, log_exporter, instrument_legacy, cohere_client_v2 +): + stream = cohere_client_v2.chat_stream( + model="command", messages=[{"role": "user", "content": "Tell me a joke, pirate style"}] + ) + + res = "" + for chunk in stream: + if chunk.type == "content-delta": + res += chunk.delta.message.content.text + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + json.loads(cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [ + { + "type": "text", + "text": res, + "thinking": None + } + ] + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 7 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "6cd6ce61-bb3b-46f6-907e-fcfab45e51b6" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_v2_chat_legacy_with_tool_calls_and_history( + span_exporter, log_exporter, instrument_legacy, cohere_client_v2 +): + user_prompt = "What is the weather and current time in Tokyo?" + res1 = cohere_client_v2.chat( + model="command-r", + messages=[{"role": "user", "content": user_prompt}], + tools=TOOLS, + ) + res2 = cohere_client_v2.chat( + model="command-r", + messages=[ + {"role": "user", "content": user_prompt}, + { + "role": "assistant", + "content": res1.message.content, + "tool_calls": res1.message.tool_calls + }, + { + "role": "tool", + "tool_call_id": res1.message.tool_calls[0].id, + "content": "4:20 PM" + }, + { + "role": "tool", + "tool_call_id": res1.message.tool_calls[1].id, + "content": "Sunny 20 degrees Celsius" + }, + ], + tools=TOOLS, + ) + + spans = span_exporter.get_finished_spans() + assert len(spans) == 2 + sorted_spans = sorted(spans, key=lambda x: x.start_time) + span1 = sorted_spans[0] + span2 = sorted_spans[1] + assert span1.name == "cohere.chat" + assert span2.name == "cohere.chat" + assert span1.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert span2.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert span1.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert span2.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert span1.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command-r" + assert span2.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command-r" + + for span in [span1, span2]: + assert ( + span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == user_prompt + ) + assert span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.role") == "user" + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.name") + == TOOLS[0].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.description") + == TOOLS[0].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.parameters")) + == TOOLS[0].get("function").get("parameters") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.name") + == TOOLS[1].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.description") + == TOOLS[1].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.parameters")) + == TOOLS[1].get("function").get("parameters") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.parameters")) + == TOOLS[1].get("function").get("parameters") + ) + + assert ( + json.loads(span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [{ + "type": "text", + "text": res1.message.tool_plan + }] + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.role") + == "assistant" + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.id") + == res1.message.tool_calls[0].id + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.name") + == res1.message.tool_calls[0].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.arguments") + == res1.message.tool_calls[0].function.arguments + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.id") + == res1.message.tool_calls[1].id + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.name") + == res1.message.tool_calls[1].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.arguments") + == res1.message.tool_calls[1].function.arguments + ) + + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.name") + == res1.message.tool_calls[1].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.arguments") + == res1.message.tool_calls[1].function.arguments + ) + + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.id") + == res1.message.tool_calls[0].id + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.name") + == res1.message.tool_calls[0].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.arguments") + == res1.message.tool_calls[0].function.arguments + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.id") + == res1.message.tool_calls[1].id + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.name") + == res1.message.tool_calls[1].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.arguments") + == res1.message.tool_calls[1].function.arguments + ) + + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.1.content") == res1.message.content + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.1.role") == "assistant" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.2.content") == "4:20 PM" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.2.role") == "tool" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.3.content") == "Sunny 20 degrees Celsius" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.3.role") == "tool" + + assert span2.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.role") == "assistant" + assert json.loads(span2.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) == [{ + "type": "text", + "text": res2.message.content[-1].text + }] + + assert span1.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 62 + assert span1.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == span1.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + span1.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + span1.attributes.get("gen_ai.response.id") + == "965405bb-b9da-4dc5-b329-e708a795e188" + ) + assert span2.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 94 + assert span2.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == span2.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + span2.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + span2.attributes.get("gen_ai.response.id") + == "00f7ec58-cd22-4b62-b068-0e7ece6bbf67" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_v2_chat_legacy_with_tool_calls_and_streaming( + span_exporter, log_exporter, instrument_legacy, cohere_client_v2 +): + user_prompt = "What is the weather and current time in Tokyo?" + res1 = cohere_client_v2.chat_stream( + model="command-r", + messages=[{"role": "user", "content": user_prompt}], + tools=TOOLS, + ) + + plan = "" + for chunk in res1: + if chunk.type == "tool-plan-delta": + plan += chunk.delta.message.tool_plan + + spans = span_exporter.get_finished_spans() + assert len(spans) == 1 + span = spans[0] + assert span.name == "cohere.chat" + assert span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command-r" + + assert ( + span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == user_prompt + ) + assert span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.role") == "user" + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.name") + == TOOLS[0].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.description") + == TOOLS[0].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.parameters")) + == TOOLS[0].get("function").get("parameters") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.name") + == TOOLS[1].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.description") + == TOOLS[1].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.parameters")) + == TOOLS[1].get("function").get("parameters") + ) + + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [{ + "type": "text", + "text": plan + }] + ) + assert span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.role") == "assistant" + assert ( + span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.id") + == "get_time_dg5wwc00d8v5" + ) + assert span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.name") == "get_time" + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.arguments")) + == {"location": "Tokyo"} + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.id") + == "get_weather_bc8241gkqss5" + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.name") + == "get_weather" + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.arguments")) + == {"location": "Tokyo"} + ) + + assert span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 62 + assert span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + span.attributes.get("gen_ai.response.id") + == "e6d757a9-f0f3-40fe-9b8a-44cdc3bd18a7" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_chat_with_events_with_content( + span_exporter, log_exporter, instrument_with_content, cohere_client +): + user_message = "Tell me a joke, pirate style" + res = cohere_client.chat(model="command", message=user_message) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {"content": user_message}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "COMPLETE", + "message": {"content": res.text}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +def test_cohere_chat_with_events_with_no_content( + span_exporter, log_exporter, instrument_with_no_content, cohere_client +): + user_message = "Tell me a joke, pirate style" + cohere_client.chat(model="command", message=user_message) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "COMPLETE", + "message": {}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_chat_legacy_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client +): + res = await async_cohere_client.chat(model="command", message="Tell me a joke, pirate style") + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content") + == res.text + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 7 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "ea2d074c-4f25-47cb-bef8-b00dc2ae991b" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_chat_with_events_with_content_async( + span_exporter, log_exporter, instrument_with_content, async_cohere_client +): + user_message = "Tell me a joke, pirate style" + res = await async_cohere_client.chat(model="command", message=user_message) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {"content": user_message}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "COMPLETE", + "message": {"content": res.text}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_chat_with_events_with_no_content_async( + span_exporter, log_exporter, instrument_with_no_content, async_cohere_client +): + user_message = "Tell me a joke, pirate style" + await async_cohere_client.chat(model="command", message=user_message) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "COMPLETE", + "message": {}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_chat_legacy_with_streaming_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client +): + stream = async_cohere_client.chat_stream(model="command", message="Tell me a joke, pirate style") + + res = "" + async for chunk in stream: + if chunk.event_type == "text-generation": + res += chunk.text + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content") + == res + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 7 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "dcdb9a85-a8dc-4f4c-9779-f7c1801248f3" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_v2_chat_legacy_with_streaming_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client_v2 +): + stream = async_cohere_client_v2.chat_stream( + model="command", messages=[{"role": "user", "content": "Tell me a joke, pirate style"}] + ) + + res = "" + async for chunk in stream: + if chunk.type == "content-delta": + res += chunk.delta.message.content.text + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == "Tell me a joke, pirate style" + ) + assert ( + json.loads(cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [ + { + "type": "text", + "text": res, + "thinking": None + } + ] + ) + assert cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 7 + assert cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == cohere_span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + cohere_span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "599ae0aa-0ef6-49e4-b7f4-e2fafc40ca2c" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_v2_chat_legacy_with_tool_calls_and_history_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client_v2 +): + user_prompt = "What is the weather and current time in Tokyo?" + res1 = await async_cohere_client_v2.chat( + model="command-r7b-12-2024", + messages=[{"role": "user", "content": user_prompt}], + tools=TOOLS, + ) + res2 = await async_cohere_client_v2.chat( + model="command-r7b-12-2024", + messages=[ + {"role": "user", "content": user_prompt}, + { + "role": "assistant", + "content": res1.message.content, + "tool_calls": res1.message.tool_calls + }, + { + "role": "tool", + "tool_call_id": res1.message.tool_calls[0].id, + "content": "4:20 PM" + }, + { + "role": "tool", + "tool_call_id": res1.message.tool_calls[1].id, + "content": "Sunny 20 degrees Celsius" + }, + ], + tools=TOOLS, + ) + + spans = span_exporter.get_finished_spans() + assert len(spans) == 2 + sorted_spans = sorted(spans, key=lambda x: x.start_time) + span1 = sorted_spans[0] + span2 = sorted_spans[1] + assert span1.name == "cohere.chat" + assert span2.name == "cohere.chat" + assert span1.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert span2.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert span1.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert span2.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert span1.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command-r7b-12-2024" + assert span2.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command-r7b-12-2024" + + for span in [span1, span2]: + assert ( + span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == user_prompt + ) + assert span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.role") == "user" + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.name") + == TOOLS[0].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.description") + == TOOLS[0].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.parameters")) + == TOOLS[0].get("function").get("parameters") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.name") + == TOOLS[1].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.description") + == TOOLS[1].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.parameters")) + == TOOLS[1].get("function").get("parameters") + ) + + assert ( + json.loads(span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [{ + "type": "text", + "text": res1.message.tool_plan + }] + ) + assert span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.role") == "assistant" + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.id") + == res1.message.tool_calls[0].id + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.name") + == res1.message.tool_calls[0].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.arguments") + == res1.message.tool_calls[0].function.arguments + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.id") + == res1.message.tool_calls[1].id + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.name") + == res1.message.tool_calls[1].function.name + ) + assert ( + span1.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.arguments") + == res1.message.tool_calls[1].function.arguments + ) + + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.1.content") == res1.message.content + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.1.role") == "assistant" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.2.content") == "4:20 PM" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.2.role") == "tool" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.3.content") == "Sunny 20 degrees Celsius" + assert span2.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.3.role") == "tool" + + assert span2.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.role") == "assistant" + assert json.loads(span2.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) == [{ + "type": "text", + "text": res2.message.content[-1].text + }] + + assert span1.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 62 + assert span1.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == span1.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + span1.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + span1.attributes.get("gen_ai.response.id") + == "b7391518-e53e-4486-98ea-fabffcde31c2" + ) + assert span2.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 78 + assert span2.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == span2.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + span2.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + span2.attributes.get("gen_ai.response.id") + == "8289d4ee-a83b-4ce2-b7e1-245d9778fcf5" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_v2_chat_legacy_with_tool_calls_and_streaming_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client_v2 +): + user_prompt = "What is the weather and current time in Tokyo?" + res1 = async_cohere_client_v2.chat_stream( + model="command-r", + messages=[{"role": "user", "content": user_prompt}], + tools=TOOLS, + ) + + plan = "" + async for chunk in res1: + if chunk.type == "tool-plan-delta": + plan += chunk.delta.message.tool_plan + + spans = span_exporter.get_finished_spans() + assert len(spans) == 1 + span = spans[0] + assert span.name == "cohere.chat" + assert span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "chat" + assert span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command-r" + + assert ( + span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content") + == user_prompt + ) + assert span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.role") == "user" + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.name") + == TOOLS[0].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.description") + == TOOLS[0].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.0.parameters")) + == TOOLS[0].get("function").get("parameters") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.name") + == TOOLS[1].get("function").get("name") + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.description") + == TOOLS[1].get("function").get("description") + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_REQUEST_FUNCTIONS}.1.parameters")) + == TOOLS[1].get("function").get("parameters") + ) + + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content")) + == [{ + "type": "text", + "text": plan + }] + ) + assert span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.role") == "assistant" + assert ( + span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.id") + == "get_time_mp1131yrhbga" + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.name") + == "get_time" + ) + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.0.arguments")) + == {"location": "Tokyo"} + ) + assert ( + span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.id") + == "get_weather_yxz1xx2m07cn" + ) + assert span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.name") == "get_weather" + assert ( + json.loads(span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.tool_calls.1.arguments")) + == {"location": "Tokyo"} + ) + + assert span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) == 62 + assert span.attributes.get( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS + ) == span.attributes.get( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS + ) + span.attributes.get(SpanAttributes.LLM_USAGE_PROMPT_TOKENS) + assert ( + span.attributes.get("gen_ai.response.id") + == "ce257b09-c6da-4aed-b722-6384504180f5" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +def assert_message_in_logs(log: LogData, event_name: str, expected_content: dict): + assert log.log_record.attributes.get(EventAttributes.EVENT_NAME) == event_name + assert ( + log.log_record.attributes.get(GenAIAttributes.GEN_AI_SYSTEM) + == GenAIAttributes.GenAiSystemValues.COHERE.value + ) + + if not expected_content: + assert not log.log_record.body + else: + assert log.log_record.body + assert dict(log.log_record.body) == expected_content diff --git a/tests/test_instrumentations/test_cohere/test_completion.py b/tests/test_instrumentations/test_cohere/test_completion.py new file mode 100644 index 00000000..622ec31b --- /dev/null +++ b/tests/test_instrumentations/test_cohere/test_completion.py @@ -0,0 +1,111 @@ +import pytest +from opentelemetry.sdk._logs import LogData +from opentelemetry.semconv._incubating.attributes import ( + event_attributes as EventAttributes, +) +from opentelemetry.semconv._incubating.attributes import ( + gen_ai_attributes as GenAIAttributes, +) +from opentelemetry.semconv_ai import SpanAttributes + + +@pytest.mark.vcr +def test_cohere_completion_legacy( + span_exporter, log_exporter, instrument_legacy, cohere_client +): + res = cohere_client.generate(model="command", prompt="Tell me a joke, pirate style") + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.completion" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "completion" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.0.content") + == res.generations[0].text + ) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "64c671fc-c536-41fc-adbd-5f7c81177371" + ) + assert ( + cohere_span.attributes.get("gen_ai.response.0.id") + == "13255d0a-eef8-47fc-91f7-d2607d228fbf" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_completion_with_events_with_content( + span_exporter, log_exporter, instrument_with_content, cohere_client +): + user_message = "Tell me a joke, pirate style" + res = cohere_client.generate(model="command", prompt=user_message) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.completion" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "completion" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {"content": user_message}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "COMPLETE", + "message": {"content": res.generations[0].text}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +def test_cohere_completion_with_events_with_no_content( + span_exporter, log_exporter, instrument_with_no_content, cohere_client +): + cohere_client.generate(model="command", prompt="Tell me a joke, pirate style") + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.completion" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "completion" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) == "command" + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "COMPLETE", + "message": {}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +def assert_message_in_logs(log: LogData, event_name: str, expected_content: dict): + assert log.log_record.attributes.get(EventAttributes.EVENT_NAME) == event_name + assert ( + log.log_record.attributes.get(GenAIAttributes.GEN_AI_SYSTEM) + == GenAIAttributes.GenAiSystemValues.COHERE.value + ) + + if not expected_content: + assert not log.log_record.body + else: + assert log.log_record.body + assert dict(log.log_record.body) == expected_content diff --git a/tests/test_instrumentations/test_cohere/test_embed.py b/tests/test_instrumentations/test_cohere/test_embed.py new file mode 100644 index 00000000..ecf48875 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/test_embed.py @@ -0,0 +1,120 @@ +import json +import pytest +from opentelemetry.semconv_ai import SpanAttributes + + +@pytest.mark.vcr +def test_cohere_v2_embed_legacy( + span_exporter, log_exporter, instrument_legacy, cohere_client_v2 +): + texts = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + cohere_client_v2.embed( + input_type="search_document", + texts=texts, model="embed-english-light-v3.0" + ) + + spans = span_exporter.get_finished_spans() + assert len(spans) == 1 + cohere_span = spans[0] + assert cohere_span.name == "cohere.embed" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "embedding" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "embed-english-light-v3.0" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.0.role" + ) + == "user" + ) + assert json.loads(cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content")) == [{ + "type": "text", + "text": text + } for text in texts] + + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "74d7aae4-2939-4002-b4d4-352dfcca03cf" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_v2_embed_legacy_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client_v2 +): + texts = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + await async_cohere_client_v2.embed( + input_type="search_document", + texts=texts, model="embed-english-light-v3.0" + ) + + spans = span_exporter.get_finished_spans() + assert len(spans) == 1 + cohere_span = spans[0] + assert cohere_span.name == "cohere.embed" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "embedding" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "embed-english-light-v3.0" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.0.role" + ) + == "user" + ) + assert json.loads(cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.0.content")) == [{ + "type": "text", + "text": text + } for text in texts] + + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "3bc87f83-0534-4478-af7d-fee196c92758" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" diff --git a/tests/test_instrumentations/test_cohere/test_rerank.py b/tests/test_instrumentations/test_cohere/test_rerank.py new file mode 100644 index 00000000..c6fb0d42 --- /dev/null +++ b/tests/test_instrumentations/test_cohere/test_rerank.py @@ -0,0 +1,379 @@ +import pytest +from opentelemetry.sdk._logs import LogData +from opentelemetry.semconv._incubating.attributes import ( + event_attributes as EventAttributes, +) +from opentelemetry.semconv._incubating.attributes import ( + gen_ai_attributes as GenAIAttributes, +) +from opentelemetry.semconv_ai import SpanAttributes + + +@pytest.mark.vcr +def test_cohere_rerank_legacy( + span_exporter, log_exporter, instrument_legacy, cohere_client +): + query = "What is the capital of the United States?" + documents = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + response = cohere_client.rerank( + query=query, documents=documents, top_n=3, model="rerank-multilingual-v2.0" + ) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.rerank" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "rerank" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "rerank-multilingual-v2.0" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.{len(documents)}.role" + ) + == "user" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.{len(documents)}.content" + ) + == query + ) + + for i, doc in enumerate(documents): + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.{i}.role") + == "system" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.{i}.content") + == doc + ) + + for idx, result in enumerate(response.results): + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.{idx}.role") + == "assistant" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_COMPLETIONS}.{idx}.content" + ) + == f"Doc {result.index}, Score: {result.relevance_score}" + ) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "c995b490-c717-411c-8fd0-8bf993cd8382" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +def test_cohere_rerank_with_events_with_content( + span_exporter, log_exporter, instrument_with_content, cohere_client +): + query = "What is the capital of the United States?" + documents = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + response = cohere_client.rerank( + query=query, documents=documents, top_n=3, model="rerank-multilingual-v2.0" + ) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.rerank" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "rerank" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "rerank-multilingual-v2.0" + ) + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs( + logs[0], + "gen_ai.user.message", + {"content": {"query": query, "documents": documents}}, + ) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "unknown", + "message": { + "content": [ + { + "index": result.index, + "document": result.document, + "relevance_score": result.relevance_score, + } + for result in response.results + ] + }, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +def test_cohere_rerank_with_events_with_no_content( + span_exporter, log_exporter, instrument_with_no_content, cohere_client +): + query = "What is the capital of the United States?" + documents = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + cohere_client.rerank( + query=query, documents=documents, top_n=3, model="rerank-multilingual-v2.0" + ) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.rerank" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "rerank" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "rerank-multilingual-v2.0" + ) + + logs = log_exporter.get_finished_logs() + assert len(logs) == 2 + + # Validate user message Event + assert_message_in_logs(logs[0], "gen_ai.user.message", {}) + + # Validate model response Event + choice_event = { + "index": 0, + "finish_reason": "unknown", + "message": {}, + } + assert_message_in_logs(logs[1], "gen_ai.choice", choice_event) + + +@pytest.mark.vcr +def test_cohere_v2_rerank_legacy( + span_exporter, log_exporter, instrument_legacy, cohere_client_v2 +): + query = "What is the capital of the United States?" + documents = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + response = cohere_client_v2.rerank( + query=query, documents=documents, top_n=3, model="rerank-english-v3.0" + ) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.rerank" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "rerank" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "rerank-english-v3.0" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.{len(documents)}.role" + ) + == "user" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.{len(documents)}.content" + ) + == query + ) + + for i, doc in enumerate(documents): + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.{i}.role") + == "system" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.{i}.content") + == doc + ) + + for idx, result in enumerate(response.results): + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.{idx}.role") + == "assistant" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_COMPLETIONS}.{idx}.content" + ) + == f"Doc {result.index}, Score: {result.relevance_score}" + ) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "26c7d7a0-ca6f-49b3-a685-1e44a732603d" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +@pytest.mark.vcr +@pytest.mark.asyncio +async def test_cohere_v2_rerank_legacy_async( + span_exporter, log_exporter, instrument_legacy, async_cohere_client_v2 +): + query = "What is the capital of the United States?" + documents = [ + "Carson City is the capital city of the American state of Nevada." + + " At the 2010 United States Census, Carson City had a population of 55,274.", + "The Commonwealth of the Northern Mariana Islands is a group of islands" + + " in the Pacific Ocean that are a political division controlled by the " + + "United States. Its capital is Saipan.", + "Charlotte Amalie is the capital and largest city of the United States " + + "Virgin Islands. It has about 20,000 people. The city is on the island of Saint Thomas.", + "Washington, D.C. (also known as simply Washington or D.C., and officially " + + "as the District of Columbia) is the capital of the United States. It is a federal district. ", + "Capital punishment (the death penalty) has existed in the United States " + + "since before the United States was a country. As of 2017, capital " + + "punishment is legal in 30 of the 50 states.", + "North Dakota is a state in the United States. 672,591 people lived" + + " in North Dakota in the year 2010. The capital and seat of government is Bismarck.", + ] + + response = await async_cohere_client_v2.rerank( + query=query, documents=documents, top_n=3, model="rerank-english-v3.0" + ) + + spans = span_exporter.get_finished_spans() + cohere_span = spans[0] + assert cohere_span.name == "cohere.rerank" + assert cohere_span.attributes.get(SpanAttributes.LLM_SYSTEM) == "Cohere" + assert cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_TYPE) == "rerank" + assert ( + cohere_span.attributes.get(SpanAttributes.LLM_REQUEST_MODEL) + == "rerank-english-v3.0" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.{len(documents)}.role" + ) + == "user" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_PROMPTS}.{len(documents)}.content" + ) + == query + ) + + for i, doc in enumerate(documents): + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.{i}.role") + == "system" + ) + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_PROMPTS}.{i}.content") + == doc + ) + + for idx, result in enumerate(response.results): + assert ( + cohere_span.attributes.get(f"{SpanAttributes.LLM_COMPLETIONS}.{idx}.role") + == "assistant" + ) + assert ( + cohere_span.attributes.get( + f"{SpanAttributes.LLM_COMPLETIONS}.{idx}.content" + ) + == f"Doc {result.index}, Score: {result.relevance_score}" + ) + assert ( + cohere_span.attributes.get("gen_ai.response.id") + == "4a07fec0-e0d2-438d-a52a-986e465aa7bb" + ) + + logs = log_exporter.get_finished_logs() + assert ( + len(logs) == 0 + ), "Assert that it doesn't emit logs when use_legacy_attributes is True" + + +def assert_message_in_logs(log: LogData, event_name: str, expected_content: dict): + assert log.log_record.attributes.get(EventAttributes.EVENT_NAME) == event_name + assert ( + log.log_record.attributes.get(GenAIAttributes.GEN_AI_SYSTEM) + == GenAIAttributes.GenAiSystemValues.COHERE.value + ) + + if not expected_content: + assert not log.log_record.body + else: + assert log.log_record.body + assert dict(log.log_record.body) == expected_content From 36ff0d7d827c459608899bf5b4a8a9a83428332d Mon Sep 17 00:00:00 2001 From: Din Date: Sun, 14 Sep 2025 04:56:02 +0100 Subject: [PATCH 2/6] copy default message --- .../opentelemetry/instrumentation/cohere/streaming.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py index 4c7426e9..12048cce 100644 --- a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py @@ -162,9 +162,9 @@ def _accumulate_stream_item( ): item_dict = to_dict(item) if item_dict.get("type") == "message-start": - final_response["message"] = (item_dict.get("delta") or {}).get( - "message" - ) or DEFAULT_MESSAGE + final_response["message"] = (item_dict.get("delta") or {}).get("message") or { + **DEFAULT_MESSAGE + } final_response["id"] = item_dict.get("id") elif item_dict.get("type") == "content-start": new_content_item = ((item_dict.get("delta") or {}).get("message") or {}).get( From f89e998a588494d90040f38ae647f3096d9bb6b4 Mon Sep 17 00:00:00 2001 From: Din Date: Sun, 14 Sep 2025 11:54:24 +0100 Subject: [PATCH 3/6] tmp cohere instrumentor --- pyproject.toml | 4 +--- src/lmnr/version.py | 2 +- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index ae7c8f36..8a951cf8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -6,7 +6,7 @@ [project] name = "lmnr" -version = "0.7.12" +version = "0.7.13" description = "Python SDK for Laminar" authors = [ { name = "lmnr.ai", email = "founders@lmnr.ai" } @@ -65,7 +65,6 @@ lmnr = "lmnr.cli:cli" alephalpha=["opentelemetry-instrumentation-alephalpha>=0.46.2"] bedrock=["opentelemetry-instrumentation-bedrock>=0.46.2"] chromadb=["opentelemetry-instrumentation-chromadb>=0.46.2"] -cohere=["opentelemetry-instrumentation-cohere>=0.46.2"] crewai=["opentelemetry-instrumentation-crewai>=0.46.2"] haystack=["opentelemetry-instrumentation-haystack>=0.46.2"] lancedb=["opentelemetry-instrumentation-lancedb>=0.46.2"] @@ -93,7 +92,6 @@ all = [ "opentelemetry-instrumentation-alephalpha>=0.46.2", "opentelemetry-instrumentation-bedrock>=0.46.2", "opentelemetry-instrumentation-chromadb>=0.46.2", - "opentelemetry-instrumentation-cohere>=0.46.2", "opentelemetry-instrumentation-crewai>=0.46.2", "opentelemetry-instrumentation-haystack>=0.46.2", "opentelemetry-instrumentation-lancedb>=0.46.2", diff --git a/src/lmnr/version.py b/src/lmnr/version.py index 74ec4443..ca6f69c3 100644 --- a/src/lmnr/version.py +++ b/src/lmnr/version.py @@ -3,7 +3,7 @@ from packaging import version -__version__ = "0.7.12" +__version__ = "0.7.13" PYTHON_VERSION = f"{sys.version_info.major}.{sys.version_info.minor}" From 68b51c96e2bf5f4b7c914dcd55716e89c093c4cf Mon Sep 17 00:00:00 2001 From: Din Date: Sun, 14 Sep 2025 12:03:58 +0100 Subject: [PATCH 4/6] initialize instrumentor locally --- src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py b/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py index f6c78da1..f6de297c 100644 --- a/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py +++ b/src/lmnr/opentelemetry_lib/tracing/_instrument_initializers.py @@ -122,8 +122,6 @@ class CohereInstrumentorInitializer(InstrumentorInitializer): def init_instrumentor(self, *args, **kwargs) -> BaseInstrumentor | None: if not is_package_installed("cohere"): return None - if not is_package_installed("opentelemetry-instrumentation-cohere"): - return None from ..opentelemetry.instrumentation.cohere import CohereInstrumentor From 7870fc49f0db7e160bb54ac7ec551090dace8c6a Mon Sep 17 00:00:00 2001 From: Din Date: Sun, 14 Sep 2025 12:06:48 +0100 Subject: [PATCH 5/6] fixes --- .../instrumentation/cohere/__init__.py | 80 +++++++++++-------- 1 file changed, 45 insertions(+), 35 deletions(-) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py index 4795574f..4995a585 100644 --- a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/__init__.py @@ -23,6 +23,7 @@ aprocess_chat_v2_streaming_response, ) from .utils import dont_throw, should_emit_events +from lmnr.opentelemetry_lib.tracing.context import get_current_context from lmnr.version import __version__ from opentelemetry.instrumentation.instrumentor import BaseInstrumentor from opentelemetry.instrumentation.utils import ( @@ -232,30 +233,33 @@ def _wrap( SpanAttributes.LLM_SYSTEM: "Cohere", SpanAttributes.LLM_REQUEST_TYPE: llm_request_type.value, }, + context=get_current_context(), ) with use_span(span, end_on_exit=False): - set_span_request_attributes(span, kwargs) - _handle_input_content(span, event_logger, llm_request_type, kwargs) - try: - response = wrapped(*args, **kwargs) - except Exception as e: - if span.is_recording(): - span.set_status(Status(StatusCode.ERROR, str(e))) - span.record_exception(e) - span.end() - raise - - if to_wrap.get("stream_process_func"): - return to_wrap.get("stream_process_func")( - span, event_logger, llm_request_type, response - ) + set_span_request_attributes(span, kwargs) + _handle_input_content(span, event_logger, llm_request_type, kwargs) + + try: + response = wrapped(*args, **kwargs) + except Exception as e: + if span.is_recording(): + span.set_status(Status(StatusCode.ERROR, str(e))) + span.record_exception(e) + span.end() + raise + + if to_wrap.get("stream_process_func"): + return to_wrap.get("stream_process_func")( + span, event_logger, llm_request_type, response + ) - set_span_response_attributes(span, response) - _handle_response_content(span, event_logger, llm_request_type, response) - span.end() - return response + set_span_response_attributes(span, response) + _handle_response_content(span, event_logger, llm_request_type, response) + return response + finally: + span.end() @_with_tracer_wrapper @@ -276,30 +280,36 @@ async def _awrap( name = to_wrap.get("span_name") llm_request_type = _llm_request_type_by_method(to_wrap.get("method")) - with tracer.start_as_current_span( + span = tracer.start_span( name, kind=SpanKind.CLIENT, attributes={ SpanAttributes.LLM_SYSTEM: "Cohere", SpanAttributes.LLM_REQUEST_TYPE: llm_request_type.value, }, - ) as span: - set_span_request_attributes(span, kwargs) - _handle_input_content(span, event_logger, llm_request_type, kwargs) + context=get_current_context(), + ) + with use_span(span): try: - response = await wrapped(*args, **kwargs) - except Exception as e: - if span.is_recording(): - span.set_status(Status(StatusCode.ERROR, str(e))) - span.record_exception(e) - span.end() - raise - - set_span_response_attributes(span, response) - _handle_response_content(span, event_logger, llm_request_type, response) - - return response + set_span_request_attributes(span, kwargs) + _handle_input_content(span, event_logger, llm_request_type, kwargs) + + try: + response = await wrapped(*args, **kwargs) + except Exception as e: + if span.is_recording(): + span.set_status(Status(StatusCode.ERROR, str(e))) + span.record_exception(e) + span.end() + raise + + set_span_response_attributes(span, response) + _handle_response_content(span, event_logger, llm_request_type, response) + + return response + finally: + span.end() class CohereInstrumentor(BaseInstrumentor): From 44c847afbabc435c8f6840fb4f7b0586558a18ab Mon Sep 17 00:00:00 2001 From: Din Date: Sun, 14 Sep 2025 12:08:05 +0100 Subject: [PATCH 6/6] fixes --- .../instrumentation/cohere/streaming.py | 44 ++++++++++--------- 1 file changed, 23 insertions(+), 21 deletions(-) diff --git a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py index 12048cce..76ca9e40 100644 --- a/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py +++ b/src/lmnr/opentelemetry_lib/opentelemetry/instrumentation/cohere/streaming.py @@ -132,27 +132,29 @@ async def aprocess_chat_v2_streaming_response( "type": "function", "function": {"name": "", "arguments": "", "description": ""}, } - async for item in response: - span.add_event(name=f"{SpanAttributes.LLM_CONTENT_COMPLETION_CHUNK}") - item_to_yield = item - try: - _accumulate_stream_item( - item, current_content_item, current_tool_call_item, final_response - ) - except Exception: - pass - yield item_to_yield - - set_span_response_attributes(span, final_response) - if should_emit_events(): - emit_response_events(event_logger, llm_request_type, final_response) - elif should_send_prompts(): - _set_span_chat_response(span, final_response) - if final_response.get("error"): - span.set_status(Status(StatusCode.ERROR, final_response.get("error"))) - span.record_exception(final_response.get("error")) - else: - span.set_status(Status(StatusCode.OK)) + try: + async for item in response: + span.add_event(name=f"{SpanAttributes.LLM_CONTENT_COMPLETION_CHUNK}") + item_to_yield = item + try: + _accumulate_stream_item( + item, current_content_item, current_tool_call_item, final_response + ) + except Exception: + pass + yield item_to_yield + + set_span_response_attributes(span, final_response) + if should_emit_events(): + emit_response_events(event_logger, llm_request_type, final_response) + elif should_send_prompts(): + _set_span_chat_response(span, final_response) + if final_response.get("error"): + span.set_status(Status(StatusCode.ERROR, final_response.get("error"))) + span.record_exception(final_response.get("error")) + else: + span.set_status(Status(StatusCode.OK)) + finally: span.end()