Exception: Run with UUID b2001m223dec41618b901eqqdd865bf5d is already active. To start a new run, first end the current run with mlflow.end_run(). To start a nested run, call start_run with nested=True
这个错误的意思是:MLflow 已经有一个活动的运行(active run),但你试图启动新的 run,而没有结束当前的 run。
🔍 错误分析
错误信息
Exception: Run with UUID b2001b723dec41618b51ebddd865bf5d is already active.
To start a new run, first end the current run with mlflow.end_run().
To start a nested run, call start_run with nested=True
- 问题:MLflow 运行时只能同时有一个活动的运行(active run)。如果
mlflow.start_run()
在上一次运行后没有end_run()
,就会导致这个错误。 - 可能的原因:
- 上一次
mlflow.start_run()
没有正常关闭(比如代码中途崩溃)。 - 重复调用
execute()
方法,但start_run()
只开了新的 run,没有结束之前的 run。
- 上一次
✔️ 解决方案
✅ 方法 1:在 start_run()
之前手动检查 & 结束当前 Run
在 execute()
方法中,先检查是否有活动的 run,结束后再启动新的 run:
import mlflow
import pickle
class ETLExecutor:
def __init__(self, pipeline):
self.pipeline = pipeline
self.mlflow = mlflow
def execute(self, data):
transformed_data = self.pipeline.fit_transform(data)
# **解决 bug:手动结束之前的 run**
if self.mlflow.active_run():
self.mlflow.end_run()
# 保存 pipeline.pkl
with open("pipeline.pkl", "wb") as f:
pickle.dump(self.pipeline, f)
# 记录到 MLflow
with self.mlflow.start_run():
self.mlflow.log_params(self._get_pipeline_params())
self.mlflow.log_artifact("pipeline.pkl")
return transformed_data
def _get_pipeline_params(self):
params = {}
for step in self.pipeline.named_steps:
transformer = self.pipeline.named_steps[step]
if hasattr(transformer, "get_params"):
params.update(transformer.get_params())
return params
✅ 方法 2:使用 nested=True
如果你确实需要在已有 Run 内部创建新的 Run(比如多级 ETL 任务),可以使用:
with self.mlflow.start_run(nested=True):
self.mlflow.log_params(self._get_pipeline_params())
self.mlflow.log_artifact("pipeline.pkl")
但一般情况下,不需要嵌套 Run,方法 1 更推荐。
🚀 总结
- 最可能的原因:MLflow 上次运行没有结束,导致
start_run()
冲突。 - 最简单的修复:
- 在
start_run()
之前,检查是否有活动 Run,并先end_run()
。
- 在
- 如果确实需要嵌套 Run,可以加
nested=True
。
这样可以避免 Exception: Run is already active
这个错误 🎯