docker torcherve打包mar包并部署模型

使用Docker打包深度网络模型mar包到服务端

参考链接:Docker torchserve 部署模型流程——以WSL部署YOLO-FaceV2为例_class myhandler(basehandler): def initialize(self,-CSDN博客

1、docker拉取环境镜像命令

docker images

在这里插入图片描述

在这里插入图片描述

出现此提示为没有权限取执行命令,此时修改命令为

sudo docker images

出现类似如下界面即为成功
在这里插入图片描述

**注意:**如果没有所需镜像,那么则需要去网上的镜像网站取拉镜像。命令为

docker pull registry.cn-shanghai.aliyuncs.com/jhinno/torch-serve:v6.1
docker pull 镜像

2、启动docker并进行打包

2、1启动docker服务

systemctl start docker
docker run --rm -it -p 8080:8080 -p 8081:8081 -v /home/lxz-2/lyw/class_eval/model_store:/home/model-server/model-store registry.cn-shanghai.aliyuncs.com/jhinno/torch-serve:v6.1

–rm 表示使用完立刻清空内存。

–it 表示交互式容器,会有一个伪终端,可以理解为docker容器的终端,我个人认为docker容器就是一个虚拟机,能更加方便人们去运行代码。

-p端口映射, -p 8080:8080 表示将本地8080端口映射到虚拟机8080端口

-v路径映射: -v /home/lxz-2/lyw/class_eval/model_store:/home/model-server/model-store将 /home/lxz-2/lyw/class_eval/model_store映射/home/model-server/model-store

registry.cn-shanghai.aliyuncs.com/jhinno/torch-serve:v6.1 :所使用的环境

在这里插入图片描述

输入完上述命令后进入docker容器的伪终端,此时所使用的环境为 registry.cn-shanghai.aliyuncs.com/jhinno/torch-serve:v6.1

在这里插入图片描述

2、2 编写handler文件

handler文件,是加载模型 预处理 推理 后处理的过程的函数,可以理解为跑通模型从前到后的步骤,比如加载模型,加载好后需要对数据进行预处理,进行预处理然后进行推理,将得到的加过进行后处理,应用到实际中,最后返回。

load_model、initialize第一个是下载模型用的,第二个是初始化,例如是不是用GPU啊等参数设置的,preprocess,此时这个函数的传参data就是用户在调用接口传递数据,preprocess返回的data会进入到inference的data,同时inference返回的data会进入到postprocess,最后通过接口返回给用户

在这里插入图片描述

import datetime
import os
import pickle
import sys
import zipfile
import numpy as np
import logginglogger = logging.getLogger(__name__)
import base64
import torch
import io
from PIL import Image
from sklearn.preprocessing import StandardScaler, MinMaxScaler
from ts.torch_handler.base_handler import BaseHandler
import astclass FaceDetectHandler(BaseHandler):def __init__(self):super().__init__()# Define your scalers for normalization and standardizationself.scaler = StandardScaler()  # For standardizationself.minmax_scaler = MinMaxScaler()  # For min-max scalingself.args = 14self.order = ['ATTENDANCE_RATE','HEAD_UP_RATE', 'FRONT_RATE','FRONT_SEAT_RATE','TVOTELOG','TPREAMPANSWERLOG','TDISCUSSLOG', 'TSURVEYLOG', 'TCHOOSESOMEONELOG', 'TWORKLOG','VOTELOG','PREAMPANSWERLOG','WORKLOG','CHOOSESOMEONELOG',]self.count = ['VOTELOG', 'WORKLOG', 'PREAMPANSWERLOG', 'CHOOSESOMEONELOG', 'JOBFINISH']def load_model(self, model_path):from model import MyModelprint('loading model...')model = MyModel(1,4,1)# if not os.path.exists(model_path):#     print("Checkpoint not found: " + model_path)#     return# print("Resuming from " + model_path)states = torch.load(model_path, map_location=self.device)model.load_state_dict(states, strict=False)model = model.to(device=self.device)# print("Resumed from " + model_path)self.model = model.eval()def initialize(self, context):properties = context.system_propertieslogger.info(f"Cuda available: {torch.cuda.is_available()}")logger.info(f"GPU available: {torch.cuda.device_count()}")use_cuda = torch.cuda.is_available() and torch.cuda.device_count() > 0self.map_location = 'cuda' if use_cuda else 'cpu'self.device = torch.device(self.map_location + ':' +str(properties.get('gpu_id')) if use_cuda else 'cpu')self.manifest = context.manifestmodel_dir = properties.get('model_dir')logger.info("==================model_dir==========================="" %s loaded successfully", model_dir)self.model_pt_path = Noneself.model_path = None# 读取pth和模型if "serializedFile" in self.manifest["model"]:serialized_file = self.manifest["model"]["serializedFile"]self.model_pt_path = os.path.join(model_dir, serialized_file)model_file = self.manifest['model']['modelFile']# if "modelFile" in self.manifest["model"]:#     model_file = self.manifest['model']['modelFile']#     self.model_path = os.path.join(model_dir, model_file)# logger.info("Model file %s loaded successfully", self.model_pt_path)# with zipfile.ZipFile(model_dir + '/models.zip', 'r') as zip_ref:#     zip_ref.extractall(model_dir)self.load_model(self.model_pt_path)logger.info("Model file %s loaded successfully", self.model_pt_path)def preprocess(self, data):logger.info("preprocess ing~~~~~")logger.info(data)data_dict = data[0]['body']keys = data_dict.keys()if 'ATTENDANCE_RATE' not in keys or 'HEAD_UP_RATE' not in  keys or 'FRONT_RATE' not in keys or 'FRONT_SEAT_RATE' not in keys:return "参数不足"values_array = [data_dict[feature] for feature in self.order]MASK = [1 if value!=0 else 0 for value in values_array]MASK = np.array(MASK, dtype=np.float32).reshape(1, self.args)# 使用 StandardScaler 标准化特征数据# 将 MASK 转换为 PyTorch 张量MASK_tensor = torch.tensor(MASK, dtype=torch.float32).to(self.device)values_array = np.array(values_array, dtype=np.float32).reshape(1,self.args, 1)values_tensor = torch.tensor(values_array, dtype=torch.float32).to(self.device)logger.info(values_tensor)data = {"values_tensor":values_tensor,"MASK_tensor":MASK_tensor}return datadef inference(self, data):logger.info("inference ing~~~~~")logging.info(data)if data=="参数不足":return "参数不足"model = self.modellogger.info("model  loaded")prediction = model(data['values_tensor'],data['MASK_tensor'])logging.info(prediction)return predictiondef postprocess(self, data):logger.info("postprocess ing~~~~~")logging.info(data)if data == "参数不足":return [{"output": "参数不足"}]result = data.item()# results = data_reshape.tolist()return [{"output": result}]

可以本地编写个测试文件,看看是否能跑通


# 添加到 handler 文件的末尾if __name__ == "__main__":import logginglogging.basicConfig(level=logging.INFO)# 模拟 TorchServe 的上下文class MockContext:def __init__(self):self.system_properties = {"model_dir": "./model",  # 假设模型文件存放在 ./model 目录"gpu_id": 0              # 测试时使用 CPU}self.manifest = {"model": {"serializedFile": "model.pth",  # 假设模型权重文件名"modelFile": "model.py"        # 模型定义文件}}# 初始化 Handlerhandler = FaceDetectHandler()context = MockContext()# 确保模型目录存在os.makedirs(context.system_properties["model_dir"], exist_ok=True)# 创建一个虚拟模型文件(如果实际不存在)dummy_model_path = os.path.join(context.system_properties["model_dir"], context.manifest["model"]["serializedFile"])if not os.path.exists(dummy_model_path):torch.save(handler.model.state_dict(), dummy_model_path)# 初始化 Handlerhandler.initialize(context)# 构造测试数据(包含所有必要字段)test_data = [{"body": {"ATTENDANCE_RATE": 0.85,"HEAD_UP_RATE": 0.6,"FRONT_RATE": 0.75,"FRONT_SEAT_RATE": 0.5,"TVOTELOG": 1,"TPREAMPANSWERLOG": 2,"TDISCUSSLOG": 0,"TSURVEYLOG": 1,"TCHOOSESOMEONELOG": 0,"TWORKLOG": 3,"VOTELOG": 1,"PREAMPANSWERLOG": 2,"WORKLOG": 3,"CHOOSESOMEONELOG": 0,"LISTEN_CLASS": 0.9,"WRITE_NOTE": 0.3,"PLAY_PHONE": 0.1,"LIT_TABLE": 0.2}}]# 完整处理流程try:preprocessed = handler.preprocess(test_data)print("预处理结果:", preprocessed)if preprocessed != "参数不足":inference_result = handler.inference(preprocessed)print("推理结果:", inference_result)postprocessed = handler.postprocess(inference_result)print("最终输出:", postprocessed)else:print("错误:输入参数不完整")except Exception as e:print(f"处理出错: {str(e)}")

2.3打包

torch-model-archiver --model-name ml_regression_AICourseScoring_V2.2 --version 2.2 --model-file model.py --serialized-file test_model_loss0.2894_r20.9787_20250327_184525.pth --handler Myhandler.py

需要将参数文件、模型文件’handler文件同时放到一个文件夹下。

–model-name ml_regression_AICourseScoring_V2.2 模型的名字

–version 2.2 版本

–model-file model.py 模型文件

serialized-file test_model_loss0.2894_r20.9787_20250327_184525.pth 参数文件

–handler Myhandler.py handler文件

映射后的文件夹下的文件

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

执行完上述后命令会在当前文件下生成mar包,

在这里插入图片描述

我本地使用的是学校中台,只需上传mar包即可,本地测试参考

参考链接:Docker torchserve 部署模型流程——以WSL部署YOLO-FaceV2为例_class myhandler(basehandler): def initialize(self,-CSDN博客

第四点

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/899357.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Redis 分布式锁实现深度解析

Redis 分布式锁是分布式系统中协调多进程/服务对共享资源访问的核心机制。以下从基础概念到高级实现进行全面剖析。 一、基础实现原理 1. 最简实现(SETNX 命令) # 加锁 SET resource_name my_random_value NX PX 30000# 解锁(Lua脚本保证原…

kubernetes》》k8s》》 kubeadm、kubectl、kubelet

kubeadm 、kubectl 、kubelet kubeadm、kubectl和kubelet是Kubernetes中不可或缺的三个组件。kubeadm负责集群的快速构建和初始化,为后续的容器部署和管理提供基础;kubectl作为命令行工具,提供了与Kubernetes集群交互的便捷方式;而…

linux 硬盘扩展

场景: [rootlocalhost ~]# lsblk NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINTS sda 8:0 0 40G 0 disk ├─sda1 8:1 0 1M 0 part ├─sda2 8:2 0 1G 0 part /boot └─sda3 …

Docker Desktop 界面功能介绍

Docker Desktop 界面功能介绍 左侧导航栏 Containers(容器): 用于管理容器,包括查看运行中或已停止的容器,检查容器状态、日志,执行容器内命令,启动、停止、删除容器等操作。Images(镜像): 管理本地 Docker 镜像,可查看镜像列表、从 Docker Hub 拉取新镜像、删除镜…

C++细节知识for面试

1. linux上C程序可用的栈和堆大小分别是多少,为什么栈大小小于堆? 1. 栈(Stack)大小 栈默认为8MB,可修改。 为什么是这个大小: ​安全性:限制栈大小可防止无限递归或过深的函数调用导致内存…

数据设计(范式、步骤)

文章目录 数据设计1.数据库设计的三大范式2、数据库设计的具体步骤 数据设计 1.数据库设计的三大范式 关系型数据库的三大范式,指导如何设计一个关系型数据库。 1NF: 关系表的每个字段,都应该是不可再分的,——保证原子性。 字…

PhotoShop学习03

1.更改图像大小 通常情况下,如果我们想在某些上传图片,会发现我们的图片可能会过大或者过小,为此,我们需要调整图像的大小,使之符合网站的规则。 首先打开photoshop,打开一张图片。首先我们需要了解这张图…

Vue 项目中使用$refs来访问组件实例或 DOM 元素,有哪些注意事项?

大白话Vue 项目中使用$refs来访问组件实例或 DOM 元素,有哪些注意事项? 在 Vue 项目里,$refs 是个超实用的工具,它能让你直接访问组件实例或者 DOM 元素。不过使用的时候,有一些地方可得注意,下面咱就详细…

【安全运营】关于攻击面管理相关概念的梳理(二)

CYNC(持续可见性和网络控制) CYNC(Continuous Visibility and Network Control)即“持续可见性和网络控制”,是一个与网络安全和IT运营管理相关的概念。它强调的是在一个组织的数字环境中,确保对所有资产、…

【区块链安全 | 第二篇】区块链概念详解

文章目录 概述1. 区块链类型2 区块链五层架构3 账本模型4. 节点(Node)5. 区块(Block)6. 区块链(Blockchain)7. 区块链工作流程 核心技术1. 共识机制2. 智能合约 主要组件1. 交易(Transaction&am…

Redisson - 分布式锁和同步器

文章目录 锁(Lock)公平锁(Fair Lock)联锁(MultiLock)红锁(RedLock) 【已废弃】读写锁(ReadWriteLock)信号量(Semaphore)可过期许可信号…

HarmonyOS:GridObjectSortComponent(两个Grid之间网格元素交换)

一、概述 网格对象的编辑排序是用于网格对象的编辑、拖动排序、新增和删除。 说明 该组件从API Version 11开始支持。后续版本如有新增内容,则采用上角标单独标记该内容的起始版本。 二、导入模块 import { GridObjectSortComponent, GridObjectSortComponentItem…

RFID技术在机器人中的核心应用场景及技术实现

一、机器人定位与导航 1. 地标定位系统 实现方式: 在环境关键点部署无源RFID标签(如UHF Tag),机器人携带读写器通过读取标签ID实现绝对定位# 伪代码:RFID地标定位 def get_robot_position():detected_tags = reader.read_tags()known_positions = {tag1: (x1,y1), tag2: …

uv 命令用conda命令解释

uv:安装 | uv-zh-cn 功能 | uv-zh-cn #showkey -a 可看按键的"\eOP"转义序列是啥# 绑定快捷键 f1 到 source .venv/bin/activate函数 bind "\eOP": "source .venv/bin/activate " #conda activate# 绑定快捷键 f2 到uv add函数 …

《探秘SQL的BETWEEN:解锁数据范围查询的深度奥秘》

在数据的广袤宇宙中,结构化查询语言(SQL)宛如一座精密的导航系统,引导我们穿越数据的浩瀚星河,精准定位所需信息。其中,BETWEEN作为SQL的关键工具之一,以其独特的能力,在数据的海洋里…

大型语言模型的秘密:思考链长度与提示格式的魔力

嘿,朋友们!今天我要和大家聊聊一个超级酷的话题——大型语言模型(LLMs) 它们在“思考”和回答问题时的一些“小秘密”。你可能已经听说过**“思考链”(Chain of Thought, COT** 这个概念,它是一种让模型在回…

RHCE工程师特训指南

RHCE(红帽认证工程师)是Linux领域极具含金量的认证之一,其考试以实操为主,注重系统管理、网络服务配置及自动化运维能力。以下内容可帮助对RHCE考生高效规划学习路径。 一、RHCE认证概述 认证结构 RHCE认证分为两部分&#xff…

Vue 3 中 slot插槽的使用方法

插槽&#xff0c;名字挺新奇。但不要被他的名字难住。其实就是父组件向子件件传递信息的一种手段。我们可以用这样的方法向子组件传值。 父组件&#xff08;app.vue) <template><MyCompoent :transData"{a:reactiveObj.a,breactiveObj.b,c}"> </tem…

大模型中的召回次数是什么意思

大模型中的召回次数是什么意思 在大语言模型&#xff08;LLM&#xff09;和检索增强生成&#xff08;RAG&#xff09;系统中&#xff0c;召回次数&#xff08;Recall Count&#xff09;是一个重要的参数&#xff0c;它决定了在检索阶段从知识库中提取多少候选文档或片段。这个…