cocoindex-io/cocoindex · error · RuntimeError
Cannot use sync 'with coco.runtime()' from within an async e
Error message
Cannot use sync 'with coco.runtime()' from within an async event loop. Use 'async with coco.runtime()' instead.
What it means
coco.runtime() supports both sync and async context-manager forms. The sync __enter__ calls start_blocking(), which cannot run inside a running asyncio event loop (it blocks the loop), so it detects a running loop and raises immediately with the correct alternative.
Source
Thrown at python/cocoindex/_internal/api.py:709
"""Stop the default environment synchronously (and exit its lifespan, if any)."""
environment.stop_sync()
async def default_env() -> environment.Environment:
"""Get the default environment (starting it if needed)."""
return await environment.start()
class _DualModeRuntime:
"""Context manager that works with both `with` and `async with`."""
def __enter__(self) -> None:
try:
asyncio.get_running_loop()
except RuntimeError:
pass # No running loop — sync usage is fine
else:
raise RuntimeError(
"Cannot use sync 'with coco.runtime()' from within an async event loop. "
"Use 'async with coco.runtime()' instead."
)
start_blocking()
return None
def __exit__(self, *exc: Any) -> None:
stop_blocking()
async def __aenter__(self) -> None:
await start()
return None
async def __aexit__(self, *exc: Any) -> None:
await stop()
def runtime() -> _DualModeRuntime:View on GitHub (pinned to e84aa99b32)
Solutions
- Use `async with coco.runtime():` instead of `with coco.runtime():`
- In notebooks, use the async form (or nest_asyncio only as a last resort)
- Move the sync usage to plain non-async script code where no loop is running
Example fix
// before
with coco.runtime():
app.update_blocking()
// after
async with coco.runtime():
await app.update() Defensive patterns
Strategy: type-guard
Validate before calling
import asyncio
if asyncio.get_running_loop() is not None: # inside running loop
... # use async form
# usage
if _in_loop():
async with coco.runtime():
...
else:
with coco.runtime():
... Type guard
def in_async_loop() -> bool:
try:
asyncio.get_running_loop()
return True
except RuntimeError:
return False Try / catch
try:
with coco.runtime():
...
except RuntimeError as e:
if "async event loop" in str(e):
raise # switch call site to `async with coco.runtime()` Prevention
- In notebooks always use the async form of context managers
- Keep sync entry points (start_blocking, update_blocking) out of async code paths
When it happens
Trigger: Using `with coco.runtime():` inside an async def function or any code running on an asyncio event loop (e.g. inside a Jupyter notebook with an active loop, or an async app).
Common situations: Jupyter/IPython notebooks where a loop is always running; calling sync-style runtime setup inside async test code; copy-pasting sync examples into async apps.
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- use_mount() requires a ComponentSubpath when the function ha
- LiveComponent classes cannot be used with use_mount(). Use m
- mount() requires a ComponentSubpath when the function has no
- mount_each() requires a ComponentSubpath when the function h
- coco.use_state() cannot be called inside a `with coco.compon
AI-assisted analysis of cocoindex-io/cocoindex@e84aa99b32 (2026-09-08).
Data as JSON: /api/errors/ccf07ec0b676014a.
Report an issue: GitHub.