from __future__ import annotations

import gc
import os
import time
from typing import Any, Dict, Optional
from unittest.mock import MagicMock, patch

import pytest
from inference.core.telemetry import record_inference


def codeflash_wrap(codeflash_wrapped, codeflash_test_module_name, codeflash_test_class_name, codeflash_test_name, codeflash_function_name, codeflash_line_id, codeflash_loop_index, *args, **kwargs):
    test_id = f'{codeflash_test_module_name}:{codeflash_test_class_name}:{codeflash_test_name}:{codeflash_line_id}:{codeflash_loop_index}'
    if not hasattr(codeflash_wrap, 'index'):
        codeflash_wrap.index = {}
    if test_id in codeflash_wrap.index:
        codeflash_wrap.index[test_id] += 1
    else:
        codeflash_wrap.index[test_id] = 0
    codeflash_test_index = codeflash_wrap.index[test_id]
    invocation_id = f'{codeflash_line_id}_{codeflash_test_index}'
    test_stdout_tag = f"{codeflash_test_module_name}:{(codeflash_test_class_name + '.' if codeflash_test_class_name else '')}{codeflash_test_name}:{codeflash_function_name}:{codeflash_loop_index}:{invocation_id}"
    print(f'!$######{test_stdout_tag}######$!')
    exception = None
    gc.disable()
    try:
        counter = time.perf_counter_ns()
        return_value = codeflash_wrapped(*args, **kwargs)
        codeflash_duration = time.perf_counter_ns() - counter
    except Exception as e:
        codeflash_duration = time.perf_counter_ns() - counter
        exception = e
    gc.enable()
    print(f'!######{test_stdout_tag}:{codeflash_duration}######!')
    if exception:
        raise exception
    return return_value

def test_record_inference_when_metrics_none():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test that record_inference returns early when _metrics is None.'
    from inference.core import telemetry
    original_metrics = telemetry._metrics
    telemetry._metrics = None
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_when_metrics_none', 'record_inference', '4_0', codeflash_loop_index, 'test-model', 1.5)
        codeflash_output = codeflash_return_value
        result = codeflash_output
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_empty_model_id():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with empty string model_id.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_empty_model_id', 'record_inference', '5_0', codeflash_loop_index, '', 0.5)
        mock_metrics['model_infer_count'].add.assert_called_once_with(1, {'model.id': ''})
        mock_metrics['model_infer_duration'].record.assert_called_once_with(0.5, {'model.id': ''})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_valid_inputs():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with valid model_id and duration.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        model_id = 'gpt-4'
        duration = 2.345
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_valid_inputs', 'record_inference', '5_2', codeflash_loop_index, model_id, duration)
        codeflash_output = codeflash_return_value
        result = codeflash_output
        mock_metrics['model_infer_count'].add.assert_called_once_with(1, {'model.id': model_id})
        mock_metrics['model_infer_duration'].record.assert_called_once_with(duration, {'model.id': model_id})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_zero_duration():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with zero duration.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_zero_duration', 'record_inference', '5_0', codeflash_loop_index, 'model-1', 0.0)
        mock_metrics['model_infer_count'].add.assert_called_once()
        mock_metrics['model_infer_duration'].record.assert_called_once_with(0.0, {'model.id': 'model-1'})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_negative_duration():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with negative duration.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_negative_duration', 'record_inference', '5_0', codeflash_loop_index, 'model-2', -1.5)
        mock_metrics['model_infer_duration'].record.assert_called_once_with(-1.5, {'model.id': 'model-2'})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_very_large_duration():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with very large duration value.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        large_duration = 999999999.999
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_very_large_duration', 'record_inference', '5_1', codeflash_loop_index, 'model-large', large_duration)
        mock_metrics['model_infer_duration'].record.assert_called_once_with(large_duration, {'model.id': 'model-large'})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_very_small_duration():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with very small duration value.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        small_duration = 0.0001
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_very_small_duration', 'record_inference', '5_1', codeflash_loop_index, 'model-small', small_duration)
        mock_metrics['model_infer_duration'].record.assert_called_once_with(small_duration, {'model.id': 'model-small'})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_long_model_id():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with a very long model_id string.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        long_model_id = 'model-' + 'x' * 1000
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_long_model_id', 'record_inference', '5_1', codeflash_loop_index, long_model_id, 1.0)
        mock_metrics['model_infer_count'].add.assert_called_once_with(1, {'model.id': long_model_id})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_special_characters_in_model_id():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with special characters in model_id.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        special_model_id = "model@#$%^&*()_-+=[]{}|;:',.<>?/~`"
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_special_characters_in_model_id', 'record_inference', '5_1', codeflash_loop_index, special_model_id, 1.5)
        mock_metrics['model_infer_count'].add.assert_called_once_with(1, {'model.id': special_model_id})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_unicode_model_id():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with unicode characters in model_id.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        unicode_model_id = 'model-日本語-العربية-🚀'
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_unicode_model_id', 'record_inference', '5_1', codeflash_loop_index, unicode_model_id, 1.0)
        mock_metrics['model_infer_count'].add.assert_called_once_with(1, {'model.id': unicode_model_id})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_multiple_calls():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test multiple consecutive calls to record_inference.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_multiple_calls', 'record_inference', '5_0', codeflash_loop_index, 'model-1', 1.0)
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_multiple_calls', 'record_inference', '5_1', codeflash_loop_index, 'model-2', 2.0)
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_multiple_calls', 'record_inference', '5_2', codeflash_loop_index, 'model-1', 1.5)
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_preserves_model_id_in_metadata():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test that model_id is correctly passed in metadata dictionary.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        model_id = 'test-model-123'
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_preserves_model_id_in_metadata', 'record_inference', '5_1', codeflash_loop_index, model_id, 1.5)
        call_args = mock_metrics['model_infer_count'].add.call_args
        metadata = call_args[0][1] if call_args[0] else call_args[1].get('model.id')
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_count_always_incremented_by_one():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test that count is always incremented by exactly 1.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_count_always_incremented_by_one', 'record_inference', '5_0', codeflash_loop_index, 'model', 0.1)
        call_args = mock_metrics['model_infer_count'].add.call_args
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_with_float_infinity():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with infinity duration.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_with_float_infinity', 'record_inference', '5_0', codeflash_loop_index, 'model', float('inf'))
        mock_metrics['model_infer_duration'].record.assert_called_once_with(float('inf'), {'model.id': 'model'})
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_state_isolation():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test that function correctly uses module-level _metrics variable.'
    from inference.core import telemetry
    original_metrics = telemetry._metrics
    try:
        telemetry._metrics = None
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_state_isolation', 'record_inference', '3_1', codeflash_loop_index, 'model', 1.0)
        mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
        telemetry._metrics = mock_metrics
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_state_isolation', 'record_inference', '3_4', codeflash_loop_index, 'model', 1.0)
        mock_metrics['model_infer_count'].add.assert_called_once()
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_return_value_always_none():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test that record_inference always returns None.'
    from inference.core import telemetry
    original_metrics = telemetry._metrics
    try:
        telemetry._metrics = None
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_return_value_always_none', 'record_inference', '3_1', codeflash_loop_index, 'model', 1.0)
        codeflash_output = codeflash_return_value
        mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
        telemetry._metrics = mock_metrics
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_return_value_always_none', 'record_inference', '3_5', codeflash_loop_index, 'model', 1.0)
        codeflash_output = codeflash_return_value
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_large_scale_many_models():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference with many different models (1000 calls).'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        for i in range(1000):
            model_id = f'model-{i}'
            duration = float(i) * 0.001
            codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_large_scale_many_models', 'record_inference', '5_0_2', codeflash_loop_index, model_id, duration)
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_large_scale_same_model():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Test record_inference called 1000 times with same model.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        for i in range(1000):
            codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_large_scale_same_model', 'record_inference', '5_0_0', codeflash_loop_index, 'same-model', 0.1 * i)
        for call in mock_metrics['model_infer_count'].add.call_args_list:
            pass
    finally:
        telemetry._metrics = original_metrics

def test_record_inference_large_model_id_stress():
    codeflash_loop_index = int(os.environ['CODEFLASH_LOOP_INDEX'])
    'Stress test with maximum length model IDs.'
    from inference.core import telemetry
    mock_metrics = {'model_infer_count': MagicMock(), 'model_infer_duration': MagicMock()}
    original_metrics = telemetry._metrics
    telemetry._metrics = mock_metrics
    try:
        very_long_id = 'x' * 10000
        codeflash_return_value = codeflash_wrap(telemetry.record_inference, 'tests.inference.unit_tests.test_record_inference__unit_test_1', None, 'test_record_inference_large_model_id_stress', 'record_inference', '5_1', codeflash_loop_index, very_long_id, 1.0)
        call_args = mock_metrics['model_infer_count'].add.call_args
    finally:
        telemetry._metrics = original_metrics