CoolFace
Apppublic

Backup-bdg/OpenHands

sourceHugging Faceapache-2.0updated 1y agoView on Hugging Face
0likes
conversation_summary.py139 linesDownload Raw Back to utils
1"""Utility functions for generating conversation summaries."""2 3from typing import Optional4 5from openhands.core.config import LLMConfig6from openhands.core.logger import openhands_logger as logger7from openhands.events.action.message import MessageAction8from openhands.events.event import EventSource9from openhands.events.stream import EventStream10from openhands.llm.llm import LLM11from openhands.storage.data_models.settings import Settings12from openhands.storage.files import FileStore13 14 15async def generate_conversation_title(16    message: str, llm_config: LLMConfig, max_length: int = 5017) -> Optional[str]:18    """Generate a concise title for a conversation based on the first user message.19 20    Args:21        message: The first user message in the conversation.22        llm_config: The LLM configuration to use for generating the title.23        max_length: The maximum length of the generated title.24 25    Returns:26        A concise title for the conversation, or None if generation fails.27    """28    if not message or message.strip() == '':29        return None30 31    # Truncate very long messages to avoid excessive token usage32    if len(message) > 1000:33        truncated_message = message[:1000] + '...(truncated)'34    else:35        truncated_message = message36 37    try:38        llm = LLM(llm_config)39 40        # Create a simple prompt for the LLM to generate a title41        messages = [42            {43                'role': 'system',44                'content': 'You are a helpful assistant that generates concise, descriptive titles for conversations with OpenHands. OpenHands is a helpful AI agent that can interact with a computer to solve tasks using bash terminal, file editor, and browser. Given a user message (which may be truncated), generate a concise, descriptive title for the conversation. Return only the title, with no additional text, quotes, or explanations.',45            },46            {47                'role': 'user',48                'content': f'Generate a title (maximum {max_length} characters) for a conversation that starts with this message:\n\n{truncated_message}',49            },50        ]51 52        response = llm.completion(messages=messages)53        title = response.choices[0].message.content.strip()54 55        # Ensure the title isn't too long56        if len(title) > max_length:57            title = title[: max_length - 3] + '...'58 59        return title60    except Exception as e:61        logger.error(f'Error generating conversation title: {e}')62        return None63 64 65def get_default_conversation_title(conversation_id: str) -> str:66    """67    Generate a default title for a conversation based on its ID.68 69    Args:70        conversation_id: The ID of the conversation71 72    Returns:73        A default title string74    """75    return f'Conversation {conversation_id[:5]}'76 77 78async def auto_generate_title(79    conversation_id: str, user_id: str | None, file_store: FileStore, settings: Settings80) -> str:81    """82    Auto-generate a title for a conversation based on the first user message.83    Uses LLM-based title generation if available, otherwise falls back to a simple truncation.84 85    Args:86        conversation_id: The ID of the conversation87        user_id: The ID of the user88 89    Returns:90        A generated title string91    """92    try:93        # Create an event stream for the conversation94        event_stream = EventStream(conversation_id, file_store, user_id)95 96        # Find the first user message97        first_user_message = None98        for event in event_stream.get_events():99            if (100                event.source == EventSource.USER101                and isinstance(event, MessageAction)102                and event.content103                and event.content.strip()104            ):105                first_user_message = event.content106                break107 108        if first_user_message:109            # Get LLM config from user settings110            try:111                if settings and settings.llm_model:112                    # Create LLM config from settings113                    llm_config = LLMConfig(114                        model=settings.llm_model,115                        api_key=settings.llm_api_key,116                        base_url=settings.llm_base_url,117                    )118 119                    # Try to generate title using LLM120                    llm_title = await generate_conversation_title(121                        first_user_message, llm_config122                    )123                    if llm_title:124                        logger.info(f'Generated title using LLM: {llm_title}')125                        return llm_title126            except Exception as e:127                logger.error(f'Error using LLM for title generation: {e}')128 129            # Fall back to simple truncation if LLM generation fails or is unavailable130            first_user_message = first_user_message.strip()131            title = first_user_message[:30]132            if len(first_user_message) > 30:133                title += '...'134            logger.info(f'Generated title using truncation: {title}')135            return title136    except Exception as e:137        logger.error(f'Error generating title: {str(e)}')138    return ''139