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

Django使用StreamingHttpResponse实现人脸考勤时的页面跳转问题

问题根因
  1. 你在视频流生成函数getFace()中调用takeAttendance()拿到的render/redirect返回值没有传递给用户的页面请求,自然不会触发页面跳转。getFace()的唯一作用是给StreamingHttpResponse持续输出视频帧,当前/videoFeed请求和首页的页面请求是完全独立的两个请求,你手动修改request属性的操作没有任何作用。
  2. 你的全局摄像头实例vs只要服务端不重启就会一直运行,天然满足跳转后不需要重启摄像头的需求。
解决方案

后端修改

  1. 新增全局变量存储考勤识别结果,修改getFace逻辑,识别成功后只存结果不处理跳转:
from django.http import JsonResponse

# 原有全局变量不变,新增以下变量
attendance_result = None

def getFace(request):
    global vs,outputFrame,lock,foundFace, attendance_result
    known_face_names,known_face_encodings = getFiles() 
    face_location = []
    face_encoding = []
    while foundFace==False:
        check,frame = vs.read()
        small_frame = cv2.resize(frame,(0,0),fx=0.5,fy=0.5)
        face_roi = small_frame[:,:,::-1]
        face_location = face_recognition.face_locations(face_roi)
        face_encoding = face_recognition.face_encodings(face_roi,face_location)
        face_names = []
        names=[]
        for encoding in face_encoding:
            matches = face_recognition.compare_faces(known_face_encodings,np.array(encoding),tolerance=0.6)
            distances = face_recognition.face_distance(known_face_encodings,encoding)
            best_match_index = np.argmin(distances) 
            if matches[best_match_index]:
                name = known_face_names[best_match_index]
                face_names.append(name)
                if name not in names:
                    names.append(name)
        with lock:
            (flag,encodedImg) = cv2.imencode(".jpg",frame)
            
        if len(names)!=0:
            foundFace=True
        if foundFace==True:
            # 识别成功后存储考勤结果,不处理跳转
            if user_id in names:
                attendance = Attendance(user_ID = str(user_id),
                                        date_in = date.today(),
                                        time_in = datetime.now())
                attendance.save()
                attendance_result = {
                    "status": "success",
                    "user_id": str(user_id),
                    "time_in": str(datetime.now())
                }
            else:
                attendance_result = {"status": "failed"}
            foundFace=False
        yield(b'--frame\r\n' b'Content-Type: image/jpeg\r\n\r\n' + 
            bytearray(encodedImg) + b'\r\n')
  1. 新增考勤结果查询接口:
def get_attendance_result(request):
    global attendance_result
    res = attendance_result
    attendance_result = None # 查询后清空结果,避免重复返回
    return JsonResponse(res)
  1. 修改takeAttendance接口,直接渲染考勤页:
def takeAttendance(request):
    context={}
    if request.method=='GET':
        user_id = request.GET.get('user_id')
        time_in = request.GET.get('time_in')
        # 也可根据user_id查询数据库最新的考勤记录
        context={'attendance': {"user_ID": user_id, "time_in": time_in}}
        messages.success(request,'Check in successful')
        return render(request,'Attendance/attendance.html',context)
    else:
        return redirect('home')
  1. urls.py新增路由:
urlpatterns=[
    path('home/',views.home,name='home'),
    path('takeAttendance/',views.takeAttendance,name='takeAttendance'),
    path('videoFeed/',views.videoFeed,name='videoFeed'),
    path('getAttendanceResult/',views.get_attendance_result,name='get_attendance_result'),
]

前端修改

  1. 首页(摄像头页面)新增轮询逻辑,识别成功后自动跳转到考勤页:
// 每300ms查询一次考勤识别结果
setInterval(() => {
  fetch('/getAttendanceResult/')
  .then(res => res.json())
  .then(data => {
    if(!data) return
    if(data.status === 'success') {
      // 跳转到考勤详情页,携带参数
      window.location.href = `/takeAttendance/?user_id=${data.user_id}&time_in=${data.time_in}`
    } else {
      alert('打卡失败,未匹配到用户信息')
    }
  })
}, 300)
  1. Attendance.html新增定时跳转逻辑,停留数秒后自动返回首页:
// 3秒后自动跳转回首页
setTimeout(() => {
  window.location.href = '/home/'
}, 3000)
注意事项
  1. 原有代码中vs = cv2.videoCapture(0)存在拼写错误,应为cv2.VideoCapture(0),否则会报错。
  2. 全局变量存储考勤结果的方案仅适合本地测试、单进程部署场景,如需上线多实例部署,可替换为Redis缓存存储识别结果。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.30 04:27:04