Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/AngelAmoSanchez/TFG-RaspberryPi-BLE/llms.txt

Use this file to discover all available pages before exploring further.

All configuration is centralised in src/config.py using a Pydantic Settings class that reads values from environment variables (and an optional .env file). Every variable has a default that allows the server to start for local development, but several must be overridden before going to production.

Complete production .env example

Copy .env.example.prod as your starting point and fill in the blanks:
.env
ENVIRONMENT=production
DEBUG=false
HOST=0.0.0.0
PORT=8000

DATABASE_URL=

MQTT_ENABLED=true
MQTT_BROKER=.eu-central-1.emqxsl.com
MQTT_PORT=8883
MQTT_TOPIC=
MQTT_USERNAME=
MQTT_PASSWORD=

SECRET_KEY=
API_KEY=

DEVICES_PER_PERSON=1.5
NEAR_THRESHOLD=-60
MEDIUM_THRESHOLD=-75

LOG_LEVEL=INFO

CORS_ORIGINS=["http://localhost:5173","http://localhost:3000"]

Application

VariableDefaultDescription
APP_NAMETFG Bluetooth Detection BackendName shown in API docs and logs.
ENVIRONMENTdevelopmentRuntime environment. Set to production to enable production guards.
DEBUGtrueEnables uvicorn --reload and verbose error responses. Set to false in production.
API_VERSIONv1Prefix appended to all routes: /api/v1/….
DEBUG=true in production exposes internal stack traces in API error responses. Always set DEBUG=false for any publicly reachable deployment.

Server

VariableDefaultDescription
HOST0.0.0.0Address the uvicorn server binds to.
PORT8000TCP port the server listens on. Also set as an ENV in the Dockerfile.

Database

VariableDefaultDescription
DATABASE_URLpostgresql+asyncpg://postgres:postgres@localhost:5432/tfg_detectionsFull SQLAlchemy async connection URL. The +asyncpg driver is required for async queries.
The settings class also exposes a helper get_database_url_sync() that strips +asyncpg for Alembic, which uses a synchronous psycopg2 connection.
def get_database_url_sync(self) -> str:
    return self.database_url.replace("+asyncpg", "")
In the Docker Compose stack the hostname is postgres (the service name), not localhost. Make sure DATABASE_URL reflects this when overriding inside a container.

MQTT broker

These variables control the embedded MQTT subscriber. The subscriber only starts when MQTT_ENABLED=true and MQTT_BROKER is set.
VariableDefaultDescription
MQTT_ENABLEDfalseSet to true to start the MQTT subscriber on application startup.
MQTT_BROKER(none)Hostname or IP of the MQTT broker, e.g. abc.eu-central-1.emqxsl.com.
MQTT_PORT1883Broker port. Use 8883 for TLS (EMQX Cloud).
MQTT_TOPICtfg/detections/rawTopic the backend subscribes to for incoming detection payloads.
MQTT_USERNAME(none)Optional broker username.
MQTT_PASSWORD(none)Optional broker password.
EMQX Cloud free-tier clusters use port 8883 with TLS. The backend subscriber calls tls_set() automatically when it connects, so no extra certificate configuration is needed.

WebSocket

VariableDefaultDescription
WEBSOCKET_ENABLEDtrueReserved flag. The WebSocket endpoint at /ws is always registered; this variable is available for future conditional logic.
The WebSocket manager broadcasts two event types to connected dashboard clients:
  • detection_event — fired when new detections arrive from a Pi agent.
  • stats_update — fired when aggregated statistics are recalculated.

CORS

The cors_origins list is hardcoded in config.py with sensible development defaults, and can be extended via the CORS_ORIGINS environment variable in production:
cors_origins: list = [
    "http://localhost:3000",
    "http://localhost:5173",
    "http://127.0.0.1:5173",
    "https://*.vercel.app",
]
For production, set CORS_ORIGINS as a JSON array string:
CORS_ORIGINS=["https://your-frontend.vercel.app","https://your-custom-domain.com"]

Security

VariableDefaultDescription
SECRET_KEYdev-secret-key-change-in-productionUsed for signing tokens and other cryptographic operations. Must be changed in production.
API_KEY(none)Optional API key. When set, Pi agents should send it in the X-API-Key request header.
Never commit a real SECRET_KEY or API_KEY to source control. Generate a secure value with openssl rand -hex 32.

Statistics

VariableDefaultDescription
DEVICES_PER_PERSON1.5Divisor used to estimate the number of people from unique detected BLE devices. estimated_people = unique_devices / devices_per_person.
Adjust this ratio based on your deployment context. In a consumer environment where most people carry one or two Bluetooth devices, 1.5 is a reasonable estimate.

RSSI proximity thresholds

The backend classifies each detection into one of three zones based on its RSSI value (signal strength in dBm):
VariableDefaultZone assigned when
NEAR_THRESHOLD-60rssi >= NEAR_THRESHOLD → zone near
MEDIUM_THRESHOLD-75rssi >= MEDIUM_THRESHOLD and rssi < NEAR_THRESHOLD → zone medium
(implicit)rssi < MEDIUM_THRESHOLD → zone far
These thresholds match the Pi agent scanner defaults and the ZoneEnum values stored in the detections table (near, medium, far).

Logging

VariableDefaultDescription
LOG_LEVELINFOPython logging level. Accepted values: DEBUG, INFO, WARNING, ERROR, CRITICAL.
Log lines follow the format:
%(asctime)s - %(name)s - %(levelname)s - %(message)s

Build docs developers (and LLMs) love