run-llama/llama_index · error · ValueError
No async database URI or engine provided, cannot initialize
Error message
No async database URI or engine provided, cannot initialize DB sessionmaker
What it means
SQLChatStore's async session factory (_get_async_sessionmaker) requires either an async_database_uri (e.g. 'sqlite+aiosqlite:///chat.db', 'postgresql+asyncpg://...') or an explicit async engine. If neither an async engine instance nor an async URI is configured at first async use, initialization raises immediately.
Source
Thrown at llama-index-core/llama_index/core/storage/chat_store/sql.py:132
) -> Tuple[AsyncEngine, sessionmaker]:
"""Set up database connections and session factories."""
# Create async engine and session factory if async URI is provided
if self._async_session_factory is not None and self._async_engine is not None:
return self._async_engine, self._async_session_factory
elif self.async_database_uri or self._async_engine:
self._async_engine = self._async_engine or create_async_engine(
self.async_database_uri
)
if self.async_database_uri is None:
self.async_database_uri = self._async_engine.url
self._async_session_factory = sessionmaker( # type: ignore
bind=self._async_engine, expire_on_commit=False, class_=AsyncSession
)
return self._async_engine, self._async_session_factory # type: ignore
else:
raise ValueError(
"No async database URI or engine provided, cannot initialize DB sessionmaker"
)
async def _setup_tables(self, async_engine: AsyncEngine) -> Table:
"""Set up database tables."""
# Create metadata with schema
if self.db_schema is not None and not self._is_sqlite_database():
# Only set schema for databases that support it
self._metadata = MetaData(schema=self.db_schema)
# Create schema if it doesn't exist (PostgreSQL, SQL Server, etc.)
async with async_engine.begin() as conn:
await conn.execute(
text(f'CREATE SCHEMA IF NOT EXISTS "{self.db_schema}"')
)
# Create messages table with status column
self._table = Table(View on GitHub (pinned to afd0fef371)
Solutions
- Provide an async URI: SQLChatStore(async_database_uri='sqlite+aiosqlite:///chat.db', table_name='chat_store').
- Or pass a pre-built engine: create_async_engine(...) handed to SQLChatStore(async_engine=engine).
- Install the async driver if missing (pip install aiosqlite or asyncpg) so the +aiosqlite/+asyncpg URL resolves.
- For PostgreSQL pass both URIs: database_uri='postgresql+psycopg2://...' for sync paths and async_database_uri='postgresql+asyncpg://...' for async paths.
Example fix
# before
store = SQLChatStore(database_uri='sqlite:///chat.db')
msgs = await store.aget_messages('sess1') # ValueError
# after
store = SQLChatStore(
database_uri='sqlite:///chat.db',
async_database_uri='sqlite+aiosqlite:///chat.db',
) Defensive patterns
Strategy: validation
Validate before calling
def make_sql_chat_store(sync_uri: str | None, async_uri: str | None):
if not (async_uri or ('+' in (sync_uri or '') and any(d in sync_uri for d in ('aiosqlite', 'asyncpg')))):
raise ValueError('Provide async_database_uri or an async engine for async chat-store access')
return SQLChatStore(database_uri=sync_uri, async_database_uri=async_uri) Type guard
def supports_async(uri_or_engine) -> bool:
if uri_or_engine is None:
return False
url = str(uri_or_engine)
return any(d in url for d in ('aiosqlite', 'asyncpg', 'asyncmy')) Try / catch
try:
messages = await store.aget_messages(session_id)
except ValueError as e:
if 'No async database URI' in str(e):
messages = store.get_messages(session_id) # fall back to sync path
else:
raise Prevention
- Always configure SQLChatStore with both database_uri and async_database_uri when mixing sync and async code.
- Use async dialect URLs: sqlite+aiosqlite:///, postgresql+asyncpg://.
- Install the async driver (aiosqlite/asyncpg) in the deployment environment.
When it happens
Trigger: Constructing SQLChatStore(database_uri='sqlite:///chat.db') (sync URI only, no +aiosqlite) and then calling an async method such as aget_messages() or aset_messages(), which triggers async engine creation.
Common situations: Reusing a sync database URI string for an async-first app; FastAPI/asyncio services configured with the plain sqlite/postgres URL; forgetting the asyncpg/aiosqlite dialect prefix after switching from sync to async usage.
Related errors
- Aborting parsing document; {numTags} elements found
- Command failed: {command} {result.stderr}
- Streaming is not enabled. Please use achat() instead.
- EmptyIndex only supports response_mode=generation.
- Unknown retriever mode: {retriever_mode}
AI-assisted analysis of run-llama/llama_index@afd0fef371 (2026-08-15).
Data as JSON: /api/errors/469a1d2235de75e5.
Report an issue: GitHub.