bytedance/deer-flow · error · HTTPException

Failed to delete memory fact.

Error message

Failed to delete memory fact.

What it means

Raised as HTTP 500 by the DELETE /memory/facts/{fact_id} endpoint when the underlying memory manager's delete_fact call fails with an OSError. The memory backend is filesystem-based, so this signals an I/O failure while persisting the deletion (disk full, permission denied, missing/corrupted store file), not a bad request.

Source

Thrown at backend/app/gateway/routers/memory.py:357

    "/memory/facts/{fact_id}",
    response_model=MemoryResponse,
    response_model_exclude_none=True,
    summary="Delete Memory Fact",
    description="Delete a single saved memory fact by its fact id.",
)
async def delete_memory_fact_endpoint(fact_id: str, http_request: Request) -> MemoryResponse:
    """Delete a single fact from memory by fact id."""
    manager = await asyncio.to_thread(get_memory_manager)
    try:
        memory_data = await asyncio.to_thread(manager.delete_fact, fact_id, user_id=_resolve_memory_user_id(http_request))
    except NotImplementedError:
        raise _unsupported_501(manager, "delete fact") from None
    except KeyError as exc:
        raise HTTPException(status_code=404, detail=f"Memory fact '{fact_id}' not found.") from exc
    except (MemoryConflictError, MemoryCorruptionError) as exc:
        raise _map_memory_manager_error(exc) from exc
    except OSError as exc:
        raise HTTPException(status_code=500, detail="Failed to delete memory fact.") from exc

    return MemoryResponse(**memory_data)


@router.patch(
    "/memory/facts/{fact_id}",
    response_model=MemoryResponse,
    response_model_exclude_none=True,
    summary="Patch Memory Fact",
    description="Partially update a single saved memory fact by its fact id while preserving omitted fields.",
)
async def update_memory_fact_endpoint(fact_id: str, request: FactPatchRequest, http_request: Request) -> MemoryResponse:
    """Partially update a single fact manually."""
    manager = await asyncio.to_thread(get_memory_manager)
    try:
        memory_data = await asyncio.to_thread(
            manager.update_fact,
            fact_id=fact_id,

View on GitHub (pinned to 1dd6ba1acb)

Solutions

  1. Check Gateway logs for the chained OSError (raise ... from exc preserves it) to see the exact errno and path.
  2. Verify write permission and free space on the memory store directory configured for the memory backend.
  3. Ensure only one Gateway instance writes to the same memory store path.
  4. If the store file is corrupted, restore from a /memory/export backup and retry the delete.

Example fix

# before: memory store dir owned by root after a volume mount
sudo chown -R appuser:appgroup /var/lib/deerflow/memory
# after: delete succeeds once the process can write the store
# curl -X DELETE http://localhost:2026/api/memory/facts/<fact_id>
Defensive patterns

Strategy: retry

Validate before calling

import os
STORE_DIR = get_memory_store_path_from_config()  # the configured memory store location
assert os.path.isdir(STORE_DIR), f"missing store dir {STORE_DIR}"
assert os.access(STORE_DIR, os.W_OK), f"store dir not writable: {STORE_DIR}"

Try / catch

try:
    resp = requests.delete(f"{BASE}/api/memory/facts/{fact_id}")
except requests.RequestException:
    raise  # transport error, not the 500
if resp.status_code >= 500:
    log_and_retry_with_backoff(resp)  # transient I/O: inspect detail + server logs
elif resp.status_code == 404:
    pass  # already gone — treat delete as idempotent success

Prevention

When it happens

Trigger: Calling DELETE /api/memory/facts/{fact_id} (or the same route through nginx /api proxy) while the memory store directory is unwritable, the JSON backing file is locked by another process, the disk is full, or the store path was deleted mid-request.

Common situations: Running the Gateway as a user without write access to the memory store directory; container volume mount read-only; disk exhaustion; concurrent Gateway processes writing the same store file.

Related errors


AI-assisted analysis of bytedance/deer-flow@1dd6ba1acb (2026-08-14). Data as JSON: /api/errors/f3cc8dc0f975e092. Report an issue: GitHub.