{"record":{"id":"f67ce74a766c03a1","repo":"mlflow/mlflow","slug":"invalid-parameter-value-f67ce7","errorCode":"INVALID_PARAMETER_VALUE","errorMessage":"Exactly one of {param1_name} or {param2_name} must be provided","messagePattern":"Exactly one of (.+?) or (.+?) must be provided","errorType":"error_code","errorClass":"MlflowException","httpStatus":400,"severity":"error","filePath":"mlflow/store/tracking/gateway/sqlalchemy_mixin.py","lineNumber":110,"sourceCode":"    KEKManager,\n    _encrypt_secret,\n    _mask_secret_value,\n)\nfrom mlflow.utils.mlflow_tags import (\n    MLFLOW_EXPERIMENT_IS_GATEWAY,\n    MLFLOW_EXPERIMENT_SOURCE_ID,\n    MLFLOW_EXPERIMENT_SOURCE_TYPE,\n)\nfrom mlflow.utils.search_utils import SearchUtils\nfrom mlflow.utils.time import get_current_time_millis\n\n\ndef _validate_one_of(\n    param1_name: str, param1_value: Any, param2_name: str, param2_value: Any\n) -> None:\n    \"\"\"Validate that exactly one of two parameters is provided.\"\"\"\n    if (param1_value is None) == (param2_value is None):\n        raise MlflowException(\n            f\"Exactly one of {param1_name} or {param2_name} must be provided\",\n            error_code=INVALID_PARAMETER_VALUE,\n        )\n\n\n_TARGETED_BUDGET_SCOPES = (BudgetTargetScope.ENDPOINT.value,)\n\n\ndef _normalize_budget_target_value(\n    target_scope: str | None, target_value: str | None\n) -> str | None:\n    \"\"\"Enforce the budget policy target_value/target_scope invariant at the store layer.\n\n    ENDPOINT-scoped policies must carry a ``target_value`` (the ID of the endpoint to\n    match; without one the policy silently never matches any request and thus never\n    enforces). Policies with any other scope must not carry one, so a stray\n    ``target_value`` is dropped. This mirrors the REST handler validation so\n    direct/programmatic store callers cannot persist a policy that violates the","sourceCodeStart":92,"sourceCodeEnd":128,"githubUrl":"https://github.com/mlflow/mlflow/blob/6a27f2decc0b76eb1b54af31849784addb357dbc/mlflow/store/tracking/gateway/sqlalchemy_mixin.py#L92-L128","documentation":"_validate_one_of enforces that exactly one of two mutually exclusive lookup parameters (e.g. name vs id/uid) is supplied. If both are provided, or both are None, the gateway store lookup methods (get_secret_info, get_gateway_model_definition, get_gateway_endpoint) raise MlflowException with INVALID_PARAMETER_VALUE. This prevents ambiguous lookups.","triggerScenarios":"Calling get_secret_info, get_gateway_model_definition, or get_gateway_endpoint with both identifier arguments set (e.g. secret_id and secret_name) or with both omitted (None).","commonSituations":"Refactored code that kept an old id argument while adding a name argument; dynamic callers building kwargs where an unset variable defaults to None so neither key is populated; copy-pasted lookup calls that pass both fields 'to be safe'.","solutions":["Pass exactly one of the two parameters — delete the redundant one from the call.","If you have both values available, choose the one the API prefers (usually the stable id) and drop the other.","When values come from user input/config, validate before calling: (name is None) != (id is None) must be True, otherwise raise a clear upstream error."],"exampleFix":"// before\nstore.get_gateway_endpoint(endpoint_id='e123', endpoint_name='my-endpoint')  # both set -> error\n\n// after\nstore.get_gateway_endpoint(endpoint_name='my-endpoint')  # exactly one provided","handlingStrategy":"validation","validationCode":"def validate_exactly_one(**kwargs):\n    provided = [k for k, v in kwargs.items() if v is not None]\n    if len(provided) != 1:\n        raise ValueError(f'Exactly one of {list(kwargs)} must be provided, got: {provided or \"none\"}')\n\n# usage before the store call:\n# validate_exactly_one(endpoint_id=endpoint_id, endpoint_name=endpoint_name)","typeGuard":"def has_exactly_one(a, b) -> bool:\n    return (a is None) != (b is None)","tryCatchPattern":"from mlflow.exceptions import MlflowException\ntry:\n    ep = store.get_gateway_endpoint(endpoint_id=endpoint_id, endpoint_name=endpoint_name)\nexcept MlflowException as e:\n    if 'must be provided' in str(e):\n        raise ValueError('Pass exactly one of endpoint_id or endpoint_name to get_gateway_endpoint.') from e\n    raise","preventionTips":["Centralize gateway lookups in one helper that accepts a single identifier argument and resolves it to (id, name) internally.","Never 'pass both to be safe' — the invariant is exactly one; document this at call sites.","When building kwargs dynamically, filter out None values and assert exactly one key remains before calling.","Write unit tests covering all three cases: only-id, only-name, both/none (must raise)."],"tags":["mlflow","gateway","parameter-validation","mutually-exclusive-args","sqlalchemy-mixin"],"backgroundTag":"mutually-exclusive-parameters","analyzedSha":"6a27f2decc0b76eb1b54af31849784addb357dbc","analyzedAt":"2026-08-29T20:54:51.419Z","schemaVersion":2},"datasetVersion":"2026-08-29T22:17:34.462Z"}