code: def _validate_and_apply_step_config(self):
      if "using" in self.step_config:
          if self.step_config["using"] not in [
              "custom",
              "automl/flaml",
          ]:
              raise MlflowException(
                  f"Invalid train step configuration value {self.step_config['using']} for "
                  f"key 'using'. Supported values are: ['custom', 'automl/flaml']",
                  error_code=INVALID_PARAMETER_VALUE,
              )
      else:
          self.step_config["using"] = "custom"
  
      if "tuning" in self.step_config:
          if "enabled" in self.step_config["tuning"] and isinstance(
              self.step_config["tuning"]["enabled"], bool
          ):
              self.step_config["tuning_enabled"] = self.step_config[
                  "tuning"
              ]["enabled"]
          else:
              raise MlflowException(
                  "The 'tuning' configuration in the train step must include an "
                  "'enabled' key whose value is either true or false.",
                  error_code=INVALID_PARAMETER_VALUE,
              )
  
          if self.step_config["tuning_enabled"]:
              if "sample_fraction" in self.step_config["tuning"]:
                  sample_fraction = float(
                      self.step_config["tuning"]["sample_fraction"]
                  )
                  if 0 < sample_fraction <= 1.0:
                      self.step_config[
                          "sample_fraction"
                      ] = sample_fraction
                  else:
                      raise MlflowException(
                          "The tuning 'sample_fraction' configuration in the train step "
                          "must be between 0 and 1.",
                          error_code=INVALID_PARAMETER_VALUE,
                      )
              else:
                  self.step_config["sample_fraction"] = 1.0
  
              if "algorithm" not in self.step_config["tuning"]:
                  self.step_config["tuning"][
                      "algorithm"
                  ] = "hyperopt.rand.suggest"
  
              if "parallelism" not in self.step_config["tuning"]:
                  self.step_config["tuning"]["parallelism"] = 1
  
              if "max_trials" not in self.step_config["tuning"]:
                  raise MlflowException(
                      "The 'max_trials' configuration in the train step must be provided.",
                      error_code=INVALID_PARAMETER_VALUE,
                  )
  
              if "parameters" not in self.step_config["tuning"]:
                  raise MlflowException(
                      "The 'parameters' configuration in the train step must be provided "
                      " when tuning is enabled.",
                      error_code=INVALID_PARAMETER_VALUE,
                  )
  
      else:
          self.step_config["tuning_enabled"] = False
  
      if "estimator_params" not in self.step_config:
          self.step_config["estimator_params"] = {}
  
      self.target_col = self.step_config.get("target_col")
      if self.target_col is None:
          raise MlflowException(
              "Missing target_col config in recipe config.",
              error_code=INVALID_PARAMETER_VALUE,
          )
      self.recipe = self.step_config.get("recipe")
      if self.recipe is None:
          raise MlflowException(
              "Missing recipe config in recipe config.",
              error_code=INVALID_PARAMETER_VALUE,
          )
      self.positive_class = self.step_config.get("positive_class")
      self.extended_task = _get_extended_task(
          self.recipe, self.positive_class
      )
      self.rebalance_training_data = self.step_config.get(
          "rebalance_training_data", True
      )
      self.skip_data_profiling = self.step_config.get(
          "skip_data_profiling", False
      )
      if (
          "estimator_method" not in self.step_config
          and self.step_config["using"] == "custom"
      ):
          raise MlflowException(
              "Missing 'estimator_method' configuration in the train step, "
              "which is using 'custom'.",
              error_code=INVALID_PARAMETER_VALUE,
          )
  
      self.predict_prefix = self.step_config.get(
          "predict_prefix", "predicted_"
      )
      self.predict_scores_for_all_classes = self.step_config.get(
          "predict_scores_for_all_classes", True
      )
      self.primary_metric = _get_primary_metric(
          self.step_config.get("primary_metric"), self.extended_task
      )
      builtin_metrics = _get_builtin_metrics(self.extended_task)
      custom_metrics = _get_custom_metrics(
          self.step_config, self.extended_task
      )
      self.user_defined_custom_metrics = {
          metric.name: metric for metric in custom_metrics
      }
      self.evaluation_metrics = {
          metric.name: metric for metric in builtin_metrics
      }
      self.evaluation_metrics.update(self.user_defined_custom_metrics)
      self.evaluation_metrics_greater_is_better = {
          metric.name: metric.greater_is_better
          for metric in builtin_metrics
      }
      self.evaluation_metrics_greater_is_better.update(
          {
              metric.name: metric.greater_is_better
              for metric in custom_metrics
          }
      )
      if (
          self.primary_metric is not None
          and self.primary_metric not in self.evaluation_metrics
      ):
          raise MlflowException(
              f"The primary metric '{self.primary_metric}' is a custom metric, but its"
              " corresponding custom metric configuration is missing from `recipe.yaml`.",
              error_code=INVALID_PARAMETER_VALUE,
          )
      self.code_paths = [os.path.join(self.recipe_root, "steps")]
  
imports: import datetime
  import importlib
  import logging
  import os
  import re
  import shutil
  import sys
  import warnings
  import cloudpickle
  import yaml
  import mlflow
  from mlflow.entities import SourceType, ViewType
  from mlflow.environment_variables import MLFLOW_RECIPES_EXECUTION_TARGET_STEP_NAME
  from mlflow.exceptions import BAD_REQUEST, INVALID_PARAMETER_VALUE, MlflowException
  from mlflow.models import Model
  from mlflow.recipes.artifacts import DataframeArtifact, HyperParametersArtifact, ModelArtifact, RunArtifact
  from mlflow.recipes.cards import BaseCard
  from mlflow.recipes.step import BaseStep, StepClass
  from mlflow.recipes.utils.execution import get_step_output_path
  from mlflow.recipes.utils.metrics import _get_builtin_metrics, _get_custom_metrics, _get_error_fn, _get_extended_task, _get_model_type_from_template, _get_primary_metric, _load_custom_metrics, transform_multiclass_metrics_dict
  from mlflow.recipes.utils.step import get_merged_eval_metrics, get_pandas_data_profiles, validate_classification_config
  from mlflow.recipes.utils.tracking import TrackingConfig, apply_recipe_tracking_config, get_recipe_tracking_config, get_run_tags_env_vars, log_code_snapshot
  from mlflow.recipes.utils.wrapped_recipe_model import WrappedRecipeModel
  from mlflow.tracking import MlflowClient
  from mlflow.tracking.fluent import _get_experiment_id
  from mlflow.utils.databricks_utils import get_databricks_env_vars, get_databricks_run_url
  from mlflow.utils.file_utils import TempDir
  from mlflow.utils.mlflow_tags import MLFLOW_RECIPE_PROFILE_NAME, MLFLOW_RECIPE_STEP_NAME, MLFLOW_RECIPE_TEMPLATE_NAME, MLFLOW_SOURCE_TYPE
  from mlflow.utils.string_utils import strip_prefix
label_desc: Use image node_id 2 for calling the TrainStep obj's underlying member method code with example usage: obj._validate_and_apply_step_config() without return types