更新时间:2024-10-24 GMT+08:00

创建Workflow模型注册节点

功能介绍

通过对ModelArts模型管理的能力进行封装,实现将训练后的结果注册到模型管理中,便于后续服务部署、更新等步骤的执行。主要应用场景如下:

  • 注册ModelArts训练作业中训练完成的模型。
  • 注册自定义镜像中的模型。

属性总览

您可以使用ModelStep来构建模型注册节点,ModelStep结构如下:

表1 ModelStep

属性

描述

是否必填

数据类型

name

模型注册节点的名称。只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符,一个Workflow里的两个step名称不能重复

str

inputs

模型注册节点的输入列表

ModelInput或者ModelInput的列表

outputs

模型注册节点的输出列表

ModelOutput或者ModelOutput的列表

title

title信息,主要用于前端的名称展示

str

description

模型注册节点的描述信息

str

policy

节点执行的policy

StepPolicy

depend_steps

依赖的节点列表

Step或者Step的列表

表2 ModelInput

属性

描述

是否必填

数据类型

name

模型注册节点的输入名称,只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符。同一个Step的输入名称不能重复

str

data

模型注册节点的输入数据对象

OBS、SWR或订阅模型相关对象,当前仅支持OBSPath、SWRImage、OBSConsumption、OBSPlaceholder、SWRImagePlaceholder、DataConsumptionSelector、GalleryModel

表3 ModelOutput

属性

描述

是否必填

数据类型

name

模型注册节点的输出名称,只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符。同一个Step的输出名称不能重复

str

model_config

模型注册相关配置信息

ModelConfig

表4 ModelConfig

属性

描述

是否必填

数据类型

model_type

模型的类型,支持的格式有("TensorFlow", "MXNet", "Caffe", "Spark_MLlib", "Scikit_Learn", "XGBoost", "Image", "PyTorch", "Template","Custom")默认为TensorFlow。

str

model_name

模型的名称,支持1-64位可见字符(含中文),名称可以包含字母、中文、数字、中划线、下划线。

str、Placeholder

model_version

模型的版本,格式需为“数值.数值.数值”,其中数值为1-2位正整数。该字段不填时,版本号自动增加。

注意:

版本不可以出现例如01.01.01等以0开头的版本号形式。

str、Placeholder

runtime

模型运行时环境,runtime可选值与model_type相同。

str、Placeholder

description

模型备注信息,1-100位长度,不能包含&!'"<>=

str

execution_code

执行代码存放的OBS地址,默认值为空,名称固定为“customize_service.py”。

推理代码文件需存放在模型“model”目录。该字段不需要填,系统也能自动识别出model目录下的推理代码。

str

dependencies

推理代码及模型需安装的包,默认为空。从配置文件读取。

str

model_metrics

模型精度信息,从配置文件读取。

str

apis

模型所有的apis入参出参信息(选填),从配置文件中解析出来。

str

initial_config

模型配置相关数据。

dict

template

模板的相关配置项,使用模板导入模型(即model_type为Template)时必选

Template

dynamic_load_mode

动态加载模式,当前仅支持"Single"

str、Placeholder

prebuild

模型是否提前构建,默认为False

bool、Placeholder

install_type

模型的安装类型,支持"real_time", "edge", "batch",该字段不填时默认均支持

list[str]

表5 Template

属性

描述

是否必填

数据类型

template_id

所使用的模板ID,模板中会内置一个输入输出模式

str、Placeholder

infer_format

输入输出模式ID,提供时覆盖模板中的内置输入输出模式

str、Placeholder

template_inputs

模板输入项配置,即配置模型的源路径

list of TemplateInputs object

表6 TemplateInputs

属性

描述

是否必填

数据类型

input_id

输入项ID,从模板详情中获取

str、Placeholder

input

模板输入路径,可以是OBS文件路径或OBS目录路径。使用多输入项的模板创建模型时,如果模板定义的目标路径input_properties是一样的,则此处输入的obs目录或者obs文件不能重名,否则会覆盖。

str、Placeholder、Storage

使用案例

主要包含六种场景的用例:

  • 基于JobStep的输出注册模型
  • 基于OBS数据注册模型
  • 使用模板方式注册模型
  • 使用自定义镜像注册模型
  • 使用自定义镜像+OBS的方式注册模型
  • 使用订阅模型+OBS的方式注册模型

从训练作业中注册模型(模型输入来源JobStep的输出)

import modelarts.workflow as wf

# 构建一个OutputStorage对象,对训练输出目录做统一管理
storage = wf.data.OutputStorage(name="storage_name", title="title_info", description="description_info") # name字段必填,title, description可选填 

# 定义输入的数据集对象
dataset = wf.data.DatasetPlaceholder(name="input_dataset")

# 通过JobStep来定义一个训练节点,输入使用数据集,并将训练结果输出到OBS
job_step = wf.steps.JobStep(
    name="training_job", # 训练节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="图像分类训练", # 标题信息,不填默认使用name
    algorithm=wf.AIGalleryAlgorithm(
        subscription_id="subscription_id", # 算法订阅ID,也可直接填写版本号
        item_version_id="item_version_id", # 算法订阅版本ID,也可直接填写版本号
        parameters=[
            wf.AlgorithmParameters(
                name="parameter_name", 
                value=wf.Placeholder(name="parameter_name", placeholder_type=wf.PlaceholderType.STR, default="fake_value",description="description_info")
            ) # 算法超参的值使用Placeholder对象来表示,支持int, bool, float, str四种类型
        ]
    ),  # 训练使用的算法对象,示例中使用AIGallery订阅的算法;部分算法超参的值如果无需修改,则在parameters字段中可以不填写,系统自动填充相关超参值
    
    inputs=wf.steps.JobInput(name="data_url", data=dataset), # JobStep的输入在运行时配置;data字段也可使用wf.data.Dataset(dataset_name="fake_dataset_name", version_name="fake_version_name")表示
    outputs=wf.steps.JobOutput(name="train_url", obs_config=wf.data.OBSOutputConfig(obs_path=storage.join("directory_path"))), # JobStep的输出
    spec=wf.steps.JobSpec(
        resource=wf.steps.JobResource(
            flavor=wf.Placeholder(name="train_flavor", placeholder_type=wf.PlaceholderType.JSON, description="训练资源规格")
           
        )
    )# 训练资源规格信息
)

# 通过ModelStep来定义一个模型注册节点,输入来源于JobStep的输出

# 定义模型名称参数
model_name = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.STR)

model_registration = wf.steps.ModelStep(
    name="model_registration",  # 模型注册节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="模型注册",  # 标题信息
    inputs=wf.steps.ModelInput(name='model_input', data=job_step.outputs["train_url"].as_input()),  # ModelStep的输入来源于依赖的JobStep的输出
    outputs=wf.steps.ModelOutput(name='model_output',model_config=wf.steps.ModelConfig(model_name=model_name, model_type="TensorFlow")), # ModelStep的输出
    depend_steps=job_step # 依赖的作业类型节点对象
)
# job_step是wf.steps.JobStep的 实例对象,train_url是wf.steps.JobOutput的name字段值

workflow = wf.Workflow(
    name="model-step-demo",
    desc="this is a demo workflow",
    steps=[job_step, model_registration],
    storages=[storage]
)

从训练作业中注册模型(模型输入来源OBS路径,训练完成的模型已存储到OBS路径)

import modelarts.workflow as wf
# 通过ModelStep来定义一个模型注册节点,输入来源于OBS中

# 定义OBS数据对象
obs = wf.data.OBSPlaceholder(name = "obs_placeholder_name", object_type = "directory" ) # object_type必须是file或者directory

# 定义模型名称参数
model_name = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.STR)

model_registration = wf.steps.ModelStep(
    name="model_registration",  # 模型注册节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="模型注册",  # 标题信息
    inputs=wf.steps.ModelInput(name='model_input', data=obs),  # ModelStep的输入在运行时配置;data字段的值也可使用wf.data.OBSPath(obs_path="fake_obs_path")表示
    outputs=wf.steps.ModelOutput(name='model_output',model_config=wf.steps.ModelConfig(model_name=model_name, model_type="TensorFlow"))# ModelStep的输出
)

workflow = wf.Workflow(
    name="model-step-demo",
    desc="this is a demo workflow",
    steps=[model_registration]
)

使用模板的方式注册模型

import modelarts.workflow as wf
# 通过ModelStep来定义一个模型注册节点,并通过预置模板进行注册

# 定义预置模板对象,Template对象中的字段可使用Placeholder表示
template = wf.steps.Template(
    template_id="fake_template_id",
    infer_format="fake_infer_format",
    template_inputs=[
        wf.steps.TemplateInputs(
            input_id="fake_input_id",
            input="fake_input_file"
        )
    ]
)

# 定义模型名称参数
model_name = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.STR)

model_registration = wf.steps.ModelStep(
    name="model_registration",  # 模型注册节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="模型注册",  # 标题信息
    outputs=wf.steps.ModelOutput(
          name='model_output',
          model_config=wf.steps.ModelConfig(
              model_name=model_name, 
              model_type="Template",
              template=template
          )
    )# ModelStep的输出
)

workflow = wf.Workflow(
    name="model-step-demo",
    desc="this is a demo workflow",
    steps=[model_registration]
)

从自定义镜像中注册模型

import modelarts.workflow as wf
# 通过ModelStep来定义一个模型注册节点,输入来源于自定义镜像地址

# 定义镜像数据
swr = wf.data.SWRImagePlaceholder(name="placeholder_name")

# 定义模型名称参数
model_name = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.STR)

model_registration = wf.steps.ModelStep(
    name="model_registration",  # 模型注册节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="模型注册",  # 标题信息
    inputs=wf.steps.ModelInput(name="input",data=swr), # ModelStep的输入在运行时配置;data字段的值也可使用wf.data.SWRImage(swr_path="fake_path")表示
    outputs=wf.steps.ModelOutput(name='model_output',model_config=wf.steps.ModelConfig(model_name=model_name, model_type="TensorFlow"))# ModelStep的输出
)

workflow = wf.Workflow(
    name="model-step-demo",
    desc="this is a demo workflow",
    steps=[model_registration]
)

使用自定义镜像+OBS的方式注册模型

import modelarts.workflow as wf
# 通过ModelStep来定义一个模型注册节点,输入来源于自定义镜像地址

# 定义镜像数据
swr = wf.data.SWRImagePlaceholder(name="placeholder_name")

# 定义OBS模型数据
model_obs = wf.data.OBSPlaceholder(name = "obs_placeholder_name", object_type = "directory" ) # object_type必须是file或者directory

# 定义模型名称参数
model_name = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.STR)

model_registration = wf.steps.ModelStep(
    name="model_registration",  # 模型注册节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="模型注册",  # 标题信息
    inputs=[
        wf.steps.ModelInput(name="input",data=swr), # ModelStep的输入在运行时配置;data字段的值也可使用wf.data.SWRImage(swr_path="fake_path")表示
        wf.steps.ModelInput(name="input",data=model_obs) # ModelStep的输入在运行时配置;data字段的值也可使用wf.data.OBSPath(obs_path="fake_obs_path")表示
    ], 
    outputs=wf.steps.ModelOutput(
        name='model_output',
        model_config=wf.steps.ModelConfig(
            model_name=model_name, 
            model_type="Custom",
            dynamic_load_mode="Single"
        )
    )# ModelStep的输出
)

workflow = wf.Workflow(
    name="model-step-demo",
    desc="this is a demo orkflow",
    steps=[model_registration]
)

使用订阅模型+OBS的方式注册模型

该方式本质上与自定义镜像+OBS的方式没有区别,只是自定义镜像变成从订阅模型中获取。

具体使用案例:

import modelarts.workflow as wf

# 定义订阅的模型对象
base_model = wf.data.GalleryModel(subscription_id="fake_subscription_id", version_num="fake_version") # 从gallery订阅的模型,一般由开发者自行创建发布

# 定义OBS模型数据
model_obs = wf.data.OBSPlaceholder(name = "obs_placeholder_name", object_type = "directory" ) # object_type必须是file或者directory

# 定义模型名称参数
model_name = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.STR)

model_registration = wf.steps.ModelStep(
    name="model_registration",  # 模型注册节点的名称,命名规范(只能包含英文字母、数字、下划线(_)、中划线(-),并且只能以英文字母开头,长度限制为64字符),一个Workflow里的两个step名称不能重复
    title="模型注册",  # 标题信息
    inputs=[
        wf.steps.ModelInput(name="input",data=base_model) # ModelStep的输入使用订阅的模型
        wf.steps.ModelInput(name="input",data=model_obs) # ModelStep的输入在运行时配置;data字段的值也可使用wf.data.OBSPath(obs_path="fake_obs_path")表示
    ], 
    outputs=wf.steps.ModelOutput(
        name='model_output',
        model_config=wf.steps.ModelConfig(
            model_name=model_name, 
            model_type="Custom",
            dynamic_load_mode="Single"
        )
    )# ModelStep的输出
)

workflow = wf.Workflow(
    name="model-step-demo",
    desc="this is a demo workflow",
    steps=[model_registration]
)

上述案例中,系统会自动获取订阅模型中的自定义镜像,然后结合输入的OBS模型路径,注册生成一个新的模型,其中model_obs可以替换成JobStep的动态输出。

model_type支持的类型有:"TensorFlow"、"MXNet"、"Caffe"、 "Spark_MLlib"、 "Scikit_Learn"、"XGBoost"、 "Image"、"PyTorch"、"Template"、"Custom"。

在wf.steps.ModelConfig对象中,如果model_type字段未填写,则表示默认使用"TensorFlow"。

  • 如果您构建的工作流对注册的模型类型没有修改的需求,则按照上述示例使用即可。
  • 如果您构建的工作流需要多次运行可以修改模型类型,则可使用占位符参数的方式进行编写:

    model_type = wf.Placeholder(name="placeholder_name", placeholder_type=wf.PlaceholderType.ENUM, default="TensorFlow", enum_list=["TensorFlow", "MXNet", "Caffe", "Spark_MLlib", "Scikit_Learn", "XGBoost", "Image", "PyTorch", "Template", "Custom"], description="模型类型")