You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于Flask+YOLOv8的多IP摄像头目标检测无输出故障排查

问题分析与修复方案

核心问题点

  1. 命令行参数解析时机错误:在video_feed路由中调用parse_args(),导致每次请求都会重新解析命令行参数,且启动时CAMERAS为空,页面渲染时无摄像头元素。
  2. Flask启动特性:app.run()是阻塞方法,之后的print('Main method')只有进程终止后才会执行,这是正常行为,并非Bug。
  3. 多路视频流生成逻辑缺陷:摄像头读取失败时会导致帧列表与模型数量不匹配,且每个摄像头实例化一个YOLO模型造成资源浪费;同时页面多个img请求同一流会导致画面混乱。
  4. 页面渲染时机问题:访问/时CAMERAS未初始化,模板循环无输出。

具体修复步骤

1. 调整参数解析与全局变量初始化

将命令行参数解析移到启动阶段,提前初始化摄像头、模型和CAMERAS变量,确保页面渲染时已有数据:

from flask import Flask, render_template, Response
from ultralytics import YOLO
import cv2
import numpy as np
import argparse

CAMERAS = []
caps = []
model = None  # 共用一个YOLO模型,无需为每个摄像头实例化

app = Flask(__name__)

class_names = [...]  # 补充你的类别列表

def parse_args():
    parser = argparse.ArgumentParser(description='Multi-Camera Object Detection')
    parser.add_argument('-urls', nargs='+', help='List of URLs for the cameras', required=True)
    return parser.parse_args()

# 提前初始化资源
args = parse_args()
CAMERAS = args.urls
caps = [cv2.VideoCapture(url) for url in args.urls]
model = YOLO("./models/best_10Class_20Epochs.pt")  # 共用一个模型

2. 修复视频流生成函数

处理摄像头读取失败的情况,正确使用YOLO模型检测,避免索引错误:

def generate_frames(cam_idx):
    cap = caps[cam_idx]
    while True:
        success, img = cap.read()
        if not success:
            # 摄像头读取失败时,返回空白帧
            img = np.zeros((480, 640, 3), dtype=np.uint8)
        
        # YOLO检测并绘制bounding box
        results = model(img, stream=True)
        for r in results:
            boxes = r.boxes
            for box in boxes:
                x1, y1, x2, y2 = map(int, box.xyxy[0])
                conf = box.conf[0].item()
                cls = int(box.cls[0])
                # 绘制框和类别标签
                cv2.rectangle(img, (x1, y1), (x2, y2), (0, 255, 0), 2)
                cv2.putText(img, f"{class_names[cls]} {conf:.2f}", (x1, y1-10), 
                            cv2.FONT_HERSHEY_SIMPLEX, 0.5, (0,255,0), 2)
        
        # 编码帧为JPEG格式
        _, buffer = cv2.imencode('.jpg', img)
        frame = buffer.tobytes()
        yield (b'--frame\r\n'
               b'Content-Type: image/jpeg\r\n\r\n' + frame + b'\r\n')

3. 修改路由配置

为每个摄像头单独提供视频流路由,确保页面每个img对应正确的流:

@app.route('/')
def index():
    return render_template('index_ip.html', cameras=CAMERAS, cam_count=len(CAMERAS))

@app.route('/video_feed/<int:cam_idx>')
def video_feed(cam_idx):
    if cam_idx < 0 or cam_idx >= len(caps):
        return "Invalid camera index", 404
    return Response(generate_frames(cam_idx), mimetype='multipart/x-mixed-replace; boundary=frame')

4. 修复前端模板

让每个img请求对应摄像头的视频流:

<!DOCTYPE html>
<html>
<head>
    <title>Multi-Camera Object Detection</title>
    <style>
        .grid-container {
            display: grid;
            grid-template-columns: repeat(auto-fit, minmax(640px, 1fr));
            gap: 1rem;
            padding: 1rem;
        }
        .grid-item {
            position: relative;
        }
        .grid-item img {
            width: 100%;
            height: auto;
            border-radius: 8px;
        }
        .overlay {
            position: absolute;
            top: 10px;
            left: 10px;
            background: rgba(0,0,0,0.7);
            color: white;
            padding: 0.5rem;
            border-radius: 4px;
            font-size: 0.9rem;
        }
    </style>
</head>
<body>
    <div class="grid-container">
        {% for idx in range(cam_count) %}
        <div class="grid-item">
            <img src="{{ url_for('video_feed', cam_idx=idx) }}" alt="{{ cameras[idx] }}">
            <div class="overlay">
                <p>Camera {{ cameras[idx] }}</p>
            </div>
        </div>
        {% endfor %}
    </div>
</body>
</html>

5. 修正启动逻辑

移除不必要的代码,确保Flask正常启动:

if __name__ == '__main__':
    print('Starting Flask server...')
    app.run(debug=True, host='0.0.0.0', port=3000)
    # app.run()是阻塞方法,后续代码仅在进程终止后执行,属于正常行为

额外优化建议

  • 添加摄像头心跳检测,定期检查cap.isOpened(),若断开则尝试重连。
  • 使用多线程处理多路摄像头读取,避免单线程阻塞导致画面卡顿。
  • 生产环境关闭Flask的debug=True,避免重载时重复初始化资源。

内容的提问来源于stack exchange,提问作者Deepak Pawade

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 20:03:24