- Move global config files to globals iso global folder, as the name global conflicts with python language
- Creation of Traicie Vancancy Definition specialist - Allow to invoke non-interaction specialists from withing Evie's mgmt interface (eveai_app) - Improvements to crewai specialized classes - Introduction to json editor for showing specialists arguments and results in a better way - Introduction of more complex pagination (adding extra arguments) by adding a global 'get_pagination_html' - Allow follow-up of ChatSession / Specialist execution - Improvement in logging of Specialists (but needs to be finished)
This commit is contained in:
@@ -47,6 +47,7 @@ class TuningLogRecord(logging.LogRecord):
|
||||
self._tuning_specialist_id = None
|
||||
self._tuning_retriever_id = None
|
||||
self._tuning_processor_id = None
|
||||
self._session_id = None
|
||||
self.component = os.environ.get('COMPONENT_NAME', 'eveai_app')
|
||||
|
||||
def getMessage(self):
|
||||
@@ -87,16 +88,18 @@ class TuningLogRecord(logging.LogRecord):
|
||||
'tuning_specialist_id': self._tuning_specialist_id,
|
||||
'tuning_retriever_id': self._tuning_retriever_id,
|
||||
'tuning_processor_id': self._tuning_processor_id,
|
||||
'session_id': self._session_id,
|
||||
}
|
||||
|
||||
def set_tuning_data(self, tenant_id=None, catalog_id=None, specialist_id=None,
|
||||
retriever_id=None, processor_id=None):
|
||||
retriever_id=None, processor_id=None, session_id=None,):
|
||||
"""Set tuning-specific data"""
|
||||
object.__setattr__(self, '_tuning_tenant_id', tenant_id)
|
||||
object.__setattr__(self, '_tuning_catalog_id', catalog_id)
|
||||
object.__setattr__(self, '_tuning_specialist_id', specialist_id)
|
||||
object.__setattr__(self, '_tuning_retriever_id', retriever_id)
|
||||
object.__setattr__(self, '_tuning_processor_id', processor_id)
|
||||
object.__setattr__(self, '_session_id', session_id)
|
||||
|
||||
|
||||
class TuningFormatter(logging.Formatter):
|
||||
@@ -120,6 +123,12 @@ class TuningFormatter(logging.Formatter):
|
||||
identifiers.append(f"Catalog: {record.catalog_id}")
|
||||
if hasattr(record, 'processor_id') and record.processor_id:
|
||||
identifiers.append(f"Processor: {record.processor_id}")
|
||||
if hasattr(record, 'specialist_id') and record.specialist_id:
|
||||
identifiers.append(f"Specialist: {record.specialist_id}")
|
||||
if hasattr(record, 'retriever_id') and record.retriever_id:
|
||||
identifiers.append(f"Retriever: {record.retriever_id}")
|
||||
if hasattr(record, 'session_id') and record.session_id:
|
||||
identifiers.append(f"Session: {record.session_id}")
|
||||
|
||||
formatted_msg = (
|
||||
f"{formatted_msg}\n"
|
||||
@@ -149,22 +158,93 @@ class GraylogFormatter(logging.Formatter):
|
||||
'specialist_id': record.specialist_id,
|
||||
'retriever_id': record.retriever_id,
|
||||
'processor_id': record.processor_id,
|
||||
'session_id': record.session_id,
|
||||
}
|
||||
return super().format(record)
|
||||
|
||||
|
||||
class TuningLogger:
|
||||
"""Helper class to manage tuning logs with consistent structure"""
|
||||
|
||||
def __init__(self, logger_name, tenant_id=None, catalog_id=None, specialist_id=None, retriever_id=None, processor_id=None):
|
||||
def __init__(self, logger_name, tenant_id=None, catalog_id=None, specialist_id=None, retriever_id=None,
|
||||
processor_id=None, session_id=None, log_file=None):
|
||||
"""
|
||||
Initialize a tuning logger
|
||||
|
||||
Args:
|
||||
logger_name: Base name for the logger
|
||||
tenant_id: Optional tenant ID for context
|
||||
catalog_id: Optional catalog ID for context
|
||||
specialist_id: Optional specialist ID for context
|
||||
retriever_id: Optional retriever ID for context
|
||||
processor_id: Optional processor ID for context
|
||||
session_id: Optional session ID for context and log file naming
|
||||
log_file: Optional custom log file name to use
|
||||
"""
|
||||
|
||||
self.logger = logging.getLogger(logger_name)
|
||||
self.tenant_id = tenant_id
|
||||
self.catalog_id = catalog_id
|
||||
self.specialist_id = specialist_id
|
||||
self.retriever_id = retriever_id
|
||||
self.processor_id = processor_id
|
||||
self.session_id = session_id
|
||||
self.log_file = log_file
|
||||
# Determine whether to use a session-specific logger
|
||||
if session_id:
|
||||
# Create a unique logger name for this session
|
||||
session_logger_name = f"{logger_name}_{session_id}"
|
||||
self.logger = logging.getLogger(session_logger_name)
|
||||
|
||||
def log_tuning(self, tuning_type: str, message: str, data=None, level=logging.DEBUG):
|
||||
# If this logger doesn't have handlers yet, configure it
|
||||
if not self.logger.handlers:
|
||||
# Determine log file path
|
||||
if not log_file and session_id:
|
||||
log_file = f"logs/tuning_{session_id}.log"
|
||||
elif not log_file:
|
||||
log_file = "logs/tuning.log"
|
||||
|
||||
# Configure the logger
|
||||
self._configure_session_logger(log_file)
|
||||
else:
|
||||
# Use the standard tuning logger
|
||||
self.logger = logging.getLogger(logger_name)
|
||||
|
||||
def _configure_session_logger(self, log_file):
|
||||
"""Configure a new session-specific logger with appropriate handlers"""
|
||||
# Create and configure a file handler
|
||||
file_handler = logging.handlers.RotatingFileHandler(
|
||||
filename=log_file,
|
||||
maxBytes=1024 * 1024 * 3, # 3MB
|
||||
backupCount=3
|
||||
)
|
||||
file_handler.setFormatter(TuningFormatter())
|
||||
file_handler.setLevel(logging.DEBUG)
|
||||
|
||||
# Add the file handler to the logger
|
||||
self.logger.addHandler(file_handler)
|
||||
|
||||
# Add Graylog handler in production
|
||||
env = os.environ.get('FLASK_ENV', 'development')
|
||||
if env == 'production':
|
||||
try:
|
||||
graylog_handler = GELFUDPHandler(
|
||||
host=GRAYLOG_HOST,
|
||||
port=GRAYLOG_PORT,
|
||||
debugging_fields=True
|
||||
)
|
||||
graylog_handler.setFormatter(GraylogFormatter())
|
||||
self.logger.addHandler(graylog_handler)
|
||||
except Exception as e:
|
||||
# Fall back to just file logging if Graylog setup fails
|
||||
fallback_logger = logging.getLogger('eveai_app')
|
||||
fallback_logger.warning(f"Failed to set up Graylog handler: {str(e)}")
|
||||
|
||||
# Set logger level and disable propagation
|
||||
self.logger.setLevel(logging.DEBUG)
|
||||
self.logger.propagate = False
|
||||
|
||||
|
||||
def log_tuning(self, tuning_type: str, message: str, data=None, level=logging.DEBUG):
|
||||
"""Log a tuning event with structured data"""
|
||||
try:
|
||||
# Create a standard LogRecord for tuning
|
||||
@@ -186,6 +266,7 @@ class TuningLogger:
|
||||
record.specialist_id = self.specialist_id
|
||||
record.retriever_id = self.retriever_id
|
||||
record.processor_id = self.processor_id
|
||||
record.session_id = self.session_id
|
||||
|
||||
if data:
|
||||
record.tuning_data = data
|
||||
|
||||
Reference in New Issue
Block a user