| import inspect |
| import time |
| from datetime import datetime |
| from functools import wraps |
| from typing import Any, Callable |
|
|
| import streamlit as st |
|
|
|
|
| def summarize_parameter_value(value: str, max_length: int = 100) -> str: |
| """Summarize parameter values that are too long or complex.""" |
| if not value: |
| return "" |
|
|
| |
| if "DataFrame" in value and "[" in value and "]" in value: |
| try: |
| dims = value[value.find("[") + 1 : value.find("]")] |
| return f"DataFrame[{dims}]" |
| except Exception: |
| return "DataFrame" |
|
|
| |
| if value.startswith(("[", "(", "{")): |
| try: |
| item_count = value.count(",") + 1 |
| return f"{value[:20]}... ({item_count} items)" |
| except Exception: |
| return f"{value[:20]}..." |
|
|
| |
| if len(value) > max_length: |
| return f"{value[:max_length]}..." |
|
|
| return value |
|
|
|
|
| def timer(include_params: bool = False) -> Callable: |
| """ |
| Decorator to time function execution and store results in session state. |
| |
| Args: |
| include_params: Whether to include function parameters in timing logs |
| """ |
|
|
| def decorator(func: Callable) -> Callable: |
| @wraps(func) |
| def wrapper(*args: Any, **kwargs: Any) -> Any: |
| if not st.session_state.get("ENABLE_TIMING", False): |
| return func(*args, **kwargs) |
|
|
| start = time.perf_counter() |
| result = func(*args, **kwargs) |
| end = time.perf_counter() |
| duration = end - start |
|
|
| |
| if "timing_stats" not in st.session_state: |
| st.session_state.timing_stats = {} |
| st.session_state.timing_logs = [] |
|
|
| |
| if func.__name__ not in st.session_state.timing_stats: |
| st.session_state.timing_stats[func.__name__] = [] |
|
|
| |
| st.session_state.timing_stats[func.__name__].append(duration) |
|
|
| |
| log_entry = { |
| "timestamp": datetime.now().isoformat(), |
| "function": func.__name__, |
| "duration": duration, |
| } |
|
|
| if include_params: |
| |
| sig = inspect.signature(func) |
| param_names = list(sig.parameters.keys()) |
|
|
| |
| param_values = {} |
| for i, arg in enumerate(args): |
| if i < len(param_names): |
| param_values[param_names[i]] = summarize_parameter_value( |
| str(arg), |
| max_length=40, |
| ) |
| param_values.update( |
| { |
| k: summarize_parameter_value(str(v), max_length=40) |
| for k, v in kwargs.items() |
| } |
| ) |
|
|
| log_entry["parameters"] = param_values |
|
|
| st.session_state.timing_logs.append(log_entry) |
| return result |
|
|
| return wrapper |
|
|
| return decorator |
|
|