Troubleshooting Guide#
This guide helps you diagnose and fix common issues with EngiAI.
Docker Issues#
Container Won’t Start#
Symptoms: Container exits immediately or fails health checks
Check logs:
docker-compose logs -f chatbot
Common Causes:
Missing API keys:
# Check your .env file cat .env | grep API_KEY
Solution: Ensure
OPENAI_API_KEY,GOOGLE_API_KEY, andTAVILY_API_KEYare setPort already in use:
# Check what's using port 8501 lsof -i :8501
Solution: Stop the conflicting service or change port in
docker-compose.ymlInsufficient resources:
Increase Docker memory allocation (Docker Desktop → Settings → Resources)
Recommended: 4GB RAM minimum
Can’t Access UI#
Symptom: Browser can’t connect to http://localhost:8501
Steps:
Check containers are running:
docker-compose psAll containers should show “Up” status
Check Docker Desktop is running (if using Docker Desktop)
Try accessing via Docker host IP:
# Find container IP docker inspect engiai-chatbot | grep IPAddress
Check firewall settings (Linux):
sudo ufw allow 8501
Permission Errors (Linux)#
Symptom: “Permission denied” errors
Solution: Add user to docker group:
sudo usermod -aG docker $USER
# Log out and back in for changes to take effect
Out of Disk Space#
Symptom: Build fails or containers crash
Check disk usage:
docker system df
Clean up:
# Remove unused images and containers
docker system prune -a
# Remove specific images
docker rmi $(docker images -q)
Local Development Issues#
Ruff Not Found in VS Code#
Symptom: VS Code shows “Ruff not found”
Solutions:
Ensure conda environment is activated:
conda activate engiai
Restart VS Code after activating environment
Set Python interpreter in VS Code:
Cmd/Ctrl + Shift + P→ “Python: Select Interpreter”Choose
engiaiconda environment
Pre-commit Not Working#
Symptom: Hooks don’t run on commit
Solutions:
Reinstall hooks:
pre-commit installRun manually to test:
pre-commit run --all-files
Skip hooks temporarily (not recommended):
git commit --no-verify
Environment Creation Fails#
Symptom: conda env create fails
Solutions:
Update conda:
conda update -n base conda
Clear conda cache:
conda clean --all
Try creating environment again:
conda env remove -n engiai conda create -n engiai python=3.13 -y conda activate engiai pip install -e ".[dev,test]"
Import Errors#
Symptom: ModuleNotFoundError when running Python
Solutions:
Verify environment is activated:
conda activate engiai which python # Should point to conda env
Verify you’re in project root:
pwd # Should show .../engiai
Reinstall package:
pip install -e .
Streamlit Command Not Found#
Symptom: streamlit: command not found
Solution: Activate conda environment:
conda activate engiai
streamlit run src/ui/streamlit_app.py
API & Configuration Issues#
Missing API Keys Error#
Symptom: ValueError about missing configuration
Check .env file exists:
ls -la .env
If missing, create from example:
cp .env.example .env
# Edit .env and add your keys
Verify keys are set:
# Don't run this in production - just for debugging
cat .env | grep API_KEY
Chatbot Not Responding#
Symptoms: No response or timeout errors
Possible Causes:
Invalid OpenAI API key:
Verify key at https://platform.openai.com/api-keys
Check you have sufficient credits
API rate limiting:
Wait a few minutes and try again
Check OpenAI dashboard for rate limits
Network issues:
# Test connectivity curl https://api.openai.com/v1/models -H "Authorization: Bearer $OPENAI_API_KEY"
Web Search Not Working#
Symptom: Search tool fails
Check the selected search provider:
The default
SEARCH_PROVIDER=duckduckgorequires internet access but no key.EngiAI uses DuckDuckGo Lite first. If DuckDuckGo temporarily blocks automated requests, it retries once and then uses keyless search-engine fallbacks. No Tavily credits are consumed in this mode.
For Tavily, verify
SEARCH_PROVIDER=tavilyandTAVILY_API_KEYin.env.
Database Errors#
Symptom: “database is locked” or connection errors
For SQLite:
# Close other applications using the database
# Or use PostgreSQL instead
For PostgreSQL:
Check PostgreSQL is running:
# Docker docker-compose ps postgres # Local (macOS) brew services list | grep postgresql # Local (Linux) sudo systemctl status postgresql
Verify connection string:
# Check DATABASE_URL in .env cat .env | grep DATABASE_URL
For Docker, ensure hostname is
postgresnotlocalhost:# Correct for Docker DATABASE_URL=postgresql://user:pass@postgres:5432/engineer_assistant # Correct for local DATABASE_URL=sqlite:///data/conversations.db
“Could not translate host name ‘postgres’” (Local)#
Symptom: Error when running locally with Streamlit
Cause: Your .env is configured for Docker
Solution: Change DATABASE_URL to use SQLite:
# In .env file
DATABASE_URL=sqlite:///data/conversations.db
The whole stack fails to start after a Postgres major bump#
Symptom: make docker-up never finishes. docker compose logs postgres
repeats:
FATAL: database files are incompatible with server
DETAIL: The data directory was initialized by PostgreSQL version 15,
which is not compatible with this version 17.
Cause: a major version cannot read another major’s data directory. Postgres
exits, restart: unless-stopped restarts it into the same failure, and because
chatbot waits on condition: service_healthy nothing else comes up either —
so the visible symptom is the whole stack hanging, not a database error.
Solution: see Upgrading the PostgreSQL major version. Short form, if the conversation history is expendable:
./docker-compose-wrapper.sh down
docker volume rm engiai_postgres_data
./docker-compose-wrapper.sh up -d
The app says “Falling back to SQLite” and every conversation is gone#
Symptom: the UI starts but the chat list is empty, and the logs show:
Could not connect to database (... FATAL: password authentication failed
for user "engiai_user"). Falling back to SQLite.
Cause: POSTGRES_PASSWORD and the password inside DATABASE_URL disagree.
The first is what initdb gave the role when the volume was created; the
second is what the app connects with. They can diverge for months without
symptoms — the running database still has the old password — and the mismatch
only appears once the volume is recreated.
Nothing is actually lost: the Postgres data is still in its volume, and the empty database you are looking at is a fresh SQLite file.
Solution: make them match in .env, then recreate the volume so initdb
applies the intended password:
grep -E '^(POSTGRES_PASSWORD|DATABASE_URL)=' .env # compare the two
MMORE / RAG Issues#
MMORE takes forever to become healthy on first start#
Expected. A cold start pulls ~1.5 GB of image plus the embedding, SPLADE and reranker weights. The healthcheck allows 600s for this, and the chatbot waits on the service being healthy, so the whole stack appears to hang.
docker compose logs -f mmore-rag-service # watch the model downloads
The cache lives in data/mmore/cache/ and is shared with the evaluation
service, so this cost is paid once. Start the main service and let it warm the
cache before bringing up the eval service, rather than having both race the
same download.
Search returns nothing, but the service is healthy#
The service starts fine with an empty index — health says nothing about content. Check what is actually indexed:
curl -s "http://localhost:8000/list_files?collection_name=my_docs"
make mmore-index-verify
If it is empty, build it: make mmore-index (or make mmore-index-eval for
port 8001).
If documents are indexed but results still come back empty, the score
threshold may be wrong for your MMORE version. The search_documents tool
filters at MMORE_MIN_SIMILARITY (default 0.3); if an upstream bump changed
the score scale, that floor can silently suppress everything. Compare raw
scores with no floor:
python scripts/inspect_mmore.py --retrieve "topology optimization" --max-matches 10
409 Conflict when adding a document#
MMORE already holds that fileId. Upload does not overwrite. Either delete
first, or replace in place:
curl -X DELETE http://localhost:8000/v1/files/<fileId>
# or, for a manifest document:
python scripts/build_mmore_index.py --only <file_id> --force
scripts/import_local_papers.py treats a 409 as “already imported” and moves
on rather than retrying.
An upload seems to hang#
MMORE v2 indexes asynchronously, and upload_file blocks until the background
job finishes — that is deliberate, so callers can assume “returned means
searchable”. Large scanned PDFs on CPU genuinely take minutes. Inspect the job:
curl -s http://localhost:8000/v1/jobs/<jobId> # queued | processing | done | failed
Raise MMORE_INDEX_TIMEOUT (default 900s) if legitimate work is being cut off.
Note job records live in memory, expire after two hours, and are lost on
restart — the durable answer to “is it indexed?” is /list_files.
Upload dies with “Connection reset by peer”#
Almost always the container being OOM-killed mid-job (docker inspect mmore-rag-service --format '{{.State.ExitCode}}' returns 137). Processing a
PDF loads marker’s six models plus the embedding and reranker models, which
peaks at several GB on top of whatever is already resident.
Two things make this much worse:
Both services indexing at once. The main and eval services each need the full pipeline in memory. Build one index at a time.
Models stay resident after a job. A service that has processed a PDF holds those models.
docker restart mmore-rag-servicereleases them.
The reliable sequence on a memory-constrained host is:
docker restart mmore-rag-service # drop retained models
make mmore-index
docker restart mmore-rag-service
make mmore-eval-up && make mmore-index-eval
If it still will not fit, raise Docker Desktop’s memory limit
(Settings → Resources) or index on a larger machine and copy
data/mmore/index/mmore.db across — it is a single portable file.
Permission denied writing the index (Linux)#
The container runs as uid 1000. If your host user differs, the bind mounts
under data/mmore/ are not writable. Add a docker-compose.override.yml:
services:
mmore-rag-service:
user: "${UID}:${GID}"
Docker Desktop on macOS and Windows does not have this problem.
MMORE_PATH no longer does anything#
It pointed at a local MMORE source checkout that the stack no longer needs.
Remove it from your .env. MMORE now runs from a pinned upstream image; see
services/mmore/README.md.
Prusa MCP Issues#
MCP Connection Failed#
Symptom: Prusa agent can’t connect
Check MCP server is running:
# For Docker deployment
docker-compose ps prusa-mcp-server
# Test connection
curl http://localhost:8765/sse
Solutions:
Check
SKIP_MCPsetting in.env:SKIP_MCP=true # Disables MCP integration SKIP_MCP=false # Enables MCP integration
Verify MCP server is accessible:
# From container docker exec engiai-chatbot curl -v http://prusa-mcp-server:8765/sse
Tools Not Loading#
Symptom: Prusa-related tools missing
Solution: Set SKIP_MCP=true to disable MCP integration if you don’t need 3D printing features
Whiteboard Canvas Issues#
Fuller coverage lives in Whiteboard Canvas; this is the subset that gets mistaken for a broken app.
The assistant says it cannot draw#
Symptom: asked for a diagram, the assistant replies that the whiteboard is unavailable.
Cause: the canvas MCP server is not reachable, so the agent is dropped rather than offered — deliberately, so it can never claim to have drawn something it could not.
docker compose ps excalidraw-mcp-server
docker logs excalidraw-mcp-server | grep "allowed hosts"
Check SKIP_MCP and SKIP_CANVAS are both false. SKIP_MCP=true
disables the canvas as well as the printer.
The app will not start with the canvas enabled#
Symptom: httpx2.ConnectError: All connection attempts failed at startup.
Cause: enabling the canvas means SKIP_MCP=false, which enables the Prusa
agent too. Both servers need to be running, or start neither:
docker compose up -d prusa-mcp-server excalidraw-mcp-server
My drawing disappeared when the assistant drew#
Cause: it was never sent. The UI only learns what is on the canvas when you press 📤 Send to Chat, so an unsent drawing is replaced by whatever the assistant draws next. Send first.
Drawings vanish between sessions#
Scenes are stored per conversation in the EngiAI database and restored when you reopen the chat. If they are not coming back, the conversation may never have been saved — a chat with no messages is not written to the database, and its whiteboard goes with it.
Host Service & GUI Integration#
“Cannot connect to host service” Error#
Symptom: Can’t open PrusaSlicer or other GUI apps from Docker
Check host service is running:
lsof -i :9999
Start host service (on your local machine):
python services/host_service.py
Verify from Docker:
docker exec engiai-chatbot curl http://host.docker.internal:9999/health
PrusaSlicer Won’t Open#
Solutions:
Verify PrusaSlicer is installed on host machine
Verify host service whitelist includes the app (in
services/host_service.py)
Port 9999 Already in Use#
Solution: Change port in .env:
HOST_SERVICE_PORT=9998
Then restart both host service and Docker containers.
SSH & HPC Connection Issues#
“SSH key is encrypted” Error (Docker)#
Symptom: Can’t connect to HPC cluster from Docker
Solution: Use SSH agent forwarding
On host machine, add key to SSH agent:
# macOS ssh-add --apple-use-keychain ~/.ssh/id_ed25519 # Linux ssh-add ~/.ssh/id_ed25519
Verify key is loaded:
ssh-add -lRestart Docker container:
docker-compose restart chatbot
“Agent has no identities” Error#
Check SSH agent is running:
echo $SSH_AUTH_SOCK
# Should show a path like: /private/tmp/com.apple.launchd.*/Listeners
Start SSH agent if needed:
eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519
Connection Works Locally But Fails in Docker#
Checklist:
✅ SSH agent is running on host:
ssh-add -l✅
SSH_AUTH_SOCKenvironment variable is set✅
~/.ssh/confighasAddKeysToAgent yesandUseKeychain yes✅ Restart Docker after adding keys
SSH Key Permission Errors#
Fix permissions:
chmod 700 ~/.ssh
chmod 600 ~/.ssh/id_ed25519
chmod 644 ~/.ssh/id_ed25519.pub
chmod 600 ~/.ssh/config
chmod 644 ~/.ssh/known_hosts
HPC Job Submission Fails#
Common Issues:
Can’t connect to cluster:
# Test SSH manually ssh your-cluster-alias
SLURM commands not found:
Verify you’re on a login node
Check cluster documentation
Job fails immediately:
# Check job logs cat slurm-<jobid>.out cat slurm-<jobid>.err
Module not found:
# Check available modules module avail
Performance Issues#
Slow Response Times#
Possible Causes:
Large document collection:
Monitor MMORE service performance
Consider limiting search scope with file_ids
Slow API responses:
Check OpenAI API status
Try different model (e.g., gpt-4o-mini)
Insufficient resources:
Increase Docker memory allocation
Close other applications
High Memory Usage#
Solutions:
Limit conversation history length
Clear browser cache
Restart Docker containers:
docker-compose restart
Streamlit Performance Issues#
Solutions:
Reduce max tokens in settings
Limit chat history length
Use a smaller LLM model
Close unused browser tabs
Clear Streamlit cache:
streamlit cache clear
Testing Issues#
Tests Failing#
Run tests with verbose output:
pytest -v
Run specific test:
pytest tests/test_specific_file.py -v
Skip slow tests:
pytest -m "not slow"
Import Errors in Tests#
Ensure package is installed:
pip install -e .
Common Error Messages#
“ModuleNotFoundError: No module named ‘src’”#
Solution: Install package in development mode:
pip install -e .
“ValueError: Invalid configuration”#
Solution: Check all required environment variables in .env
“Connection refused” (Port 8501)#
Solutions:
Check Docker containers are running
Check firewall settings
Try different port in docker-compose.yml
“OSError: [Errno 28] No space left on device”#
Solution: Free up disk space or clean Docker:
docker system prune -a
Getting Help#
If your issue isn’t covered here:
Check logs:
# Docker docker compose logs -f chatbot # Local: the app logs to the terminal running Streamlit — there is no # application log file. (`data/local_import.log` is written only by # scripts/import_local_papers.py.)
Search GitHub Issues: https://github.com/gioelemo/EngiAI/issues
Open a new issue with:
Operating system
Python version
Full error message
Steps to reproduce
What you’ve tried
Review documentation:
Prevention Tips#
✅ Always activate conda environment before running commands
✅ Keep
.envfile up to date with required keys✅ Use Docker for consistent deployment
✅ Regularly update dependencies
✅ Back up your database regularly
✅ Monitor API usage and credits
✅ Test in development before deploying to production