# People Flow Project People flow analysis for street videos using YOLO tracking and face-based demographic estimation. ## What it does - Counts unique people when they cross a configured line - Estimates one age bucket per counted track: `minor`, `adult`, or `senior` - Estimates one gender bucket per counted track: `male` or `female` - Writes an annotated output video, per-video JSON, and batch summary CSV ## Pipeline 1. Detect and track `person` objects with Ultralytics YOLO. 2. Assign a stable `track_id` with BoT-SORT or ByteTrack. 3. Count each track once when it crosses the configured line. 4. Sample person crops for each track and run DeepFace age/gender analysis. 5. Use track-level voting so each counted person lands in only one age bucket and one gender bucket. ## Project Layout - `main.py`: CLI entrypoint - `src/people_flow/`: application modules - `configs/default_config.yaml`: default runtime settings - `outputs/`: generated result files - `docs/plans/`: design and implementation notes ## Recommended Environment - Linux - NVIDIA GPU with CUDA - Python `3.10` or `3.11` `deepface` and its transitive dependencies are not a good fit for Python `3.14`, so do not build this environment on the current local interpreter version. ## Install ```bash python3.11 -m venv .venv source .venv/bin/activate pip install --upgrade pip pip install -r requirements.txt ``` ## Single Video ```bash python main.py video \ --input "/path/to/video.mp4" \ --line "0.1,0.55,0.9,0.55" ``` ## Batch Directory ```bash python main.py batch \ --input-dir "/path/to/videos" \ --line "0.1,0.55,0.9,0.55" ``` ## RTSP Stream ```bash python main.py --output-dir outputs rtsp \ --input "rtsp://user:password@host:554/stream" ``` RTSP mode behaves differently from offline video mode: - The stream is sampled at one processed frame per second - Statistics are isolated into 30-minute windows - Each completed window writes one JSON file - `latest.json` is overwritten on every completed window - RTSP mode does not save annotated video by default ## Output Files Each processed video produces: - `outputs//.annotated.mp4` - `outputs//.json` Batch mode also produces: - `outputs/batch_summary.csv` RTSP mode produces: - `outputs/rtsp_stream/latest.json` - `outputs/rtsp_stream/windows/stats_YYYY-MM-DD_HH-MM-SS.json` ## Docker On Ubuntu 24.04 x86_64 The project can be packaged for an x86_64 NVIDIA host with Docker. The expected weight layout is: - `weights/yolo11n.pt` - `weights/deepface/age_model_weights.h5` - `weights/deepface/gender_model_weights.h5` - `weights/deepface/retinaface.h5` Build the image: ```bash docker build -t people-flow-project:test . ``` The Docker image uses [`requirements-docker.txt`](/Users/zxmacmini1/Documents/人流检测/people_flow_project/requirements-docker.txt) so the container installs `opencv-python-headless` instead of the desktop OpenCV wheel. The image bakes in all runtime weights and copies the DeepFace `.h5` files into `~/.deepface/weights` during build. Run the management API container: ```bash docker run -d \ --name people-flow-project \ --restart unless-stopped \ --gpus all \ --shm-size 1g \ -p 18082:18082 \ -e RTSP_URL="rtsp://user:password@host:554/stream" \ -v /path/to/config:/opt/people-flow/config \ -v /path/to/outputs:/opt/people-flow/outputs \ people-flow-project:test ``` Or use Compose: ```bash docker compose up --build people-flow-project ``` Container behavior: - Seeds `config/local.yaml` from `config/config.example.yaml` when needed - Writes RTSP updates through the child API to `runtime.rtsp_url` - Exposes `GET /api/manage/health` on `http://127.0.0.1:18082` - Persists config and outputs through mounted `./config` and `./outputs` ## Notes - `minor` means age `< 18` - `adult` means age `18-59` - `senior` means age `>= 60` - Tracks without a reliable face result are counted only in `total_people` and `unknown_attributes`