mirror of
https://github.com/tiennm99/litellm.git
synced 2026-07-19 22:19:07 +00:00
Merge pull request #18938 from BerriAI/litellm_fix_generate_two_telemetry
[fix] generate two telemetry in responses
This commit is contained in:
@@ -1853,6 +1853,14 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
cache_hit=cache_hit,
|
||||
standard_logging_object=kwargs.get("standard_logging_object", None),
|
||||
)
|
||||
litellm_params = self.model_call_details.get("litellm_params", {})
|
||||
is_sync_request = (
|
||||
litellm_params.get(CallTypes.acompletion.value, False) is not True
|
||||
and litellm_params.get(CallTypes.aresponses.value, False) is not True
|
||||
and litellm_params.get(CallTypes.aembedding.value, False) is not True
|
||||
and litellm_params.get(CallTypes.aimage_generation.value, False) is not True
|
||||
and litellm_params.get(CallTypes.atranscription.value, False) is not True
|
||||
)
|
||||
try:
|
||||
## BUILD COMPLETE STREAMED RESPONSE
|
||||
complete_streaming_response: Optional[
|
||||
@@ -1915,7 +1923,6 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
self.has_run_logging(event_type="sync_success")
|
||||
for callback in callbacks:
|
||||
try:
|
||||
litellm_params = self.model_call_details.get("litellm_params", {})
|
||||
should_run = self.should_run_callback(
|
||||
callback=callback,
|
||||
litellm_params=litellm_params,
|
||||
@@ -2185,22 +2192,7 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
|
||||
if (
|
||||
callback == "openmeter"
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"acompletion", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aembedding", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aimage_generation", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"atranscription", False
|
||||
)
|
||||
is not True
|
||||
and is_sync_request
|
||||
):
|
||||
global openMeterLogger
|
||||
if openMeterLogger is None:
|
||||
@@ -2229,22 +2221,7 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
)
|
||||
if (
|
||||
isinstance(callback, CustomLogger)
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"acompletion", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aembedding", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aimage_generation", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"atranscription", False
|
||||
)
|
||||
is not True
|
||||
and is_sync_request
|
||||
and self.call_type
|
||||
!= CallTypes.pass_through.value # pass-through endpoints call async_log_success_event
|
||||
): # custom logger class
|
||||
@@ -2272,22 +2249,7 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
)
|
||||
if (
|
||||
callable(callback) is True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"acompletion", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aembedding", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aimage_generation", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"atranscription", False
|
||||
)
|
||||
is not True
|
||||
and is_sync_request
|
||||
and customLogger is not None
|
||||
): # custom logger functions
|
||||
print_verbose(
|
||||
@@ -2737,6 +2699,15 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
event_type="sync_failure"
|
||||
): # prevent double logging
|
||||
return
|
||||
litellm_params = self.model_call_details.get("litellm_params", {})
|
||||
is_sync_request = (
|
||||
litellm_params.get(CallTypes.acompletion.value, False) is not True
|
||||
and litellm_params.get(CallTypes.aresponses.value, False) is not True
|
||||
and litellm_params.get(CallTypes.aembedding.value, False) is not True
|
||||
and litellm_params.get(CallTypes.aimage_generation.value, False) is not True
|
||||
and litellm_params.get(CallTypes.atranscription.value, False) is not True
|
||||
)
|
||||
|
||||
try:
|
||||
start_time, end_time = self._failure_handler_helper_fn(
|
||||
exception=exception,
|
||||
@@ -2762,7 +2733,6 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
self.has_run_logging(event_type="sync_failure")
|
||||
for callback in callbacks:
|
||||
try:
|
||||
litellm_params = self.model_call_details.get("litellm_params", {})
|
||||
should_run = self.should_run_callback(
|
||||
callback=callback,
|
||||
litellm_params=litellm_params,
|
||||
@@ -2830,14 +2800,7 @@ class Logging(LiteLLMLoggingBaseClass):
|
||||
)
|
||||
if (
|
||||
isinstance(callback, CustomLogger)
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"acompletion", False
|
||||
)
|
||||
is not True
|
||||
and self.model_call_details.get("litellm_params", {}).get(
|
||||
"aembedding", False
|
||||
)
|
||||
is not True
|
||||
and is_sync_request
|
||||
): # custom logger class
|
||||
callback.log_failure_event(
|
||||
start_time=start_time,
|
||||
|
||||
@@ -668,6 +668,7 @@ def responses(
|
||||
optional_params=dict(responses_api_request_params),
|
||||
litellm_params={
|
||||
**responses_api_request_params,
|
||||
"aresponses": _is_async,
|
||||
"litellm_call_id": litellm_call_id,
|
||||
"metadata": metadata,
|
||||
},
|
||||
|
||||
@@ -14,6 +14,7 @@ import time
|
||||
from litellm.constants import SENTRY_DENYLIST, SENTRY_PII_DENYLIST
|
||||
from litellm.litellm_core_utils.litellm_logging import Logging as LitellmLogging
|
||||
from litellm.litellm_core_utils.litellm_logging import set_callbacks
|
||||
from litellm.types.utils import ModelResponse
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@@ -277,6 +278,87 @@ async def test_logging_non_streaming_request():
|
||||
litellm.callbacks = original_callbacks
|
||||
|
||||
|
||||
@pytest.mark.parametrize("async_flag", ["acompletion", "aresponses"])
|
||||
def test_success_handler_skips_sync_callbacks_for_async_requests(logging_obj, async_flag):
|
||||
"""Ensure sync success callbacks are skipped when async call type flags are set."""
|
||||
from litellm.integrations.custom_logger import CustomLogger
|
||||
|
||||
class DummyLogger(CustomLogger):
|
||||
pass
|
||||
|
||||
logging_obj.stream = False # simulate non-streaming request where sync callbacks would normally run
|
||||
logging_obj.model_call_details["litellm_params"] = {async_flag: True}
|
||||
logging_obj.litellm_params = logging_obj.model_call_details["litellm_params"]
|
||||
|
||||
dummy_logger = DummyLogger()
|
||||
dummy_logger.log_success_event = MagicMock()
|
||||
dummy_logger.log_stream_event = MagicMock()
|
||||
|
||||
model_response = ModelResponse(
|
||||
id="resp-123",
|
||||
model="gpt-4o-mini",
|
||||
choices=[
|
||||
{
|
||||
"message": {"role": "assistant", "content": "hello"},
|
||||
"finish_reason": "stop",
|
||||
"index": 0,
|
||||
}
|
||||
],
|
||||
usage={"prompt_tokens": 1, "completion_tokens": 1, "total_tokens": 2},
|
||||
)
|
||||
|
||||
with patch.object(
|
||||
logging_obj,
|
||||
"get_combined_callback_list",
|
||||
return_value=[dummy_logger],
|
||||
):
|
||||
logging_obj.success_handler(result=model_response)
|
||||
|
||||
dummy_logger.log_success_event.assert_not_called()
|
||||
dummy_logger.log_stream_event.assert_not_called()
|
||||
|
||||
|
||||
@pytest.mark.parametrize("call_type", ["completion", "responses"])
|
||||
def test_success_handler_runs_sync_callbacks_for_sync_requests(logging_obj, call_type):
|
||||
"""Ensure sync success callbacks execute when call type is sync (completion/responses)."""
|
||||
from litellm.integrations.custom_logger import CustomLogger
|
||||
|
||||
class DummyLogger(CustomLogger):
|
||||
pass
|
||||
|
||||
logging_obj.stream = False
|
||||
logging_obj.call_type = call_type
|
||||
logging_obj.model_call_details["litellm_params"] = {}
|
||||
logging_obj.litellm_params = {}
|
||||
|
||||
dummy_logger = DummyLogger()
|
||||
dummy_logger.log_success_event = MagicMock()
|
||||
dummy_logger.log_stream_event = MagicMock()
|
||||
|
||||
model_response = ModelResponse(
|
||||
id="resp-123",
|
||||
model="gpt-4o-mini",
|
||||
choices=[
|
||||
{
|
||||
"message": {"role": "assistant", "content": "hello"},
|
||||
"finish_reason": "stop",
|
||||
"index": 0,
|
||||
}
|
||||
],
|
||||
usage={"prompt_tokens": 1, "completion_tokens": 1, "total_tokens": 2},
|
||||
)
|
||||
|
||||
with patch.object(
|
||||
logging_obj,
|
||||
"get_combined_callback_list",
|
||||
return_value=[dummy_logger],
|
||||
):
|
||||
logging_obj.success_handler(result=model_response)
|
||||
|
||||
dummy_logger.log_success_event.assert_called_once()
|
||||
dummy_logger.log_stream_event.assert_not_called()
|
||||
|
||||
|
||||
def test_get_user_agent_tags():
|
||||
from litellm.litellm_core_utils.litellm_logging import StandardLoggingPayloadSetup
|
||||
|
||||
|
||||
Reference in New Issue
Block a user