Update process.py

Keep current logic for analysis, generation, images and add simple mode for chatbot
This commit is contained in:
Patrick Motsch 2026-01-11 13:41:16 +01:00 committed by GitHub
parent 6ded28e21a
commit 4715f627be
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -60,21 +60,28 @@ async def process(self, parameters: Dict[str, Any]) -> ActionResult:
logger.error(f"Invalid documentList type: {type(documentListParam)}") logger.error(f"Invalid documentList type: {type(documentListParam)}")
documentList = DocumentReferenceList(references=[]) documentList = DocumentReferenceList(references=[])
resultType = parameters.get("resultType", "txt") # Optional: if omitted, formats determined from prompt. Default "txt" is validation fallback only.
resultType = parameters.get("resultType")
simpleMode = parameters.get("simpleMode", False) simpleMode = parameters.get("simpleMode", False)
if not aiPrompt: if not aiPrompt:
logger.error(f"aiPrompt is missing or empty. Parameters: {parameters}") logger.error(f"aiPrompt is missing or empty. Parameters: {parameters}")
return ActionResult.isFailure( return ActionResult.isFailure(
error="AI prompt is required" error="AI prompt is required"
) )
# Determine output extension and default MIME type without duplicating service logic # Handle optional resultType: if None, formats determined from prompt by AI
if resultType:
normalized_result_type = (str(resultType).strip().lstrip('.').lower() or "txt") normalized_result_type = (str(resultType).strip().lstrip('.').lower() or "txt")
output_extension = f".{normalized_result_type}" output_extension = f".{normalized_result_type}"
output_mime_type = "application/octet-stream" # Prefer service-provided mimeType when available output_format = output_extension.replace('.', '') or 'txt'
logger.info(f"Using result type: {resultType} -> {output_extension}, simpleMode: {simpleMode}") logger.info(f"Using result type: {resultType} -> {output_extension}, simpleMode: {simpleMode}")
else:
# No format specified - AI will determine formats from prompt
normalized_result_type = None
output_extension = None
output_format = None
logger.debug("resultType not provided - formats will be determined from prompt by AI")
output_mime_type = "application/octet-stream" # Prefer service-provided mimeType when available output_mime_type = "application/octet-stream" # Prefer service-provided mimeType when available
@ -96,8 +103,8 @@ async def process(self, parameters: Dict[str, Any]) -> ActionResult:
# Update progress - preparing AI call # Update progress - preparing AI call
self.services.chat.progressLogUpdate(operationId, 0.4, "Preparing AI call") self.services.chat.progressLogUpdate(operationId, 0.4, "Preparing AI call")
# Build options # Build output format for simple mode
output_format = output_extension.replace('.', '') or 'txt' output_format_for_call = output_extension.replace('.', '') if output_extension else (output_format or 'txt')
# Simple mode: fast path without document generation pipeline # Simple mode: fast path without document generation pipeline
if simpleMode: if simpleMode:
@ -132,7 +139,7 @@ async def process(self, parameters: Dict[str, Any]) -> ActionResult:
prompt=aiPrompt, prompt=aiPrompt,
context=context_text if context_text else None, context=context_text if context_text else None,
options=AiCallOptions( options=AiCallOptions(
resultFormat=output_format, resultFormat=output_format_for_call,
operationType=OperationTypeEnum.DATA_ANALYSE, operationType=OperationTypeEnum.DATA_ANALYSE,
processingMode=ProcessingModeEnum.BASIC processingMode=ProcessingModeEnum.BASIC
) )
@ -158,49 +165,44 @@ async def process(self, parameters: Dict[str, Any]) -> ActionResult:
) )
else: else:
# Full mode: use unified callAiContent method # Full mode: use unified callAiContent method
# For document generation (xlsx, docx, pdf, etc.), use DATA_GENERATE with document intent # Detect image generation from resultType (if provided)
from modules.datamodels.datamodelAi import OperationTypeEnum imageFormats = ["png", "jpg", "jpeg", "gif", "webp"]
isImageGeneration = normalized_result_type in imageFormats if normalized_result_type else False
# Always use DATA_GENERATE with document intent for ai.process # Build options with correct operationType
# This ensures proper document generation pipeline is used from modules.datamodels.datamodelAi import OperationTypeEnum
# resultFormat in options can be None - formats will be determined by AI if not provided
options = AiCallOptions( options = AiCallOptions(
resultFormat=output_format, resultFormat=output_format, # Can be None - formats determined by AI
operationType=OperationTypeEnum.DATA_GENERATE operationType=OperationTypeEnum.IMAGE_GENERATE if isImageGeneration else OperationTypeEnum.DATA_GENERATE
) )
generation_intent = "document"
# Get generationIntent from parameters (required for DATA_GENERATE)
# Default to "document" if not provided (most common use case)
# For code generation, use ai.generateCode action or explicitly pass generationIntent="code"
generationIntent = parameters.get("generationIntent", "document")
# Update progress - calling AI # Update progress - calling AI
self.services.chat.progressLogUpdate(operationId, 0.6, "Calling AI") self.services.chat.progressLogUpdate(operationId, 0.6, "Calling AI")
# Use unified callAiContent method # Use unified callAiContent method with BOTH documentList and contentParts
# If contentParts provided (pre-extracted), use them directly # Extraction is handled by AI service - no extraction here
# Otherwise, pass documentList and let callAiContent handle Phases 5A-5E internally # outputFormat: Optional - if None, formats determined from prompt by AI
# Note: ContentExtracted documents (from context.extractContent) are now handled # Note: ContentExtracted documents (from context.extractContent) are now handled
# automatically in _extractAndPrepareContent() (Phase 5B) # automatically in _extractAndPrepareContent() (Phase 5B)
if contentParts:
# Pre-extracted ContentParts - use them directly
aiResponse = await self.services.ai.callAiContent(
prompt=aiPrompt,
options=options,
contentParts=contentParts, # Pre-extracted ContentParts
outputFormat=output_format,
parentOperationId=operationId,
generationIntent=generation_intent
)
else:
# Pass documentList - callAiContent handles Phases 5A-5E internally
# This includes automatic detection of ContentExtracted documents
logger.info(f"ai.process: Calling callAiContent with {len(documentList.references)} document references") logger.info(f"ai.process: Calling callAiContent with {len(documentList.references)} document references")
if documentList.references: if documentList.references:
for idx, ref in enumerate(documentList.references): for idx, ref in enumerate(documentList.references):
logger.info(f" Passing reference {idx + 1}: documentId={ref.documentId}") logger.info(f" Passing reference {idx + 1}: documentId={ref.documentId}")
aiResponse = await self.services.ai.callAiContent( aiResponse = await self.services.ai.callAiContent(
prompt=aiPrompt, prompt=aiPrompt,
options=options, options=options,
documentList=documentList, # callAiContent macht Phasen 5A-5E documentList=documentList, # Pass documentList - AI service handles extraction
outputFormat=output_format, contentParts=contentParts, # Pass contentParts if provided (or None)
outputFormat=output_format, # Can be None - AI determines from prompt
parentOperationId=operationId, parentOperationId=operationId,
generationIntent=generation_intent generationIntent=generationIntent # REQUIRED for DATA_GENERATE
) )
# Update progress - processing result # Update progress - processing result