This project implements a real-time temperature monitoring system based on the **Atlas Scientific EZO-RTD™** sensor module, interfaced via I²C to a Raspberry Pi. It extends a previous air quality monitoring platform (originally built around the HTU21D sensor) by replacing the temperature/humidity measurement stage with a high-precision RTD (Resistance Temperature Detector) circuit that provides temperature-only readings with significantly improved accuracy.
## 1. Resumen del Proyecto
The system follows a layered architecture: a C daemon reads sensor data over I²C, writes it to a JSON file, and a lightweight HTML/CSS/JS dashboard served by Nginx polls that file every second to display live temperature readings in a browser.
Este repositorio documenta la arquitectura de software y los lineamientos de diseño de hardware para un sistema de adquisición de datos en tiempo real orientado a fotobiorreactores. Aunque el repositorio fue inicializado bajo el título de un proyecto para la sonda de temperatura PT1000, el sistema actual constituye una plataforma integral para el monitoreo simultáneo de cuatro parámetros críticos utilizando módulos OEM de la serie EZO de Atlas Scientific:
---
* **Temperatura** (Sonda RTD PT1000)
* **Potencial de Hidrógeno** (Sonda de pH)
* **Oxígeno Disuelto** (Sonda DO galvánica/óptica)
La solución implementa una topología de red distribuida localmente, utilizando un modelo Cliente-Servidor optimizado por un proxy inverso para la gestión del tráfico y la mitigación de restricciones de intercambio de recursos de origen cruzado (CORS).
The EZO-RTD is a complete circuit board that conditions RTD signals and communicates digitally. It supports both UART and I²C protocols. In this project it operates in **I²C mode**.
### 2.1. Capa de Presentación (Frontend)
Interfaz gráfica de usuario (GUI) asíncrona desarrollada en HTML5, CSS3 y JavaScript puro (ES6+). Implementa rutinas de *polling* de alta frecuencia (1000 ms) para la actualización de métricas en tiempo real y renderizado de series temporales mediante la biblioteca `Chart.js`.
Key specifications:
### 2.2. Capa de Enrutamiento y Proxy (Nginx)
Servidor web Nginx configurado en el puerto `8888`. Actúa como servidor de archivos estáticos para la capa de presentación y opera como proxy inverso, redirigiendo todas las solicitudes HTTP bajo el prefijo `/api/` hacia el proceso de Node.js en el puerto `3000`.
| Parameter | Value |
### 2.3. Capa de Lógica de Negocio y API (Backend)
|---|---|
Servidor HTTP desarrollado en entorno Node.js utilizando el framework Express. Sus responsabilidades principales incluyen:
| I²C Address | `0x66` |
* Exposición de endpoints RESTful para la transmisión de telemetría.
| Supply Voltage | 3.3 V – 5.0 V |
* Simulación de retardos y latencias físicas inherentes al protocolo I2C (300 ms - 900 ms).
| Temperature Range | −126.000 °C to 1254.000 °C |
* Implementación de un analizador léxico (*Lexical Parser*) capaz de procesar el conjunto de instrucciones oficial de Atlas Scientific (calibración, compensación ambiental y diagnóstico).
| Resolution | 0.001 °C |
| Accuracy | ±(0.1 °C + 0.0017 × |T|) |
| Communication | I²C / UART |
| Response Time | ≈ 1 s per reading |
### Wiring — ISCCB-2 → Raspberry Pi
### 2.4. Capa Física (Adquisición de Datos)
Demonios ejecutables compilados en C/C++ responsables de la interrogación directa de los registros de hardware en el bus I2C de la Raspberry Pi a través de los pines GPIO (SDA/SCL).
| ISCCB-2 Pin | Raspberry Pi Pin | Signal |
## 3. Características Técnicas Implementadas
|---|---|---|
| VCC | Pin 1 | 3.3 V |
| GND | Pin 6 | Ground |
| SDA | Pin 3 (GPIO2) | I²C Data |
| SCL | Pin 5 (GPIO3) | I²C Clock |
| OFF | — | Not connected |
> **Note:** The `OFF` pin is used to put the EZO circuit into low-power sleep mode. It is left unconnected in this implementation, meaning the circuit remains always active.
* **Motor de Evaluación de Alarmas:** Subsistema lógico que compara la telemetría en tiempo real contra umbrales de operación críticos y de advertencia definidos paramétricamente en el archivo `config/alarms.json`.
* **Consola de Hardware Virtual:** Emulador integrado en la interfaz de usuario que permite la inyección de cadenas de comandos estandarizadas hacia los módulos EZO, facilitando rutinas de calibración multipunto y configuración de registros de compensación.
* **Módulo de Exportación de Datos:** Procesamiento de arreglos de datos históricos en el cliente y serialización a formato `.xlsx` utilizando la biblioteca `SheetJS`, permitiendo la extracción de registros tabulares para análisis posterior.
---
## 4. Estructura del Directorio Fuente
## Repository Structure
```text
/
```
├── api/
basic-ui-dashboard/
│ └── server.js # Lógica de enrutamiento Express y simulador de protocolo EZO
├── config/
│ ├── alarms.json # Definición de límites operativos de seguridad
│ └── sensors.json # Metadatos y resolución de los instrumentos
├── data/
├── data/
│ ├── EZORTD.json # Live temperature output (written by daemon)
│ └── *.json # Vectores de estado transitorios poblados por procesos C++
│ ├── EZORTD.csv # CSV log with timestamps (written by daemon)
├── frontend/
│ └── HTU21D.json # Legacy HTU21D data (retained from previous project)
│ ├── index.html # Interfaz principal de control
├── images/
│ ├── dashboard.js # Rutinas de renderizado y evaluación de estado
│ ├── thermometer-outline.svg
│ ├── mock-service.js # Interfaz de comunicación asíncrona con el backend
│ ├── water-outline.svg
│ ├── export-service.js # Lógica de construcción de conjuntos de datos para gráficos
│ ├── cloud-outline.svg
│ └── export-excel.js # Formateo y serialización de archivos de hoja de cálculo
│ └── sunny-outline.svg
├── logs/
│ └── *.csv # Registros históricos persistentes para series temporales
├── sensors/
├── sensors/
│ ├── EZORTD/
│ └── */*.c # Código fuente de los controladores de hardware (I2C)
│ │ ├── ezortd.h # EZO RTD library header
│ │ ├── ezortd.c # I²C communication implementation
Minimal single-sensor dashboard. Fetches `data/EZORTD.json` and refreshes every 1 second. Suitable for monitoring a single RTD probe.
### `index-css.html` — Multi-sensor Dashboard
Extended dashboard supporting temperature, humidity, CO₂, and atmospheric pressure from multiple JSON sources. Sensor cards are currently wired to `HTU21D.json`; the other fetch calls are commented out pending integration of additional sensors.
---
## Migration Notes from HTU21D
The previous version of this project used the HTU21D sensor for combined temperature and humidity measurements. The EZO-RTD replaces only the temperature measurement stage. Key differences:
| Aspect | HTU21D | EZO-RTD |
|---|---|---|
| I²C Address | `0x40` | `0x66` |
| I²C Bus | Bus 1 | Bus 1 |
| Measurements | Temperature + Humidity | Temperature only |
| Resolution | 0.01 °C | 0.001 °C |
| Communication library | `libi2c` (SMBus) | Raw I²C (`linux/i2c-dev.h`) |
The HTU21D source files are retained in `sensors/HTU21D/` for reference.
---
## Troubleshooting
**Sensor not detected at `0x66`:**
Check that I²C mode is selected on the EZO-RTD. The default factory mode is UART. To switch to I²C, consult the [Atlas Scientific EZO-RTD datasheet](https://atlas-scientific.com/circuits/ezo-rtd-circuit/) and follow the UART-to-I²C mode switching procedure.
**`ioctl: Operation not permitted`:**
Run the executable with `sudo` or add the user to the `i2c` group:
```sh
sudo usermod -aG i2c $USER
```
**JSON file not updating:**
Verify the daemon is running (`ps aux | grep ezortd_daemon`) and that the output path in `ezortd_daemon.c` is correct and writable.
**Browser shows `--` (no data):**
Confirm Nginx is serving files from the correct directory and that `data/EZORTD.json` exists and is valid JSON.