This is a small surface area — two files in the costs module and a
rewritten .env.example — but the user-visible blast radius
was significant. Anybody running a default install (Qdrant since v3, never
LanceDB) had no working semantic search: BOQ position vectors
weren’t indexed, similarity-search lookups in the
/match-elements wizard fell through to the keyword path, and the
AI-classification hint chips never lit up. The probe failed in a way that
logged a warning and continued; the upsert path then no-op'd on every
write. It was a silent miss in the dependency-detection layer.
The two changes
Vector-backend probe matches the configured backend
_vector_available() in costs/vector_adapter.py now
dispatches on settings.vector_backend: it probes
qdrant_client when the backend is qdrant (the
default since v3 — config.py:237) and only falls back to
probing lancedb when the backend is explicitly
lancedb. Symptom was unmistakable once you knew the cause:
/match-elements showed “AI Semantic Search is offline”
even though Qdrant was healthy and reporting zero indexed vectors. With
the probe corrected, the next cost upsert seeds the collection and the AI
path lights back up.
backend/.env.example rewritten with structured sections
Restructured into labelled sections (Database, Vector backend, Demo creds,
Optional AI keys, etc.), fixed the stale VECTOR_BACKEND=lancedb
comment that was lying about the default, made it explicit that
DATABASE_URL must be uncommented for
PostgreSQL to take effect (otherwise the SQLite fallback wins silently),
and exposed the DEMO_*_PASSWORD vars so a fresh install can
pin the canonical demo credentials at first boot instead of inheriting an
auto-generated token nobody can recover.
Why this matters
Issue #162 is the kind of bug that punishes people for trying the right setup
first. The whole point of switching the production default from LanceDB to
Qdrant in v3 was to give users a real vector store with persistence,
replication, and a UI — the price for that was a separate service to run.
Anyone who set up Qdrant exactly as documented, then opened
/match-elements, was told their semantic search was offline. The
probe was looking for the wrong library. The fix is a five-line dispatch but
it restores the headline AI feature on every default install. The
.env.example rewrite is in the same release because the two
surfaces share the same root cause — configuration that drifted from its
defaults without anyone noticing.
Upgrade
pip install --upgrade openconstructionerp
No Alembic migration, no DB change — the Qdrant collection itself is
created lazily on first upsert, so after the upgrade the next cost-row
save() will populate the index and AI semantic search returns to
service on its own. No manual reindex needed. If you customised
backend/.env, diff it against the rewritten
backend/.env.example and copy in the new
DEMO_*_PASSWORD section if you want pinned demo credentials.
Try v5.2.3 today.
Live demo in your browser, or self-host in five minutes. AGPL-3.0, no signup required.