🌊 HLADINATOR
HLADINATOR is an interactive and visually engaging web application for monitoring the current status and history of Czech reservoirs. The application provides precise data on water level, outflow, inflow, current volume, and additionally collects weather history (temperature and precipitation) directly from the source.
Data source: Povodí Vltavy (pvl.cz) and other river basin administrators in the Czech Republic.
🚀 How to Run the Application Locally
The application is built on a modern stack (React, Vite, TypeScript, Recharts, Leaflet). You don't need any complex backend to run it locally; the data is read directly from pre-generated static JSON files.
- Install dependencies (if you haven't already):
npm install - Start the local development server:
npm run dev - Open your browser at
http://localhost:5173.
🔄 How to Update Data (Scraping)
Povodí Vltavy does not provide a standard API for weather history, nor does it support direct requests from client browsers (due to CORS and security restrictions). Therefore, we use our own custom scraper.
To manually fetch the latest data from the river basin websites, run in your terminal:
npm run data:update
This command performs two actions:
npm run scrape: Scrapes the website for all 53 reservoirs and river stations, parses historical measurement tables, extracts precise inflow, outflow, volume, precipitation, and temperature. It then merges this data intelligently with your local database (public/data/*.json) and automatically backfills missing values from previous steps to avoid zero-drop anomalies in the charts.npm run build-index: Updates the main index filelakes_index.json, which the app uses to render fast previews (e.g., in the side menu or on the map).
⏰ Automated Data Updates (Cron / Scheduler)
To automatically accumulate weather and precipitation history even when your machine is off or you are sleeping, we recommend automating the execution of the npm run data:update script.
Here are the most common deployment methods:
Option A: Using Crontab on macOS / Linux (Local)
If you have a computer or home server (like a Raspberry Pi) running continuously:
- Open the terminal and type:
crontab -e - Add the following line at the end of the file (adjust the paths to your project and Node.js installation):
# Run scraping every 15 minutes */15 * * * * cd /Users/davis/WebstormProjects/davisfe.cz && /usr/local/bin/npm run data:update >> scraper.log 2>&1 - Save and close the editor. The system scheduler will take care of the rest.
Option B: Using GitHub Actions (For Production Hosting)
Once you push the project to GitHub, you can create a workflow file (e.g., .github/workflows/scrape.yml) to run the scraping script every hour on GitHub runners for free, and automatically commit and publish the updated .json data files back to the repository.
Option C: Built-in Simple Scheduler (Recommended for Development)
If you do not want to set up system cron, the project has a built-in scheduler. Open another terminal tab/window and run:
npm run data:watch
This command triggers an immediate update and then automatically schedules updates at 7 minutes past every 10-minute step (e.g., 18:07, 18:17, 18:27...). This delay ensures that the river basin web page has updated its data, preventing duplicate/empty requests.
🐳 Running in Docker (Production & Own Server)
If you want to deploy the application on your own server and run a PostgreSQL (TimescaleDB) database alongside it for future data collection, a Docker Compose configuration is prepared inside the Docker directory.
Requirements:
- Installed Docker and Docker Compose.
Deployment:
-
Go to the
Dockerdirectory and build/run the containers in the background:cd Docker docker-compose up -d --build -
Docker Compose will launch two containers:
hladinator-db: PostgreSQL (TimescaleDB) database running on port5432with apgdatavolume for data persistence.hladinator-web: Apache web server serving the built React static application on port80.
-
The web application is then accessible on port
80of your server.
🛠️ Fixing Anomalies in History (Zero Drops / Teeth in Graphs)
If the scraper hasn't run for a while (e.g., when your computer was turned off) and data was filled in subsequently, anomalies or drops to zero (teeth) might appear in the inflow and volume graphs. To clean up the entire history and interpolate these points from the last known state, run:
npm run data:fix
This script scans all data JSON files, detects anomalies/zeros, and repairs them.
📁 Key File and Folder Structure
/scripts/lakesConfig.ts- Contains configuration definitions for all 53 monitored reservoirs and rivers (including their river basin ID, GPS coordinates, maximum capacity limits, and elevation heights). You can add new stations here./public/data/- Static storage location for generated JSON files. In production, these must be exposed as static assets./src/components/- Holds user interface components, the Leaflet map, andLakeDetail.tsx(renders historical hydrology and weather charts via Recharts with automatic anomaly filtering).