diff --git a/autogpt_platform/backend/backend/blocks/io.py b/autogpt_platform/backend/backend/blocks/io.py index 8b40c61fc8..a9c3859490 100644 --- a/autogpt_platform/backend/backend/blocks/io.py +++ b/autogpt_platform/backend/backend/blocks/io.py @@ -471,10 +471,8 @@ class AgentFileInputBlock(AgentInputBlock): # Determine return format based on user preference # for_external_api: always returns data URI (base64) - honors "Produce Base64 Output" - # for_local_processing: returns local file path - return_format = ( - "for_external_api" if input_data.base_64 else "for_local_processing" - ) + # for_block_output: smart format - workspace:// in CoPilot, data URI in graphs + return_format = "for_external_api" if input_data.base_64 else "for_block_output" yield "result", await store_media_file( file=input_data.value, diff --git a/autogpt_platform/backend/backend/util/gcs_utils.py b/autogpt_platform/backend/backend/util/gcs_utils.py index c8795ca0fd..3f91f21897 100644 --- a/autogpt_platform/backend/backend/util/gcs_utils.py +++ b/autogpt_platform/backend/backend/util/gcs_utils.py @@ -60,16 +60,21 @@ async def download_with_fresh_session(bucket: str, blob: str) -> bytes: session = aiohttp.ClientSession( connector=aiohttp.TCPConnector(limit=10, force_close=True) ) + client: async_gcs_storage.Storage | None = None try: client = async_gcs_storage.Storage(session=session) content = await client.download(bucket, blob) - await client.close() return content except Exception as e: if "404" in str(e) or "Not Found" in str(e): raise FileNotFoundError(f"File not found: gcs://{bucket}/{blob}") raise finally: + if client: + try: + await client.close() + except Exception: + pass # Best-effort cleanup await session.close() diff --git a/autogpt_platform/backend/backend/util/workspace.py b/autogpt_platform/backend/backend/util/workspace.py index 692c97e03e..a2f1a61b9e 100644 --- a/autogpt_platform/backend/backend/util/workspace.py +++ b/autogpt_platform/backend/backend/util/workspace.py @@ -196,13 +196,13 @@ class WorkspaceManager: # Resolve path with session prefix path = self._resolve_path(path) - # Check if file exists at path - existing = await get_workspace_file_by_path(self.workspace_id, path) - if existing is not None: - if overwrite: - # Delete existing file first - await self.delete_file(existing.id) - else: + # Check if file exists at path (only error for non-overwrite case) + # For overwrite=True, we let the write proceed and handle via UniqueViolationError + # This ensures the new file is written to storage BEFORE the old one is deleted, + # preventing data loss if the new write fails + if not overwrite: + existing = await get_workspace_file_by_path(self.workspace_id, path) + if existing is not None: raise ValueError(f"File already exists at path: {path}") # Auto-detect MIME type if not provided