yolov5 web端部署进行图片和视频检测

2023-10-08 20:45

本文主要是介绍yolov5 web端部署进行图片和视频检测,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

目录

1、思路

2、代码结构

3、代码运行

4、api接口代码

5、web ui界面

6、参考资料

7、代码分享 


1、思路

通过搭建flask微型服务器后端,以后通过vue搭建网页前端。flask是第一个第三方库。与其他模块一样,安装时可以直接使用python的pip命令实现。flask是web开发框架,简单易学,因此用flask来搭建web服务也非常简单。

在pycharm新建一个项目,命名为web2020,然后新建一个python文件,命名为main.py。在代码中输入如下代码:

from flask import  Flask    #导入Flask类
app=Flask(__name__)         #实例化并命名为app实例
if __name__=="__main__":app.run(port=2020,host="127.0.0.1",debug=True)   #调用run方法,设定端口号,启动服务

路由定义:

from flask import  Flask
app=Flask(__name__)@app.route('/')
def index():return 'welcome to my webpage!'if __name__=="__main__":app.run(port=2020,host="127.0.0.1",debug=True)

通过这种方式,实现python调用模型,然后通过web服务器进行数据输入输出,最后通过浏览器web页面进行展示。

2、代码结构

前端代码结构

后端代码结构

3、代码运行

4、api接口代码

import datetime
import logging as rel_log
import os
import shutil
from datetime import timedelta
from flask import *
from flask import Flask, render_template, Response
from processor.AIDetector_pytorch import Detectorimport core.main# import camera driver
if os.environ.get('CAMERA'):Camera = import_module('camera_' + os.environ['CAMERA']).Camera
else:from camera import CameraUPLOAD_FOLDER = r'./uploads'ALLOWED_EXTENSIONS = set(['png', 'jpg'])
app = Flask(__name__)
app.secret_key = 'secret!'
app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDERwerkzeug_logger = rel_log.getLogger('werkzeug')
werkzeug_logger.setLevel(rel_log.ERROR)# 解决缓存刷新问题
app.config['SEND_FILE_MAX_AGE_DEFAULT'] = timedelta(seconds=1)# 添加header解决跨域
@app.after_request
def after_request(response):response.headers['Access-Control-Allow-Origin'] = '*'response.headers['Access-Control-Allow-Credentials'] = 'true'response.headers['Access-Control-Allow-Methods'] = 'POST'response.headers['Access-Control-Allow-Headers'] = 'Content-Type, X-Requested-With'return response#图片检测接口
def allowed_file(filename):return '.' in filename and filename.rsplit('.', 1)[1] in ALLOWED_EXTENSIONS#@app.route('/')
#def hello_world():
#    return redirect(url_for('static', filename='./index.html'))
@app.route('/')
def index():"""Video streaming home page."""return render_template('index.html')@app.route('/upload', methods=['GET', 'POST'])
def upload_file():file = request.files['file']print(datetime.datetime.now(), file.filename)#if file and allowed_file(file.filename):src_path = os.path.join(app.config['UPLOAD_FOLDER'], file.filename)file.save(src_path)shutil.copy(src_path, './tmp/ct')image_path = os.path.join('./tmp/ct', file.filename)pid, image_info = core.main.c_main(image_path, current_app.model, file.filename.rsplit('.', 1)[1])return jsonify({'status': 1,'image_url': 'http://127.0.0.1:5003/tmp/ct/' + pid,'draw_url': 'http://127.0.0.1:5003/tmp/draw/' + pid,'image_info': image_info})#return jsonify({'status': 0})@app.route("/download", methods=['GET'])
def download_file():# 需要知道2个参数, 第1个参数是本地目录的path, 第2个参数是文件名(带扩展名)return send_from_directory('data', 'testfile.zip', as_attachment=True)# show photo
@app.route('/tmp/<path:file>', methods=['GET'])
def show_photo(file):if request.method == 'GET':if not file is None:image_data = open(f'tmp/{file}', "rb").read()response = make_response(image_data)response.headers['Content-Type'] = 'image/png'return response#视频检测接口
def gen(camera):"""Video streaming generator function."""while True:frame = camera.get_frame()yield (b'--frame\r\n'b'Content-Type: image/jpeg\r\n\r\n' + frame + b'\r\n')@app.route('/video_start')
def video_feed():"""Video streaming route. Put this in the src attribute of an img tag."""return Response(gen(Camera()),mimetype='multipart/x-mixed-replace; boundary=frame')#视频流检测接口
#@app.route('/livestream_start')#程序启动入口
if __name__=='__main__': files = ['uploads', 'tmp/ct', 'tmp/draw','tmp/image', 'tmp/mask', 'tmp/uploads']for ff in files:if not os.path.exists(ff):os.makedirs(ff)with app.app_context():current_app.model = Detector()app.run(host='127.0.0.1', port=5003, debug=True)

5、web ui界面

<template><el-tabs stretch=true v-model="activeName" type="card" @tab-click="handleClick"><el-tab-pane  label="图片检测" name="first"><div id="Content"><el-dialogtitle="AI预测中":visible.sync="dialogTableVisible":show-close="false":close-on-press-escape="false":append-to-body="true":close-on-click-modal="false":center="true"><el-progress :percentage="percentage"></el-progress><span slot="footer" class="dialog-footer">请耐心等待约3秒钟</span></el-dialog><div id="CT"><div id="CT_image"><el-cardid="CT_image_1"class="box-card"style="border-radius: 8px;width: 800px;height: 360px;margin-bottom: -30px;"><div class="demo-image__preview1"><divv-loading="loading"element-loading-text="上传图片中"element-loading-spinner="el-icon-loading"><el-image:src="url_1"class="image_1":preview-src-list="srcList"style="border-radius: 3px 3px 0 0"><div slot="error"><div slot="placeholder" class="error"><el-buttonv-show="showbutton"type="primary"icon="el-icon-upload"class="download_bt"v-on:click="true_upload">上传图像<inputref="upload"style="display: none"name="file"type="file"@change="update"/></el-button></div></div></el-image></div><div class="img_info_1" style="border-radius: 0 0 5px 5px"><span style="color: white; letter-spacing: 6px">原始图像</span></div></div><div class="demo-image__preview2"><divv-loading="loading"element-loading-text="处理中,请耐心等待"element-loading-spinner="el-icon-loading"><el-image:src="url_2"class="image_1":preview-src-list="srcList1"style="border-radius: 3px 3px 0 0"><div slot="error"><div slot="placeholder" class="error">{{ wait_return }}</div></div></el-image></div><div class="img_info_1" style="border-radius: 0 0 5px 5px"><span style="color: white; letter-spacing: 4px">检测结果</span></div></div></el-card></div><div id="info_patient"><!-- 卡片放置表格 --><el-card style="border-radius: 8px"><div slot="header" class="clearfix"><span>检测目标</span><el-buttonstyle="margin-left: 35px"v-show="!showbutton"type="primary"icon="el-icon-upload"class="download_bt"v-on:click="true_upload2">重新选择图像<inputref="upload2"style="display: none"name="file"type="file"@change="update"/></el-button></div><el-tabs v-model="activeName"><el-tab-pane label="检测到的目标" name="first"><!-- 表格存放特征值 --><el-table:data="feature_list"height="390"borderstyle="width: 750px; text-align: center"v-loading="loading"element-loading-text="数据正在处理中,请耐心等待"element-loading-spinner="el-icon-loading"lazy><el-table-column label="目标类别" width="250px"><template slot-scope="scope"><span>{{ scope.row[2] }}</span></template></el-table-column><el-table-column label="目标大小" width="250px"><template slot-scope="scope"><span>{{ scope.row[0] }}</span></template></el-table-column><el-table-column label="置信度" width="250px"><template slot-scope="scope"><span>{{ scope.row[1] }}</span></template></el-table-column></el-table></el-tab-pane></el-tabs></el-card></div></div></div></el-tab-pane><el-tab-pane label="视频检测" name="second"><h3>视频名称</h3><img :src="vidoedectetion"> </el-tab-pane><el-tab-pane label="视频流检测" name="third"></el-tab-pane><el-tab-pane label="多路视频流检测" name="fourth"></el-tab-pane></el-tabs></template><script>
import axios from "axios";export default {name: "Content",data() {return {vidoedectetion:"http://127.0.0.1:5003" + "/video_start",server_url: "http://127.0.0.1:5003",activeName: "first",active: 0,centerDialogVisible: true,url_1: "",url_2: "",textarea: "",srcList: [],srcList1: [],feature_list: [],feature_list_1: [],feat_list: [],url: "",visible: false,wait_return: "等待上传",wait_upload: "等待上传",loading: false,table: false,isNav: false,showbutton: true,percentage: 0,fullscreenLoading: false,opacitys: {opacity: 0,},dialogTableVisible: false,};},created: function () {document.title = "Yolov5安全帽检测web推理部署";},methods: {true_upload() {this.$refs.upload.click();},true_upload2() {this.$refs.upload2.click();},next() {this.active++;},// 获得目标文件getObjectURL(file) {var url = null;if (window.createObjcectURL != undefined) {url = window.createOjcectURL(file);} else if (window.URL != undefined) {url = window.URL.createObjectURL(file);} else if (window.webkitURL != undefined) {url = window.webkitURL.createObjectURL(file);}return url;},// 上传文件update(e) {this.percentage = 0;this.dialogTableVisible = true;this.url_1 = "";this.url_2 = "";this.srcList = [];this.srcList1 = [];this.wait_return = "";this.wait_upload = "";this.feature_list = [];this.feat_list = [];this.fullscreenLoading = true;this.loading = true;this.showbutton = false;let file = e.target.files[0];this.url_1 = this.$options.methods.getObjectURL(file);let param = new FormData(); //创建form对象param.append("file", file, file.name); //通过append向form对象添加数据var timer = setInterval(() => {this.myFunc();}, 30);let config = {headers: { "Content-Type": "multipart/form-data" },}; //添加请求头axios.post(this.server_url + "/upload", param, config).then((response) => {this.percentage = 100;clearInterval(timer);this.url_1 = response.data.image_url;this.srcList.push(this.url_1);this.url_2 = response.data.draw_url;this.srcList1.push(this.url_2);this.fullscreenLoading = false;this.loading = false;this.feat_list = Object.keys(response.data.image_info);for (var i = 0; i < this.feat_list.length; i++) {response.data.image_info[this.feat_list[i]][2] = this.feat_list[i];this.feature_list.push(response.data.image_info[this.feat_list[i]]);}this.feature_list.push(response.data.image_info);this.feature_list_1 = this.feature_list[0];this.dialogTableVisible = false;this.percentage = 0;this.notice1();});},myFunc() {if (this.percentage + 33 < 99) {this.percentage = this.percentage + 33;} else {this.percentage = 99;}},drawChart() {},notice1() {this.$notify({title: "预测成功",message: "点击图片可以查看大图",duration: 0,type: "success",});},},mounted() {this.drawChart();},
};
</script><style>
.el-button {padding: 12px 20px !important;
}#hello p {font-size: 15px !important;/*line-height: 25px;*/
}.n1 .el-step__description {padding-right: 20%;font-size: 14px;line-height: 20px;/* font-weight: 400; */
}
</style><style scoped>
* {box-sizing: border-box;margin: 0;padding: 0;
}.dialog_info {margin: 20px auto;
}.text {font-size: 14px;
}.item {margin-bottom: 18px;
}.clearfix:before,
.clearfix:after {display: table;content: "";
}.clearfix:after {clear: both;
}.box-card {width: 680px;height: 200px;border-radius: 8px;margin-top: -20px;
}.divider {width: 50%;
}#CT {display: flex;height: 100%;width: 100%;flex-wrap: wrap;justify-content: center;margin: 0 auto;margin-right: 0px;max-width: 1800px;
}#CT_image_1 {width: 90%;height: 40%;margin: 0px auto;padding: 0px auto;margin-right: 180px;margin-bottom: 0px;border-radius: 4px;
}#CT_image {margin-bottom: 60px;margin-left: 30px;margin-top: 5px;
}.image_1 {width: 275px;height: 260px;background: #ffffff;box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
}.img_info_1 {height: 30px;width: 275px;text-align: center;background-color: #21b3b9;line-height: 30px;
}.demo-image__preview1 {width: 250px;height: 290px;margin: 20px 60px;float: left;
}.demo-image__preview2 {width: 250px;height: 290px;margin: 20px 460px;/* background-color: green; */
}.error {margin: 100px auto;width: 50%;padding: 10px;text-align: center;
}.block-sidebar {position: fixed;display: none;left: 50%;margin-left: 600px;top: 350px;width: 60px;z-index: 99;
}.block-sidebar .block-sidebar-item {font-size: 50px;color: lightblue;text-align: center;line-height: 50px;margin-bottom: 20px;cursor: pointer;display: block;
}div {display: block;
}.block-sidebar .block-sidebar-item:hover {color: #187aab;
}.download_bt {padding: 10px 16px !important;
}#upfile {width: 104px;height: 45px;background-color: #187aab;color: #fff;text-align: center;line-height: 45px;border-radius: 3px;box-shadow: 0 0 2px 0 rgba(0, 0, 0, 0.1), 0 2px 2px 0 rgba(0, 0, 0, 0.2);color: #fff;font-family: "Source Sans Pro", Verdana, sans-serif;font-size: 0.875rem;
}.file {width: 200px;height: 130px;position: absolute;left: -20px;top: 0;z-index: 1;-moz-opacity: 0;-ms-opacity: 0;-webkit-opacity: 0;opacity: 0; /*css属性&mdash;&mdash;opcity不透明度,取值0-1*/filter: alpha(opacity=0);cursor: pointer;
}#upload {position: relative;margin: 0px 0px;
}#Content {width: 85%;height: 800px;background-color: #ffffff;margin: 15px auto;display: flex;min-width: 1200px;
}.divider {background-color: #eaeaea !important;height: 2px !important;width: 100%;margin-bottom: 50px;
}.divider_1 {background-color: #ffffff;height: 2px !important;width: 100%;margin-bottom: 20px;margin: 20px auto;
}.steps {font-family: "lucida grande", "lucida sans unicode", lucida, helvetica,"Hiragino Sans GB", "Microsoft YaHei", "WenQuanYi Micro Hei", sans-serif;color: #21b3b9;text-align: center;margin: 15px auto;font-size: 20px;font-weight: bold;text-align: center;
}.step_1 {/*color: #303133 !important;*/margin: 20px 26px;
}#info_patient {margin-top: 10px;margin-right: 160px;
}
</style>

6、参考资料

yolov5-flask-web - 知乎 (zhihu.com)

Flask部署YOLOv5 - 知乎 (zhihu.com)

https://zhuanlan.zhihu.com/p/104273184

特别感谢作者

GitHub - Sharpiless/Yolov5-Flask-VUE: 基于Flask+VUE前后端,在阿里云公网WEB端部署YOLOv5目标检测模型

7、代码分享 

这篇关于yolov5 web端部署进行图片和视频检测的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/167877

相关文章

python管理工具之conda安装部署及使用详解

《python管理工具之conda安装部署及使用详解》这篇文章详细介绍了如何安装和使用conda来管理Python环境,它涵盖了从安装部署、镜像源配置到具体的conda使用方法,包括创建、激活、安装包... 目录pytpshheraerUhon管理工具:conda部署+使用一、安装部署1、 下载2、 安装3

使用MongoDB进行数据存储的操作流程

《使用MongoDB进行数据存储的操作流程》在现代应用开发中,数据存储是一个至关重要的部分,随着数据量的增大和复杂性的增加,传统的关系型数据库有时难以应对高并发和大数据量的处理需求,MongoDB作为... 目录什么是MongoDB?MongoDB的优势使用MongoDB进行数据存储1. 安装MongoDB

Linux使用fdisk进行磁盘的相关操作

《Linux使用fdisk进行磁盘的相关操作》fdisk命令是Linux中用于管理磁盘分区的强大文本实用程序,这篇文章主要为大家详细介绍了如何使用fdisk进行磁盘的相关操作,需要的可以了解下... 目录简介基本语法示例用法列出所有分区查看指定磁盘的区分管理指定的磁盘进入交互式模式创建一个新的分区删除一个存

C#使用HttpClient进行Post请求出现超时问题的解决及优化

《C#使用HttpClient进行Post请求出现超时问题的解决及优化》最近我的控制台程序发现有时候总是出现请求超时等问题,通常好几分钟最多只有3-4个请求,在使用apipost发现并发10个5分钟也... 目录优化结论单例HttpClient连接池耗尽和并发并发异步最终优化后优化结论我直接上优化结论吧,

SpringBoot使用Apache Tika检测敏感信息

《SpringBoot使用ApacheTika检测敏感信息》ApacheTika是一个功能强大的内容分析工具,它能够从多种文件格式中提取文本、元数据以及其他结构化信息,下面我们来看看如何使用Ap... 目录Tika 主要特性1. 多格式支持2. 自动文件类型检测3. 文本和元数据提取4. 支持 OCR(光学

使用Python进行文件读写操作的基本方法

《使用Python进行文件读写操作的基本方法》今天的内容来介绍Python中进行文件读写操作的方法,这在学习Python时是必不可少的技术点,希望可以帮助到正在学习python的小伙伴,以下是Pyth... 目录一、文件读取:二、文件写入:三、文件追加:四、文件读写的二进制模式:五、使用 json 模块读写

Spring常见错误之Web嵌套对象校验失效解决办法

《Spring常见错误之Web嵌套对象校验失效解决办法》:本文主要介绍Spring常见错误之Web嵌套对象校验失效解决的相关资料,通过在Phone对象上添加@Valid注解,问题得以解决,需要的朋... 目录问题复现案例解析问题修正总结  问题复现当开发一个学籍管理系统时,我们会提供了一个 API 接口去

C#中图片如何自适应pictureBox大小

《C#中图片如何自适应pictureBox大小》文章描述了如何在C#中实现图片自适应pictureBox大小,并展示修改前后的效果,修改步骤包括两步,作者分享了个人经验,希望对大家有所帮助... 目录C#图片自适应pictureBox大小编程修改步骤总结C#图片自适应pictureBox大小上图中“z轴

k8s部署MongDB全过程

《k8s部署MongDB全过程》文章介绍了如何在Kubernetes集群中部署MongoDB,包括环境准备、创建Secret、创建服务和Deployment,并通过Robo3T工具测试连接... 目录一、环境准备1.1 环境说明1.2 创建 namespace1.3 创建mongdb账号/密码二、创建Sec

Java中的Opencv简介与开发环境部署方法

《Java中的Opencv简介与开发环境部署方法》OpenCV是一个开源的计算机视觉和图像处理库,提供了丰富的图像处理算法和工具,它支持多种图像处理和计算机视觉算法,可以用于物体识别与跟踪、图像分割与... 目录1.Opencv简介Opencv的应用2.Java使用OpenCV进行图像操作opencv安装j