def get_screenshot(self, carNo, show_view=True): """ 截图一帧 :param carNo: :param show_view: :return: """ try: # 打开rtsp cap = VideoCapture(self.URL) ret, frame = cap.read() if not ret: consoleLog(self.logPre, "未捕获到帧") imencode('.jpg', frame)[1].tofile(self.img_path.format(carNo=carNo, now=fmt_date(fmt=FMT_DATETIME))) if show_view: # 预览窗口 namedWindow('view', WINDOW_NORMAL | WINDOW_KEEPRATIO) imshow("view", frame) waitKey(5 * 1000) except Exception as e: consoleLog(self.logPre, "保存截图异常:", repr(e)) finally: if cap: cap.release() destroyAllWindows()
def __init__(self, place, ip, port, user, pwd, logPre=">"): """ 主码流: rtsp://admin:[email protected]:554/h264/ch1/main/av_stream rtsp://admin:[email protected]:554/MPEG-4/ch1/main/av_stream 子码流: rtsp://admin:[email protected]/mpeg4/ch1/sub/av_stream rtsp://admin:[email protected]/h264/ch1/sub/av_stream :param place: :param ip: :param port: :param user: :param pwd: :param logPre: """ self.logPre = logPre self.URL = f"rtsp://{user}:{pwd}@{ip}:{port}/h264/ch1/sub/av_stream" # 截图或视频保存位置 img_dir = path.join(BASE_DIR, "logs", "camera_img", place, fmt_date(fmt=FMT_DATE)) if not path.exists(img_dir): makedirs(img_dir) # 截图保存文件名 self.img_path = path.join(img_dir, "{carNo}" + "_" + "{now}" + ".jpg") # 视频保存文件名 self.video_path = path.join(img_dir, "{carNo}" + "_" + "{now}" + ".avi")
def videotape_seconds(self, carNo, t_seconds, show_view=True): """ 录像 :param carNo: :param show_view: :return: """ try: # 打开rtsp cap = VideoCapture(self.URL) # 视频分辨率 size = (int(cap.get(CAP_PROP_FRAME_WIDTH)), int(cap.get(CAP_PROP_FRAME_HEIGHT))) # 帧率 fps = cap.get(CAP_PROP_FPS) # 视频保存格式avi fourcc = VideoWriter_fourcc(*'XVID') # 视频保存obj outfile = VideoWriter(self.video_path.format(carNo=carNo, now=fmt_date(fmt=FMT_DATETIME)), fourcc, fps, size) if show_view: # 预览窗口 namedWindow('view', WINDOW_NORMAL | WINDOW_KEEPRATIO) ret, frame = cap.read() t1 = time() while ret: if time() - t1 >= t_seconds: break ret, frame = cap.read() outfile.write(frame) if show_view: imshow("view", frame) waitKey(1) else: consoleLog(self.logPre, "未捕获到帧") except Exception as e: consoleLog(self.logPre, "视频录制异常:", repr(e)) finally: if cap: cap.release() if outfile: outfile.release() destroyAllWindows()
def save_menulist_role(req, role_id): """ 保存角色下的菜单 :param req: :param role_id: :return: """ ret = ResModel() ret.msg = req_invalid_check(req) if ret.msg: # 请求合法性校验不通过 return JsonResponse(ret.to_dic()) # 中间件校验token后赋值USER_ID mod_user_id = req.META.get("USER_ID") mids = req.POST.get('ids', '') # 先删除要保存或修改的角色菜单,然后再添加 sql_ins = """insert into {tablerm}({tablerm_id},{tablerm_rid},{tablerm_mid},{tablerm_upduid}, {tablerm_atime}) values(%(rmid)s, %(rid)s, %(mid)s, %(uid)s, %(atime)s) """ now_date = fmt_date() # 开启事务 with connection() as con: con.execute_sql( "delete from {tablerm} where {tablerm_rid}=%(rid)s".format( **SQL_DIC_ROLEMENU), {"rid": role_id}) if mids: for mid in mids.split(","): con.execute_sql( sql_ins.format(**SQL_DIC_ROLEMENU), { "rmid": str(uuid1()).replace('-', ''), "rid": role_id, "mid": mid, "uid": mod_user_id, "atime": now_date }) ret.msg = '已保存' ret.code = ret.ResCode.succ return JsonResponse(ret.to_dic())
def upload_file(req): """ 文件上传 :param req: pathPre,file :return: """ ret = ResModel() ret.msg = req_invalid_check(req) if ret.msg: # 请求合法性校验不通过 return JsonResponse(ret.to_dic()) file_obj = req.FILES.get('file') if not file_obj: ret.msg = '未选择文件' return JsonResponse(ret.to_dic()) # 允许指定类型前缀,以区分不同业务 path_pre = req.POST.get('pathPre', '') # 上传路径 up_path_pre = settings.UPLOAD_DIR # 按日期年月分组 now_date = fmt_date(fmt=FMT_DATE) up_path = path.join(up_path_pre, path_pre, now_date) if not path.exists(up_path): makedirs(up_path) # 重命名,防止重名 file_type = path.splitext(file_obj.name)[1] file_name = str(uuid1()).replace('-', '') + file_type # 保存文件 with open(path.join(up_path, file_name), 'wb') as fp: for chunk in file_obj.chunks(): fp.write(chunk) ret.msg = '已上传' ret.code = ret.ResCode.succ # fileSize单位是字节.fileSize/1024单位即kb;fileSize/1024/1024单位即mb ret.data = {"oldName": file_obj.name, "newName": path.join(settings.STATIC_ROOT, settings.UPLOAD_ROOT, path_pre, now_date, file_name), "fileType": file_type.split(".")[-1], "fileSize": file_obj.size} return JsonResponse(ret.to_dic())
def reset_phone_email(req, code_way, sid): """ 更换/添加手机号、email :param req: :param code_way: smscode.短信验证码;emailcode.email验证码 :param sid: :return: """ ret = ResModel() ret.msg = req_invalid_check(req) if ret.msg: # 请求合法性校验不通过 return JsonResponse(ret.to_dic()) # 中间件校验token后赋值USER_ID user_id = req.META.get("USER_ID") if not user_id: ret.msg = "用户信息不存在" return JsonResponse(ret.to_dic()) # 图形验证码or短信验证码 auth_code = req.POST.get('authCode', '').upper() # 新phone或者新email new_aim = req.POST.get('newAim', '') if not auth_code: ret.msg = '验证码不可空' return JsonResponse(ret.to_dic()) if not new_aim: ret.msg = '参数异常' return JsonResponse(ret.to_dic()) # 获取redis缓存数据 r = RedisCtrl() verify_code = r.get_one(REDIS_KEY_PRE_SID + sid) if not verify_code: ret.msg = '验证码已过期' return JsonResponse(ret.to_dic()) if code_way == 'emailcode': # 登录方式.emailcode.email验证码 user_code = r.get_one(REDIS_KEY_PRE_EMAILCODE + new_aim) ret.msg = '该email验证码已过期' sub_sql = "{table1_email}=%(new)s,{table1_emailsucc}='" + DrUser.EMAIL_SUCC[ 1][0] + "'," elif code_way == 'smscode': # 登录方式.smscode.短信验证码 user_code = r.get_one(REDIS_KEY_PRE_SMSCODE + new_aim) ret.msg = '该手机号验证码已过期' sub_sql = "{table1_phone}=%(new)s," else: # 其他code_way,反馈失败 return JsonResponse(ret.to_dic()) # 校验验证码 if not user_code: # 验证码不存在 return JsonResponse(ret.to_dic()) if user_code != auth_code: # 校验验证码 ret.msg = '验证码错误' # 记录错误次数,多次失败则需重新请求sid err_cnt = r.get_one(REDIS_KEY_PRE_CODEERR + user_id) if not err_cnt: err_cnt = 1 r.set_one(REDIS_KEY_PRE_CODEERR + user_id, str(err_cnt), expt=60 * 5) else: err_cnt = int(err_cnt) + 1 r.set_one(REDIS_KEY_PRE_CODEERR + user_id, str(err_cnt), expt=60 * 5) if int(err_cnt) >= 10: # 尝试次数大于10次,则需重新发送sms r.del_one(REDIS_KEY_PRE_SMSCODE + user_id) r.del_one(REDIS_KEY_PRE_EMAILCODE + user_id) r.del_one(REDIS_KEY_PRE_CODEERR + user_id) # 同一个验证码尝试次数过多 flog.warning(f"[{user_id}]用户的{code_way}验证码尝试次数过多") ret.msg = '验证码错误,请重新加载' return JsonResponse(ret.to_dic()) # 设置 with connection() as con: con.execute_sql( "update {table1} set " + sub_sql + ",{table1_utime}=%(ut)s where {table1_id}=%(uid)s".format( **SQL_DIC_USER), { "new": new_aim, "uid": user_id, "ut": fmt_date() }) ret.msg = '已修改' ret.code = ret.ResCode.succ return JsonResponse(ret.to_dic())
def reset_pwd(req, code_way, sid): """ 重置密码 :param req: :param code_way: smscode.短信验证码;emailcode.email验证码 :param sid: :return: """ ret = ResModel() ret.msg = req_invalid_check(req) if ret.msg: # 请求合法性校验不通过 return JsonResponse(ret.to_dic()) # 中间件校验token后赋值USER_ID user_id = req.META.get("USER_ID") if not user_id: ret.msg = "用户信息不存在" return JsonResponse(ret.to_dic()) # 图形验证码or短信验证码 auth_code = req.POST.get('authCode', '').upper() new_pwd = req.POST.get('newPwd', '').upper() if not auth_code: ret.msg = '验证码不可空' return JsonResponse(ret.to_dic()) if not new_pwd: ret.msg = '新密码不可空' return JsonResponse(ret.to_dic()) # 获取redis缓存数据 r = RedisCtrl() verify_code = r.get_one(REDIS_KEY_PRE_SID + sid) if not verify_code: ret.msg = '验证码已过期' return JsonResponse(ret.to_dic()) if code_way == 'emailcode': # 登录方式.emailcode.email验证码 user_code = r.get_one(REDIS_KEY_PRE_EMAILCODE + user_id) elif code_way == 'smscode': # 登录方式.smscode.短信验证码 user_code = r.get_one(REDIS_KEY_PRE_SMSCODE + user_id) else: # 其他code_way,反馈失败 return JsonResponse(ret.to_dic()) # 校验验证码 if not user_code: # 短信验证码不存在 ret.msg = '验证码已过期' return JsonResponse(ret.to_dic()) if user_code != auth_code: # 校验验证码 ret.msg = '验证码错误' # 记录错误次数,多次失败则需重新请求sid err_cnt = r.get_one(REDIS_KEY_PRE_CODEERR + user_id) if not err_cnt: err_cnt = 1 r.set_one(REDIS_KEY_PRE_CODEERR + user_id, str(err_cnt), expt=60 * 5) else: err_cnt = int(err_cnt) + 1 r.set_one(REDIS_KEY_PRE_CODEERR + user_id, str(err_cnt), expt=60 * 5) if int(err_cnt) >= 10: # 尝试次数大于10次,则需重新发送sms r.del_one(REDIS_KEY_PRE_SMSCODE + user_id) r.del_one(REDIS_KEY_PRE_EMAILCODE + user_id) r.del_one(REDIS_KEY_PRE_CODEERR + user_id) # 同一个验证码尝试次数过多 flog.warning(f"重置密码时[{user_id}]用户的验证码尝试次数过多") ret.msg = '验证码错误,请重新加载' return JsonResponse(ret.to_dic()) # 设置密码 p = PwdCtrl() salt = p.get_salt() pwd = p.create_md5(src_str=new_pwd, salt=salt) with connection() as con: con.execute_sql( """update {table1} set {table1_pwd}=%(pwd)s,{table1_salt}=%(salt)s ,{table1_utime}=%(ut)s where {table1_id}=%(uid)s""".format(**SQL_DIC_USER), { "pwd": pwd, "uid": user_id, "salt": salt, "ut": fmt_date() }) ret.msg = '已修改密码' ret.code = ret.ResCode.succ return JsonResponse(ret.to_dic())