如何将自定义回归指标关联到SageMaker模型注册表中的模型?
解决SageMaker Pipeline自定义回归指标集成到模型注册表的简便方案
核心问题
SageMaker内置模型评估步骤对regression_metrics下的指标有白名单限制,非官方指标会触发模型注册失败,直接传入包含自定义指标的JSON报告无法被系统识别。
简便替代方案
方案1:将自定义指标迁移到custom_metrics字段
SageMaker的ModelMetrics原生支持custom_metrics字段,专门用于存储官方未定义的指标,无需修改评估容器:
- 修改评估步骤的输出JSON结构,把自定义指标从
regression_metrics移到custom_metrics数组,示例格式:
"regression_metrics": { "r2": { "value": -1.3766111872212665, "standard_deviation": 0.022653980022771227 } }, "custom_metrics": [ { "name": "custom_metric_one", "value": 1.3766111872212665, "standard_deviation": 0.22653980022771227 } ]
- 保持原有的
ModelMetrics代码不变,model_statistics会自动解析该结构,注册时SageMaker会将custom_metrics中的指标同步到模型注册表。
方案2:用Python镜像做轻量数据处理
如果无法修改评估步骤的输出格式,可在评估步骤后添加一个SageMaker Processing步骤(使用官方Python镜像,无需自定义容器),批量处理JSON文件:
- 读取S3上的原始评估报告
- 将
regression_metrics下的自定义指标迁移到custom_metrics字段 - 把处理后的JSON写回S3,用新路径传入模型注册步骤
示例处理脚本:
import json import boto3 import os s3 = boto3.client('s3') def process_eval_report(input_dir, output_dir): # 读取原始报告 with open(os.path.join(input_dir, 'evaluation.json'), 'r') as f: eval_data = json.load(f) # 分离官方与自定义指标 official_reg_metrics = ['r2', 'mse', 'rmse', 'mae', 'mape'] custom_metrics = [] cleaned_reg_metrics = {} for metric_name, metric_values in eval_data['regression_metrics'].items(): if metric_name in official_reg_metrics: cleaned_reg_metrics[metric_name] = metric_values else: custom_metrics.append({ 'name': metric_name, 'value': metric_values['value'], 'standard_deviation': metric_values['standard_deviation'] }) # 更新报告内容 eval_data['regression_metrics'] = cleaned_reg_metrics eval_data['custom_metrics'] = custom_metrics # 写入处理后的报告 with open(os.path.join(output_dir, 'processed_eval.json'), 'w') as f: json.dump(eval_data, f) if __name__ == '__main__': process_eval_report('/opt/ml/processing/input', '/opt/ml/processing/output')
方案3:注册前直接提取自定义指标
如果评估报告无法修改,可在模型注册前读取报告内容,提取自定义指标后通过ModelMetrics的custom_metrics参数传入:
import boto3 import json from sagemaker.model_metrics import ModelMetrics, MetricsSource, CustomMetric # 从S3读取评估报告 s3 = boto3.client('s3') bucket, key = eval_report_s3_uri.replace('s3://', '').split('/', 1) response = s3.get_object(Bucket=bucket, Key=key) eval_report = json.loads(response['Body'].read().decode('utf-8')) # 提取自定义指标 custom_metric_list = [] for metric_name, metric_data in eval_report['regression_metrics'].items(): if metric_name != 'r2': # 过滤官方指标 custom_metric_list.append( CustomMetric( name=metric_name, value=metric_data['value'], standard_deviation=metric_data['standard_deviation'] ) ) # 构建ModelMetrics model_metrics = ModelMetrics( model_statistics=MetricsSource( s3_uri=eval_report_s3_uri, content_type="application/json", ), custom_metrics=custom_metric_list ) # 执行模型注册 model_package = model_builder.build().register( model_package_group_name=model_package_group_name, approval_status=model_approval_status, model_metrics=model_metrics, )
验证方式
模型注册成功后,进入SageMaker控制台的模型注册表,查看对应模型版本的「指标」标签,确认自定义指标是否正常显示。
内容的提问来源于stack exchange,提问作者Luca Guarro
相关产品推荐
相关产品推荐

