# AI智能视觉检测 **Repository Path**: get2bad/visual_ai ## Basic Information - **Project Name**: AI智能视觉检测 - **Description**: 实时视频流 AI 检测服务 - **Primary Language**: Unknown - **License**: GPL-2.0 - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2025-12-17 - **Last Updated**: 2026-03-05 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # lf_ai - 实时视频流 AI 检测服务 [![Version](https://img.shields.io/badge/version-2.7.4-blue.svg)](https://github.com/yourusername/lf_ai) [![Python](https://img.shields.io/badge/python-3.10+-green.svg)](https://www.python.org/) [![License](https://img.shields.io/badge/license-MIT-orange.svg)](LICENSE) > 实时视频流 AI 检测服务 > 支持多路视频流并发处理、RTSP/RTMP/HTTP-FLV/HLS 输入、GPU 加速推理、实时 RTMP 推流输出 --- ## 目录 - [项目简介](#项目简介) - [核心特性](#核心特性) - [快速开始](#快速开始) - [系统架构](#系统架构) - [项目结构](#项目结构) - [配置说明](#配置说明) - [API 文档](#api-文档) - [部署指南](#部署指南) - [开发指南](#开发指南) - [性能优化](#性能优化) - [常见问题](#常见问题) --- ## 项目简介 **lf_ai** 是一个实时视频流 AI 检测服务。项目采用分层架构,支持多种检测场景(人车检测、火焰识别、安全帽检测、车牌识别等),可应用于安防监控、无人机巡检等领域。 ### 技术栈 - **后端框架**: Flask + Gevent (异步服务) - **AI 推理**: PyTorch + Ultralytics YOLO (支持 TensorRT 加速) - **视频处理**: FFmpeg (多格式支持 + NVENC 硬件编码) - **消息队列**: MQTT (异步告警推送) - **并发模型**: 多进程 + 多线程 (规避 GIL,每路流独立进程) ### 应用场景 - **实时视频监控**: RTSP/RTMP 流接入,实时目标检测 - **无人机巡检**: 空中视频实时分析,异常自动告警 - **交通监控**: 车辆识别、车牌识别、违章检测 - **安全预警**: 火焰检测、烟雾识别、异常行为识别 - **数据分析**: 人流统计、区域入侵检测、目标轨迹追踪 --- ## 核心特性 ### 性能特点 - **低延迟**: 端到端延迟 < 1s,丢帧策略防止堆积 - **多路并发**: 每路流独立进程,互不影响,支持数十路同时处理 - **动态调度**: 动态跳帧、队列满丢旧帧,确保实时性 - **内存优化**: LRU 缓存 + 模型共享,内存占用可控 ### 功能特性 - **多格式支持**: RTSP/RTMP/HTTP-FLV/HLS/本地文件 - **灵活渲染**: 可配置检测框/标签/置信度/ID 显示 - **实时告警**: MQTT 推送 + HTTP 回调 - **图像分析**: 单图检测、图像差异对比 - **扩展能力**: 车牌识别等可插拔扩展 - **热配置**: 配置热加载,无需重启服务 ### 硬件加速 - **GPU 推理**: 支持 CUDA + TensorRT 加速 - **NVENC 编码**: NVIDIA 硬件编码,降低 CPU 负载 - **多模型支持**: PyTorch (.pt) / ONNX (.onnx) / TensorRT (.engine) --- ## 快速开始 ### 前置要求 - **Python**: 3.10 或更高版本 - **FFmpeg**: 系统已安装 `ffmpeg` 和 `ffprobe` - **GPU (可选)**: NVIDIA 显卡 + CUDA (用于 GPU 加速) ### 安装步骤 #### 1. 克隆项目 ```bash git clone https://github.com/yourusername/lf_ai.git cd lf_ai ``` #### 2. 创建虚拟环境 ```bash python3 -m venv .venv310 source .venv310/bin/activate # Windows: .venv310\Scripts\activate ``` #### 3. 安装依赖 **CPU 版本** (Mac / 无显卡环境): ```bash pip install -r requirements-cpu.txt ``` **GPU 版本** (NVIDIA GPU): ```bash pip install -r requirements-gpu.txt ``` #### 4. 配置环境 编辑 [config.ini](config.ini) 文件,设置运行环境: ```ini [app] env = dev # 开发环境: dev, 生产环境: platform ``` #### 5. 启动服务 ```bash python launch.py ``` 服务默认运行在 `http://0.0.0.0:8001` #### 6. 验证服务 ```bash curl http://127.0.0.1:8001/health ``` 返回 `{"status": "ok"}` 表示服务正常运行。 ### 示例:发起视频流分析 ```bash curl -X POST http://127.0.0.1:8001/stream/analyse \ -H "Content-Type: application/json" \ -d '{ "url": "rtmp://example.com/live/input", "targetUrl": "rtmp://example.com/live/output", "type": "person_car", "modelType": 3, "maxDet": 2000, "boxesFlag": true, "labelsFlag": true }' ``` ### 示例:停止流分析 ```bash curl -X POST http://127.0.0.1:8001/stop/stream \ -H "Content-Type: application/json" \ -d '{"url": "rtmp://example.com/live/output"}' ``` --- ## 系统架构 ### 架构概览 项目采用分层架构,将业务逻辑、基础设施、运行时管线清晰分离: ```mermaid graph TB subgraph Presentation["接口层 (Presentation Layer)"] API[Flask HTTP API] Swagger[Swagger 文档] DTO[数据传输对象 DTO] end subgraph Application["应用层 (Application Layer)"] UseCase[业务用例 Use Cases] Factory[分析工厂 Factory] Registry[解析器注册表 Registry] Resolver[场景解析器 Resolvers] end subgraph Runtime["运行时层 (Runtime Layer)"] Processor[流处理器 Processor] Worker[工作进程 Worker] FrameProc[帧处理器] Renderer[渲染器] end subgraph Infrastructure["基础设施层 (Infrastructure Layer)"] FFmpeg[FFmpeg 视频处理] MQTT[MQTT 消息推送] Model[AI 模型加载] Cache[缓存管理] end Presentation --> Application Application --> Runtime Runtime --> Infrastructure style Presentation fill:#e1f5ff style Application fill:#fff3e0 style Runtime fill:#f3e5f5 style Infrastructure fill:#e8f5e9 ``` ### 数据流(端到端) **实时流分析处理流程**: ```mermaid flowchart LR A[客户端请求] --> B[Flask API] B --> C[DTO 映射] C --> D[分析工厂] D --> E[场景解析器] E --> F[流处理器] F --> G[启动子进程] subgraph Worker["子进程 Worker"] H[FFmpeg 拉流] --> I[帧解码] I --> J[AI 模型推理] J --> K[结果过滤] K --> L[检测框绘制] L --> M{是否告警?} M -->|是| N[MQTT 推送] M -->|否| O[继续处理] N --> O O --> P[FFmpeg 推流] end G --> H P --> Q[RTMP 服务器] style A fill:#e3f2fd style B fill:#fff3e0 style Q fill:#e8f5e9 style Worker fill:#f3e5f5 ``` **处理步骤说明**: 1. **HTTP 请求** → Flask 接收 `/stream/analyse` 2. **请求解析** → DTO 映射为 `Request` 实体 3. **服务分发** → `analyse_factory` 选择对应的 resolver 4. **进程调度** → `StreamProcessor` 启动子进程 `StreamWorker` 5. **视频拉取** → FFmpeg 拉流并解码为 rawvideo (BGR24) 6. **逐帧推理** → `FrameProcessor` 调用 AI 模型检测目标 7. **结果过滤** → 按置信度、区域、类别过滤 8. **渲染绘制** → 在帧上绘制检测框和标签 9. **告警触发** → 满足条件时发送 MQTT/HTTP 回调 10. **视频推流** → FFmpeg 编码并推送到 RTMP 服务器 ### 并发模型 ```mermaid graph TB subgraph MainProcess["主进程 Main Process"] Flask[Flask HTTP 服务
端口: 8001] Scheduler[任务调度器] Manager[进程管理器] end subgraph Stream1["子进程 1 - 流 A"] FFmpeg1_Pull[FFmpeg 拉流进程] Worker1[StreamWorker] Thread1[写入线程
队列大小: 6] FFmpeg1_Push[FFmpeg 推流进程] FFmpeg1_Pull --> Worker1 Worker1 --> Thread1 Thread1 --> FFmpeg1_Push end subgraph Stream2["子进程 2 - 流 B"] FFmpeg2_Pull[FFmpeg 拉流进程] Worker2[StreamWorker] Thread2[写入线程
队列大小: 6] FFmpeg2_Push[FFmpeg 推流进程] FFmpeg2_Pull --> Worker2 Worker2 --> Thread2 Thread2 --> FFmpeg2_Push end subgraph StreamN["子进程 N - 流 N"] FFmpegN_Pull[FFmpeg 拉流进程] WorkerN[StreamWorker] ThreadN[写入线程
队列大小: 6] FFmpegN_Push[FFmpeg 推流进程] FFmpegN_Pull --> WorkerN WorkerN --> ThreadN ThreadN --> FFmpegN_Push end Flask --> Scheduler Scheduler --> Manager Manager --> Stream1 Manager --> Stream2 Manager --> StreamN RTSP1[RTSP 输入源 A] --> FFmpeg1_Pull FFmpeg1_Push --> RTMP1[RTMP 输出 A] RTSP2[RTSP 输入源 B] --> FFmpeg2_Pull FFmpeg2_Push --> RTMP2[RTMP 输出 B] RTSPN[RTSP 输入源 N] --> FFmpegN_Pull FFmpegN_Push --> RTMPN[RTMP 输出 N] style MainProcess fill:#e3f2fd style Stream1 fill:#fff3e0 style Stream2 fill:#f3e5f5 style StreamN fill:#e8f5e9 ``` **并发特点**: - **主进程**: Flask HTTP 服务 + 任务调度 - **每路流一个子进程**: 规避 Python GIL,隔离故障 - **子进程内**: - 1 个 FFmpeg 拉流进程 (解码) - 1 个 FFmpeg 推流进程 (编码) - 1 个写入线程 (队列满丢旧帧,保证实时性) 核心原则: 宁可丢帧,不允许堆积导致延迟 ### 核心组件关系 ```mermaid graph LR subgraph HTTP["HTTP 层"] API[AppEndpoint
API 路由] Mapper[RequestMapper
请求映射] end subgraph UseCases["用例层"] Analyse[Analyse
流/视频/图片分析] Stop[StopStream
停止流] Active[ActiveStreams
活跃流查询] end subgraph Services["服务层"] Factory[AnalyseFactory
分析工厂] Registry[ResolverRegistry
解析器注册表] Lifecycle[StreamLifecycle
流生命周期] end subgraph Resolvers["场景解析器"] PersonCar[PersonCar
人车检测] Fire[Fire
火焰检测] Helmet[Helmet
安全帽] Others[其他场景...] end subgraph Processors["处理器层"] StreamProc[StreamProcessor
流处理调度] VideoProc[VideoProcessor
视频处理] Worker[StreamWorker
工作进程] end subgraph Runtime["运行时组件"] FrameProc[FrameProcessor
帧处理] Inference[FrameInference
推理封装] Drawer[DetectionDrawer
检测框绘制] Filter[DetectionFilter
结果过滤] Writer[StreamWriter
推流写入] end subgraph Infra["基础设施"] FFmpegCmd[FFmpegCmd
FFmpeg 命令] ModelHandler[ModelHandler
模型加载] MQTTSender[MQTTAsyncSender
消息推送] LocalCache[LocalCache
本地缓存] end API --> Mapper Mapper --> Analyse Analyse --> Factory Factory --> Registry Registry --> PersonCar Registry --> Fire Registry --> Helmet Registry --> Others PersonCar --> StreamProc Fire --> StreamProc Helmet --> StreamProc Stop --> Lifecycle Active --> Lifecycle StreamProc --> Worker VideoProc --> Worker Worker --> FrameProc FrameProc --> Inference FrameProc --> Filter FrameProc --> Drawer FrameProc --> Writer Inference --> ModelHandler Writer --> FFmpegCmd FrameProc --> MQTTSender StreamProc --> LocalCache style HTTP fill:#e3f2fd style UseCases fill:#fff3e0 style Services fill:#f3e5f5 style Resolvers fill:#e8f5e9 style Processors fill:#fce4ec style Runtime fill:#fff9c4 style Infra fill:#e0f2f1 ``` --- ## 项目结构 ``` lf_ai/ ├── launch.py # 服务启动入口 ├── config.ini # 环境配置 (dev/platform) ├── requirements-cpu.txt # CPU 环境依赖 ├── requirements-gpu.txt # GPU 环境依赖 ├── Dockerfile # Docker 构建文件 ├── README.md # 项目文档 ├── ARCH_REFACTORING_PLAN.md # 架构重构计划 ├── CONFIG_REFRESH_GUIDE.md # 配置刷新指南 │ ├── app/ # 应用主目录 │ ├── presentation/ # 【接口层】HTTP API 与数据传输对象 │ │ ├── http/ # Flask 路由与 Swagger │ │ │ ├── app_endpoint.py # 主要 API 端点 │ │ │ ├── __init__.py # 路由注册 │ │ │ └── swagger_configs/ # Swagger 文档配置 │ │ └── dto/ # 数据传输对象 │ │ └── request_mapper.py # 请求映射器 │ │ │ ├── application/ # 【应用层】业务用例与服务 │ │ ├── use_cases/ # 用例(业务流程入口) │ │ │ ├── analyse.py # 流/视频/图片分析 │ │ │ ├── active_streams.py # 查询活跃流 │ │ │ ├── stop_stream.py # 停止流 │ │ │ ├── stream_standby.py # 流预热 │ │ │ └── pic_diff.py # 图片差异分析 │ │ ├── services/ # 服务(工厂、注册表、辅助) │ │ │ ├── analyse_factory.py # 核心分发工厂 │ │ │ ├── resolver_registry.py # Resolver 注册表 │ │ │ ├── resolver_contract.py # Resolver 接口协议 │ │ │ ├── model_path_resolver.py # 模型路径解析 │ │ │ ├── handle_type_guesser.py # 媒体类型识别 │ │ │ ├── request_accessor.py # 请求字段访问器 │ │ │ ├── image_diff_helper.py # 图像差异算法 │ │ │ ├── image_diff_processor.py # 图像差异处理 │ │ │ ├── stream_lifecycle.py # 流生命周期管理 │ │ │ └── resolvers/ # 业务场景 Resolver │ │ │ ├── person_car.py # 人车检测 │ │ │ ├── fire.py # 火焰检测 │ │ │ ├── helmet.py # 安全帽检测 │ │ │ └── ... # 其他场景 │ │ └── ports/ # 接口定义(依赖反转) │ │ ├── media.py # 媒体接口 │ │ ├── messaging.py # 消息接口 │ │ ├── model.py # 模型接口 │ │ └── storage.py # 存储接口 │ │ │ ├── runtime/ # 【运行时层】性能关键路径 │ │ ├── streaming/ # 实时流处理核心 │ │ │ ├── frame_processor.py # 帧处理主循环 │ │ │ ├── frame_inference.py # 推理封装 │ │ │ ├── stream_writer.py # 推流写入线程 │ │ │ ├── stream_trigger.py # 告警触发器 │ │ │ ├── detection_filter.py # 检测结果过滤 │ │ │ └── condition_filter.py # 条件过滤器 │ │ ├── orchestration/ # 进程调度与管理 │ │ │ ├── stream_processor.py # 流处理调度器 │ │ │ ├── video_processor.py # 视频处理调度器 │ │ │ ├── process_manager.py # 子进程管理器 │ │ │ ├── caches.py # 全局缓存 │ │ │ └── stream_standby.py # 流预热管理 │ │ ├── workers/ # 子进程工作单元 │ │ │ ├── stream_worker.py # 流处理 Worker │ │ │ └── video_worker.py # 视频处理 Worker │ │ ├── rendering/ # 渲染与绘制 │ │ │ ├── detection_drawer.py # 检测框绘制 │ │ │ ├── color_manager.py # 颜色管理 │ │ │ └── color_configs.py # 颜色配置 │ │ ├── media_helper.py # 媒体辅助(截图/水印) │ │ └── model_predict.py # 通用推理封装 │ │ │ ├── infrastructure/ # 【基础设施层】外部依赖 │ │ ├── ffmpeg/ # FFmpeg 封装 │ │ │ ├── ffmpeg_cmd.py # 命令拼接 │ │ │ └── ffmpeg_util.py # 工具函数 │ │ ├── messaging/ # 消息推送 │ │ │ ├── mqtt_connector.py # MQTT 连接器 │ │ │ ├── mqtt_async_sender.py # 异步发送器 │ │ │ └── mqtt_trigger.py # MQTT 触发器 │ │ ├── ml/ # 模型加载与管理 │ │ │ ├── model_handler.py # 模型处理器 │ │ │ └── download_util.py # 模型下载 │ │ ├── cache/ # 缓存实现 │ │ │ └── local_cache.py # 本地 TTL 缓存 │ │ └── misc/ # 工具集合 │ │ ├── logger.py # 日志封装 │ │ ├── log_handler.py # 日志轮转 │ │ ├── license_checker.py # License 校验 │ │ └── ... # 其他工具 │ │ │ ├── entity/ # 【实体层】数据模型 │ │ ├── request.py # 请求实体 │ │ └── result.py # 响应实体 │ │ │ ├── domain/ # 【领域层】领域类型与策略 │ │ ├── entities/ # 领域实体 │ │ ├── policies/ # 领域策略 │ │ └── types/ # 领域类型 │ │ └── media_extensions.py # 媒体扩展类型 │ │ │ ├── extensions/ # 【扩展层】可插拔功能 │ │ └── plate_recognition/ # 车牌识别扩展 │ │ ├── plate_recognizer.py # 车牌识别器 │ │ ├── plate_processor.py # 车牌处理器 │ │ └── ... │ │ │ ├── conf/ # 配置管理 │ │ ├── app_config.py # 配置加载器 │ │ ├── config_parser.py # 配置解析器 │ │ ├── constants.py # 常量定义 │ │ └── yaml/ # YAML 配置文件 │ │ ├── app_config_dev.yaml # 开发环境配置 │ │ └── app_config_platform.yaml # 生产环境配置 │ │ │ └── tools/ # 运维工具 │ ├── api_doc_export.py # API 文档导出 │ ├── batch_export.py # 批量导出 │ └── image_diff_benchmark.py # 性能测试 │ ├── asset/ # 资源文件 │ ├── model/ # AI 模型存储 │ │ ├── person_car/ # 人车检测模型 │ │ └── rail_transit/ # 轨道交通模型 │ ├── font/ # 字体资源 │ └── icon/ # 图标资源 │ ├── logs/ # 日志目录 │ └── backup/ # 日志备份 │ └── tmp_static/ # 临时静态文件(截图等) ``` ### 关键模块说明 | 模块 | 职责 | 性能关键 | |------|------|---------| | **presentation** | HTTP 接口、请求映射 | ❌ | | **application** | 业务逻辑、服务编排 | ❌ | | **runtime** | 实时管线、多进程调度 | ✅ | | **infrastructure** | FFmpeg、MQTT、模型加载 | ✅ (部分) | | **entity/domain** | 数据模型、领域定义 | ❌ | 注: ✅ 标记为性能关键路径,修改时需格外小心 --- ## 配置说明 ### 配置文件结构 - **config.ini**: 环境选择器(`dev` 或 `platform`) - **app_config_dev.yaml**: 开发环境配置 - **app_config_platform.yaml**: 生产环境配置 ### 主要配置项 #### FFmpeg 配置 ```yaml ffmpeg: pull_scale_enable: false # 是否降低拉流分辨率 pull_scale_width: 1280 pull_scale_height: 720 analyze_duration: '10000000' # 流分析持续时间(微秒) probe_size: '10000000' # 探测大小(字节) video_encoder: "h264_nvenc" # 视频编码器(h264_nvenc/libx264) push_fps: 30 # 推流帧率 write_queue_size: 6 # 写入队列大小(越小延迟越低) timeout_restart_threshold: 20 # 连续丢帧多少次后重启推流 ``` #### 帧处理配置 ```yaml frame: skip: 2 # 跳帧策略(1=每帧推理,2=每2帧推理) infer_fps: 30 # 推理节拍器(0=禁用) ``` #### 模型配置 ```yaml model: path: asset/model/ # 模型文件路径 type: 3 # 1:pt, 2:onnx, 3:engine warmup: true # 是否进行模型预热 warmup_imgsz: 960 # 预热图像尺寸 ``` #### MQTT 配置 ```yaml mqtt: host: 127.0.0.1 port: 1883 username: mqtt_user password: mqtt_password topic: ai_analyse ``` #### 日志配置 ```yaml log: level: INFO # 日志级别 backup_days: 7 # 日志备份保留天数 frame_log_interval: 5 # 每N帧打印一次详细日志 ``` #### 绘制优化配置 ```yaml draw: disable_chinese_text_threshold: 50 # 检测框超过此阈值禁用中文标签 high_performance_threshold: 120 # 超过此阈值启用极速模式(只画框) frame_skip_threshold: 150 # 超过此阈值启用跳帧绘制 ``` ### 配置热更新 ```bash # 重新加载配置(无需重启服务) curl -X POST http://127.0.0.1:8001/config/reload # 查看当前配置 curl http://127.0.0.1:8001/config/info ``` --- ## API 文档 ### 核心接口 #### 1. 健康检查 ```bash GET /health ``` **响应示例**: ```json { "status": "ok", "version": "2.7.4" } ``` #### 2. 流分析 ```bash POST /stream/analyse ``` **请求参数**: | 字段 | 类型 | 必填 | 说明 | |------|------|------|------| | url | string | ✅ | 输入流地址(RTSP/RTMP/HTTP-FLV等) | | targetUrl | string | ❌ | 输出流地址(RTMP) | | type | string | ✅ | 检测类型(person_car/fire/helmet等) | | modelType | int | ❌ | 模型类型(1:pt, 2:onnx, 3:engine) | | maxDet | int | ❌ | 最大检测数(默认5000) | | conf | float | ❌ | 置信度阈值(默认0.25) | | boxesFlag | bool | ❌ | 是否绘制检测框(默认true) | | labelsFlag | bool | ❌ | 是否绘制标签(默认true) | | confFlag | bool | ❌ | 是否显示置信度(默认false) | | idFlag | bool | ❌ | 是否显示ID(默认false) | | download | bool | ❌ | 是否先下载(视频文件,默认false) | **请求示例**: ```bash curl -X POST http://127.0.0.1:8001/stream/analyse \ -H "Content-Type: application/json" \ -d '{ "url": "rtmp://example.com/live/input", "targetUrl": "rtmp://example.com/live/output", "type": "person_car", "modelType": 3, "maxDet": 2000, "conf": 0.5, "boxesFlag": true, "labelsFlag": true }' ``` #### 3. 停止流 ```bash POST /stop/stream ``` **请求参数**: | 字段 | 类型 | 必填 | 说明 | |------|------|------|------| | url | string | ✅ | 要停止的目标流地址(targetUrl) | **请求示例**: ```bash curl -X POST http://127.0.0.1:8001/stop/stream \ -H "Content-Type: application/json" \ -d '{"url": "rtmp://example.com/live/output"}' ``` #### 4. 图片分析 ```bash POST /pic/analyse ``` **请求参数**: | 字段 | 类型 | 必填 | 说明 | |------|------|------|------| | url | string | ✅ | 图片URL地址 | | type | string | ✅ | 检测类型 | | conf | float | ❌ | 置信度阈值 | #### 5. 图片差异对比 ```bash POST /pic/diff ``` **请求参数**: | 字段 | 类型 | 必填 | 说明 | |------|------|------|------| | urls | array | ✅ | 两张图片的URL数组 | | threshold | float | ❌ | 差异阈值 | #### 6. 查询活跃流 ```bash GET /stream/active ``` #### 7. 流预热 ```bash POST /stream/standby ``` 用于预先拉取流并保持连接,降低后续分析的启动延迟。 ### Swagger 文档 启动服务后访问:`http://127.0.0.1:8001/apidocs` --- ## 部署指南 ### Docker 部署 #### 1. 构建镜像 ```bash docker build -t lf_ai:latest . ``` #### 2. 运行容器 **CPU 版本**: ```bash docker run -d \ --name lf_ai \ -p 8001:8001 \ -v $(pwd)/asset:/app/asset \ -v $(pwd)/logs:/app/logs \ lf_ai:latest ``` **GPU 版本**: ```bash docker run -d \ --name lf_ai \ --gpus all \ -p 8001:8001 \ -v $(pwd)/asset:/app/asset \ -v $(pwd)/logs:/app/logs \ lf_ai:latest ``` ### 生产环境部署 #### 1. 系统要求 - **操作系统**: Ubuntu 20.04+ / CentOS 7+ - **CPU**: 8核心+(推荐16核) - **内存**: 16GB+(推荐32GB) - **GPU**: NVIDIA RTX 3090/4090(可选) - **存储**: 100GB+ SSD #### 2. GPU 环境配置 ```bash # 安装 NVIDIA 驱动 ubuntu-drivers devices sudo ubuntu-drivers autoinstall # 验证驱动 nvidia-smi # 安装 CUDA(推荐 11.8+) # 参考:https://developer.nvidia.com/cuda-downloads # 验证 PyTorch CUDA 支持 python -c "import torch; print(torch.cuda.is_available())" # 验证 FFmpeg NVENC 支持 ffmpeg -hide_banner -encoders | grep nvenc ``` #### 3. 服务配置 编辑 `app/conf/yaml/app_config_platform.yaml`: ```yaml # 启用 NVENC 硬件编码 ffmpeg: video_encoder: "h264_nvenc" # 使用 TensorRT 引擎 model: type: 3 # engine # 配置日志级别 log: level: WARNING # 生产环境降低日志输出 ``` #### 4. 使用 Systemd 管理服务 创建服务文件 `/etc/systemd/system/lf_ai.service`: ```ini [Unit] Description=AI Service After=network.target [Service] Type=simple User=ai_user WorkingDirectory=/opt/lf_ai Environment="PATH=/opt/lf_ai/.venv310/bin" ExecStart=/opt/lf_ai/.venv310/bin/python launch.py Restart=always RestartSec=10 [Install] WantedBy=multi-user.target ``` 启动服务: ```bash sudo systemctl daemon-reload sudo systemctl enable lf_ai sudo systemctl start lf_ai sudo systemctl status lf_ai ``` #### 5. Nginx 反向代理 ```nginx upstream lf_ai_backend { server 127.0.0.1:8001; } server { listen 80; server_name ai.example.com; location / { proxy_pass http://lf_ai_backend; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_connect_timeout 300s; proxy_send_timeout 300s; proxy_read_timeout 300s; } } ``` ### Nuitka 打包(单文件可执行程序) ```bash python -m nuitka \ --standalone \ --onefile \ --follow-imports \ --assume-yes-for-downloads \ --remove-output \ --output-dir=dist \ --output-filename=ai_infer_service \ launch.py ``` --- ## 开发指南 ### 新增检测场景(Resolver) #### 1. 创建 Resolver 文件 在 `app/application/services/resolvers/` 目录下创建新文件,例如 `my_scene.py`: ```python from app.runtime.orchestration.stream_processor import StreamProcessor from app.runtime.orchestration.video_processor import VideoProcessor def analyse_stream(model_path, request): """实时流分析""" return StreamProcessor().analyse_stream( model_path=model_path, request=request ) def analyse_video(model_path, request): """视频文件分析""" return VideoProcessor().analyse_video( model_path=model_path, request=request ) def analyse_pic(model_path, request): """单图分析""" from app.runtime.model_predict import model_predict return model_predict(model_path, request) ``` #### 2. 准备模型文件 将模型文件放置在 `asset/model/my_scene/` 目录下: ``` asset/model/my_scene/ ├── best.pt # PyTorch 模型 ├── best.onnx # ONNX 模型 └── best.engine # TensorRT 引擎 ``` #### 3. 发起请求 ```bash curl -X POST http://127.0.0.1:8001/stream/analyse \ -H "Content-Type: application/json" \ -d '{ "url": "rtmp://example.com/live/input", "targetUrl": "rtmp://example.com/live/output", "type": "my_scene", "modelType": 3 }' ``` ### 自定义检测框样式 编辑 `app/runtime/rendering/detection_drawer.py`: ```python def draw_detections(self, image, detections, request): for det in detections: # 自定义线宽 line_width = max(2, request.line_width or 3) # 自定义颜色 color = self.color_manager.get_color(det.class_id) # 绘制矩形框 cv2.rectangle( image, (x1, y1), (x2, y2), color, line_width ) # 自定义标签 label = f"{det.class_name} {det.conf:.2f}" if det.id: label = f"[{det.id}] {label}" self.draw_label(image, label, x1, y1, color) ``` ### 自定义告警规则 编辑 `app/runtime/streaming/stream_trigger.py`: ```python def should_trigger(self, detections, request): """自定义触发逻辑""" # 示例:目标数量超过阈值 if len(detections) > request.threshold: return True # 示例:特定类别出现 for det in detections: if det.class_name in ['fire', 'smoke']: return True return False ``` ### 代码规范 - 使用 **PEP 8** Python 代码风格 - 函数命名:snake_case - 类命名:PascalCase - 常量命名:UPPER_CASE - 添加类型注解(Type Hints) - 编写文档字符串(Docstrings) ### 测试 ```bash # 运行单元测试 pytest tests/ # 性能测试 python app/tools/image_diff_benchmark.py ``` --- ## 性能优化 ### 低延迟优化策略 #### 1. 丢帧策略 - **队列满丢旧帧**: 写入队列满时,丢弃最旧的帧,只保留最新帧 - **动态跳帧**: 根据检测目标数量动态调整跳帧率 - **推理节拍器**: 固定推理频率,防止堆积 #### 2. 多进程隔离 - 每路流独立子进程,规避 Python GIL - 进程间不共享内存,隔离故障 - 子进程崩溃不影响主服务 #### 3. GPU 加速 - **推理加速**: TensorRT 引擎(.engine)性能最佳 - **编码加速**: 使用 NVENC 硬件编码 - **模型预热**: 启动时预先运行推理,降低首帧延迟 #### 4. 绘制优化 ```yaml draw: disable_chinese_text_threshold: 50 # 目标多时禁用中文标签 high_performance_threshold: 120 # 目标多时只画框不画标签 frame_skip_threshold: 150 # 目标多时跳帧绘制 ``` ### 性能调优参数 #### 降低延迟 ```yaml ffmpeg: write_queue_size: 4 # 减小队列(默认6) push_fps: 25 # 降低推流帧率 frame: skip: 3 # 增加跳帧(每3帧推理一次) infer_fps: 25 # 降低推理频率 model: type: 3 # 使用 TensorRT 引擎 ``` #### 提升准确率 ```yaml frame: skip: 1 # 每帧都推理 # API 请求参数 { "conf": 0.5, # 提高置信度阈值 "maxDet": 1000 # 减少最大检测数 } ``` #### 多路并发优化 ```yaml # 降低单路资源占用 ffmpeg: pull_scale_enable: true # 降低拉流分辨率 pull_scale_width: 960 pull_scale_height: 540 push_fps: 20 frame: skip: 2 ``` ### 性能监控 查看系统资源占用: ```bash # CPU/内存/GPU 占用 htop nvidia-smi -l 1 # 进程列表 ps aux | grep python # 日志监控 tail -f logs/app.log ``` --- ## 常见问题 ### Q1: 模型文件不存在错误 **问题**: `FileNotFoundError: Model file not found` **解决方案**: 1. 检查模型文件路径是否正确:`asset/model/{type}/best.{pt|onnx|engine}` 2. 确认 `config.ini` 中的 `env` 设置正确 3. 检查 YAML 配置中的 `model.path` 设置 ### Q2: 推流断开 (Broken pipe) **问题**: 推流过程中出现 `Broken pipe` 错误 **解决方案**: 1. 检查输出 RTMP 地址是否正确 2. 确认 RTMP 服务器是否正常运行 3. 检查网络连接是否稳定 4. 降低推流码率和帧率 ### Q3: GPU 内存不足 (CUDA out of memory) **问题**: `RuntimeError: CUDA out of memory` **解决方案**: 1. 减少并发处理的流数量 2. 降低模型输入分辨率(`maxDet` 参数) 3. 使用更小的模型 4. 启用 `pull_scale_enable` 降低输入分辨率 ### Q4: 延迟过高 **问题**: 端到端延迟超过3秒 **解决方案**: 1. 增加跳帧率:`frame.skip: 3` 2. 减小写入队列:`ffmpeg.write_queue_size: 4` 3. 降低推流帧率:`ffmpeg.push_fps: 20` 4. 使用 TensorRT 引擎:`model.type: 3` 5. 启用 NVENC 编码:`ffmpeg.video_encoder: h264_nvenc` ### Q5: 画面没有检测框 **问题**: 推流正常但看不到检测框 **解决方案**: 1. 检查 `boxesFlag: true` 和 `labelsFlag: true` 2. 确认模型推理是否正常(查看日志) 3. 降低置信度阈值:`conf: 0.25` 4. 检查是否触发了高性能模式(目标过多时自动禁用标签) ### Q6: FFmpeg 找不到 **问题**: `FileNotFoundError: ffmpeg not found` **解决方案**: ```bash # Ubuntu/Debian sudo apt-get update sudo apt-get install ffmpeg # CentOS/RHEL sudo yum install ffmpeg # macOS brew install ffmpeg # 验证安装 ffmpeg -version ffprobe -version ``` ### Q7: MQTT 连接失败 **问题**: `ConnectionRefusedError: [Errno 111] Connection refused` **解决方案**: 1. 检查 MQTT broker 是否运行 2. 确认 YAML 中的 MQTT 配置正确 3. 检查防火墙设置 4. 测试 MQTT 连接:`mosquitto_pub -h -p -t test -m "hello"` ### Q8: 车牌识别准确性问题 **问题**: 车牌识别扩展返回结果不理想 **解决方案**: 1. 确保车辆检测框准确 2. 提高输入图像分辨率 3. 调整车牌识别模型的置信度阈值 4. 检查光照条件 ### Q9: 服务启动失败 **问题**: `python launch.py` 启动报错 **解决方案**: 1. 检查 Python 版本:`python --version` (需要 3.10+) 2. 确认依赖已安装:`pip list | grep -E "torch|flask|opencv"` 3. 检查端口是否被占用:`lsof -i:8001` 4. 查看详细日志:`python launch.py` 查看错误堆栈 ### Q10: Docker 容器无法访问 GPU **问题**: Docker 中无法使用 GPU 加速 **解决方案**: ```bash # 安装 nvidia-docker2 distribution=$(. /etc/os-release;echo $ID$VERSION_ID) curl -s -L https://nvidia.github.io/nvidia-docker/gpgkey | sudo apt-key add - curl -s -L https://nvidia.github.io/nvidia-docker/$distribution/nvidia-docker.list | \ sudo tee /etc/apt/sources.list.d/nvidia-docker.list sudo apt-get update && sudo apt-get install -y nvidia-docker2 sudo systemctl restart docker # 测试 GPU 访问 docker run --rm --gpus all nvidia/cuda:11.8.0-base-ubuntu22.04 nvidia-smi ``` --- ## 相关文档 - [架构重构计划](ARCH_REFACTORING_PLAN.md) - [配置刷新指南](CONFIG_REFRESH_GUIDE.md) - [Swagger API 文档](http://127.0.0.1:8001/apidocs) ## License 本项目采用 MIT 许可证。详见 [LICENSE](LICENSE) 文件。 ## 贡献 欢迎提交 Issue 和 Pull Request! ## 联系方式 - Email: tinx.wills@gmail.com --- **更新日期**: 2026-01-12 **版本**: v2.7.5